CoAP 协议网关

简介

CoAP 网关以 Publish-Subscribe Broker for the CoAPCoAP 协议网关 - 图1 (opens new window) 为标准,实现了发布、订阅、和消息接收功能。

出于安全性的考虑,CoAP 网关实现了 连接模式 以提供客户端接入认证功能来限制未授权的 CoAP 客户端接入系统。

快速开始

EMQX 5.0 可以通过 Dashboard 配置并启用 CoAP 网关。

也可以通过 HTTP API 或 emqx.conf 来启用,例如:

  1. curl -X 'PUT' 'http://127.0.0.1:18083/api/v5/gateway/coap' \
  2. -u <your-application-key>:<your-security-key> \
  3. -H 'Content-Type: application/json' \
  4. -d '{
  5. "name": "coap",
  6. "enable": true,
  7. "mountpoint": "coap/",
  8. "connection_required": false,
  9. "listeners": [
  10. {
  11. "type": "udp",
  12. "name": "default",
  13. "bind": "5683",
  14. "max_conn_rate": 1000,
  15. "max_connections": 1024000
  16. }
  17. ]
  18. }'
  1. gateway.coap {
  2. mountpoint = "coap/"
  3. connection_required = false
  4. listeners.udp.default {
  5. bind = "5683"
  6. max_connections = 1024000
  7. max_conn_rate = 1000
  8. }
  9. }

提示

通过配置文件来配置网关,需要在每个节点上手动同步配置文件;而通过 Dashboard 或者 HTTP API 管理则会自动同步至整个集群。

CoAP 网关支持 UDP、DTLS 类型的监听器,其完整可配置的参数列表请参考:网关配置 - 监听器

工作模式

CoAP 网关支持 2 种工作模式:

  • 无连接模式:该模式完全遵循 Publish-Subscribe Broker for the CoAPCoAP 协议网关 - 图2 (opens new window) 协议,在该模式下不需要连接认证、会话、心跳维持等操作,仅支持:

    • 消息发布
    • 订阅主题
    • 取消订阅
  • 连接模式:该模式下定义了连接认证、会话、和心跳维持等概念。客户端在发布订阅前需要先创建连接,成功连接后客户端将获得会话令牌(Token),在后续的通信中都需要在 Query String 加入令牌信息。它实现了如下功能:

    • 创建连接
    • 关闭连接
    • 会话保持 (心跳, 可选的)
    • 认证

是否开启 连接模式connection_required 参数决定,例如

  1. # emqx.conf
  2. gateway.coap {
  3. ## true: 开启连接模式
  4. ## false: 关闭连接模式
  5. connection_required = true
  6. }

提示

连接模式 仅新增了连接管理相关接口。该模式下仍可以执行发布/订阅、取消订阅等操作,但每次请求需要携带 ClientId 和 Token。

认证

仅在 连接模式 下可用。 客户端 ID、用户名、密码由客户端的 创建连接 请求提供,CoAP 网关支持以下认证器类型:

例如,通过 HTTP API 或 emqx.conf 为 CoAP 网关创建一个内置数据库认证:

  1. curl -X 'POST' \
  2. 'http://127.0.0.1:18083/api/v5/gateway/coap/authentication' \
  3. -u <your-application-key>:<your-security-key> \
  4. -H 'accept: application/json' \
  5. -H 'Content-Type: application/json' \
  6. -d '{
  7. "backend": "built_in_database",
  8. "mechanism": "password_based",
  9. "password_hash_algorithm": {
  10. "name": "sha256",
  11. "salt_position": "suffix"
  12. },
  13. "user_id_type": "username"
  14. }'
  1. gateway.coap {
  2. authentication {
  3. backend = built_in_database
  4. mechanism = password_based
  5. password_hash_algorithm {
  6. name = sha256
  7. salt_position = suffix
  8. }
  9. user_id_type = username
  10. }
  11. }

与 MQTT 协议不同,网关仅支持创建一个认证器,而不是认证器列表(或认证链)。当不启用任何认证器时,表示所有的 CoAP 客户端都具有接入的权限。

其他类型的认证器的配置格式参考:安全 - 认证器

发布订阅

