もっと柔軟にintdashを活用したいみなさん、
こんにちは。ソリューションアーキテクトの伊勢です。
近年、お客様やパートナー様が自らカスタム機能を実装する場面が増えています。
intdashではサーバーAPIにアクセスするためのSDKを提供しています。 構成を刷新したintdash SDKが2024年6月バージョンより正式リリースとなりました。1
SDKは非常に幅広い使い方が可能です。
入門シリーズとして実践的な内容に落とし込んで解説していきます。
はじめに
intdash APIとは
産業向けIoTデータ伝送プラットフォームであるintdashが、製品群やサーバー外にデータを受け渡すためのインタフェースです。
2つのAPIがあります。
種類 | 概要 | 通信プロトコル | 用途 |
---|---|---|---|
REST API | いわゆるGETやPOSTのリクエスト・レスポンス | HTTP/HTTPS | ユーザー/エッジ/計測などの参照・更新 |
リアルタイムAPI | 高速データ伝送向けの特殊なAPI | aptpod独自のiSCP | 計測データのストリーム2 |
intdash SDKとは
intdash APIを利用するためのクライアントライブラリーです。
各種プログラミング言語向けに対応しています。
各種プログラミング言語の使いどころはこんな感じです。
言語 | 特徴・用途 |
---|---|
Python | 入門向け、プロトタイピング、AI/機械学習 |
Go | 高速・並列サーバー処理、バックエンドシステム構築 |
Rust | 高速・メモリ安全性、リソースが限られるエッジ処理 |
TypeScript | ブラウザ・フロントエンド |
Swift | iPhoneアプリ |
C# | Windowsプラットフォーム、Unityアプリ |
Kotlin | Androidアプリ、Java互換 |
この入門シリーズではintdash SDK for Pythonを使って説明します。
intdash API/SDKでできること
intdash APIへのデータフローは
2つのAPI ✖️データ取得/データ送信
に大別され、これを組み合わせてカスタム処理を実装します。
入門シリーズでもこの順で説明していきます。
# | データフロー | 適用例 |
---|---|---|
① | REST APIで計測データ取得 | データ分析、レポーティング |
② | REST APIで計測データ送信 | データ登録、保留データアップロード |
③ | リアルタイムAPIで計測データ取得 | 遠隔監視、リアルタイムデータ分析 |
④ | リアルタイムAPIで計測データ送信 | 遠隔制御、リアルタイムデータ登録 |
目的別のインストール手順・必要ソフトウェア
実現したいことによって対応した手順が必要です。
# | SDKインストール手順 | 必要ソフトウェア |
---|---|---|
① | OpenAPI Generatorで生成 | Java、npm |
② | OpenAPI Generatorで生成 Protocol Buffersエンコーダーを生成 |
Java、npm、Buf CLI |
③ ④ |
パッケージをインストール | 各言語のパッケージ管理ツール |
具体的な手順は記事ごとに説明します。3
インストール
今回はREST APIでデータ取得するためのインストール方法を説明します。
手順
少し多いため、説明しながら進めていきます。
- OpenAPI GeneratorでSDK生成
- Javaインストール
- npmインストール
- OpenAPI Generatorインストール
- intdash SDK for Python生成
- Python実行環境設定
- Pythonインストール
- Python仮想環境の設定
- 依存パッケージインストール
- 動作確認
- import確認
- エッジ一覧取得
- Python開発環境整備
- Pythonパス設定
- フォーマッター、Linterの整備
- サンプルプログラム準備
- 利用パッケージインストール
- サンプルプログラム実行
OpenAPI GeneratorでSDK生成
REST API用のSDKをOpenAPI Generatorで生成します。
Javaインストール
OpenAPI Generator を実行するためにJava実行環境が必要です。
Javaが実行できるか確認します。
java --version
存在しない場合はインストールします。
brew install openjdk
npmインストール
OpenAPI Generator をインストールするために、Node.jsのパッケージ管理ツール npmが必要です。
npmはNode.jsに含まれているため、Node.jsをインストールします。
brew install node
npm -v
OpenAPI Generatorインストール
OpenAPI Generator は、API仕様に基づいてクライアントライブラリー、ドキュメントなどを自動生成するツールです。
インストールしてバージョンを確認します。
npm install @openapitools/openapi-generator-cli npx @openapitools/openapi-generator-cli version
intdash SDK for Python生成
intdashのAPI仕様からSDKを生成します。
OpenAPI Specificationファイルのバージョンを指定します。
package-name
で指定するパッケージ名でディレクトリが生成されます。
また、開発時に参照するドキュメントを生成しています。
VERSION=v2.7.0 SRC_DIR="." ./node_modules/.bin/openapi-generator-cli version-manager set 6.1.0 ./node_modules/.bin/openapi-generator-cli generate \ -g python -i https://docs.intdash.jp/api/intdash-api/${VERSION}/openapi_public.yaml \ --package-name=intdash \ --additional-properties=generateSourceCodeOnly=true \ --global-property=modelTests=false,apiTests=false,modelDocs=true,apiDocs=true \ --http-user-agent=SDK-Sample-Python-Client/Gen-By-OASGenerator \ -o "$SRC_DIR" ls -l intdash
Python実行環境設定
Pythonプログラムを実行する環境を構築します。
Pythonインストール
Pythonが実行できるか確認します。
python --version
存在しない場合はインストールします。
brew install python
python --version
Python仮想環境作成
Python仮想環境を作成します。
ローカルPCのPythonバージョンアップが開発中のプログラムに影響するのを防ぐため、仮想環境は有効です。
Pythonと任意のバージョンを指定して仮想環境を作成します。 作成後に有効化して、Pythonとパッケージ管理ツール pipのバージョンを確認します。
python3.xx -m venv venv . ./venv/bin/activate python --version pip --version
依存パッケージインストール
intdash SDKが利用するPythonパッケージをインストールします。
- pydantic: データバリデーションおよびデータモデルライブラリ
- python-dateutil: 日付と時刻の操作ライブラリ
- urllib3: HTTPクライアントライブラリ
pip install pydantic python-dateutil urllib3
これでSDKを利用できる準備が整いました。
動作確認
簡単なリクエストを試してみます。
import確認
Pythonを起動してpackage-name
で指定したパッケージをimport
します。
エラーが出なければ、正常に読み込めています。
python
>>> import intdash
エッジ一覧取得
最も簡単な例としてエッジ一覧を取得してみます。
intdash APIの認証方法には3種類あります。
- ユーザーで認証:
- ユーザーに紐づくAPIトークンで認証
- ユーザー情報に基づいてアクセストークンを払い出して認証
- エッジで認証:
- エッジ情報に基づいてアクセストークンを払い出して認証
今回はAPIトークンで認証します。
intdashのUIであるWeb ConsoleのMy Pageで払い出します。
エッジサービスのAPIオブジェクトを生成してエッジ一覧の取得メソッドを呼びます。
from intdash import ApiClient, Configuration from intdash.api import authentication_service_edges_api # APIトークンで認証 client = ApiClient( Configuration( host="https://example.intdash.jp/api", api_key={ "IntdashToken": "YOUR_API_TOKEN" }, ) ) # エッジサービスのAPIオブジェクトを生成 api = authentication_service_edges_api.AuthenticationServiceEdgesApi(client) # エッジ一覧の取得 edges = api.list_edges() print(edges)
intdash SDKでREST APIにアクセスできました。
基本的にはこのように
- 認証
- 各サービスAPIのメソッドでREST APIにアクセス
を実装していきます。
Python開発環境整備
開発効率を高めるために開発環境の整備は重要です。
開発者によって好みが分かれるところですが、このサンプル作成に使ったVS Code設定をご紹介します。
なお、作成した仮想環境をVS CodeのSelect Interpreterで指定しておくとターミナル起動時に楽です。
Pythonパス設定
生成したSDKを含めてPython実行時にサンプルプログラムを参照できるように環境変数PYTHONPATH
にワークスペースを設定します。
"terminal.integrated.env.osx": { "PYTHONPATH": "${workspaceFolder}" },
フォーマッター、Linterの整備
VS Codeの拡張機能で以下をインストールします。
- Ruff:Python向けの高速なフォーマッター兼Linter
- My Type Checker:Pythonの静的型チェックツール
Ruffの設定です。
保存時に自動でフォーマット、Lintエラー修正、importの整列・削除をさせています。
"[python]": { "editor.formatOnSave": true, "editor.defaultFormatter": "charliermarsh.ruff", "editor.codeActionsOnSave": { "source.fixAll.ruff": "explicit", "source.organizeImports.ruff": "explicit", }, },
My Type Checkerの設定です。
型チェック中に見つからないインポートがあってもエラーを無視します。外部ライブラリで型情報が不足している場合に有効です。
"mypy-type-checker.args": [ "--disallow-untyped-defs", "--ignore-missing-imports", ], "mypy-type-checker.showNotifications": "onError",
やってみた
特定のエッジの計測のうち、GPSデータを全部取り出して地図上にプロットします。
サンプルプログラムをGitHubで公開しています。
対象とするエッジはこちらです。
社用車には当社製エッジコンピューター EDGEPLANT T1が搭載されています。
準備
追加で実行前の準備があります。
利用パッケージインストール
サンプルプログラムに必要なパッケージをインストールします。
pip install folium matplotlib
- folium: OpenStreetMap表示
- matplotlib: 地図プロット時のカラー情報制御
実行結果
PYTHONPATH
が指定されていないときは設定します。
echo $PYTHONPATH export PYTHONPATH=/path/to/your_workspace:
実行します。
python lesson1/src/gnss_plot.py --api_url https://example.intdash.jp --api_token <YOUR_API_TOKEN> --project_uuid <YOUR_PROJECT_UUID> --edge_uuids <YOUR_EDGE_UUID1> <YOUR_EDGE_UUID2> <YOUR_EDGE_UUID3>
社用車のエッジUUIDは何回か変わっているため、複数指定できるようにしました。
HTMLが出力されます。
GPSデータの緯度経度をプロットしています。
- 2020年1月からの計測1,400件を取得
- 取り出したGPSデータの緯度経度を10分ごとにサンプリング
- 会社からの距離が近いほど青く遠いほど赤く描画
- 訪問先でエッジを起動した場合はルート途中は描画されない
サンプルプログラム説明
REST APIアクセス部分を解説します。
構成図
時系列データベースに蓄積された計測データをREST APIから取り出します。
計測リスト取得
プロジェクトUUID、エッジUUIDを指定して計測のリストを取得しています。
api = measurement_service_measurements_api.MeasurementServiceMeasurementsApi(client) measurements = api.list_project_measurements( project_uuid=project_uuid, edge_uuid=edge_uuid, limit=LIMIT )
開発中の大量データ取得防止のためlimit
で取得件数を絞っています。
データポイントリスト取得
計測ごとにデータポイントを取得します。
取得対象を緯度経度に限定します。
data_id_filter
で以下のいずれかを指定していします。
#:0/GNRMC
- T1から収集されるNMEAフォーマットの緯度経度を含むGNRMC
#:1/gnss_coordinates
- iPhoneアプリ intdash Motion V2で収集されるフォーマットの緯度経度
api = measurement_service_data_points_api.MeasurementServiceDataPointsApi(client) stream = api.list_project_data_points( project_uuid=project_uuid, name=meas_uuid, data_id_filter=[ "#:0/GNRMC", # NMEA "#:1/gnss_coordinates", # intdash Motion ], )
データポイントは複数行に分かれたJSONであるJSONLines形式で取得されます。
1行ごとにJSON化して、データを取り出します。
#:0/GNRMC
- JSONの
data.s
から取得- 旧プロトコルiSCPv1で送信されたデータの格納形式
- 社用車のT1がiSCPv1で送信するため
- NMEAフォーマットのCSV形式をパースして緯度経度を取得
- JSONの
#:1/gnss_coordinates
- JSONの
data.d
から取得- 新プロトコルiSCPv2の格納形式
- BASE64文字列をデコードしてバイナリ値を取得
- 2次元ベクトルであるバイナリ値から64ビット浮動小数点数値を2つ取得
- JSONの
line_json = json.loads(line.decode()) if "data" in line_json: # iSCPv1 NMEA if "s" in line_json["data"]: x, y = parse_gnrmc(line_json["data"]["s"]) # iSCPv2 elif "d" in line_json["data"]: base64_encoded = line_json["data"]["d"] bin_data = base64.b64decode(base64_encoded) x, y = struct.unpack(">dd", bin_data)
おわりに
今回はシリーズ初回としてSDKの概要とREST APIでのデータ取得をご紹介しました。
次回はより高度な使い方を試していきます。
今回少し触れた取得データの形式についてもより詳細に説明します。