chore: 初始开源发布

iotlcm-bot:独立飞书应用机器人(读取 Worker 终态 Run JSON,渲染并发送全量同步结果卡片)。

- Go module:git.5iot.com/iotlcm/iotlcm-bot → git.5iot.com/iotlcm-public/iotlcm-bot
- 飞书凭据占位:appId/appSecret/chatId → ${FEISHU_APP_ID}/${FEISHU_APP_SECRET}/${FEISHU_CHAT_ID}
- 移除内部资产:CI 触发器
- Dockerfile 改用公共基础镜像(golang:1.25-alpine → scratch)
- README 重写(命令/配置/挂载契约/常见问题),去掉内部环境路径
- 补 Apache-2.0 LICENSE,LF 行尾 + .gitattributes
This commit is contained in:
MiFaZhan
2026-10-22 16:14:24 +08:00
commit 5732bf3384
33 changed files with 2676 additions and 0 deletions
+49
View File
@@ -0,0 +1,49 @@
package render
import (
"encoding/json"
"git.5iot.com/iotlcm-public/iotlcm-bot/internal/archive"
"strings"
"testing"
)
func TestSupplyBlockCoversEveryTrafficOperation(t *testing.T) {
observation := json.RawMessage(`{"schemaVersion":1,"resolutionMs":1000,"summary":{"targetChannels":1,"validChannels":1,"confirmedChannels":1,"confirmedChannelMs":6000,"longestMs":6000}}`)
for _, operation := range []string{"previous_day_usage_full_sync", "previous_month_usage_full_sync", "current_month_usage_full_sync", "traffic_usage_full_sync"} {
a := archive.RunArchive{Run: archive.RunSummary{Operation: operation, SupplyObservation: observation}}
if supplyBlock(a) == "" {
t.Fatalf("traffic operation %q must show supply block", operation)
}
}
for _, operation := range []string{"sim_status_queue_full_sync", "imei_full_sync"} {
a := archive.RunArchive{Run: archive.RunSummary{Operation: operation, SupplyObservation: observation}}
if supplyBlock(a) != "" {
t.Fatalf("non-traffic operation %q must omit supply block", operation)
}
}
}
func TestSupplyCompatibilityAndPartial(t *testing.T) {
a := archive.RunArchive{Run: archive.RunSummary{Operation: "current_month_usage_full_sync"}}
if supplyBlock(a) != "" {
t.Fatal("legacy archive must omit telemetry")
}
a.Run.SupplyObservation = json.RawMessage(`{"schemaVersion":1,"resolutionMs":1000,"partial":true,"summary":{"targetChannels":2,"validChannels":2,"confirmedChannels":1,"confirmedChannelMs":6000,"longestMs":6000},"channels":[{"chanKey":"a","confirmedWait":{"totalMs":6000,"longestMs":6000},"producerStageMs":{"global_capacity":6000}}]}`)
text := supplyBlock(a)
for _, want := range []string{"partial", "6.0通道秒", "global_capacity", "约1秒分辨率", "≥5秒"} {
if !strings.Contains(text, want) {
t.Fatalf("missing %s in %s", want, text)
}
}
if strings.Contains(text, "全程供料充足") {
t.Fatal("unsupported conclusion")
}
a.Run.SupplyObservation = json.RawMessage(`"bad"`)
if !strings.Contains(supplyBlock(a), "不可用") {
t.Fatal("bad optional telemetry must degrade")
}
a.Run.SyncType = "replay"
if supplyBlock(a) != "" {
t.Fatal("replay changed")
}
}