チャンネルフィードデータ転送

 概要

Channel Feeds Data Forwarding サービスは、任意の UbiBot デバイスからの元データのコピーを指定した URL エンドポイントに転送します。
これにより、UbiBot デバイスをサードパーティのプラットフォームのビジネスロジックやアプリケーションとシームレスに接続することが可能になります。
このサービスを利用するには、UbiBot プラットフォーム上での 有効化 と、受信データフィードを正しく処理するための データエンドポイント側での開発作業 が必要です。

 

 有効化方法

1. https://console.ubibot.com にログインしてください。

2. 左側メニューから 「Data Factory」→「Data Forwarding」 をクリックします。

3. 「Add new forwarding」 の手順に従って設定してください。

 

 データ転送メッセージ形式

データ転送は、指定されたエンドポイント URL に対して POST リクエスト を送信することで行われます。Content-Type ヘッダーは “application/json” に設定されます。
元のフィードデータはリクエストボディ内に以下の形式で含まれます。

フィードデータは JSON 形式 で指定された URL に転送されます。

1. device のユニークな channel_id(文字列)を使用して、異なるデバイスからのデータを識別できます。

2. product_id(文字列):デバイスモデル

3. serial(文字列):デバイスのシリアル番号

4. feeds は以下を含む配列です:

5. created_at:データがサンプリングされた時刻(ISO 8601 形式)

6. field1..field10:センサーの測定値

7. status:SSID や ICCID などのステータス情報

注意:各メッセージに対して、15 秒以内に UbiBot プラットフォームにレスポンスを返す必要 があります。

転送されるデータ例:

{
	"channel_id": "123456",
	"product_id": "ubibot-ws1p",
	"serial": "123456XXXXX",
	"feeds": [{
		"created_at": "2022-04-24T09:06:56Z",
		"field1": 24.495308
	}, {
		"created_at": "2022-04-24T09:06:56Z",
		"field2": 82
	}, {
		"created_at": "2022-04-24T09:07:00Z",
		"field5": -34
	}],
	"status": "mac=98:7b:f3:10:a1:e2,usb=1",
	"ssid_base64": "VFBHUw=="
}

 

エンドポイントレスポンスの要件

  • エンドポイントのレスポンスは 15 秒以内 に返す必要があります。それ以外の場合、プラットフォームは接続を切断します。
  • エンドポイントが “SUCCESS” という文字列を返した場合、プラットフォームはこの転送リクエストを 成功 とマークします。エンドポイントが “ERROR” という文字列を返した場合、リクエストは 失敗 と見なされます。UbiBot プラットフォームは、統計目的のため、すべてのレスポンス結果を記録します。

 

簡単な PHP エンドポイント例

<?php

try{
    $data = file_get_contents('php://input'); //get POST payload forwarded from the UbiBot platform
    $json = json_decode($data, true); //parse input data into json. You can handle the $json object from here. 
    //------Please make sure the response is made within 15 seconds, otherwise connection will be disconnected and marked unsuccessful.----------//
    $myfile = file_put_contents('log.txt', $data.PHP_EOL , FILE_APPEND | LOCK_EX);  //Write to a local log file for the demo. 
    echo "SUCCESS"; // if the request has been handled successfully. 
}
catch (Exception $ex)
{
    echo "ERROR";// if there is some error encountered 
}

 

簡単な Node.js エンドポイント例

const http = require('http');
const server = http.createServer(function (req, res) {
    let type = req.headers["content-type"];
    if (req.method.toLowerCase() === 'post' && type === "application/json") {
        try{
            ////get POST payload
            var jsonData = "";
            req.on("data", function(chunk) {
                jsonData += chunk;
            });
            req.on("end", function() {
                //parse input data into json
                var reqObj = JSON.parse(jsonData);
                
                //-----------Make sure response is sent within 15 seconds------------//
                var fs = require('fs');
                fs.writeFile("log.txt", JSON.stringify(reqObj), function(err) {
                    if(err) {
                        res.end('ERROR');//mark request as error
                    }
                });
                res.end('SUCCESS');//mark request as successful
            });
        }catch{
            res.end('ERROR');//mark request as error
        }
    }else{
        res.end('ERROR');//mark request as error
    }
});
//Setup listening IP and port
server.listen(8080, "127.0.0.1", function () {
    console.log("server is started listen port 8080");
});

 

簡単な Python エンドポイント例

from http.server import BaseHTTPRequestHandler, HTTPServer
import cgi
import json

class testHTTPServer_RequestHandler(BaseHTTPRequestHandler):
    def do_POST(self):
        try:
            ctype, pdict = cgi.parse_header(self.headers.get('content-type'))
            if ctype == 'application/json':
                #get POST payload, parse input data into json
                length = int(self.headers['content-length'])
                jsonArray = json.loads(self.rfile.read(length))
                #-----------Make sure response is made within 15 seconds------------#
                myfile = open("log.txt",'a')
                myfile.write(json.dumps(jsonArray))
                myfile.write("\n")
                myfile.close()
                #request handled successfully
                self.protocal_version = 'HTTP/1.1'
                self.send_response(200)
                self.send_header("Welcome", "Contect")
                self.end_headers()
                self.wfile.write(bytes("SUCCESS", "utf-8"))
                return
            else:
                #request handled with error
                self.protocal_version = 'HTTP/1.1'  
                self.send_response(300)
                self.send_header("Welcome", "Contect")
                self.end_headers()
                self.wfile.write(bytes("ERROR", "utf-8"))
                return
        except:
            #request handled with error
            self.protocal_version = 'HTTP/1.1'
            self.send_response(300)
            self.send_header("Welcome", "Contect")
            self.end_headers()
            self.wfile.write(bytes("ERROR", "utf-8"))
            return

def run():
    port = 8080
    print('starting server, port', port)
    # Server settings
    server_address = ('', port)
    httpd = HTTPServer(server_address, testHTTPServer_RequestHandler)
    print('running server...')
    httpd.serve_forever()

if __name__ == '__main__':
    run()

 

簡単な C# ASP.NET エンドポイント例

using Microsoft.AspNetCore.Http;
using Microsoft.AspNetCore.Mvc;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;

namespace demo1.Controllers
{
    public class FeedData
    {
        public DateTime created_at { get; set; }
        public object field1 { get; set; }
        public object field2 { get; set; }
        public object field3 { get; set; }
        public object field4 { get; set; }
        public object field5 { get; set; }
        public object field6 { get; set; }
        public object field7 { get; set; }
        public object field8 { get; set; }
        public object field9 { get; set; }
        public object field10 { get; set; }

    }
    public class DeviceData
    {
        public string channel_id { get; set; }
        public string status { get; set; }
        public List feeds { get; set; }

        public string ssid_base64 { get; set; }
    }

    [Route("api/[controller]")]
    [ApiController]
    public class RestApiController : ControllerBase
    {
        [HttpPost]
        [Route("recv")]
        public string ReceiveData([FromBody] DeviceData data)
        {
            try
            {
                //Data is used for processing
                return "SUCCESS";//Successfully processed a request
            }
            catch (Exception)
            {
                return "ERROR";//An error occurred while processing your request
            }
        }
    }
}
ブログに戻る