eclipse / packages

IoT Packages project
https://eclipse.org/packages
Eclipse Public License 2.0
46 stars 66 forks source link

Fix curl command in 'Receiving command at device' c2e tour section. #503

Closed calohmn closed 1 year ago

calohmn commented 1 year ago

The curl command in the Receiving a command at the device chapter was not returning the command that was sent to Ditto via

curl -i -X POST -u ditto:ditto -H 'Content-Type: application/json' -w '\n' --data '{
  "water-amount": "3liters"
}' ${DITTO_API_BASE_URL:?}/api/2/things/org.eclipse.packages.c2e:demo-device/inbox/messages/start-watering?timeout=0

as written in the "Sending a command to the device via its digital twin" chapter.

calohmn commented 1 year ago

When I follow the "Receiving a command at the device" section and run

curl -i -k -u demo-device@org.eclipse.packages.c2e:demo-secret -H 'hono-ttd: 50' -H 'application/json' -w '\n' --data '{
  "topic": "org.eclipse.packages.c2e/demo-device/things/twin/commands/modify",
  "headers": {},
  "path": "/features/temperature/properties/value",
  "value": 45
}' ${HTTP_ADAPTER_BASE_URL:?}/telemetry

without having sent a Ditto message on the /api/2/things/org.eclipse.packages.c2e:demo-device/inbox/messages/start-watering before, there is an immediate response - there is no waiting for a Ditto start-watering message.

If I do send the start-watering message on the /api/2/things/[...] endpoint before and then run the above telemetry request, there is still the same kind of response

{
  "topic": "org.eclipse.packages.c2e/demo-device/things/twin/commands/modify",
  "headers": {
    "context-tags": "upstream.name=ditto-connectivity;",
    "tracestate": "",
    "ditto-originator": "pre-authenticated:hono-connection-org.eclipse.packages.c2e",
    "response-required": false,
    "traceparent": "00-753c1407a2328fb3b7d4d3221274e466-bafa1f16e627d8bb-01",
    "etag": "\"hash:2d\"",
    "requested-acks": [],
    "content-type": "application/json",
    "correlation-id": "677c06ad-a267-4e1f-9270-cc72112c2d63"
  },
  "path": "/features/temperature/properties/value",
  "status": 204
}

This isn't containing the start-watering message and doesn't look like how the response is documented to look like in the expandable "Example of a received command at the device" section.

{
  "topic": "org.eclipse.packages.c2e/demo-device/things/live/messages/start-watering",
  "headers": {
    "correlation-id": "d84b1ceb-797b-45f5-bc87-78e9b5396645",
    "x-forwarded-for": "10.244.0.1",
    "version": 2,
    "timeout": "0",
    "x-forwarded-user": "ditto",
    "accept": "*/*",
    "x-real-ip": "10.244.0.1",
    "x-ditto-dummy-auth": "nginx:ditto",
    "host": "172.17.0.2:30385",
    "content-type": "application/json",
    "timestamp": "2020-02-28T08:04:43.518+01:00",
    "user-agent": "curl/7.58.0"
  },
  "path": "/inbox/messages/start-watering",
  "value": {
    "water-amount": "3liters"
  }
}

With the command used in this PR

curl -i -k -u demo-device@org.eclipse.packages.c2e:demo-secret -H 'hono-ttd: 50' -H 'application/json' -w '\n' --data '{
  "topic": "org.eclipse.packages.c2e/demo-device/things/live/messages/start-watering",
  "path": "/inbox/messages/start-watering"
}' ${HTTP_ADAPTER_BASE_URL:?}/telemetry

there is actual waiting for a command - then returning the expected start-watering message after that had been sent to Ditto.

thjaeckle commented 1 year ago

Is the Ditto connection to Hono configured in a way to send responses to the command topic, responding to the telemetry update with a success response? In that case, the success response will be sent immediately sent as a command and no other request is waiting for the message to arrive.

The command you propose will work (because noone ist receiving it an answering to it, running into a timeout after 60 seconds), but it is nonsense to send a message from the device, which noone will receive just to get a downlink message.

calohmn commented 1 year ago

(The Ditto connection to Hono via Kafka is defined in packages/cloud2edge/post-install/hono-kafka-connection.json. For the AMQP connection there is packages/cloud2edge/post-install/hono-amqp-connection.json.)

The command you propose will work (because noone ist receiving it an answering to it, running into a timeout after 60 seconds), but it is nonsense to send a message from the device, which noone will receive just to get a downlink message.

In the c2e tour examples, the communication from and to the device is done via the HTTP adapter. In order for the device to receive a command message via the HTTP adapter, the device has to send a /telemetry request, supplying a hono-ttd header with the amount of type to wait for the command, which is then sent to the device by means of the HTTP response.

But you are right, sending a proper message here in the telemetry request isn't the way to do it. In Hono, there is a special content type for sending an empty message: application/vnd.eclipse-hono-empty-notification. Using that, the curl command looks like this:

curl -i -X POST -k -u demo-device@org.eclipse.packages.c2e:demo-secret -H 'hono-ttd: 50' \
  -H 'Content-Type: application/vnd.eclipse-hono-empty-notification' ${HTTP_ADAPTER_BASE_URL:?}/telemetry

And this also returns the Ditto message. I've updated the PR with that.

calohmn commented 1 year ago

However, it should maybe be mentioned that there is no guarantee that the expected message is returned as a response. It might also be the Ditto response to a telemetry update command sent back.. AFAIR this is quite random what Hono delivers and you could even miss messages in the time you open the next request for long polling.

Agreed. I think alongside the HTTP example there should also be one using MQTT (with mosquitto_sub), where you have a long-running connection, getting all commands. I'll look into adding that as part of the changes for #505.