IoT Hub 메시지 라우팅 쿼리 구문

메시지 라우팅을 사용하면 사용자가 디바이스 원격 분석 메시지, 디바이스 수명 주기 이벤트 및 디바이스 쌍 변경 이벤트 등의 여러 데이터 형식을 다양한 엔드포인트로 라우팅할 수 있습니다. 또한 이 데이터를 라우팅하기 전에 다양한 쿼리를 적용하여 사용자에게 중요한 데이터를 수신할 수 있습니다. 이 문서에서는 IoT Hub 메시지 라우팅 쿼리 언어를 설명하고 몇 가지 일반적인 쿼리 패턴을 제공합니다.

참고 항목

클라우드-디바이스 메시지, 디바이스 트윈스, 디바이스 관리 등 이 문서에 언급된 일부 기능은 IoT Hub의 표준 계층에서만 사용할 수 있습니다. 기본 및 표준/무료 IoT Hub 계층에 대한 자세한 내용은 솔루션에 적합한 IoT Hub 계층 선택을 참조하세요.

메시지 라우팅을 사용하면 메시지 속성 및 메시지 본문뿐만 아니라 디바이스 쌍 태그 및 디바이스 쌍 속성에 대해서도 쿼리할 수 있습니다. 메시지 본문이 JSON 형식이 아닌 경우 메시지 라우팅에서 메시지를 계속 라우팅할 수 있지만 메시지 본문에 쿼리를 적용할 수는 없습니다. 쿼리는 부울 식으로 설명됩니다. 즉, 식이 true이면 쿼리가 성공하고 들어오는 모든 데이터가 라우팅됩니다. 그렇지 않으면 쿼리가 실패하고 들어오는 데이터가 라우팅되지 않습니다. 식이 null 또는 정의되지 않은 값으로 평가되면 부울 false 값으로 처리되고 IoT Hub 경로 리소스 로그에 오류가 생성됩니다. 저장하고 평가할 경로에 대해 올바른 쿼리 구문을 사용해야 합니다.

메시지 속성에 따른 쿼리

IoT Hub는 프로토콜 전체에서의 상호 운용성을 위해 모든 디바이스-클라우드 메시징에 대해 일반적인 형식을 정의합니다. IoT Hub는 메시지의 다음 JSON 표현을 가정합니다. 시스템 속성은 모든 사용자에 대해 추가되며 메시지의 콘텐츠를 식별합니다. 사용자는 선택적으로 메시지에 애플리케이션 속성을 추가할 수 있습니다. IoT Hub 디바이스-클라우드 메시징이 대/소문자를 구분하지 않으므로 고유한 속성 이름을 사용하는 것이 좋습니다. 예를 들어, 이름이 같은 속성이 여러 개 있는 경우 IoT Hub는 속성 중 하나만 전송합니다.

{ 
  "message": { 
    "systemProperties": { 
      "contentType": "application/json", 
      "contentEncoding": "UTF-8", 
      "iothub-message-source": "deviceMessages", 
      "iothub-enqueuedtime": "2017-05-08T18:55:31.8514657Z" 
    }, 
    "appProperties": { 
      "processingPath": "{cold | warm | hot}", 
      "verbose": "{true, false}", 
      "severity": 1-5, 
      "testDevice": "{true | false}" 
    }, 
    "body": "{\"Weather\":{\"Temperature\":50}}" 
  } 
} 

시스템 속성

시스템 속성은 메시지의 내용과 원본을 식별하는 데 도움이 되며, 그중 일부는 다음 표에 설명되어 있습니다.

속성 Type 설명
contentType string 사용자가 메시지의 콘텐츠 형식을 지정합니다. 메시지 본문에 대한 쿼리를 허용하려면 이 값이 application/JSON으로 설정되어야 합니다.
contentEncoding string 사용자가 메시지의 인코딩 형식을 지정합니다. contentType 속성이 application/JSON으로 설정된 경우 허용되는 값은 UTF-8, UTF-16UTF-32입니다.
iothub-connection-device-id string 이 값은 IoT Hub에 의해 설정되며 디바이스의 ID를 식별합니다. 쿼리하려면 $connectionDeviceId을 사용합니다.
iothub-connection-module-id string 이 값은 IoT Hub에 의해 설정되며 에지 모듈의 ID를 식별합니다. 쿼리하려면 $connectionModuleId을 사용합니다.
iothub-enqueuedtime string 이 값은 IoT Hub에 의해 설정되며 UTC에서 메시지를 큐에 넣는 실제 시간을 나타냅니다. 쿼리하려면 $enqueuedTime을 사용합니다.
dt-dataschema string 이 값은 IoT Hub를 통해 디바이스-클라우드 메시지에 대해 설정됩니다. 디바이스 연결에 설정된 디바이스 모델 ID 세트를 포함합니다. 쿼리하려면 $dt-dataschema을 사용합니다.
dt-subject string 디바이스-클라우드 메시지를 전송하는 구성 요소의 이름입니다. 쿼리하려면 $dt-subject을 사용합니다.

