You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用IoT Agent JSON与Orion LD配置双向属性设备的问题排查

双向可配置IoT参数的Fiware Orion LD + IoT Agent JSON配置问题

场景说明

拥有一台IoT设备,其运行时可配置参数支持两种修改方式:用户主动修改,或设备自身为优化功耗自行重配置。设备仅通过HTTP通信,无独立配置端点,需在上报测量数据时顺带接收配置更新。采用Fiware Orion LD与IoT Agent JSON组合方案,尝试用双向属性适配该场景(参数非真实执行器,支持双方修改),但配置过程中遇到问题。

部署环境(Docker Compose)

version: "3.8"
services:

  ngsi-ld-context-server:
    image: nginx:latest
    hostname: ngsi-ld-context-server
    container_name: ngsi-ld-context-server
    networks:
      - fiware
    ports:
      - "9090:80"
    volumes:
      - ./ngsild-context.jsonld:/usr/share/nginx/html/ngsild-context.jsonld

  fiware-mongo-db:
    image: mongo:4.4
    hostname: fiware-mongo-db
    container_name: fiware-mongo-db
    networks:
      - fiware
    ports:
      - "27017:27017"

  orion-ld:
    platform: linux/amd64
    image: quay.io/fiware/orion-ld:1.4.0
    hostname: orion-ld
    container_name: orion-ld
    networks:
      - fiware
    depends_on:
      - fiware-mongo-db
    ports:
      - "1026:1026"
    command: -dbhost fiware-mongo-db -logLevel DEBUG -forwarding -experimental

  iot-agent-json:
    image: quay.io/fiware/iotagent-json:2.2.0
    hostname: iot-agent-json
    container_name: iot-agent-json
    networks:
      - fiware
    depends_on:
      - fiware-mongo-db
      - orion-ld
    ports:
      - "4041:4041"
      - "7896:7896"
    environment:
      - IOTA_CB_HOST=orion-ld 
      - IOTA_CB_PORT=1026
      - IOTA_NORTH_PORT=4041
      - IOTA_REGISTRY_TYPE=mongodb 
      - IOTA_LOG_LEVEL=DEBUG 
      - IOTA_TIMESTAMP=true 
      - IOTA_AUTOCAST=true 
      - IOTA_MONGO_HOST=fiware-mongo-db 
      - IOTA_MONGO_PORT=27017
      - IOTA_MONGO_DB=iotagenjson 
      - IOTA_HTTP_PORT=7896
      - IOTA_PROVIDER_URL=http://iot-agent-json:4041
      - IOTA_DEFAULT_RESOURCE=/iot/json

      - IOTA_CB_NGSI_VERSION=ld 
      - IOTA_JSON_LD_CONTEXT=http://ngsi-ld-context-server/ngsild-context.jsonld
      - IOTA_FALLBACK_TENANT=openiot

networks:
  fiware:
    driver: bridge

配置流程与问题

1. 创建设备服务

首先通过以下配置创建设备服务:

{
    "services": [
        {
            "apikey": "4jggokgpepnvsb2uv4s40d59ov",
            "cbroker": "http://orion-ld:1026",
            "entity_type": "Device",
            "resource": "/iot/json"
        }
    ]
}

2. 首次配置双向属性(失败)

参照IoT Agent NGSILD教程配置双向属性(因设备采用轮询模式,未提供端点):

{
  "devices": [
    {
      "device_id": "device001",
      "entity_name": "urn:ngsi-ld:Device:device001",
      "entity_type": "Device",
      "attributes": [
        {
            "name": "sampleTime",
            "type": "Property",
            "reverse": [
                {
                    "object_id": "sampleTime",
                    "type": "Property"
                }
            ]
        }
      ]
    }
  ]
}

执行后收到错误响应:

{
    "name": "ENTITY_GENERIC_ERROR",
    "message": "Error accesing entity data for device: urn:ngsi-ld:Device:device001 of type: Device"
}

查看IoT Agent日志发现,Agent尝试向Orion LD创建的订阅中notification.attributes为空数组,而Orion LD不允许空数组:

