コンテンツにスキップ
JelinaJelina Documentation技術ドキュメント
公式サイトに戻る

Lua スクリプト完全リファレンス

このページは、Edge-EMS Builder の式エンジン(集約式、トリガー条件・アクション、後処理アクション、MQTT 配信・購読内容)で使用するスクリプト機能の完全リファレンスです。構文は Lua 5.x で、組み込み Lua ランタイムが解析・実行します。入門には 式エンジン を参照してください。ここでは組み込みモジュール、グローバル関数のシグネチャ、戻り値の規約を網羅します。

⚠️ 初期の Java 版 Edge-EMS Builder(QLExpress4 エンジン、Java に似た構文)を使用した方へ:${...} の変数参照は基本的に共通ですが、スクリプト本体は標準 Lua 構文へ変更されています(new ArrayList() → {}、.add(x) → table.insert(t, x)、new HashMap() → {}、.put(k, v) → t[k] = v など)。組み込み関数名の多くは維持されているため、このページと照合して移行できます。

  • スクリプト言語:Lua 5.x。関数名とプレースホルダーは大文字・小文字を区別します。
  • データプレースホルダー:${dataKey} は実行前に現在値へ置換されます。他デバイスのデータには ${[deviceCode]dataKey} を使用します。
  • センチネル値:取得できないデータは文字列 __Null__ になります。明示的に比較するか isNull / isNotNull を使用し、数値計算の前に tonumber で変換してください。
  • 戻り値は用途ごとに異なります(後述の「戻り値の規約」参照)。戻り値型の誤りは、最も多い設定ミスです。
  • モジュール関数は require("モジュール名") の後に呼び出します。グローバル関数(buildCommonWriteMap、jsonToMap など)は require なしで直接呼び出します。
  • ログ:Logger の既定出力レベルは WARN です。実際に出力されるのは Logger.warn() / Logger.error() のみなので、デバッグで Logger.info() / Logger.debug() だけを使用しないでください。