사용 가능한 다른 시스템 속성에 대한 자세한 내용은 IoT Hub 메시지 만들기 및 읽기를 참조하세요.

애플리케이션 속성

애플리케이션 속성은 메시지에 추가할 수 있는 사용자 정의 문자열입니다. 이러한 필드는 선택 사항입니다.

메시지 속성 쿼리 식

메시지 시스템 속성에 대한 쿼리는 접두사로 $ 기호를 사용해야 합니다. 애플리케이션 속성에 대한 쿼리는 이름으로 액세스하며 $ 기호를 접두사로 사용하지 않아야 합니다. 애플리케이션 속성 이름이 $로 시작하는 경우, IoT Hub는 먼저 시스템 속성에서 해당 항목을 검색하며, 찾을 수 없으면 애플리케이션 속성에서 검색합니다. 다음 예제에서는 시스템 속성 및 애플리케이션 속성을 쿼리하는 방법을 보여 줍니다.

시스템 속성 contentEncoding에서 쿼리하려면 다음을 수행합니다.

$contentEncoding = 'UTF-8'

애플리케이션 속성 processingPath에서 쿼리하려면 다음을 수행합니다.

processingPath = 'hot'

이러한 쿼리를 결합하려면 부울 식 및 함수를 사용하면 됩니다.

$contentEncoding = 'UTF-8' AND processingPath = 'hot'

지원되는 연산자 및 함수의 전체 목록은 디바이스 및 모듈 쌍, 작업 및 메시지 라우팅에 대한 IoT Hub 쿼리 언어식 및 조건에 표시됩니다.

메시지 본문에 따른 쿼리

메시지 본문에 대한 쿼리를 사용하려면 메시지가 JSON 형식이어야 하고 UTF-8, UTF-16 또는 UTF-32로 인코딩되어야 합니다. contentType 시스템 속성은 application/JSON이어야 합니다. contentEncoding 시스템 속성은 해당 시스템 속성에서 지원하는 UTF 인코딩 값 중 하나여야 합니다. 이러한 시스템 속성을 지정하지 않은 경우 IoT Hub는 메시지 본문에 대해 쿼리 식을 평가하지 않습니다.

다음 JavaScript 예제에서는 올바르게 구성되고 인코딩된 JSON 본문을 사용하여 메시지를 만드는 방법을 보여 줍니다.

var messageBody = JSON.stringify(Object.assign({}, {
    "Weather": {
        "Temperature": 50,
        "Time": "2017-03-09T00:00:00.000Z",
        "PrevTemperatures": [
            20,
            30,
            40
        ],
        "IsEnabled": true,
        "Location": {
            "Street": "One Microsoft Way",
            "City": "Redmond",
            "State": "WA"
        },
        "HistoricalData": [
            {
                "Month": "Feb",
                "Temperature": 40
            },
            {
                "Month": "Jan",
                "Temperature": 30
            }
        ]
    }
}));

// Encode message body using UTF-8  
var messageBytes = Buffer.from(messageBody, "utf8");

var message = new Message(messageBytes);

// Set message body type and content encoding 
message.contentEncoding = "utf-8";
message.contentType = "application/json";

// Add other custom application properties   
message.properties.add("Status", "Active");

deviceClient.sendEvent(message, (err, res) => {
    if (err) console.log('error: ' + err.toString());
    if (res) console.log('status: ' + res.constructor.name);
});

C#의 메시지 인코딩 샘플은 .NET용 Microsoft Azure IoT SDK에 제공된 HubRoutingSample을 참조하세요. 이 샘플은 메시지 라우팅 자습서에 사용되는 것과 같습니다. Program.cs 파일에는 인코딩된 파일 중 하나를 읽고, 디코딩하고, ASCII로 다시 작성하여 읽을 수 있도록 하는 ReadOneRowFromFile라는 메서드도 있습니다.

