DuckDBにCSVを食わせてみたけど、こんどはJSONを食わせてみたい。AWS IoTとかで送られてくるのはLambdaとかで処理されていなければ、普通はJSONだから。

とりあえず、AWS IoTで吐きそうなダミーデータをPythonで吐いてみる。デバイスIDとタイムスタンプ、温度と湿度と機器のステイタス、バッテリ状態くらいかな。送信デバイスは10個。タイムスタンプは1分に一回の時系列送信で、12月1日から10日まで。
import json
import random
from datetime import datetime, timedelta
固定デバイスIDリスト
device_ids = [
"device_001",
"device_002",
"device_003",
"device_004",
"device_005",
"device_006",
"device_007",
"device_008",
"device_009",
"device_010",
]
JSONデータのサンプルフォーマットを生成する関数
def generate_iot_data(device_id, timestamp):
status = random.choice(["active", "inactive", "error"])
if status in ["inactive", "error"]:
temperature = 0.0
humidity = 0.0
battery = 0.0
else:
temperature = round(random.uniform(15.0, 35.0), 2)
humidity = round(random.uniform(30.0, 70.0), 2)
battery = round(random.uniform(20.0, 100.0), 1)
return {
"device_id": device_id,
"timestamp": timestamp.isoformat(),
"temperature": temperature,
"humidity": humidity,
"status": status,
"battery": battery
}
12月1日から10日まで1分間隔のデータ生成
start_date = datetime(2024, 12, 1, 0, 0)
end_date = datetime(2024, 12, 10, 23, 59)
interval = timedelta(minutes=1)
data_list = []
current_time = start_date
while current_time <= end_date:
for device_id in device_ids:
data_list.append(generate_iot_data(device_id, current_time))
current_time += interval
ファイルに書き出し
data_file = "iot_sample_data.json"
with open(data_file, "w", encoding="utf-8") as file:
json.dump(data_list, file, ensure_ascii=False, indent=4)
print(f"{len(data_list)}個のIoTデータを{data_file}に出力しました。")
実行すると、28.5MBのJSONファイルが生成された。
中身はこんな感じ。
[
{
"device_id": "device_001",
"timestamp": "2024-12-01T00:00:00",
"temperature": 0.0,
"humidity": 0.0,
"status": "error",
"battery": 0.0
},
{
"device_id": "device_002",
"timestamp": "2024-12-01T00:00:00",
"temperature": 0.0,
"humidity": 0.0,
"status": "error",
"battery": 0.0
},
{
"device_id": "device_003",
"timestamp": "2024-12-01T00:00:00",
"temperature": 0.0,
"humidity": 0.0,
"status": "inactive",
"battery": 0.0
},
(snip)
{
"device_id": "device_010",
"timestamp": "2024-12-10T23:59:00",
"temperature": 0.0,
"humidity": 0.0,
"status": "inactive",
"battery": 0.0
}
]
device_010のエラーとアクティブ比率を求めてみる。
CREATE TABLE iot_data AS SELECT * FROM read_json('iot_sample_data.json', auto_detect = TRUE);
SELECT
status,
COUNT(*) AS count,
ROUND(100.0 * COUNT() / SUM(COUNT()) OVER (), 2) AS ratio_percentage
FROM iot_data
WHERE device_id = 'device_010'
GROUP BY status;

┌──────────┬───────┬─────────────────┐
│ status │ count │ ratio_percentage │
│ varchar │ int64 │ double │
├──────────┼───────┼─────────────────┤
│ error │ 4743 │ 32.94 │
│ inactive │ 4869 │ 33.81 │
│ active │ 4788 │ 33.25 │
└──────────┴───────┴─────────────────┘
なるほど、便利ね。状態はランダム生成したので、比率は同じくらいになっている。生のデータじゃないからね。
ここまで、主にChatGPT o4使ったわけだけど、手元ではPythonの実行すらしていないw 便利な世の中ね。
SQLite 3.38.0(2022/2/22)からは、JSONを扱えるようだけど、DuckDBのように直接ロードすることはできないみたい。シェルスクリプトとかで処理する場合は、こういうところはアドバンテージあるね。
オリジナル投稿:
DuckDBにJSONを食わせてみる|kinneko|pixivFANBOX
https://kinneko.fanbox.cc/posts/9051307