記法 説明
${variable} 現在値を返す
${variable[-1s]} 1 秒前の値を返す
${variable[-5s]} 5 秒前の値を返す
${variable[raw]} 自動型変換せず、そのまま挿入します。数値 1000 と 2 進数 1000 などを区別しにくい場合に raw で制御します。[raw] は必ず末尾に配置します。
${[deviceA]variable} 共有デバイス deviceA の値を返す
${variable[@timestamp]} 指定した絶対時刻の値を返す
${variable[#N]} 最新から N 番目の履歴値を返す。省略時は最新値
${[deviceA]variable[-5s][#N]} 共有デバイス deviceA の、5 秒前時点で最新から N 番目のサンプル値を返す

ポイントの値を取得できない場合は、センチネル文字列 __Null__ が挿入されます。if ${some_key} == "__Null__" then ... end のように明示的に判定してください。

スクリプトを入力する場所によって戻り値の要件は大きく異なり、特に誤りが発生しやすい点です。

用途 入力箇所 戻り値の要件
トリガー条件 条件式 単一のブール値(true = 条件成立)
トリガーアクション(式型プラン) アクション内容(Expression) 配列テーブル(1 から始まる連続インデックス)。要素は buildCommonWriteMap(...) などが返す map。空テーブル {} は「書き込みなし」
トリガーアクション(混合書き込み型プラン) 各 dataKey に個別設定するアクション 単一値(文字列・数値・ブール)を dataKey の書き込み内容とする。buildCommonWriteMap 配列は返さない
後処理アクション 主アクション完了後のスクリプト 式型アクションと同じ書き込み記述の配列テーブル。固定変数 ${trigger_result}(ブール)と ${trigger_write_result}(JSON 文字列。jsonToMap で解析)で主処理結果を確認可能
集約ポイントの式 集約データ計算式 単一値(数値、文字列など)を集約ポイントの最新値とする
MQTT 配信内容(publishContent) MQTT 配信設定 Lua テーブル。JSON へシリアライズして配信ペイロードとする
MQTT 購読アクション(actionContent) MQTT 購読設定 式型アクションと同じ書き込み記述の配列テーブル
MQTT 応答 Topic(responseTopic) MQTT 購読設定 単一の文字列を応答配信 Topic とする
MQTT 応答内容(response) MQTT 購読設定 文字列はそのまま送信。Lua テーブルなど、その他の値は JSON へシリアライズ

1 回のスクリプト呼び出しにはタイムアウト(既定 10 秒)があり、超過すると実行が失敗します。ループ内で無制限に履歴照会や HTTP 要求を行わないでください。

以下のモジュールは、事前に require("モジュール名") で読み込みます。

タイムゾーン、書式設定、日時計算などに対応する総合的な日時処理モジュールです。

local OffsetDateTime = require("OffsetDateTime")
メソッド 説明 戻り値
new() 現在日時を作成 OffsetDateTime
new(sec, nsec?) Unix タイムスタンプから作成 OffsetDateTime
now() 現在日時を取得 OffsetDateTime
parse(str) 日時文字列を解析 OffsetDateTime | (nil, err)
parseInLocation(str, location) 指定タイムゾーンで日時を解析 OffsetDateTime | (nil, err)
unix(sec, nsec?) Unix 秒から作成 OffsetDateTime
unixMilli(msec) ミリ秒タイムスタンプから作成 OffsetDateTime
unixMicro(usec) マイクロ秒タイムスタンプから作成 OffsetDateTime

インスタンスメソッド:日時要素

Section titled “インスタンスメソッド:日時要素”
メソッド 説明 戻り値
year() 年を取得 number
month() 月を取得 (1-12) number
day() 日を取得 (1-31) number
hour() 時を取得 (0-23) number
minute() 分を取得 (0-59) number
second() 秒を取得 (0-59) number
nanosecond() ナノ秒を取得 number
yearDay() 年初からの日数を取得 number
weekday() 曜日を取得 (0=日曜日) number
isoWeek() ISO 週情報を取得 {year, week}
date() 年月日を取得 {year, month, day}
clock() 時分秒を取得 {hour, minute, second}

インスタンスメソッド:日時計算

Section titled “インスタンスメソッド:日時計算”
メソッド 説明 戻り値
add(durationStr) 時間間隔を加算 OffsetDateTime | (nil, err)
addDate(years, months, days) 年・月・日を加算 OffsetDateTime
sub(other) 時間差を計算(ナノ秒) number
addYears(n) 年を加算 OffsetDateTime
addMonths(n) 月を加算 OffsetDateTime
addDays(n) 日を加算 OffsetDateTime
addHours(n) 時間を加算 OffsetDateTime
addMinutes(n) 分を加算 OffsetDateTime
addSeconds(n) 秒を加算 OffsetDateTime
addMilliseconds(n) ミリ秒を加算 OffsetDateTime
addMicroseconds(n) マイクロ秒を加算 OffsetDateTime
addNanoseconds(n) ナノ秒を加算 OffsetDateTime

インスタンスメソッド:時間差の計算

Section titled “インスタンスメソッド:時間差の計算”
メソッド 説明 戻り値
diffYears(other) 年数の差を計算 number
diffMonths(other) 月数の差を計算 number
diffDays(other) 日数の差を計算 number
diffHours(other) 時間の差を計算 number
diffMinutes(other) 分数の差を計算 number
diffSeconds(other) 秒数の差を計算 number

インスタンスメソッド:日時比較

Section titled “インスタンスメソッド:日時比較”
メソッド 説明 戻り値
equal(other) 等しいか boolean
before(other) より前か boolean
after(other) より後か boolean
isZero() ゼロ値か boolean

インスタンスメソッド:日時判定

Section titled “インスタンスメソッド:日時判定”
メソッド 説明 戻り値
isToday() 今日か boolean
isYesterday() 昨日か boolean
isTomorrow() 明日か boolean
isThisWeek() 今週か boolean
isThisMonth() 今月か boolean
isThisYear() 今年か boolean
isBetween(start, end) 範囲内か boolean
isInRange(start, end) 範囲内か boolean

インスタンスメソッド:書式設定

Section titled “インスタンスメソッド:書式設定”
メソッド 説明 戻り値
format(layout) 指定書式で整形 string
toString() 文字列へ変換 string
toDateTimeString() 日時形式 string
toDateString() 日付形式 string
toTimeString() 時刻形式 string
toYearString() 年 string
toMonthString() 月 string
toDayString() 日 string
toHourString() 時 string
toMinuteString() 分 string
toSecondString() 秒 string

インスタンスメソッド:Unix タイムスタンプ

Section titled “インスタンスメソッド:Unix タイムスタンプ”
メソッド 説明 戻り値
unix() Unix 秒タイムスタンプ number
unixMilli() Unix ミリ秒タイムスタンプ number
unixMicro() Unix マイクロ秒タイムスタンプ number
unixNano() Unix ナノ秒タイムスタンプ number

インスタンスメソッド:タイムゾーン

Section titled “インスタンスメソッド:タイムゾーン”
メソッド 説明 戻り値
utc() UTC タイムゾーンへ変換 OffsetDateTime
local() ローカルタイムゾーンへ変換 OffsetDateTime
in(location) 指定タイムゾーンへ変換 OffsetDateTime | (nil, err)

インスタンスメソッド:その他

Section titled “インスタンスメソッド:その他”
メソッド 説明 戻り値
truncate(durationStr) 指定精度で切り捨て OffsetDateTime | (nil, err)
round(durationStr) 指定精度で丸め OffsetDateTime | (nil, err)
toTime() Go time.Time へ変換 time.Time
local layouts = OffsetDateTime.Layout
-- layouts.DateTime = "2006-01-02 15:04:05"
-- layouts.Date = "2006-01-02"
-- layouts.Time = "15:04:05"
local OffsetDateTime = require("OffsetDateTime")
local Logger = require("Logger")
-- 現在日時を取得
local now = OffsetDateTime.now()
Logger.warn(now:toString())
-- 日時を解析
local dt = OffsetDateTime.parse("2024-01-15T10:30:00.000Z")
Logger.warn("年份: " .. dt:year())
Logger.warn("月份: " .. dt:month())
-- 日時計算
local tomorrow = now:addDays(1)
local nextWeek = now:addDays(7)
Logger.warn("明天: " .. tomorrow:toDateString())
-- 日時比較
if now:isToday() then
Logger.warn("今天!")
end
-- 時間差
local hours = nextWeek:diffHours(now)
Logger.warn("相差小时: " .. hours)
-- 書式設定
Logger.warn(now:format("2006-01-02 15:04:05"))
Logger.warn(now:toDateTimeString())

時・分・秒だけを持ち、日付やタイムゾーンを含まない時刻型です。

local LocalTime = require("LocalTime")
メソッド 説明 戻り値
new(hour, minute, second) 時刻を作成 LocalTime | (nil, err)
now() 現在日時を取得 LocalTime
parse(str) “HH:mm:ss” を解析 LocalTime | (nil, err)
fromTime(time.Time) time.Time から作成 LocalTime | (nil, err)
fromDuration(durationStr) 時間間隔から作成 LocalTime | (nil, err)
メソッド 説明 戻り値
hour() 時を取得 number
minute() 分を取得 number
second() 秒を取得 number
toString() “HH:mm:ss” へ変換 string
toDuration() 時間間隔文字列へ変換 string
equal(other) 等しいか boolean
before(other) より前か boolean
after(other) より後か boolean
beforeOrEqual(other) 以前または同じか boolean
afterOrEqual(other) 以後または同じか boolean
isZero() 00:00:00 か boolean
diffSeconds(other) 秒数の差 number
diffMinutes(other) 分数の差 number
diffHours(other) 時間の差 number
addSeconds(n) 秒を加算 LocalTime
addMinutes(n) 分を加算 LocalTime
addHours(n) 時間を加算 LocalTime
subSeconds(n) 秒を減算 LocalTime
subMinutes(n) 分を減算 LocalTime
subHours(n) 時間を減算 LocalTime
local LocalTime = require("LocalTime")
local Logger = require("Logger")
-- 時刻を作成
local workStart = LocalTime.new(9, 0, 0) -- 09:00:00
local workEnd = LocalTime.new(17, 30, 0) -- 17:30:00
-- 現在日時を取得
local now = LocalTime.now()
Logger.warn("当前时间: " .. now:toString())
-- 日時比較
if now:isBetween(workStart, workEnd) then
Logger.warn("工作时间")
else
Logger.warn("非工作时间")
end
-- 日時計算
local breakTime = workStart:addHours(3):addMinutes(30) -- 12:30:00
Logger.warn("午休时间: " .. breakTime:toString())
-- 時間差
local workHours = workEnd:diffHours(workStart)
Logger.warn("工作时长: " .. workHours .. " 小时")

汎用ユーティリティモジュール

Section titled “汎用ユーティリティモジュール”

システムログと連携するログ出力モジュールです。

local Logger = require("Logger")
メソッド 説明 パラメーター
info(msg) INFO ログを出力 string
warn(msg) WARN ログを出力 string
error(msg) ERROR ログを出力 string
debug(msg) DEBUG ログを出力 string
infof(fmt, ...) INFO ログを書式設定して出力 string, …
warnf(fmt, ...) WARN ログを書式設定して出力 string, …
errorf(fmt, ...) ERROR ログを書式設定して出力 string, …
debugf(fmt, ...) DEBUG ログを書式設定して出力 string, …
local Logger = require("Logger")
Logger.info("系统启动")
Logger.warn("磁盘空间不足")
Logger.error("数据库连接失败")
Logger.debug("变量值: x=10")
-- 書式を整えて出力
local user = "admin"
local action = "login"
Logger.infof("用户 %s 执行操作: %s", user, action)
Logger.warnf("重试次数: %s", 3)

注:Edge-EMS Builder の既定ログ出力レベルは WARN です。WARN と ERROR のみ出力されます。


JSON のシリアライズ・デシリアライズと操作を行うモジュールです(bytedance/sonic ベース)。

local JSON = require("JSON")
メソッド 説明 戻り値
encode(value) JSON へシリアライズ string | (nil, err)
decode(text) デシリアライズ table | (nil, err)
メソッド 説明 戻り値
toJSONString(value) シリアライズ(エラー返却なし) string
toJSONStringIndent(value, prefix?, indent?) 書式を整えてシリアライズ string
toMap(jsonStr) map へ変換 table | (nil, err)
toStringMap(jsonStr) string map へ変換 table | (nil, err)
toSlice(jsonStr) 配列へ変換 table | (nil, err)
isValid(jsonStr) JSON 形式を検証 boolean
pretty(jsonStr) JSON を整形 string
merge(json1, json2) 2 つの JSON をマージ string | (nil, err)
get(jsonStr, key) 値を取得 any | (nil, err)
set(jsonStr, key, value) 値を設定 string | (nil, err)
remove(jsonStr, key) キーを削除 string | (nil, err)
clone(value) ディープコピー any | (nil, err)
local JSON = require("JSON")
local Logger = require("Logger")
-- 基本的なシリアライズ・デシリアライズ
local obj = {name = "张三", age = 30, tags = {"developer", "golang"}}
local jsonStr = JSON.encode(obj)
Logger.warn(jsonStr) -- {"name":"张三","age":30,"tags":["developer","golang"]}
local decoded, err = JSON.decode(jsonStr)
if not decoded then
Logger.warn("解析失败: " .. err)
else
Logger.warn("姓名: " .. decoded.name)
end
-- 書式を整えて出力
local pretty = JSON.pretty(jsonStr)
Logger.warn(pretty)
-- JSON を検証
if JSON.isValid(jsonStr) then
Logger.warn("有效的 JSON")
end
-- JSON を操作
local newJson = JSON.set(jsonStr, "city", "北京")
Logger.warn(newJson) -- {"name":"张三","age":30,"tags":[...],"city":"北京"}
local age = JSON.get(newJson, "age")
Logger.warn("年龄: " .. age) -- 30
local removed = JSON.remove(newJson, "age")
Logger.warn(removed) -- {"name":"张三","tags":[...],"city":"北京"}
-- JSON をマージ
local json1 = '{"a":1}'
local json2 = '{"b":2}'
local merged = JSON.merge(json1, json2)
Logger.warn(merged) -- {"a":1,"b":2}
-- ディープコピー
local original = {data = {x = 10}}
local copied = JSON.clone(original)

一致判定、検索、置換、分割などに対応する正規表現モジュールです。

local Regex = require("Regex")
メソッド 説明 戻り値
match(text, pattern) 一致するか boolean
findAll(text, pattern, limit?) すべての一致を検索(キャプチャグループを含む) {{full, g1, g2, …}, …} | (nil, err)
replace(text, pattern, repl) 置換($1 などのグループ参照に対応) string | (nil, err)
split(text, pattern, limit?) 正規表現で分割 {string, …} | (nil, err)
isEmail(text) メールアドレスか boolean
isPhone(text) 携帯電話番号か(中国) boolean
isIP(text) IP アドレスか boolean
isURL(text) URL か boolean
local Regex = require("Regex")
local Logger = require("Logger")
-- 一致判定
if Regex.match("abc123", "\\d+") then
Logger.warn("包含数字")
end
-- すべての一致を検索(キャプチャグループを含む)
local matches = Regex.findAll("a1 b22 c333", "(\\w)(\\d+)")
-- matches = {{"a1","a","1"}, {"b22","b","22"}, {"c333","c","333"}}
for i, m in ipairs(matches) do
Logger.warn("匹配 " .. i .. ": " .. m[1] .. ", 字母=" .. m[2] .. ", 数字=" .. m[3])
end
-- 置換(グループ参照に対応)
local s = Regex.replace("abc-123-def", "(\\d+)", "[$1]")
Logger.warn(s) -- "abc-[123]-def"
-- 分割
local parts = Regex.split("a,b,,c", ",", -1)
-- parts = {"a", "b", "", "c"}
for i, p in ipairs(parts) do
Logger.warn("部分 " .. i .. ": '" .. p .. "'")
end
-- 検証
Logger.warn(Regex.isEmail("test@example.com")) -- true
Logger.warn(Regex.isPhone("13812345678")) -- true
Logger.warn(Regex.isIP("192.168.1.1")) -- true
Logger.warn(Regex.isURL("https://example.com")) -- true

文字列処理ユーティリティです。

local String = require("String")
メソッド 説明 戻り値
trim(s) 前後の空白を除去 string
upper(s) 大文字へ変換 string
lower(s) 小文字へ変換 string
contains(s, sub) 部分文字列を含むか boolean
startsWith(s, prefix) 指定プレフィックスで始まるか boolean
endsWith(s, suffix) 指定サフィックスで終わるか boolean
local String = require("String")
local s = " Hello World "
Logger.warn(String.trim(s)) -- "Hello World"
Logger.warn(String.upper(s)) -- " HELLO WORLD "
Logger.warn(String.lower(s)) -- " hello world "
Logger.warn(String.contains("hello", "ll")) -- true
Logger.warn(String.startsWith("hello", "he")) -- true
Logger.warn(String.endsWith("hello", "lo")) -- true

数学計算ユーティリティです。

local Math = require("Math")
メソッド 説明 戻り値
round(n) 四捨五入 number
floor(n) 負の無限大方向へ丸め number
ceil(n) 正の無限大方向へ丸め number
abs(n) 絶対値 number
max(a, b) 最大値 number
min(a, b) 最小値 number
local Math = require("Math")
Logger.warn(Math.round(3.6)) -- 4
Logger.warn(Math.floor(3.9)) -- 3
Logger.warn(Math.ceil(3.1)) -- 4
Logger.warn(Math.abs(-5)) -- 5
Logger.warn(Math.max(10, 20)) -- 20
Logger.warn(Math.min(10, 20)) -- 10

配列とキー・値の走査に対応する、テーブル(table)操作ユーティリティです。

local TableUtils = require("TableUtils")
メソッド 説明 戻り値
keys(tbl) すべてのキーを取得 {string, …}
values(tbl) すべての値を取得 {any, …}
map(tbl, fn) マッピング(fn(value, key)) {any, …}
filter(tbl, fn) フィルタリング(fn(value, key)) {any, …}
reduce(tbl, fn, init) 畳み込み(fn(acc, value, key)) any
sortBy(tblOfMaps, key) キーでソート(安定ソート) {map, …}
local T = require("TableUtils")
-- keys/values
local obj = {a = 1, b = 2, c = 3}
local keys = T.keys(obj) -- {"a", "b", "c"}
local values = T.values(obj) -- {1, 2, 3}
-- map(配列)
local arr = {1, 2, 3}
local doubled = T.map(arr, function(v, i)
return v * 2
end)
-- doubled = {2, 4, 6}
-- map(キー・値ペア)
local mapped = T.map({a=1, b=2}, function(v, k)
return k .. ":" .. v
end)
-- mapped = {"a:1", "b:2"}
-- filter
local arr = {1, 2, 3, 4, 5}
local even = T.filter(arr, function(v, i)
return v % 2 == 0
end)
-- even = {2, 4}
-- reduce
local sum = T.reduce({1, 2, 3}, function(acc, v, i)
return acc + v
end, 0)
-- sum = 6
-- sortBy
local users = {
{name="张三", age=30},
{name="李四", age=25},
{name="王五", age=35}
}
local sorted = T.sortBy(users, "age")
-- sorted = {{name="李四",age=25}, {name="张三",age=30}, {name="王五",age=35}}

以下の関数はグローバルスコープに直接登録されており、require は不要です。

関数 用途
cp56Time2aToOffsetDateTime(hex[, byteOrder]) IEC 60870-5 の時刻をデコードし、OffsetDateTime を返す
offsetDateTimeToCP56Time2a(time[, byteOrder]) 時刻を 16 進ペイロードへエンコード

byteOrder は AB / BA に対応し、省略時は標準の AB を使用します。明示指定時には 4 レジスターのペイロードに対応します。ゼロ埋め位置が曖昧な場合はエラーを返すため、デバイスのレジスター配置と照合してください。

関数 説明 戻り値
jsonToMap(str) JSON を map へ変換 table | (nil, err)
jsonToList(str) JSON を list へ変換 table | (nil, err)
jsonToListMap(str) JSON を map の list へ変換 table | (nil, err)
completeDateTime(str) 日時文字列を補完 string | (nil, err)
quoteJson(str) JSON の引用符をエスケープ string
simpleUUID() 簡易 UUID を生成 string
convertString(str) 文字列の型変換 any
isNull(any) 値が空かを判定 bool
isNotNull(any) 値が空でないかを判定 bool

isNull は nil、空文字列、大文字・小文字を区別しない “null”、センチネル __Null__ を空と扱います。Lua の or 0 ではこのセンチネルを処理できません。

local Logger = require("Logger")
-- JSON 解析
local map, err = jsonToMap('{"a":1,"b":2}')
if map then
Logger.warn(map.a) -- 1
end
local list = jsonToList('[1,2,3]')
-- list = {1, 2, 3}
-- 日時を補完
local fullTime = completeDateTime("2024-01-15")
-- fullTime = "2024-01-15T00:00:00.000+08:00"
-- UUID 生成
local id = simpleUUID()
Logger.warn(id) -- 32 桁の UUID 文字列

関数 説明 戻り値
getLatestDataValue(dataKey) 最新のデータ値を取得 any
getAccountCache(key) アカウントキャッシュを取得 any
getEMSDataCache(key) EMS データキャッシュを取得 any
getShareCache(key) 共有キャッシュを取得 any
getMqttCache(key) MQTT キャッシュを取得 any
getTriggerCache(key) トリガーキャッシュを取得 any
getDeviceShareValue(deviceCode, dataKey) 単一の deviceCode と dataKey から、そのデバイスの共有データ最新値を取得 string | nil
getDeviceShareValues(deviceCodes, dataKey) デバイス一覧と dataKey から、各デバイスの対象データ最新値を取得 table
getAllDeviceShareValues(dataKey) dataKey から、共有空間内の全デバイスの対象データ最新値を取得 table
local Logger = require("Logger")
-- デバイスの最新データを取得
local value = getLatestDataValue("device1.temperature")
Logger.warn("当前温度: " .. value)
-- アカウント情報を取得
local account = getAccountCache("user123")
if account then
Logger.warn("用户名: " .. account.username)
end
-- 共有データを取得
local sharedData = getShareCache("shared_config")
-- 単一デバイスの共有データ最新値を取得
local val = getDeviceShareValue("device1", "temperature")
if val ~= nil then
Logger.warn("设备 device1 温度: " .. val)
end
-- デバイス一覧から各デバイスの共有データ値を取得
local deviceCodes = {"device1", "device2"}
local shareValues = getDeviceShareValues(deviceCodes, "temperature")
if shareValues then
for deviceCode, dataValue in pairs(shareValues) do
Logger.warn("设备 " .. deviceCode .. " 温度: " .. dataValue)
end
end
-- 全デバイスの共有データ値を取得
local allShareValues = getAllDeviceShareValues("temperature")
if allShareValues then
for deviceCode, dataValue in pairs(allShareValues) do
Logger.warn("设备 " .. deviceCode .. " 温度: " .. dataValue)
end
end

dataKey パターンによる最新値の一括照会

Section titled “dataKey パターンによる最新値の一括照会”

以下の関数はローカルの最新値キャッシュを走査し、dataKey のプレフィックス、サフィックス、キーワードで絞り込んだポイント情報を返します。戻り値は {dataKey: FrontDataDTO} テーブルです。

戻り値のフィールド(各値は FrontDataDTO オブジェクトで、主に次のフィールドを含みます):

フィールド 型 説明
DataKey string データの一意のキー
DataValue string 最新値
DataType string データ型
DataName string データ名
DataUnit string 単位
CollectionTime OffsetDateTime 収集時刻

注意:nil はキャッシュに一致項目がないことを示します。dataType は列挙値(Collection / Customization / Aggregation / Share)と完全に一致させてください。

関数 説明 戻り値
getLatestDataValuesBySuffix(dataType, suffix) 指定型で dataKey が suffix で終わる最新値を照会 table | nil
getAllLatestDataValuesBySuffix(suffix) 全型で dataKey が suffix で終わる最新値を照会 table | nil
関数 説明 戻り値
getLatestDataValuesByPrefix(dataType, prefix) 指定型で dataKey が prefix で始まる最新値を照会 table | nil
getAllLatestDataValuesByPrefix(prefix) 全型で dataKey が prefix で始まる最新値を照会 table | nil
関数 説明 戻り値
getLatestDataValuesByPrefixAndSuffix(dataType, prefix, suffix) 指定型で dataKey が prefix と suffix の両方を満たす最新値を照会 table | nil
getAllLatestDataValuesByPrefixAndSuffix(prefix, suffix) 全型で dataKey が prefix と suffix の両方を満たす最新値を照会 table | nil

あいまい検索(キーワードを含む)

Section titled “あいまい検索(キーワードを含む)”
関数 説明 戻り値
getLatestDataValuesByFuzzy(dataType, keyword) 指定型で dataKey が keyword を含む最新値を照会 table | nil
getAllLatestDataValuesByFuzzy(keyword) 全型で dataKey が keyword を含む最新値を照会 table | nil
local Logger = require("Logger")
-- "_power" で終わる全収集データの最新値を照会
local powerValues = getLatestDataValuesBySuffix("Collection", "_power")
if powerValues then
for dataKey, dto in pairs(powerValues) do
Logger.warn(dataKey .. " = " .. dto.DataValue)
end
end
-- 全データ型で "_power" で終わる最新値を照会(型の制限なし)
local allPower = getAllLatestDataValuesBySuffix("_power")
-- "meter1." で始まる全収集データを照会
local meterValues = getLatestDataValuesByPrefix("Collection", "meter1.")
if meterValues then
for dataKey, dto in pairs(meterValues) do
Logger.warnf("%s = %s (%s)", dataKey, dto.DataValue, dto.DataUnit)
end
end
-- 全データ型で "meter1." で始まるデータを照会
local allMeter = getAllLatestDataValuesByPrefix("meter1.")
-- dataKey が "meter1." で始まり "_voltage" で終わる収集データを照会
local voltages = getLatestDataValuesByPrefixAndSuffix("Collection", "meter1.", "_voltage")
-- 全データ型で prefix と suffix の両方を満たすデータを照会
local allVoltages = getAllLatestDataValuesByPrefixAndSuffix("meter1.", "_voltage")
-- あいまい検索:集約データで dataKey が "temp" を含む最新値を照会
local tempValues = getLatestDataValuesByFuzzy("Aggregation", "temp")
if tempValues then
for dataKey, dto in pairs(tempValues) do
Logger.warn("温度点位: " .. dataKey .. " = " .. dto.DataValue)
end
end
-- あいまい検索:全データ型で dataKey が "temp" を含む最新値を照会
local allTemp = getAllLatestDataValuesByFuzzy("temp")

関数 説明 戻り値
getDeviceList(ignoreLocal) デバイス一覧を取得。ignoreLocal=true でローカルを除外 table
getDeviceCodeList(ignoreLocal) deviceCode 一覧を取得。ignoreLocal=true でローカルを除外 table
local Logger = require("Logger")
-- 全デバイス一覧を取得
local allDevices = getDeviceList(false)
if allDevices then
for i, device in ipairs(allDevices) do
Logger.warn("设备: " .. device.deviceCode .. " - " .. device.deviceName)
end
end
-- ローカルを除くデバイス一覧を取得
local otherDevices = getDeviceList(true)
if otherDevices then
for i, device in ipairs(otherDevices) do
Logger.warn("共享设备: " .. device.deviceCode)
end
end
-- 全デバイスコード一覧を取得(完全なデバイス一覧の取得より高速)
local deviceCodes = getDeviceCodeList(false)
if deviceCodes then
for i, code in ipairs(deviceCodes) do
Logger.warn("设备编码: " .. code)
end
end
-- ローカルを除くデバイスコード一覧を取得
local otherDeviceCodes = getDeviceCodeList(true)

関数 説明 戻り値
getHistoryData(dataType, dataKey, startTime?, endTime?, formatMap?) 履歴データを取得 table
getShareHistoryData(deviceCode, dataKey, startTime?, endTime?, formatMap?) 指定デバイスの共有履歴データを取得 table
getTimeData(dataKey, time?, interval?) 指定時刻のデータを取得 table
getShareTimeData(deviceCode, dataKey, time?, interval?) 指定時刻の共有データを取得 table
deleteCustomizationData(dataKey, startTime?, endTime?) カスタムデータを削除 boolean

パラメーターの説明:

  • startTime/endTime/time:次の形式に対応します。
    • OffsetDateTime オブジェクト(推奨)
    • 日時文字列(例:“2024-01-15T10:00:00.000Z”)
    • 短縮文字列(例:“2024-01-15”。自動補完されます)
  • formatMap:戻り値のフィールド名を指定する任意のパラメーター(table 型)。
    • dataKey:データキーのフィールド名(既定値:“dataKey”)
    • dataValue:データ値のフィールド名(既定値:“dataValue”)
    • collectionTime:収集時刻のフィールド名(既定値:“collectionTime”)

Customization 型の戻り値フィールド:

getHistoryData / getTimeData が Customization データに返す時刻フィールドは、スケジュールの種類によって異なります。

  • DailyChange:availableTime(ISO 8601 の完全な日時)と expiredTime を返します。
  • DailyRepeat:availableTime(HH:mm:ss 文字列)と expiredTime(HH:mm:ss 文字列)を返します。
local OffsetDateTime = require("OffsetDateTime")
local Logger = require("Logger")
-- 方法 1:OffsetDateTime オブジェクトを使用(推奨)
local now = OffsetDateTime.now()
local startTime = now:addDays(-7)
local endTime = now
local data = getHistoryData("Collection", "temperature", startTime, endTime)
-- 方法 1 の拡張:formatMap で戻り値のフィールド名を指定
local formatMap = {
dataKey = "key",
dataValue = "value",
collectionTime = "time"
}
local data = getHistoryData("Collection", "temperature", startTime, endTime, formatMap)
-- 方法 2:日時文字列を使用
local data = getHistoryData("Collection", "temperature", "2024-01-01T00:00:00.000Z", "2024-01-31T23:59:59.000Z")
-- 方法 3:短縮文字列を使用(自動補完)
local data = getHistoryData("Collection", "temperature", "2024-01-01", "2024-01-31")
-- 共有履歴データを照会
local sharedData = getShareHistoryData("space1", "pressure", startTime, endTime)
-- 指定時刻のデータを照会
local value = getTimeData("temperature", now, "5m")
-- カスタムデータを削除
local deleted = deleteCustomizationData("data1", startTime, endTime)
Logger.warn("删除成功: " .. tostring(deleted))

関数 説明 戻り値
buildCommonWriteMap(dataType, dataKey, dataValue, availableDate, expiredDate, changeMod) 汎用書き込み map を構築 table
buildGeneralWriteMap(dataType, dataKey, dataValue, changeMod) 汎用書き込み map を構築(簡易版、時刻パラメーターなし) table
buildCustomizationWriteMap(dataKey, dataValue, availableDate, expiredDate) DailyChange 時間帯別データの書き込み map を構築(dataType=Customization を暗黙指定) table
buildDailyRepeatWriteMap(dataKey, dataValue, availableTime, expiredTime) DailyRepeat 時間帯別データの書き込み map を構築(dataType=Customization を暗黙指定、時刻は HH:mm:ss 文字列) table
updateDailyRepeatSchedule(dataKey, scheduleAvailableDate, scheduleExpiredDate) DailyRepeat 設定全体の有効期間を更新。両日付に nil を指定でき、制限なし(無期限有効)を表す boolean
buildAlarmObservationMap(sourceCode, alarmKey, state, alarmType, alarmLevel, alarmContent[, detailKey]) アラームイベント観測を構築。state は ACTIVE / NORMAL / UNKNOWN table
buildCommonAlarmMap(alarmType, alarmContent) 汎用アラーム map を構築 table
buildMqttAlarmMap(alarmType, alarmContent, mqttConnectionConfigId, topic, qos) MQTT アラーム map を構築 table
buildSlaveWriteMap(deviceCode, dataType, dataKey, dataValue, availableDate, expiredDate, changeMod) スレーブ書き込み map を構築 table

アラーム観測には安定した sourceCode + alarmKey を使用し、正常時は NORMAL、欠損・オフライン時は UNKNOWN を送信します。イベント状態と観測状態は異なります。アラームのライフサイクル を参照してください。従来のアラーム構築関数は、引き続き個別レコードを生成します。

収集データ書き込みの係数逆変換は CommBridge が行います。旧 buildCollectionWriteMap は削除済みのため、汎用書き込み構築関数を使用し、二重換算しないでください。

パラメーターの説明:

  • dataType:操作するデータ型。Collection(収集)/ Customization(カスタム・時間帯別)/ Aggregation(集約)/ Share(共有)/ Alarm(アラーム)。
  • availableDate / expiredDate:Customization の DailyChange でのみ必要です。ISO 8601 文字列または OffsetDateTime オブジェクトを指定し、その他の型では nil を渡します。
  • availableTime / expiredTime:Customization の DailyRepeat でのみ必要です。"HH:mm:ss"(例:"08:00:00")形式で、日付をまたぐ指定はできません。
  • changeMod:ブール値。true は値が変化した場合にのみ書き込みます。
local OffsetDateTime = require("OffsetDateTime")
-- 収集ポイントへ書き込み
local writeCollection = buildCommonWriteMap("Collection", "temperature", 25.5, nil, nil, false)
-- カスタムポイントへ書き込み(DailyChange:完全な日時範囲)
local writeCustom = buildCommonWriteMap(
"Customization", "mode", "1",
"2024-01-15T07:00:00+08:00",
"2024-01-15T18:00:00+08:00",
false
)
-- カスタムポイントへ書き込み(DailyChange:専用短縮関数を使用)
local writeCustom2 = buildCustomizationWriteMap(
"mode", "1",
"2024-01-15T07:00:00+08:00",
"2024-01-15T18:00:00+08:00"
)
-- カスタムポイントへ書き込み(DailyRepeat:毎日の繰り返し時間帯、HH:mm:ss 形式)
local writeDailyRepeat = buildDailyRepeatWriteMap("charge_mode", "1", "08:00:00", "18:00:00")
-- DailyRepeat 設定全体の有効期間を更新(適用日付範囲を設定)
local OffsetDateTime = require("OffsetDateTime")
local ok = updateDailyRepeatSchedule("charge_mode",
OffsetDateTime.parse("2026-01-01T00:00:00+08:00"),
OffsetDateTime.parse("2026-12-31T23:59:59+08:00"))
-- 無期限有効へ更新(両日付に nil を指定)
local ok2 = updateDailyRepeatSchedule("charge_mode", nil, nil)
-- 開始時刻のみ設定し、終了は指定しない(nil は無期限)
local ok3 = updateDailyRepeatSchedule("charge_mode", "2026-01-01", nil)
-- 集約ポイントへ書き込み(簡易版、時刻パラメーターなし)
local writeAgg = buildGeneralWriteMap("Aggregation", "avg_temp", 22.5, false)
-- アラームを構築(ローカルのアラームレコードへ書き込み)
local alarm = buildCommonAlarmMap("TEMP_HIGH", "温度超过80°C")
-- MQTT アラームを構築(MQTT 接続 ID を関連付け、MQTT Broker にも報告)
local mqttAlarm = buildMqttAlarmMap("TEMP_HIGH", "温度超过80°C", 1, "alarm/upload", 1)
-- スレーブの共有データへ書き込み
local slaveWrite = buildSlaveWriteMap("DeviceB", "Share", "shared_temp", 25.5, nil, nil, false)

関数 説明 戻り値
toFixedLengthBinary(value, length) 固定長の 2 進数へ変換 string | (nil, err)
toDecimal(binaryStr) 2 進数を 10 進数へ変換 number | (nil, err)
-- 10 進数を 2 進数へ変換
local binary = toFixedLengthBinary(10, 8)
Logger.warn(binary) -- "00001010"
-- 2 進数を 10 進数へ変換
local decimal = toDecimal("00001010")
Logger.warn(decimal) -- 10

local Logger = require("Logger")
local JSON = require("JSON")
local OffsetDateTime = require("OffsetDateTime")
local Math = require("Math")
local Logger = require("Logger")
Logger.info("设备监控脚本启动")
-- デバイスの最新データを取得
local temperature = getLatestDataValue("device1.temperature")
local humidity = getLatestDataValue("device1.humidity")
Logger.infof("当前温度: %.1f°C, 湿度: %.1f%%", temperature, humidity)
-- 温度アラームを判定
if temperature > 80 then
local alarm = buildCommonAlarmMap("TEMP_HIGH", "温度超过80°C")
Logger.error("温度告警: " .. JSON.toJSONString(alarm))
end
-- 履歴データを照会
local now = OffsetDateTime.now()
local startTime = now:addHours(-24)
local history = getHistoryData(
"device1",
"temperature",
startTime:toString(),
now:toString()
)
Logger.infof("获取到 %d 条历史数据", #history)
-- 平均値を計算
local sum = 0
for i, record in ipairs(history) do
sum = sum + record.value
end
local avg = sum / #history
Logger.infof("24小时平均温度: %.2f°C", Math.round(avg * 100) / 100)
local JSON = require("JSON")
local Regex = require("Regex")
local TableUtils = require("TableUtils")
local String = require("String")
local Logger = require("Logger")
-- キャッシュから設定を取得
local configJson = getShareCache("device_config")
local config = JSON.decode(configJson)
-- 有効なデバイスを抽出
local enabledDevices = TableUtils.filter(config.devices, function(device, index)
return device.enabled == true
end)
-- デバイス名を取得
local deviceNames = TableUtils.map(enabledDevices, function(device, index)
return device.name
end)
-- データクレンジング
local cleanedNames = TableUtils.map(deviceNames, function(name, index)
-- 空白を除去して大文字へ変換
return String.upper(String.trim(name))
end)
-- デバイス番号の形式を検証
for i, device in ipairs(enabledDevices) do
if not Regex.match(device.id, "^DEV\\d{6}$") then
Logger.warnf("设备编号格式错误: %s", device.id)
end
end
-- 結果を出力
Logger.info("处理完成: " .. JSON.toJSONString(cleanedNames))

  1. エラー処理:多くの関数は (result, error) を返します。使用時にエラーを確認してください。
  2. 日時形式:日時文字列は ISO 8601 を使用します。
  3. 正規表現:Go の正規表現構文を使用し、Lua 標準の pattern とは異なります。
  4. テーブル走査:TableUtils の map/filter/reduce は、配列部分(1..n)の後にキー・値ペアを走査します。
  5. ログレベル:Logger の出力レベルはシステム設定で決まります。
  6. JSON 性能:ランタイムは高性能な JSON 処理を採用し、大量のシリアライズに適しています。
if isNotNull(${some_key}) then
return {}
end
return { buildCommonWriteMap("Collection", "target_key", ${some_key}, nil, nil, false) }