메시지 본문 쿼리 식

메시지 본문에 대한 쿼리에는 $body 접두사가 있어야 합니다. 쿼리 식에 본문 참조, 본문 배열 참조 또는 여러 본문 참조를 사용할 수 있습니다. 또한 쿼리 식은 본문 참조를 메시지 시스템 속성 참조 또는 메시지 애플리케이션 속성 참조와 결합할 수 있습니다. 예를 들어 다음 예제는 모든 유효한 쿼리 식입니다.

$body.Weather.HistoricalData[0].Month = 'Feb' 
$body.Weather.Temperature = 50 AND $body.Weather.IsEnabled 
length($body.Weather.Location.State) = 2 
$body.Weather.Temperature = 50 AND processingPath = 'hot'

쿼리 및 함수는 본문 참조의 속성에 대해서만 실행할 수 있습니다. 전체 본문 참조에서 쿼리 또는 함수를 실행할 수 없습니다. 예를 들어 다음 쿼리는 지원되지 ‘않으며’ undefined를 반환합니다.

$body[0] = 'Feb'

변경된 사항을 기반으로 쌍 알림 페이로드를 필터링하려면 메시지 본문에서 쿼리를 실행합니다. 예를 들어 sendFrequency에 desired 속성 변경이 있고 값이 10보다 큰 경우 필터링하려면 다음을 수행합니다.

$body.properties.desired.telemetryConfig.sendFrequency > 10

속성 값에 관계없이 속성 변경이 포함된 메시지를 필터링하려면 is_defined() 함수를 사용할 수 있습니다(값이 기본 형식인 경우).

is_defined($body.properties.desired.telemetryConfig.sendFrequency)

디바이스 또는 모듈 쌍에 따른 쿼리

메시지 라우팅을 사용하면 JSON 개체인 디바이스 쌍 또는 모듈 쌍 태그 및 속성에서 쿼리를 사용할 수 있습니다. 다음 샘플에서는 태그 및 속성이 있는 디바이스 쌍을 보여 줍니다.

{
    "tags": { 
        "deploymentLocation": { 
            "building": "43", 
            "floor": "1" 
        } 
    }, 
    "properties": { 
        "desired": { 
            "telemetryConfig": { 
                "sendFrequency": "5m" 
            }, 
            "$metadata" : {...}, 
            "$version": 1 
        }, 
        "reported": { 
            "telemetryConfig": { 
                "sendFrequency": "5m", 
                "status": "success" 
            },
            "batteryLevel": 55, 
            "$metadata" : {...}, 
            "$version": 4 
        } 
    } 
} 

참고 항목

모듈은 해당 디바이스에서 쌍 태그를 상속하지 않습니다. 디바이스 모듈(예: IoT Edge 모듈)에서 발생하는 메시지에 대한 쌍 쿼리는 해당 디바이스 쌍이 아닌 모듈 쌍에 대해 쿼리합니다.

쌍 쿼리 식

디바이스 쌍 또는 모듈 쌍에 대한 쿼리에는 $twin 접두사가 있어야 합니다. 쿼리 식은 쌍 태그 또는 속성 참조를 본문 참조, 메시지 시스템 속성 참조 또는 메시지 애플리케이션 속성 참조와 결합할 수도 있습니다. 쿼리가 대/소문자를 구분하지 않으므로 태그 및 속성에 고유한 이름을 사용하는 것이 좋습니다. 이 권장 사항은 디바이스 쌍과 모듈 쌍 둘 다에 적용됩니다. 또한 twin, $twin, body 또는 $body는 속성 이름으로 사용하지 않는 것이 좋습니다. 예를 들어 다음 예제는 모든 유효한 쿼리 식입니다.

$twin.properties.desired.telemetryConfig.sendFrequency = '5m'
$body.Weather.Temperature = 50 AND $twin.properties.desired.telemetryConfig.sendFrequency = '5m'
$twin.tags.deploymentLocation.floor = 1 

제한 사항

라우팅 쿼리는 속성 이름, 메시지 본문 경로 또는 디바이스/모듈 쌍 경로(()<>@,;:\"/?={})에서 공백 또는 다음 문자 중 어떤 문자도 사용할 수 없습니다.

다음 단계