CoAP 网关基于 Publish-Subscribe Broker for the CoAPCoAP 协议网关 - 图3 (opens new window) 协议中定义的请求路径和请求方法 实现了发布订阅的接口。

详情参考下文中的 消息发布订阅主题取消订阅

网关内无独立的发布订阅的权限控制,其对主题的权限控制需要统一在 授权(Authorization) 中管理。

用户层接口

客户端库

附录:客户端接入接口说明

创建连接

仅在 连接模式 下可用。

该接口用于向 CoAP 网关创建客户端连接。当开启 CoAP 网关的认证功能后,网关会对该请求中的 clientid, username, password 进行验证,以防止非法用户登录系统。

请求参数表:

  • 方法(Method): POST
  • 请求路径(URI):mqtt/connection{?QueryString*},其中 QueryString 可用参数为
    • clientid:必填参数;UTF8 字符串,网关以该字符串作为该连接的唯一标识。
    • username:可选参数,UTF8 字符串,用于连接认证。
    • password:可选参数,UTF8 字符串,用于连接认证。
  • 消息体(Payload):为空。

返回结果:

  • 返回码(Return Code):
    • 2.01:连接创建成功,并在消息体中返回本次连接的 Token 字符串。
    • 4.00:错误的请求格式,并在消息体中返回具体的错误信息。
    • 4.01:请求格式正确,但登录鉴权失败。并在消息体中返回具体的错误信息。
  • 消息体(Payload):当返回码为 2.01时,消息体为 Token,否则为 ErrorMessage
    • Token:用于后续请求使用的令牌字符串。
    • ErrorMessage: 错误说明,例如 Login Failed: not_authorized

libcoap 为例:

  1. # 使用 clientid 为 123, 用户名密码为 admin/public 发起创建连接请求,
  2. # 返回 Token 为 3404490787
  3. coap-client -m post -e "" "coap://127.0.0.1/mqtt/connection?clientid=123&username=admin&password=public"
  4. 3404490787

提示

连接创建成功后,可以使用 Dashboard,HTTP API 或 CLI 检查 CoAP 网关的客户端列表中是否已存在该客户端。

断开连接

仅在 连接模式 下可用。

该接口用于关闭 CoAP 客户端连接。

请求参数表:

  • 方法(Method): DELETE
  • 请求路径(URI):mqtt/connection{?QueryString*},其中 QueryString 可用参数为
    • clientid:必填参数;UTF8 字符串,网关以该字符串作为该连接的唯一标识。
    • token:必填参数;使用由创建连接方法返回的 Token 字符串
  • 消息体(Payload):为空。

返回结果:

  • 返回码(Return Code):
    • 2.01:关闭连接成功。
    • 4.00:错误的请求格式,并在消息体中返回具体的错误信息。
    • 4.01:请求格式正确,但登录鉴权失败。并在消息体中返回具体的错误信息。
  • 消息体(Payload):当返回码为 2.01 时,消息体为空;否则为具体的错误消息

例如:

  1. coap-client -m delete -e "" "coap://127.0.0.1/mqtt/connection?clientid=123&token=3404490787"

心跳

仅在 连接模式 下可用。

该接口用于维持 CoAP 客户端与网关的连接。当心跳超期后,网关会删除该客户端的会话、订阅关系,并释放所有的资源。

请求参数表:

  • 方法(Method): PUT
  • 请求路径(URI):mqtt/connection{?QueryString*},其中 QueryString 可用参数为
    • clientid:必填参数;UTF8 字符串,网关以该字符串作为该连接的唯一标识。
    • token:必填参数;使用由创建连接方法返回的 Token 字符串
  • 消息体(Payload):为空。

返回结果:

  • 返回码(Return Code):
    • 2.01:更新成功。
    • 4.00:错误的请求格式,并在消息体中返回具体的错误信息。
    • 4.01:请求格式正确,但登录鉴权失败。并在消息体中返回具体的错误信息。
  • 消息体(Payload):当返回码为 2.01 时,消息体为空;否则为具体的错误消息

例如:

  1. coap-client -m put -e "" "coap://127.0.0.1/mqtt/connection?clientid=123&token=3404490787"

提示

心跳间隔时间由 CoAP 网关的 hearbeat 配置决定,默认为 30 秒

消息发布

