Ditto中没有可用的MessageMappingProcessor

时间:2019-04-01 11:30:33

标签: javascript java iot eclipse-ditto eclipse-iot

尽管我遵循同上示例中的准则,但还是遇到了一个陌生人错误。

章鱼可以将消息发布到MQTT。我可以看到他们使用MQTT客户端。 WebApp显示已建立连接并发送发送事件。我可以通过"my.test.octopus"面板更改值。但是,当我使用API​​查询它时,我只能从webapp中获取值,而从八达通中找不到值。

我检查了连接日志,似乎是映射问题...创建连接时,我使用以下方法来创建映射:

"incomingScript": "function mapToDittoProtocolMsg(
                              headers, 
                              textPayload, 
                              bytePayload, 
                              contentType) {

    const jsonString = String.fromCharCode.apply(null, new Uint8Array(bytePayload));
    const jsonData = JSON.parse(jsonString);
    const thingId = jsonData.thingId;
    const value = { 
      temp_sensor: { 
        properties: { 
          value: jsonData.temp 
        }
      },
      altitude: { 
        properties: { 
          value: jsonData.alt 
        }
      }
    };

    return Ditto.buildDittoProtocolMsg('my.test', thingId, 'things', 'twin', 'commands', 'modify', '/features', headers, value);
}"

感谢帮助

更新

该错误显示在以下日志行中:

请参阅以下日志语句:

"The message mapper configuration failed due to: unterminated regular expression literal (incomingScript#1) - in line/column #1/472," -- ""incomingScript": "function mapToDittoProtocolMsg(headers, textPayload, bytePayload, contentType) {var jsonData = JSON.parse(textPayload);const thingId = jsonData.thingId;const value = {temp_sensor: { properties: { value: jsonData.temp } }, altitude: { properties: { value: jsonData.alt } } }; return Ditto.buildDittoProtocolMsg('my.test', thingId, 'things', 'twin', 'commands', 'modify', '/features', headers, value); }"

1 个答案:

答案 0 :(得分:1)

您的映射脚本似乎正常工作。我使用payload mapping testing from ditto-examples为它创建了一个单元测试。

此测试如下所示:

 @Test
 public void incomingBytePayloadMapping() throws IOException {
     final Resource incomingMappingFunction = new Resource("incomingScript.js");
     final PayloadMappingFunction underTest = PayloadMappingFunction.fromJavaScript(incomingMappingFunction.getContent());

     final Map<String, String> headers = new HashMap<>();
     headers.put("content-type", ContentTypes.APPLICATION_OCTET_STREAM.toString());
     headers.put("device_id", "the-thing-id");

     final byte[] bytePayload = "{\"thingId\":\"my.test.thing\",\"temp\":25.6,\"alt\":11}".getBytes();
     final ExternalMessage message = ExternalMessageFactory.newExternalMessageBuilder(headers)
             .withBytes(bytePayload)
             .build();

     final Resource expectedAdaptableJsonResource = new Resource("expectedAdaptable.json");
     final JsonObject expectedAdaptableJson = JsonFactory.newObject(expectedAdaptableJsonResource.getContent());
     final Adaptable expectedAdaptable = ProtocolFactory
             .jsonifiableAdaptableFromJson(expectedAdaptableJson)
             .setDittoHeaders(DittoHeaders.of(headers));

     PayloadMappingTestCase.assertThat(message)
             .mappedByJavascriptPayloadMappingFunction(underTest)
             .isEqualTo(expectedAdaptable)
             .verify();
 }

incomingScript.js

function mapToDittoProtocolMsg(
    headers,
    textPayload,
    bytePayload,
    contentType) {

    const jsonString = String.fromCharCode.apply(null, new Uint8Array(bytePayload));
    const jsonData = JSON.parse(jsonString);
    const thingId = jsonData.thingId;
    const value = {
        temp_sensor: {
            properties: {
                value: jsonData.temp
            }
        },
        altitude: {
            properties: {
                value: jsonData.alt
            }
        }
    };

    return Ditto.buildDittoProtocolMsg('my.test', thingId, 'things', 'twin', 'commands', 'modify', '/features', headers,
                                       value);
}

expectedAdaptable.json

{
  "topic": "my.test/my.test.thing/things/twin/commands/modify",
  "headers": {},
  "path": "/features",
  "value": {
    "temp_sensor": {
      "properties": {
        "value": 25.6
      }
    },
    "altitude": {
      "properties": {
        "value": 11
      }
    }
  }
}

到目前为止,这似乎可行,但是在此测试中,我假设以下传入的bytePayload:

final byte[] bytePayload = "{\"thingId\":\"my.test.thing\",\"temp\":25.6,\"alt\":11}".getBytes();

您能以某种方式验证章鱼发送的字节有效负载是否正确吗?章鱼真的是发送字节有效载荷还是文本有效载荷(application / json)?

更新

根据Bob Su的注释,章鱼正在发送文本有效内容。 为了映射此有效负载,您实际上必须使用文本有效负载而不是字节有效负载。在下面的内容中,您将看到更新的传入脚本。

incomingScript.js

function mapToDittoProtocolMsg(
    headers,
    textPayload,
    bytePayload,
    contentType) {

    var jsonData = JSON.parse(textPayload);
    const thingId = jsonData.thingId;
    const value = {
        temp_sensor: {
            properties: {
                value: jsonData.temp
            }
        },
        altitude: {
            properties: {
                value: jsonData.alt
            }
        }
    };

    return Ditto.buildDittoProtocolMsg('my.test', thingId, 'things', 'twin', 'commands', 'modify', '/features', headers,
                                       value);
}

该测试可以适应:

@Test
public void incomingTextPayloadMapping() throws IOException {
    final Resource incomingMappingFunction = new Resource("incomingScript.js");
    final PayloadMappingFunction underTest = PayloadMappingFunction.fromJavaScript(incomingMappingFunction.getContent());

    final Map<String, String> headers = new HashMap<>();
    headers.put("content-type", ContentTypes.APPLICATION_JSON.toString());
    headers.put("device_id", "the-thing-id");

    final ExternalMessage message = ExternalMessageFactory.newExternalMessageBuilder(headers)
            .withText("{\"thingId\":\"my.test.thing\",\"temp\":25.6,\"alt\":11}")
            .build();

    final Resource expectedAdaptableJsonResource = new Resource("expectedAdaptable.json");
    final JsonObject expectedAdaptableJson = JsonFactory.newObject(expectedAdaptableJsonResource.getContent());
    final Adaptable expectedAdaptable = ProtocolFactory
            .jsonifiableAdaptableFromJson(expectedAdaptableJson)
            .setDittoHeaders(DittoHeaders.of(headers));

    PayloadMappingTestCase.assertThat(message)
            .mappedByJavascriptPayloadMappingFunction(underTest)
            .isEqualTo(expectedAdaptable)
            .verify();
}