time=2023-08-31T06:36:43.764Z | lvl=DEBUG | corr=1cfae922-438d-473a-9511-1f4fe7ad9f3e | trans=1cfae922-438d-473a-9511-1f4fe7ad9f3e | op=IoTAgentNGSI.BidirectionalPlugin | from=n/a | srv=n/a | subsrv=n/a | msg=Extracted variables: [] | comp=IoTAgent
time=2023-08-31T06:36:43.765Z | lvl=DEBUG | corr=1cfae922-438d-473a-9511-1f4fe7ad9f3e | trans=1cfae922-438d-473a-9511-1f4fe7ad9f3e | op=IoTAgentNGSI.RestUtils | from=n/a | srv=n/a | subsrv=n/a | msg=executeWithSecurity | comp=IoTAgent
time=2023-08-31T06:36:43.765Z | lvl=DEBUG | corr=1cfae922-438d-473a-9511-1f4fe7ad9f3e | trans=1cfae922-438d-473a-9511-1f4fe7ad9f3e | op=IoTAgentNGSI.MongoDBGroupRegister | from=n/a | srv=n/a | subsrv=n/a | msg=Looking for group params ["type"] with queryObj {"type":"Device"} | comp=IoTAgent
time=2023-08-31T06:36:43.768Z | lvl=DEBUG | corr=1cfae922-438d-473a-9511-1f4fe7ad9f3e | trans=1cfae922-438d-473a-9511-1f4fe7ad9f3e | op=IoTAgentNGSI.MongoDBGroupRegister | from=n/a | srv=openiot | subsrv=/ | msg=Device group data found: {"_id":"64f033436e41de0d07b70359","resource":"/iot/json","apikey":"4jggokgpepnvsb2uv4s40d59ov","type":"Device","service":"openiot","subservice":"/"} | comp=IoTAgent
time=2023-08-31T06:36:43.769Z | lvl=DEBUG | corr=1cfae922-438d-473a-9511-1f4fe7ad9f3e | trans=1cfae922-438d-473a-9511-1f4fe7ad9f3e | op=IoTAgentNGSI.Request | from=n/a | srv=openiot | subsrv=/ | msg=Options: {
    "method": "POST",
    "headers": {
        "fiware-service": "openiot",
        "fiware-servicepath": "/",
        "NGSILD-Tenant": "openiot",
        "NGSILD-Path": "/",
        "Content-Type": "application/ld+json"
    },
    "json": {
        "@context": "http://ngsi-ld-context-server/ngsild-context.jsonld",
        "type": "Subscription",
        "entities": [
            {
                "id": "urn:ngsi-ld:Device:device001",
                "type": "Device"
            }
        ],
        "watchedAttributes": [
            "sampleTime"
        ],
        "notification": {
            "endpoint": {
                "uri": "http://iot-agent-json:4041/notify",
                "accept": "application/json"
            },
            "attributes": [],
            "format": "normalized"
        }
    },
    "uri": "http://orion-ld:1026/ngsi-ld/v1/subscriptions/"
} | comp=IoTAgent
time=2023-08-31T06:36:43.786Z | lvl=DEBUG | corr=1cfae922-438d-473a-9511-1f4fe7ad9f3e | trans=1cfae922-438d-473a-9511-1f4fe7ad9f3e | op=IoTAgentNGSI.Request | from=n/a | srv=openiot | subsrv=/ | msg=Response {
    "type": "https://uri.etsi.org/ngsi-ld/errors/BadRequestData",
    "title": "Empty Array",
    "detail": "Subscription::notification::attributes"
} | comp=IoTAgent
time=2023-08-31T06:36:43.786Z | lvl=DEBUG | corr=1cfae922-438d-473a-9511-1f4fe7ad9f3e | trans=1cfae922-438d-473a-9511-1f4fe7ad9f3e | op=IoTAgentNGSI.Subscription-LD | from=n/a | srv=openiot | subsrv=/ | msg=Unknown error subscribing device with id [400] to entity [%s]: $s | comp=IoTAgent

3. 添加expression后的问题

在配置中添加expression后,配置可正常生效:

{
  "devices": [
    {
      "device_id": "device001",
      "entity_name": "urn:ngsi-ld:Device:device001",
      "entity_type": "Device",
      "attributes": [
        {
            "name": "sampleTime",
            "type": "Property",
            "reverse": [
                {
                    "object_id": "sampleTime",
                    "type": "Property",
                    "expression": "sampleTime | tostring()"
                }
            ]
        }
      ]
    }
  ]
}

但使用getCmd参数获取命令时,会返回重复的旧命令;若在设备获取前再次更新命令,设备无法获取到最新值,疑似MongoDB未正确存储命令。

疑问

  1. 首次配置是否遗漏了必要参数或步骤?
  2. 针对这种支持设备与用户双向修改的属性场景,有没有标准的处理方案?

内容的提问来源于stack exchange,提问作者SwLibelium

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.12 07:37:03