该接口用于 CoAP 客户端为指定主题发送消息。在 连接模式 下需要额外携带身份信息。

请求参数表:

  • 方法(Method):POST
  • 请求路径(URI):ps/{+topic}{?QueryString*},其中:
    • {+topic} 为需要发布的主题,例如向 coap/test 主题发布消息,那么请求路径为 ps/coap/test
    • {?QueryString*} 为请求参数
      • clientid连接模式 下为必填参数,无连接模式 下为可选参数。
      • token: 仅用于 连接模式,必填参数;
      • retain:是否作为保留消息进行发布;布尔类型,可选参数,默认为 false
      • qos:消息 QoS,用于标识该消息的 QoS 等级,仅影响 MQTT 客户端如何接收该消息;枚举类型,可选值为 012
      • expiry:消息超期时间,单位秒;默认为 0 表示永不超期
  • 消息体(Payload):消息内容

返回结果:

  • 返回码(Return Code):
    • 2.04:发送成功。
    • 4.00:错误的请求格式,并在消息体中返回具体的错误信息。
    • 4.01:请求格式正确,但鉴权失败。并在消息体中返回具体的错误信息。
  • 消息体(Payload):当返回码为 2.04 时,消息体为空;否则为具体的错误消息

例如,无连接模式 下为 coap/test 发送一条消息:

  1. coap-client -m post -e "Hi, this is libcoap" "coap://127.0.0.1/ps/coap/test"

连接模式 下则需要携带 clientidtoken

  1. coap-client -m post -e "Hi, this is libcoap" "coap://127.0.0.1/ps/coap/test&clientid=123&token=3404490787"

订阅主题

该接口用于 CoAP 客户端订阅指定主题。在 连接模式 下需要额外携带身份信息。

请求参数表:

  • 方法(Method):POST

  • 选项值(Options):需设置 observer 为 0

  • 请求路径(URI):ps/{+topic}{?QueryString*},其中:

    • {+topic} 为需要订阅主题,例如订阅 coap/test 主题,则请求路径为 ps/coap/test
    • {?QueryString*}为请求参数
      • clientid连接模式下为必填参数,无连接模式下为可选参数。
      • token: 仅用于 连接模式,必填参数;
      • qos:订阅 QoS,用于指示网关以那种消息类型(CONNON)来投递后续接收的该消息;枚举类型,可选值为:
        • 012:设置为qos0qos1qos2。如果设置为 qos0 表示该主题上的消息会以 NON 消息进行投递;qos1qos2 表示该主题上的消息会以 CON 消息进行投递。
  • 消息体(Payload):空

返回结果:

  • 返回码(Return Code):
    • 2.05:订阅成功。
    • 4.00:错误的请求格式,并在消息体中返回具体的错误信息。
    • 4.01:请求格式正确,但鉴权失败。并在消息体中返回具体的错误信息。
  • 消息体(Payload):当返回码为 2.05 时,消息体为空;否则为具体的错误消息

例如,无连接模式 下订阅主题 coap/test

  1. coap-client -m get -s 60 -O 6,0x00 -o - -T "obstoken" "coap://127.0.0.1/ps/coap/test"

连接模式 下则需要携带 clientidtoken

  1. coap-client -m post -e "Hi, this is libcoap" "coap://127.0.0.1/ps/coap/test&clientid=123&token=3404490787"

取消订阅

该接口用于 CoAP 客户端取消订阅指定主题。在 连接模式 下需要额外携带身份信息。

请求参数表:

  • 方法(Method):GET
  • 请求路径(URI):ps/{+topic}{?QueryString*},其中:
    • {+topic} 为需要取消订阅主题,例如取消订阅 coap/test 主题,则请求路径为 ps/coap/test
    • {?QueryString*}为请求参数
      • clientid连接模式下为必填参数,无连接模式下为可选参数。
      • token: 仅用于 连接模式,必填参数;
  • 消息体(Payload):空

返回结果:

  • 返回码(Return Code):
    • 2.07:取消订阅成功。
    • 4.00:错误的请求格式,并在消息体中返回具体的错误信息。
    • 4.01:请求格式正确,但鉴权失败。并在消息体中返回具体的错误信息。
  • 消息体(Payload):当返回码为 2.07 时,消息体为空;否则为具体的错误消息