HummingBird IoT Development Platform

repository·master·Indexed 41 days ago

https://github.com/winc-link/hummingbird

An ultra-lightweight IoT development platform written in Golang, optimized for high performance and low resource consumption. It provides comprehensive IoT management tools including device and product management, rule engines, alarm centers, thing models, and data visualization. Supports flexible storage options including SQLite, LevelDB, MySQL, and TDengine.

Tokens
18.9K
Snippets
59
Records
98
Agent score
51%

What's inside HummingBird

  1. What is HummingBird

    master

    HummingBird (蜂鸟) is an ultra-lightweight IoT (Internet of Things) development platform implemented in Golang. It is designed for high performance and low memory footprint.

    Key characteristics include:

    • High Performance: Can support thousands of device connections and millions of messages on minimal hardware (e.g., 1C/1G RAM can handle thousands of devices and 80M messages).
    • Flexible Storage: Uses SQLite and LevelDB by default for lightweight, high-throughput, and high-compression storage. For large-scale or high-reliability requirements, it supports swapping to MySQL and TDengine.
    • Comprehensive IoT Features: Includes device access, product management, Thing Model (物模型), alarm centers, and rule engines.
  2. Core Features of HummingBird

    master

    HummingBird provides a full suite of IoT management capabilities:

    • Management: Product management, Device management, Image management, and Driver management.
    • Extensibility: Driver market, Plugin market, and Scene linkage (场景联动).
    • Intelligence & Monitoring: Rule engine, Alarm center, System monitoring, and Data dashboards (可视化大屏).
    • Resource Management: General resource management and driver market access.
  3. How to contribute to HummingBird

    master

    To contribute to the project, follow these workflow steps:

    1. Ensure your local master branch is up to date.
    2. Create a new branch from master using the format feature/username/description (e.g., feature/pick/mqtt_driver).
    3. Edit documentation or code and commit your changes.
    4. Submit a Pull Request (PR) to the develop branch. Wait for the author to review and merge.
  4. Quick Start with Docker Compose

    master

    You can deploy HummingBird quickly using Docker Compose. Follow these steps to clone the repository and start the services in detached mode:

    1. Clone the repository:
      git clone https://gitee.com/winc-link/hummingbird.git
    2. Navigate to the Docker manifest directory:
      cd hummingbird/manifest/docker
    3. Start the services:
      docker-compose up -d
    git clone https://gitee.com/winc-link/hummingbird.git
    cd hummingbird/manifest/docker 
    docker-compose up -d
  5. WeCom notification trigger types

    master

    The WeixinClient generates different markdown templates depending on the Trigger type defined in the models.Rule. The supported triggers are:

    1. constants.DeviceDataTrigger: Used for data-driven alerts (e.g., a specific property value exceeding a threshold). The template includes the device name, rule name, property name (with code), current value, and timestamp.
    2. constants.DeviceEventTrigger: Used for event-based alerts. The template includes the device name, rule name, event name (with code), event content (if available), and timestamp.
    3. constants.DeviceStatusTrigger: Used for device status changes. The template includes the device name, rule name, and the current device status.
  6. WebSocket message formats: WsData and WsResponse

    master

    The WebSocket server communicates using specific JSON structures for incoming and outgoing messages.

    Incoming Message (WsData)

    When a client sends a message, it is expected to follow the WsData structure (unmarshaled in readPump):

    • Code: The identifier for the requested action.
    • Data: The payload associated with the action.

    Outgoing Message (WsResponse)

    When the server sends a message, it uses the WsResponse structure:

    • Code: The dtos.WsCode identifying the response.
    • Data: An httphelper.CommonResponse containing:
      • Success: Boolean indicating if the operation succeeded.
      • ErrorCode: The error code if Success is false.
      • ErrorMsg: A localized error message (automatically translated if Success is false and ErrorCode is provided).
      • The actual data payload if Success is true.
  7. How the WebSocket server manages clients and broadcasting

    master

    The WsServer acts as a central hub for managing multiple wsClient connections using a concurrency-safe pattern:

    1. Registration: When a client connects via Handle, it is sent to the register channel. The run() goroutine then adds it to the clients map and clientIdMap.
    2. Unregistration: When a client disconnects (detected by readPump), it is sent to the unregister channel to be removed from the server's tracking.
    3. Broadcasting:
      • Internal Broadcast: The listenBroadcast() goroutine listens to a StreamClient (retrieved from the DI container). When it receives data, it wraps it in a WsResponse and sends it to the broadcast channel.
      • Client Distribution: The run() goroutine picks up messages from the broadcast channel and iterates through all registered clients, attempting to push the message into each client's individual send channel.
  8. Deploy Hummingbird using Docker Compose

    master

    You can deploy the Hummingbird stack using a docker-compose.yml file. The stack consists of three primary services: mqtt-broker, ekuiper, and hummingbird-core. These services communicate over a shared bridge network named hummingbird.

    version: "3"
    
    networks:
      hummingbird:
        driver: bridge
    services:
      mqtt-broker:
        image: registry.cn-shanghai.aliyuncs.com/winc-link/mqtt-broker:2.6
        container_name: mqtt-broker
        hostname: mqtt-broker
        restart: always
        ports:
          - "58090:58090"
        networks:
          - hummingbird
      ekuiper:
        image: registry.cn-shanghai.aliyuncs.com/winc-link/ekuiper:1.10.0-slim
        ports:
          - "127.0.0.1:9081:9081"
        container_name: ekuiper
        hostname: ekuiper
        restart: always
        user: root
        volumes:
          - ./kuiper/data:/kuiper/data
          - ./kuiper/log:/kuiper/log
        environment:
          MQTT_SOURCE__DEFAULT__SERVER: "tcp://mqtt-broker:58090"
          KUIPER__BASIC__CONSOLELOG: "true"
          KUIPER__BASIC__IGNORECASE: "false"
        networks:
          - hummingbird
      hummingbird-core:
        image: registry.cn-shanghai.aliyuncs.com/winc-link/hummingbird-core:v1.0
        container_name: hummingbird-core
        restart: always
        hostname: hummingbird-core
        ports:
          - "3000:3000"
          - "58081:58081"
          - "57081:57081"
        depends_on:
          - ekuiper
          - mqtt-broker
        volumes:
          - ./:/var/bin/hummingbird
          - /var/run/docker.sock:/var/run/docker.sock
          - ./config/configuration.toml:/etc/hummingbird-core/configuration.toml
        networks:
          - hummingbird
  9. Initialize the MySQL Client

    master

    To use the MySQL database connectivity in Hummingbird, use the NewClient function. It requires a dtos.Configuration object and a logger.LoggingClient. The function returns a pointer to a Client and an error if initialization fails.

    Note: The Client struct provides access to a Pool which is a *gorm.DB instance, allowing you to perform direct GORM operations if needed.

    import (
    	"github.com/winc-link/hummingbird/internal/dtos"
    	"github.com/winc-link/hummingbird/internal/pkg/logger"
    	"github.com/winc-link/hummingbird/internal/hummingbird/core/infrastructure/mysql"
    )
    
    // Assuming config and lc are already initialized
    client, err := mysql.NewClient(config, lc)
    if err != nil {
    	// handle error
    }
  10. Run the hummingbird-core service

    master

    The hummingbird-core service is the primary entrypoint for the hummingbird core system. It initializes the service using the core.Main function, passing in a context, a cancellation function, and a Gin engine instance. The service operates on the /api/v1 base path and requires authentication via an x-token header.

    // The service is typically run as a compiled binary.
    // It uses the Gin framework in ReleaseMode.
    // Authentication is required via the 'x-token' header.