@camstack/addon-provider-ecowitt 0.1.25 → 0.1.27
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/addon.js +515 -5
- package/dist/addon.mjs +515 -5
- package/package.json +1 -1
package/dist/addon.js
CHANGED
|
@@ -7361,6 +7361,62 @@ var RecordingConfigSchema = object({
|
|
|
7361
7361
|
scrubThumbnails: ScrubThumbnailPresetSchema.optional()
|
|
7362
7362
|
});
|
|
7363
7363
|
/**
|
|
7364
|
+
* Ops-log — the durable, append-only operations audit shared by the
|
|
7365
|
+
* recordings and events management surfaces.
|
|
7366
|
+
*
|
|
7367
|
+
* ONE row shape is reused for both domains so a single "Activity" view can
|
|
7368
|
+
* merge the recorder's DurableState ring (recordings ops-log) and the
|
|
7369
|
+
* pipeline-analytics SQLite collection (events ops-log). Each row records a
|
|
7370
|
+
* management operation, WHY it ran (reason), and its measurable effect
|
|
7371
|
+
* (itemsAffected + bytesReclaimed). Writes are best-effort — a failed log must
|
|
7372
|
+
* never fail the operation it records.
|
|
7373
|
+
*/
|
|
7374
|
+
/** Which management domain the operation belongs to. */
|
|
7375
|
+
var OpsLogDomainSchema = _enum(["recording", "events"]);
|
|
7376
|
+
/** The kind of management operation performed. */
|
|
7377
|
+
var OpsLogOpSchema = _enum([
|
|
7378
|
+
"prune",
|
|
7379
|
+
"manual-delete",
|
|
7380
|
+
"rescan",
|
|
7381
|
+
"retention-run"
|
|
7382
|
+
]);
|
|
7383
|
+
/** Why the operation ran. */
|
|
7384
|
+
var OpsLogReasonSchema = _enum([
|
|
7385
|
+
"retention",
|
|
7386
|
+
"quota",
|
|
7387
|
+
"manual",
|
|
7388
|
+
"operator"
|
|
7389
|
+
]);
|
|
7390
|
+
/** One audit row, shared verbatim by both domains. */
|
|
7391
|
+
var OpsLogEntrySchema = object({
|
|
7392
|
+
/** Unique row id. */
|
|
7393
|
+
id: string(),
|
|
7394
|
+
/** Epoch ms the operation completed. */
|
|
7395
|
+
at: number(),
|
|
7396
|
+
domain: OpsLogDomainSchema,
|
|
7397
|
+
op: OpsLogOpSchema,
|
|
7398
|
+
reason: OpsLogReasonSchema,
|
|
7399
|
+
/** The camera the op targeted; null for a cluster/global op. */
|
|
7400
|
+
deviceId: number().nullable(),
|
|
7401
|
+
/** Node that performed the op (the log carries nodeId — no cross-node aggregation). */
|
|
7402
|
+
nodeId: string(),
|
|
7403
|
+
/** Buckets / rows deleted (op-specific unit). */
|
|
7404
|
+
itemsAffected: number(),
|
|
7405
|
+
/** Bytes reclaimed by the op (0 when not measurable). */
|
|
7406
|
+
bytesReclaimed: number(),
|
|
7407
|
+
/** Free-text detail (e.g. "floor moved to <ts>"); null when none. */
|
|
7408
|
+
detail: string().nullable(),
|
|
7409
|
+
/** Who/what triggered the op. */
|
|
7410
|
+
actor: string()
|
|
7411
|
+
});
|
|
7412
|
+
/** Shared query input for the per-domain `listOpsLog` cap methods. */
|
|
7413
|
+
var OpsLogQueryInputSchema = object({
|
|
7414
|
+
/** Restrict to a single camera; omit for every row. */
|
|
7415
|
+
deviceId: number().optional(),
|
|
7416
|
+
/** Max rows returned, newest-first. */
|
|
7417
|
+
limit: number().int().min(1).max(1e3).optional()
|
|
7418
|
+
});
|
|
7419
|
+
/**
|
|
7364
7420
|
* `StorageLocationType` — an addon-declared id that identifies the *kind* of
|
|
7365
7421
|
* storage a location serves. Defined here (not in `capabilities/storage.cap.ts`)
|
|
7366
7422
|
* so the persisted record schema and the consumer-facing cap can both consume it
|
|
@@ -7604,6 +7660,160 @@ var EncodeProfileSchema = object({
|
|
|
7604
7660
|
*/
|
|
7605
7661
|
outputArgs: array(string()).optional()
|
|
7606
7662
|
});
|
|
7663
|
+
var COCO_TO_MACRO = {
|
|
7664
|
+
mapping: {
|
|
7665
|
+
person: "person",
|
|
7666
|
+
bicycle: "vehicle",
|
|
7667
|
+
car: "vehicle",
|
|
7668
|
+
motorcycle: "vehicle",
|
|
7669
|
+
airplane: "vehicle",
|
|
7670
|
+
bus: "vehicle",
|
|
7671
|
+
train: "vehicle",
|
|
7672
|
+
truck: "vehicle",
|
|
7673
|
+
boat: "vehicle",
|
|
7674
|
+
bird: "animal",
|
|
7675
|
+
cat: "animal",
|
|
7676
|
+
dog: "animal",
|
|
7677
|
+
horse: "animal",
|
|
7678
|
+
sheep: "animal",
|
|
7679
|
+
cow: "animal",
|
|
7680
|
+
elephant: "animal",
|
|
7681
|
+
bear: "animal",
|
|
7682
|
+
zebra: "animal",
|
|
7683
|
+
giraffe: "animal",
|
|
7684
|
+
suitcase: "package",
|
|
7685
|
+
backpack: "package",
|
|
7686
|
+
handbag: "package"
|
|
7687
|
+
},
|
|
7688
|
+
preserveOriginal: false
|
|
7689
|
+
};
|
|
7690
|
+
var AUDIO_MACRO_LABELS = [
|
|
7691
|
+
{
|
|
7692
|
+
id: "speech",
|
|
7693
|
+
name: "Speech",
|
|
7694
|
+
icon: "🗣️"
|
|
7695
|
+
},
|
|
7696
|
+
{
|
|
7697
|
+
id: "scream",
|
|
7698
|
+
name: "Scream / Shout",
|
|
7699
|
+
icon: "😱"
|
|
7700
|
+
},
|
|
7701
|
+
{
|
|
7702
|
+
id: "crying",
|
|
7703
|
+
name: "Crying / Baby",
|
|
7704
|
+
icon: "😢"
|
|
7705
|
+
},
|
|
7706
|
+
{
|
|
7707
|
+
id: "laughter",
|
|
7708
|
+
name: "Laughter",
|
|
7709
|
+
icon: "😂"
|
|
7710
|
+
},
|
|
7711
|
+
{
|
|
7712
|
+
id: "music",
|
|
7713
|
+
name: "Music",
|
|
7714
|
+
icon: "🎵"
|
|
7715
|
+
},
|
|
7716
|
+
{
|
|
7717
|
+
id: "dog",
|
|
7718
|
+
name: "Dog",
|
|
7719
|
+
icon: "🐕"
|
|
7720
|
+
},
|
|
7721
|
+
{
|
|
7722
|
+
id: "cat",
|
|
7723
|
+
name: "Cat",
|
|
7724
|
+
icon: "🐈"
|
|
7725
|
+
},
|
|
7726
|
+
{
|
|
7727
|
+
id: "bird",
|
|
7728
|
+
name: "Bird",
|
|
7729
|
+
icon: "🐦"
|
|
7730
|
+
},
|
|
7731
|
+
{
|
|
7732
|
+
id: "animal",
|
|
7733
|
+
name: "Animal (other)",
|
|
7734
|
+
icon: "🐾"
|
|
7735
|
+
},
|
|
7736
|
+
{
|
|
7737
|
+
id: "alarm",
|
|
7738
|
+
name: "Alarm / Siren",
|
|
7739
|
+
icon: "🚨"
|
|
7740
|
+
},
|
|
7741
|
+
{
|
|
7742
|
+
id: "doorbell",
|
|
7743
|
+
name: "Doorbell / Knock",
|
|
7744
|
+
icon: "🔔"
|
|
7745
|
+
},
|
|
7746
|
+
{
|
|
7747
|
+
id: "glass_breaking",
|
|
7748
|
+
name: "Glass Breaking",
|
|
7749
|
+
icon: "💥"
|
|
7750
|
+
},
|
|
7751
|
+
{
|
|
7752
|
+
id: "gunshot",
|
|
7753
|
+
name: "Gunshot / Explosion",
|
|
7754
|
+
icon: "💣"
|
|
7755
|
+
},
|
|
7756
|
+
{
|
|
7757
|
+
id: "vehicle",
|
|
7758
|
+
name: "Vehicle",
|
|
7759
|
+
icon: "🚗"
|
|
7760
|
+
},
|
|
7761
|
+
{
|
|
7762
|
+
id: "siren",
|
|
7763
|
+
name: "Emergency Siren",
|
|
7764
|
+
icon: "🚑"
|
|
7765
|
+
},
|
|
7766
|
+
{
|
|
7767
|
+
id: "fire",
|
|
7768
|
+
name: "Fire / Smoke",
|
|
7769
|
+
icon: "🔥"
|
|
7770
|
+
},
|
|
7771
|
+
{
|
|
7772
|
+
id: "water",
|
|
7773
|
+
name: "Water",
|
|
7774
|
+
icon: "💧"
|
|
7775
|
+
},
|
|
7776
|
+
{
|
|
7777
|
+
id: "wind",
|
|
7778
|
+
name: "Wind / Weather",
|
|
7779
|
+
icon: "🌬️"
|
|
7780
|
+
},
|
|
7781
|
+
{
|
|
7782
|
+
id: "door",
|
|
7783
|
+
name: "Door",
|
|
7784
|
+
icon: "🚪"
|
|
7785
|
+
},
|
|
7786
|
+
{
|
|
7787
|
+
id: "footsteps",
|
|
7788
|
+
name: "Footsteps",
|
|
7789
|
+
icon: "👣"
|
|
7790
|
+
},
|
|
7791
|
+
{
|
|
7792
|
+
id: "crowd",
|
|
7793
|
+
name: "Crowd / Chatter",
|
|
7794
|
+
icon: "👥"
|
|
7795
|
+
},
|
|
7796
|
+
{
|
|
7797
|
+
id: "telephone",
|
|
7798
|
+
name: "Telephone",
|
|
7799
|
+
icon: "📞"
|
|
7800
|
+
},
|
|
7801
|
+
{
|
|
7802
|
+
id: "engine",
|
|
7803
|
+
name: "Engine / Motor",
|
|
7804
|
+
icon: "⚙️"
|
|
7805
|
+
},
|
|
7806
|
+
{
|
|
7807
|
+
id: "tools",
|
|
7808
|
+
name: "Tools / Construction",
|
|
7809
|
+
icon: "🔨"
|
|
7810
|
+
},
|
|
7811
|
+
{
|
|
7812
|
+
id: "silence",
|
|
7813
|
+
name: "Silence",
|
|
7814
|
+
icon: "🤫"
|
|
7815
|
+
}
|
|
7816
|
+
];
|
|
7607
7817
|
var YAMNET_TO_MACRO = {
|
|
7608
7818
|
mapping: {
|
|
7609
7819
|
Speech: "speech",
|
|
@@ -7870,6 +8080,125 @@ var _macroLookup = /* @__PURE__ */ new Map();
|
|
|
7870
8080
|
for (const [k, v] of Object.entries(YAMNET_TO_MACRO.mapping)) _macroLookup.set(k.toLowerCase(), v);
|
|
7871
8081
|
for (const [k, v] of Object.entries(APPLE_SA_TO_MACRO.mapping)) _macroLookup.set(k.toLowerCase(), v);
|
|
7872
8082
|
/**
|
|
8083
|
+
* Unified event-kind taxonomy — THE single source of truth for
|
|
8084
|
+
* `kind → { parentKind, category, level, color, iconId, labelKey, label,
|
|
8085
|
+
* icon }`.
|
|
8086
|
+
*
|
|
8087
|
+
* This dictionary folds together what used to be scattered across four
|
|
8088
|
+
* copies:
|
|
8089
|
+
* - `capabilities/sensor-event-kinds.ts` (sensor cap colors)
|
|
8090
|
+
* - `addon-post-analysis/.../services/event-kinds.ts`
|
|
8091
|
+
* (MOTION/PERSON/VEHICLE… _COLOR constants)
|
|
8092
|
+
* - `ui-library/composites/detection-colors.ts` (CLASS_COLORS)
|
|
8093
|
+
* - `addon-post-analysis/shared/frame/box-drawer.ts` (DEFAULT_COLOR)
|
|
8094
|
+
* - the COCO / audio class maps (macro ↔ sub relationships)
|
|
8095
|
+
*
|
|
8096
|
+
* The DATA (serializable — color/iconId/labelKey/parentKind) lives here in
|
|
8097
|
+
* `@camstack/types`. The UI-side mapping `iconId → lucide component` and
|
|
8098
|
+
* `labelKey → t()` lives in `@camstack/ui-library`. UIs never hardcode a
|
|
8099
|
+
* color or an icon: they read this dictionary (server descriptors carry the
|
|
8100
|
+
* fields inline; the client resolves color/icon/label from `iconId`/`kind`).
|
|
8101
|
+
*
|
|
8102
|
+
* Two levels only (v1 YAGNI): macro → sub. `person` is a leaf macro.
|
|
8103
|
+
*/
|
|
8104
|
+
var TAXONOMY_COLORS = {
|
|
8105
|
+
motion: "#f59e0b",
|
|
8106
|
+
audio: "#06b6d4",
|
|
8107
|
+
person: "#22c55e",
|
|
8108
|
+
vehicle: "#3b82f6",
|
|
8109
|
+
animal: "#f97316",
|
|
8110
|
+
package: "#a855f7",
|
|
8111
|
+
sensor: "#8b5cf6",
|
|
8112
|
+
control: "#10b981",
|
|
8113
|
+
genericDetection: "#64748b"
|
|
8114
|
+
};
|
|
8115
|
+
var DETECTION_SUB_COLORS = {
|
|
8116
|
+
car: "#f59e0b",
|
|
8117
|
+
truck: "#d97706",
|
|
8118
|
+
bus: "#b45309",
|
|
8119
|
+
motorcycle: "#eab308",
|
|
8120
|
+
bicycle: "#ca8a04",
|
|
8121
|
+
airplane: "#60a5fa",
|
|
8122
|
+
boat: "#2563eb",
|
|
8123
|
+
train: "#1d4ed8",
|
|
8124
|
+
bird: "#14b8a6",
|
|
8125
|
+
dog: "#84cc16",
|
|
8126
|
+
cat: "#f97316",
|
|
8127
|
+
horse: "#a16207",
|
|
8128
|
+
sheep: "#a3a3a3",
|
|
8129
|
+
cow: "#78716c",
|
|
8130
|
+
elephant: "#6b7280",
|
|
8131
|
+
bear: "#7c2d12",
|
|
8132
|
+
zebra: "#404040",
|
|
8133
|
+
giraffe: "#d4a373"
|
|
8134
|
+
};
|
|
8135
|
+
function titleCase(id) {
|
|
8136
|
+
return id.split(/[-_ ]/).filter((p) => p.length > 0).map((p) => p.charAt(0).toUpperCase() + p.slice(1)).join(" ");
|
|
8137
|
+
}
|
|
8138
|
+
var entries = /* @__PURE__ */ new Map();
|
|
8139
|
+
function macro(kind, category, color, iconId, label) {
|
|
8140
|
+
entries.set(kind, {
|
|
8141
|
+
kind,
|
|
8142
|
+
parentKind: null,
|
|
8143
|
+
level: "macro",
|
|
8144
|
+
category,
|
|
8145
|
+
color,
|
|
8146
|
+
iconId,
|
|
8147
|
+
labelKey: `eventKind.${kind}`,
|
|
8148
|
+
label
|
|
8149
|
+
});
|
|
8150
|
+
}
|
|
8151
|
+
function sub(kind, parentKind, category, color, iconId, label) {
|
|
8152
|
+
entries.set(kind, {
|
|
8153
|
+
kind,
|
|
8154
|
+
parentKind,
|
|
8155
|
+
level: "sub",
|
|
8156
|
+
category,
|
|
8157
|
+
color,
|
|
8158
|
+
iconId,
|
|
8159
|
+
labelKey: `eventKind.${kind}`,
|
|
8160
|
+
label
|
|
8161
|
+
});
|
|
8162
|
+
}
|
|
8163
|
+
macro("motion", "motion", TAXONOMY_COLORS.motion, "motion", "Motion");
|
|
8164
|
+
macro("audio", "audio", TAXONOMY_COLORS.audio, "audio", "Audio");
|
|
8165
|
+
macro("person", "detection", TAXONOMY_COLORS.person, "person", "Person");
|
|
8166
|
+
macro("vehicle", "detection", TAXONOMY_COLORS.vehicle, "vehicle", "Vehicle");
|
|
8167
|
+
macro("animal", "detection", TAXONOMY_COLORS.animal, "animal", "Animal");
|
|
8168
|
+
macro("package", "package", TAXONOMY_COLORS.package, "package", "Package");
|
|
8169
|
+
macro("sensor", "sensor", TAXONOMY_COLORS.sensor, "sensor", "Sensor");
|
|
8170
|
+
macro("control", "control", TAXONOMY_COLORS.control, "control", "Control");
|
|
8171
|
+
for (const [cocoClass, macroClass] of Object.entries(COCO_TO_MACRO.mapping)) {
|
|
8172
|
+
if (macroClass !== "vehicle" && macroClass !== "animal") continue;
|
|
8173
|
+
if (entries.has(cocoClass)) continue;
|
|
8174
|
+
sub(cocoClass, macroClass, "detection", DETECTION_SUB_COLORS[cocoClass] ?? TAXONOMY_COLORS.genericDetection, cocoClass, titleCase(cocoClass));
|
|
8175
|
+
}
|
|
8176
|
+
sub("package-delivered", "package", "package", TAXONOMY_COLORS.package, "package", "Package delivered");
|
|
8177
|
+
sub("package-picked-up", "package", "package", TAXONOMY_COLORS.package, "package", "Package picked up");
|
|
8178
|
+
sub("contact", "sensor", "sensor", "#f59e0b", "door", "Contact");
|
|
8179
|
+
sub("motion-sensor", "sensor", "sensor", TAXONOMY_COLORS.sensor, "pir", "Motion sensor");
|
|
8180
|
+
sub("smoke", "sensor", "sensor", "#ef4444", "smoke", "Smoke");
|
|
8181
|
+
sub("flood", "sensor", "sensor", "#3b82f6", "water", "Water leak");
|
|
8182
|
+
sub("gas", "sensor", "sensor", "#ef4444", "gas", "Gas");
|
|
8183
|
+
sub("carbon-monoxide", "sensor", "sensor", "#dc2626", "smoke", "Carbon monoxide");
|
|
8184
|
+
sub("vibration", "sensor", "sensor", "#eab308", "vibration", "Vibration");
|
|
8185
|
+
sub("tamper", "sensor", "sensor", "#f97316", "tamper", "Tamper");
|
|
8186
|
+
sub("presence", "sensor", "sensor", "#22c55e", "presence", "Presence");
|
|
8187
|
+
sub("enum-sensor", "sensor", "sensor", TAXONOMY_COLORS.sensor, "generic", "Sensor state");
|
|
8188
|
+
sub("device-event", "sensor", "sensor", "#10b981", "button", "Device event");
|
|
8189
|
+
sub("lock", "control", "control", "#0ea5e9", "lock", "Lock");
|
|
8190
|
+
sub("switch", "control", "control", TAXONOMY_COLORS.control, "switch", "Switch");
|
|
8191
|
+
sub("siren", "control", "control", "#dc2626", "siren", "Siren");
|
|
8192
|
+
sub("button", "control", "control", "#10b981", "button", "Button");
|
|
8193
|
+
sub("doorbell", "control", "control", "#a855f7", "doorbell", "Doorbell");
|
|
8194
|
+
for (const l of AUDIO_MACRO_LABELS) {
|
|
8195
|
+
const kind = `audio-${l.id}`;
|
|
8196
|
+
if (entries.has(kind)) continue;
|
|
8197
|
+
sub(kind, "audio", "audio", TAXONOMY_COLORS.audio, kind, l.name);
|
|
8198
|
+
}
|
|
8199
|
+
/** The complete taxonomy dictionary, keyed by kind. */
|
|
8200
|
+
var EVENT_TAXONOMY = Object.freeze(Object.fromEntries(entries));
|
|
8201
|
+
/**
|
|
7873
8202
|
* Error types for the safe expression engine. Two distinct classes so callers
|
|
7874
8203
|
* can tell a compile-time (grammar) failure from a runtime (evaluation)
|
|
7875
8204
|
* failure — both are non-fatal to the host: read paths degrade to "skip link".
|
|
@@ -14824,9 +15153,10 @@ var DEVICE_LOCAL_STATE_CAPS = {
|
|
|
14824
15153
|
* `package` backs the package-drop detector — a package zone is a
|
|
14825
15154
|
* `ZoneRule` on the `'package'` stage referencing drawn polygons
|
|
14826
15155
|
* (see docs/superpowers/specs/2026-07-17-package-zones-design.md §3.1).
|
|
14827
|
-
* The orchestrator provider
|
|
14828
|
-
*
|
|
14829
|
-
* consumers read
|
|
15156
|
+
* The orchestrator provider writes this stage as a first-class slice
|
|
15157
|
+
* (Phase 4): every mutation mirrors the full `{motion, detection,
|
|
15158
|
+
* package}` shape, so consumers read the current package rules directly
|
|
15159
|
+
* off `device.state.zoneRules.value.package`.
|
|
14830
15160
|
*/
|
|
14831
15161
|
runtimeState: object({
|
|
14832
15162
|
motion: array(ZoneRuleSchema).readonly(),
|
|
@@ -18801,17 +19131,30 @@ var EventKindCategorySchema = _enum([
|
|
|
18801
19131
|
"audio",
|
|
18802
19132
|
"detection",
|
|
18803
19133
|
"sensor",
|
|
19134
|
+
"control",
|
|
18804
19135
|
"custom",
|
|
18805
19136
|
"package"
|
|
18806
19137
|
]);
|
|
19138
|
+
/** Taxonomy level — macro (timeline lane) vs sub (events-page leaf). */
|
|
19139
|
+
var EventKindLevelSchema = _enum(["macro", "sub"]);
|
|
18807
19140
|
var EventKindDescriptorSchema = object({
|
|
18808
|
-
/** Stable kind id (e.g. 'motion', '
|
|
19141
|
+
/** Stable kind id (e.g. 'motion', 'vehicle', 'car', 'lock'). */
|
|
18809
19142
|
kind: string(),
|
|
19143
|
+
/** i18n key resolved on the UI side; `label` is the English fallback. */
|
|
19144
|
+
labelKey: string(),
|
|
19145
|
+
/** English fallback label (kept for clients that don't translate). */
|
|
18810
19146
|
label: string(),
|
|
18811
19147
|
/** Hex color for timeline/legend rendering. */
|
|
18812
19148
|
color: string(),
|
|
19149
|
+
/** Dictionary id → lucide component on the UI side. */
|
|
19150
|
+
iconId: string(),
|
|
19151
|
+
/** Legacy closed-vocab glyph — fallback for `iconId`. */
|
|
18813
19152
|
icon: EventKindIconSchema,
|
|
18814
19153
|
category: EventKindCategorySchema,
|
|
19154
|
+
/** Macro parent for this kind ('car' → 'vehicle'); null for a macro. */
|
|
19155
|
+
parentKind: string().nullable(),
|
|
19156
|
+
/** Derived from `parentKind`, explicit for the client tree. */
|
|
19157
|
+
level: EventKindLevelSchema,
|
|
18815
19158
|
/** Which cap + device contributes this kind. For built-ins the camera
|
|
18816
19159
|
* itself; for sensor kinds the LINKED source device. */
|
|
18817
19160
|
source: object({
|
|
@@ -18884,11 +19227,21 @@ var TrackAudioLabelSchema = object({
|
|
|
18884
19227
|
firstAt: number(),
|
|
18885
19228
|
lastAt: number()
|
|
18886
19229
|
});
|
|
19230
|
+
/**
|
|
19231
|
+
* How a track was produced. `pipeline` (default / absent) = the spatial
|
|
19232
|
+
* detection+tracking pipeline. `sensor` = a SYNTHETIC track projected from a
|
|
19233
|
+
* linked sensor/control state change (no positions; carries a snapshot). The
|
|
19234
|
+
* spatial subsystems (tracker association, occupancy count, re-id/embedding,
|
|
19235
|
+
* resurrection) MUST skip `sensor` tracks — they have no bbox trajectory.
|
|
19236
|
+
*/
|
|
19237
|
+
var TrackSourceSchema = _enum(["pipeline", "sensor"]);
|
|
18887
19238
|
var TrackSchema = object({
|
|
18888
19239
|
trackId: string(),
|
|
18889
19240
|
deviceId: number(),
|
|
18890
19241
|
className: string(),
|
|
18891
19242
|
label: string().optional(),
|
|
19243
|
+
/** Track provenance. Absent ⇒ `pipeline` (legacy rows). */
|
|
19244
|
+
source: TrackSourceSchema.optional(),
|
|
18892
19245
|
firstSeen: number(),
|
|
18893
19246
|
lastSeen: number(),
|
|
18894
19247
|
/** Frame-rate position history (subject to maxPositionHistory cap). */
|
|
@@ -19143,6 +19496,26 @@ var TrackCascadeCountsSchema = object({
|
|
|
19143
19496
|
/** Per-track CLIP search vectors removed (best-effort). */
|
|
19144
19497
|
embeddings: number().int()
|
|
19145
19498
|
});
|
|
19499
|
+
/** Event-store footprint for one camera. */
|
|
19500
|
+
var EventStoreDeviceFootprintSchema = object({
|
|
19501
|
+
deviceId: number(),
|
|
19502
|
+
/** Persisted event rows (motion + object + audio) for the camera. */
|
|
19503
|
+
rows: number().int(),
|
|
19504
|
+
/** Event-owned media bytes on disk for the camera. */
|
|
19505
|
+
bytes: number().int()
|
|
19506
|
+
});
|
|
19507
|
+
/** Aggregate event-store footprint: global totals + per-camera breakdown. */
|
|
19508
|
+
var EventStoreFootprintSchema = object({
|
|
19509
|
+
totalRows: number().int(),
|
|
19510
|
+
totalBytes: number().int(),
|
|
19511
|
+
devices: array(EventStoreDeviceFootprintSchema).readonly()
|
|
19512
|
+
});
|
|
19513
|
+
/** Per-kind counts returned by the event-prune / device-delete mutations. */
|
|
19514
|
+
var EventPruneCountsSchema = object({
|
|
19515
|
+
motion: number().int(),
|
|
19516
|
+
object: number().int(),
|
|
19517
|
+
audio: number().int()
|
|
19518
|
+
});
|
|
19146
19519
|
DeviceType.Camera, method(object({ deviceId: number() }), array(TrackSchema).readonly()), method(object({
|
|
19147
19520
|
deviceId: number(),
|
|
19148
19521
|
trackId: string()
|
|
@@ -19206,6 +19579,21 @@ DeviceType.Camera, method(object({ deviceId: number() }), array(TrackSchema).rea
|
|
|
19206
19579
|
}), {
|
|
19207
19580
|
kind: "mutation",
|
|
19208
19581
|
auth: "admin"
|
|
19582
|
+
}), method(object({}), EventStoreFootprintSchema, {
|
|
19583
|
+
kind: "query",
|
|
19584
|
+
auth: "admin"
|
|
19585
|
+
}), method(object({
|
|
19586
|
+
olderThanMs: number(),
|
|
19587
|
+
reason: OpsLogReasonSchema.optional()
|
|
19588
|
+
}), EventPruneCountsSchema, {
|
|
19589
|
+
kind: "mutation",
|
|
19590
|
+
auth: "admin"
|
|
19591
|
+
}), method(object({ deviceId: number() }), EventPruneCountsSchema, {
|
|
19592
|
+
kind: "mutation",
|
|
19593
|
+
auth: "admin"
|
|
19594
|
+
}), method(OpsLogQueryInputSchema, array(OpsLogEntrySchema).readonly(), {
|
|
19595
|
+
kind: "query",
|
|
19596
|
+
auth: "admin"
|
|
19209
19597
|
}), method(object({
|
|
19210
19598
|
eventId: string(),
|
|
19211
19599
|
kind: MediaFileKindEnum.optional()
|
|
@@ -19230,6 +19618,76 @@ DeviceType.Camera, method(object({ deviceId: number() }), array(TrackSchema).rea
|
|
|
19230
19618
|
eventId: string(),
|
|
19231
19619
|
timestamp: number()
|
|
19232
19620
|
});
|
|
19621
|
+
/**
|
|
19622
|
+
* Cap → event-kind mapping for the SENSOR / CONTROL cap families — the table
|
|
19623
|
+
* `pipeline-analytics.listEventKinds` uses to turn a linked device's bound
|
|
19624
|
+
* caps into per-camera event-kind descriptors.
|
|
19625
|
+
*
|
|
19626
|
+
* The descriptor DATA (color / iconId / labelKey / parentKind / category)
|
|
19627
|
+
* is NOT duplicated here — every entry is derived from the single
|
|
19628
|
+
* `EVENT_TAXONOMY` dictionary (`catalogs/event-taxonomy.ts`). This file owns
|
|
19629
|
+
* ONLY the cap-name → taxonomy-kind mapping. Adding a new eventful sensor /
|
|
19630
|
+
* control cap means adding one line here (and a taxonomy entry); the anti-
|
|
19631
|
+
* drift guard `scripts/check-event-kind-coverage.ts` fails the build if an
|
|
19632
|
+
* eventful cap is missing.
|
|
19633
|
+
*/
|
|
19634
|
+
/** Map a taxonomy `iconId` onto the legacy closed `EventKindIcon` enum. */
|
|
19635
|
+
var LEGACY_ICON = {
|
|
19636
|
+
motion: "motion",
|
|
19637
|
+
audio: "audio",
|
|
19638
|
+
person: "person",
|
|
19639
|
+
vehicle: "vehicle",
|
|
19640
|
+
animal: "animal",
|
|
19641
|
+
package: "package",
|
|
19642
|
+
door: "door",
|
|
19643
|
+
pir: "pir",
|
|
19644
|
+
smoke: "smoke",
|
|
19645
|
+
water: "water",
|
|
19646
|
+
button: "button",
|
|
19647
|
+
generic: "generic",
|
|
19648
|
+
gas: "smoke",
|
|
19649
|
+
vibration: "generic",
|
|
19650
|
+
tamper: "generic",
|
|
19651
|
+
presence: "person",
|
|
19652
|
+
lock: "generic",
|
|
19653
|
+
siren: "generic",
|
|
19654
|
+
switch: "generic",
|
|
19655
|
+
doorbell: "button"
|
|
19656
|
+
};
|
|
19657
|
+
function legacyIcon(iconId) {
|
|
19658
|
+
return LEGACY_ICON[iconId] ?? "generic";
|
|
19659
|
+
}
|
|
19660
|
+
/**
|
|
19661
|
+
* Cap name → taxonomy kind id. Covers EVERY eventful sensor / control cap.
|
|
19662
|
+
* The anti-drift guard cross-checks this against the eventful caps declared
|
|
19663
|
+
* in `packages/types/src/capabilities/*.cap.ts`.
|
|
19664
|
+
*/
|
|
19665
|
+
var CAP_TO_KIND = {
|
|
19666
|
+
contact: "contact",
|
|
19667
|
+
motion: "motion-sensor",
|
|
19668
|
+
smoke: "smoke",
|
|
19669
|
+
flood: "flood",
|
|
19670
|
+
gas: "gas",
|
|
19671
|
+
"carbon-monoxide": "carbon-monoxide",
|
|
19672
|
+
vibration: "vibration",
|
|
19673
|
+
tamper: "tamper",
|
|
19674
|
+
presence: "presence",
|
|
19675
|
+
"enum-sensor": "enum-sensor",
|
|
19676
|
+
"event-emitter": "device-event",
|
|
19677
|
+
"lock-control": "lock",
|
|
19678
|
+
switch: "switch",
|
|
19679
|
+
button: "button",
|
|
19680
|
+
doorbell: "doorbell"
|
|
19681
|
+
};
|
|
19682
|
+
function buildDescriptor(capName, kind) {
|
|
19683
|
+
const t = EVENT_TAXONOMY[kind];
|
|
19684
|
+
if (t === void 0) throw new Error(`EVENT_KIND_BY_CAP: cap '${capName}' maps to unknown taxonomy kind '${kind}'`);
|
|
19685
|
+
return {
|
|
19686
|
+
...t,
|
|
19687
|
+
icon: legacyIcon(t.iconId)
|
|
19688
|
+
};
|
|
19689
|
+
}
|
|
19690
|
+
Object.freeze(Object.fromEntries(Object.entries(CAP_TO_KIND).map(([capName, kind]) => [capName, buildDescriptor(capName, kind)])));
|
|
19233
19691
|
var CameraPipelineConfigSchema = object({
|
|
19234
19692
|
engine: PipelineEngineChoiceSchema.optional(),
|
|
19235
19693
|
steps: array(PipelineStepInputSchema).readonly(),
|
|
@@ -22439,13 +22897,29 @@ method(object({
|
|
|
22439
22897
|
}), method(object({ deviceId: number() }), RecordingStatusSchema, {
|
|
22440
22898
|
kind: "mutation",
|
|
22441
22899
|
auth: "admin"
|
|
22442
|
-
}), method(object({
|
|
22900
|
+
}), method(object({
|
|
22901
|
+
deviceId: number(),
|
|
22902
|
+
reason: OpsLogReasonSchema.optional()
|
|
22903
|
+
}), object({
|
|
22443
22904
|
floorMs: number().nullable(),
|
|
22444
22905
|
deletedBuckets: number().int(),
|
|
22445
22906
|
reclaimedBytes: number().int()
|
|
22446
22907
|
}), {
|
|
22447
22908
|
kind: "mutation",
|
|
22448
22909
|
auth: "admin"
|
|
22910
|
+
}), method(object({
|
|
22911
|
+
deviceId: number(),
|
|
22912
|
+
fromMs: number().optional(),
|
|
22913
|
+
toMs: number().optional()
|
|
22914
|
+
}), object({
|
|
22915
|
+
deletedBuckets: number().int(),
|
|
22916
|
+
reclaimedBytes: number().int()
|
|
22917
|
+
}), {
|
|
22918
|
+
kind: "mutation",
|
|
22919
|
+
auth: "admin"
|
|
22920
|
+
}), method(OpsLogQueryInputSchema, array(OpsLogEntrySchema).readonly(), {
|
|
22921
|
+
kind: "query",
|
|
22922
|
+
auth: "admin"
|
|
22449
22923
|
});
|
|
22450
22924
|
/**
|
|
22451
22925
|
* `recordingExport` cap — render a footage time range into a single downloadable
|
|
@@ -25567,6 +26041,12 @@ Object.freeze({
|
|
|
25567
26041
|
addonId: null,
|
|
25568
26042
|
access: "delete"
|
|
25569
26043
|
},
|
|
26044
|
+
"pipelineAnalytics.deleteDeviceEvents": {
|
|
26045
|
+
capName: "pipeline-analytics",
|
|
26046
|
+
capScope: "device",
|
|
26047
|
+
addonId: null,
|
|
26048
|
+
access: "delete"
|
|
26049
|
+
},
|
|
25570
26050
|
"pipelineAnalytics.deleteTracks": {
|
|
25571
26051
|
capName: "pipeline-analytics",
|
|
25572
26052
|
capScope: "device",
|
|
@@ -25597,6 +26077,12 @@ Object.freeze({
|
|
|
25597
26077
|
addonId: null,
|
|
25598
26078
|
access: "view"
|
|
25599
26079
|
},
|
|
26080
|
+
"pipelineAnalytics.getEventStoreFootprint": {
|
|
26081
|
+
capName: "pipeline-analytics",
|
|
26082
|
+
capScope: "device",
|
|
26083
|
+
addonId: null,
|
|
26084
|
+
access: "view"
|
|
26085
|
+
},
|
|
25600
26086
|
"pipelineAnalytics.getKeyEvents": {
|
|
25601
26087
|
capName: "pipeline-analytics",
|
|
25602
26088
|
capScope: "device",
|
|
@@ -25639,6 +26125,12 @@ Object.freeze({
|
|
|
25639
26125
|
addonId: null,
|
|
25640
26126
|
access: "view"
|
|
25641
26127
|
},
|
|
26128
|
+
"pipelineAnalytics.listOpsLog": {
|
|
26129
|
+
capName: "pipeline-analytics",
|
|
26130
|
+
capScope: "device",
|
|
26131
|
+
addonId: null,
|
|
26132
|
+
access: "view"
|
|
26133
|
+
},
|
|
25642
26134
|
"pipelineAnalytics.listRecentTracks": {
|
|
25643
26135
|
capName: "pipeline-analytics",
|
|
25644
26136
|
capScope: "device",
|
|
@@ -25651,6 +26143,12 @@ Object.freeze({
|
|
|
25651
26143
|
addonId: null,
|
|
25652
26144
|
access: "view"
|
|
25653
26145
|
},
|
|
26146
|
+
"pipelineAnalytics.pruneEvents": {
|
|
26147
|
+
capName: "pipeline-analytics",
|
|
26148
|
+
capScope: "device",
|
|
26149
|
+
addonId: null,
|
|
26150
|
+
access: "create"
|
|
26151
|
+
},
|
|
25654
26152
|
"pipelineAnalytics.pruneEventsBefore": {
|
|
25655
26153
|
capName: "pipeline-analytics",
|
|
25656
26154
|
capScope: "device",
|
|
@@ -26413,6 +26911,12 @@ Object.freeze({
|
|
|
26413
26911
|
addonId: null,
|
|
26414
26912
|
access: "create"
|
|
26415
26913
|
},
|
|
26914
|
+
"recording.deleteFootprint": {
|
|
26915
|
+
capName: "recording",
|
|
26916
|
+
capScope: "system",
|
|
26917
|
+
addonId: null,
|
|
26918
|
+
access: "delete"
|
|
26919
|
+
},
|
|
26416
26920
|
"recording.getAvailability": {
|
|
26417
26921
|
capName: "recording",
|
|
26418
26922
|
capScope: "system",
|
|
@@ -26443,6 +26947,12 @@ Object.freeze({
|
|
|
26443
26947
|
addonId: null,
|
|
26444
26948
|
access: "view"
|
|
26445
26949
|
},
|
|
26950
|
+
"recording.listOpsLog": {
|
|
26951
|
+
capName: "recording",
|
|
26952
|
+
capScope: "system",
|
|
26953
|
+
addonId: null,
|
|
26954
|
+
access: "view"
|
|
26955
|
+
},
|
|
26446
26956
|
"recording.locateSegment": {
|
|
26447
26957
|
capName: "recording",
|
|
26448
26958
|
capScope: "system",
|
package/dist/addon.mjs
CHANGED
|
@@ -7360,6 +7360,62 @@ var RecordingConfigSchema = object({
|
|
|
7360
7360
|
scrubThumbnails: ScrubThumbnailPresetSchema.optional()
|
|
7361
7361
|
});
|
|
7362
7362
|
/**
|
|
7363
|
+
* Ops-log — the durable, append-only operations audit shared by the
|
|
7364
|
+
* recordings and events management surfaces.
|
|
7365
|
+
*
|
|
7366
|
+
* ONE row shape is reused for both domains so a single "Activity" view can
|
|
7367
|
+
* merge the recorder's DurableState ring (recordings ops-log) and the
|
|
7368
|
+
* pipeline-analytics SQLite collection (events ops-log). Each row records a
|
|
7369
|
+
* management operation, WHY it ran (reason), and its measurable effect
|
|
7370
|
+
* (itemsAffected + bytesReclaimed). Writes are best-effort — a failed log must
|
|
7371
|
+
* never fail the operation it records.
|
|
7372
|
+
*/
|
|
7373
|
+
/** Which management domain the operation belongs to. */
|
|
7374
|
+
var OpsLogDomainSchema = _enum(["recording", "events"]);
|
|
7375
|
+
/** The kind of management operation performed. */
|
|
7376
|
+
var OpsLogOpSchema = _enum([
|
|
7377
|
+
"prune",
|
|
7378
|
+
"manual-delete",
|
|
7379
|
+
"rescan",
|
|
7380
|
+
"retention-run"
|
|
7381
|
+
]);
|
|
7382
|
+
/** Why the operation ran. */
|
|
7383
|
+
var OpsLogReasonSchema = _enum([
|
|
7384
|
+
"retention",
|
|
7385
|
+
"quota",
|
|
7386
|
+
"manual",
|
|
7387
|
+
"operator"
|
|
7388
|
+
]);
|
|
7389
|
+
/** One audit row, shared verbatim by both domains. */
|
|
7390
|
+
var OpsLogEntrySchema = object({
|
|
7391
|
+
/** Unique row id. */
|
|
7392
|
+
id: string(),
|
|
7393
|
+
/** Epoch ms the operation completed. */
|
|
7394
|
+
at: number(),
|
|
7395
|
+
domain: OpsLogDomainSchema,
|
|
7396
|
+
op: OpsLogOpSchema,
|
|
7397
|
+
reason: OpsLogReasonSchema,
|
|
7398
|
+
/** The camera the op targeted; null for a cluster/global op. */
|
|
7399
|
+
deviceId: number().nullable(),
|
|
7400
|
+
/** Node that performed the op (the log carries nodeId — no cross-node aggregation). */
|
|
7401
|
+
nodeId: string(),
|
|
7402
|
+
/** Buckets / rows deleted (op-specific unit). */
|
|
7403
|
+
itemsAffected: number(),
|
|
7404
|
+
/** Bytes reclaimed by the op (0 when not measurable). */
|
|
7405
|
+
bytesReclaimed: number(),
|
|
7406
|
+
/** Free-text detail (e.g. "floor moved to <ts>"); null when none. */
|
|
7407
|
+
detail: string().nullable(),
|
|
7408
|
+
/** Who/what triggered the op. */
|
|
7409
|
+
actor: string()
|
|
7410
|
+
});
|
|
7411
|
+
/** Shared query input for the per-domain `listOpsLog` cap methods. */
|
|
7412
|
+
var OpsLogQueryInputSchema = object({
|
|
7413
|
+
/** Restrict to a single camera; omit for every row. */
|
|
7414
|
+
deviceId: number().optional(),
|
|
7415
|
+
/** Max rows returned, newest-first. */
|
|
7416
|
+
limit: number().int().min(1).max(1e3).optional()
|
|
7417
|
+
});
|
|
7418
|
+
/**
|
|
7363
7419
|
* `StorageLocationType` — an addon-declared id that identifies the *kind* of
|
|
7364
7420
|
* storage a location serves. Defined here (not in `capabilities/storage.cap.ts`)
|
|
7365
7421
|
* so the persisted record schema and the consumer-facing cap can both consume it
|
|
@@ -7603,6 +7659,160 @@ var EncodeProfileSchema = object({
|
|
|
7603
7659
|
*/
|
|
7604
7660
|
outputArgs: array(string()).optional()
|
|
7605
7661
|
});
|
|
7662
|
+
var COCO_TO_MACRO = {
|
|
7663
|
+
mapping: {
|
|
7664
|
+
person: "person",
|
|
7665
|
+
bicycle: "vehicle",
|
|
7666
|
+
car: "vehicle",
|
|
7667
|
+
motorcycle: "vehicle",
|
|
7668
|
+
airplane: "vehicle",
|
|
7669
|
+
bus: "vehicle",
|
|
7670
|
+
train: "vehicle",
|
|
7671
|
+
truck: "vehicle",
|
|
7672
|
+
boat: "vehicle",
|
|
7673
|
+
bird: "animal",
|
|
7674
|
+
cat: "animal",
|
|
7675
|
+
dog: "animal",
|
|
7676
|
+
horse: "animal",
|
|
7677
|
+
sheep: "animal",
|
|
7678
|
+
cow: "animal",
|
|
7679
|
+
elephant: "animal",
|
|
7680
|
+
bear: "animal",
|
|
7681
|
+
zebra: "animal",
|
|
7682
|
+
giraffe: "animal",
|
|
7683
|
+
suitcase: "package",
|
|
7684
|
+
backpack: "package",
|
|
7685
|
+
handbag: "package"
|
|
7686
|
+
},
|
|
7687
|
+
preserveOriginal: false
|
|
7688
|
+
};
|
|
7689
|
+
var AUDIO_MACRO_LABELS = [
|
|
7690
|
+
{
|
|
7691
|
+
id: "speech",
|
|
7692
|
+
name: "Speech",
|
|
7693
|
+
icon: "🗣️"
|
|
7694
|
+
},
|
|
7695
|
+
{
|
|
7696
|
+
id: "scream",
|
|
7697
|
+
name: "Scream / Shout",
|
|
7698
|
+
icon: "😱"
|
|
7699
|
+
},
|
|
7700
|
+
{
|
|
7701
|
+
id: "crying",
|
|
7702
|
+
name: "Crying / Baby",
|
|
7703
|
+
icon: "😢"
|
|
7704
|
+
},
|
|
7705
|
+
{
|
|
7706
|
+
id: "laughter",
|
|
7707
|
+
name: "Laughter",
|
|
7708
|
+
icon: "😂"
|
|
7709
|
+
},
|
|
7710
|
+
{
|
|
7711
|
+
id: "music",
|
|
7712
|
+
name: "Music",
|
|
7713
|
+
icon: "🎵"
|
|
7714
|
+
},
|
|
7715
|
+
{
|
|
7716
|
+
id: "dog",
|
|
7717
|
+
name: "Dog",
|
|
7718
|
+
icon: "🐕"
|
|
7719
|
+
},
|
|
7720
|
+
{
|
|
7721
|
+
id: "cat",
|
|
7722
|
+
name: "Cat",
|
|
7723
|
+
icon: "🐈"
|
|
7724
|
+
},
|
|
7725
|
+
{
|
|
7726
|
+
id: "bird",
|
|
7727
|
+
name: "Bird",
|
|
7728
|
+
icon: "🐦"
|
|
7729
|
+
},
|
|
7730
|
+
{
|
|
7731
|
+
id: "animal",
|
|
7732
|
+
name: "Animal (other)",
|
|
7733
|
+
icon: "🐾"
|
|
7734
|
+
},
|
|
7735
|
+
{
|
|
7736
|
+
id: "alarm",
|
|
7737
|
+
name: "Alarm / Siren",
|
|
7738
|
+
icon: "🚨"
|
|
7739
|
+
},
|
|
7740
|
+
{
|
|
7741
|
+
id: "doorbell",
|
|
7742
|
+
name: "Doorbell / Knock",
|
|
7743
|
+
icon: "🔔"
|
|
7744
|
+
},
|
|
7745
|
+
{
|
|
7746
|
+
id: "glass_breaking",
|
|
7747
|
+
name: "Glass Breaking",
|
|
7748
|
+
icon: "💥"
|
|
7749
|
+
},
|
|
7750
|
+
{
|
|
7751
|
+
id: "gunshot",
|
|
7752
|
+
name: "Gunshot / Explosion",
|
|
7753
|
+
icon: "💣"
|
|
7754
|
+
},
|
|
7755
|
+
{
|
|
7756
|
+
id: "vehicle",
|
|
7757
|
+
name: "Vehicle",
|
|
7758
|
+
icon: "🚗"
|
|
7759
|
+
},
|
|
7760
|
+
{
|
|
7761
|
+
id: "siren",
|
|
7762
|
+
name: "Emergency Siren",
|
|
7763
|
+
icon: "🚑"
|
|
7764
|
+
},
|
|
7765
|
+
{
|
|
7766
|
+
id: "fire",
|
|
7767
|
+
name: "Fire / Smoke",
|
|
7768
|
+
icon: "🔥"
|
|
7769
|
+
},
|
|
7770
|
+
{
|
|
7771
|
+
id: "water",
|
|
7772
|
+
name: "Water",
|
|
7773
|
+
icon: "💧"
|
|
7774
|
+
},
|
|
7775
|
+
{
|
|
7776
|
+
id: "wind",
|
|
7777
|
+
name: "Wind / Weather",
|
|
7778
|
+
icon: "🌬️"
|
|
7779
|
+
},
|
|
7780
|
+
{
|
|
7781
|
+
id: "door",
|
|
7782
|
+
name: "Door",
|
|
7783
|
+
icon: "🚪"
|
|
7784
|
+
},
|
|
7785
|
+
{
|
|
7786
|
+
id: "footsteps",
|
|
7787
|
+
name: "Footsteps",
|
|
7788
|
+
icon: "👣"
|
|
7789
|
+
},
|
|
7790
|
+
{
|
|
7791
|
+
id: "crowd",
|
|
7792
|
+
name: "Crowd / Chatter",
|
|
7793
|
+
icon: "👥"
|
|
7794
|
+
},
|
|
7795
|
+
{
|
|
7796
|
+
id: "telephone",
|
|
7797
|
+
name: "Telephone",
|
|
7798
|
+
icon: "📞"
|
|
7799
|
+
},
|
|
7800
|
+
{
|
|
7801
|
+
id: "engine",
|
|
7802
|
+
name: "Engine / Motor",
|
|
7803
|
+
icon: "⚙️"
|
|
7804
|
+
},
|
|
7805
|
+
{
|
|
7806
|
+
id: "tools",
|
|
7807
|
+
name: "Tools / Construction",
|
|
7808
|
+
icon: "🔨"
|
|
7809
|
+
},
|
|
7810
|
+
{
|
|
7811
|
+
id: "silence",
|
|
7812
|
+
name: "Silence",
|
|
7813
|
+
icon: "🤫"
|
|
7814
|
+
}
|
|
7815
|
+
];
|
|
7606
7816
|
var YAMNET_TO_MACRO = {
|
|
7607
7817
|
mapping: {
|
|
7608
7818
|
Speech: "speech",
|
|
@@ -7869,6 +8079,125 @@ var _macroLookup = /* @__PURE__ */ new Map();
|
|
|
7869
8079
|
for (const [k, v] of Object.entries(YAMNET_TO_MACRO.mapping)) _macroLookup.set(k.toLowerCase(), v);
|
|
7870
8080
|
for (const [k, v] of Object.entries(APPLE_SA_TO_MACRO.mapping)) _macroLookup.set(k.toLowerCase(), v);
|
|
7871
8081
|
/**
|
|
8082
|
+
* Unified event-kind taxonomy — THE single source of truth for
|
|
8083
|
+
* `kind → { parentKind, category, level, color, iconId, labelKey, label,
|
|
8084
|
+
* icon }`.
|
|
8085
|
+
*
|
|
8086
|
+
* This dictionary folds together what used to be scattered across four
|
|
8087
|
+
* copies:
|
|
8088
|
+
* - `capabilities/sensor-event-kinds.ts` (sensor cap colors)
|
|
8089
|
+
* - `addon-post-analysis/.../services/event-kinds.ts`
|
|
8090
|
+
* (MOTION/PERSON/VEHICLE… _COLOR constants)
|
|
8091
|
+
* - `ui-library/composites/detection-colors.ts` (CLASS_COLORS)
|
|
8092
|
+
* - `addon-post-analysis/shared/frame/box-drawer.ts` (DEFAULT_COLOR)
|
|
8093
|
+
* - the COCO / audio class maps (macro ↔ sub relationships)
|
|
8094
|
+
*
|
|
8095
|
+
* The DATA (serializable — color/iconId/labelKey/parentKind) lives here in
|
|
8096
|
+
* `@camstack/types`. The UI-side mapping `iconId → lucide component` and
|
|
8097
|
+
* `labelKey → t()` lives in `@camstack/ui-library`. UIs never hardcode a
|
|
8098
|
+
* color or an icon: they read this dictionary (server descriptors carry the
|
|
8099
|
+
* fields inline; the client resolves color/icon/label from `iconId`/`kind`).
|
|
8100
|
+
*
|
|
8101
|
+
* Two levels only (v1 YAGNI): macro → sub. `person` is a leaf macro.
|
|
8102
|
+
*/
|
|
8103
|
+
var TAXONOMY_COLORS = {
|
|
8104
|
+
motion: "#f59e0b",
|
|
8105
|
+
audio: "#06b6d4",
|
|
8106
|
+
person: "#22c55e",
|
|
8107
|
+
vehicle: "#3b82f6",
|
|
8108
|
+
animal: "#f97316",
|
|
8109
|
+
package: "#a855f7",
|
|
8110
|
+
sensor: "#8b5cf6",
|
|
8111
|
+
control: "#10b981",
|
|
8112
|
+
genericDetection: "#64748b"
|
|
8113
|
+
};
|
|
8114
|
+
var DETECTION_SUB_COLORS = {
|
|
8115
|
+
car: "#f59e0b",
|
|
8116
|
+
truck: "#d97706",
|
|
8117
|
+
bus: "#b45309",
|
|
8118
|
+
motorcycle: "#eab308",
|
|
8119
|
+
bicycle: "#ca8a04",
|
|
8120
|
+
airplane: "#60a5fa",
|
|
8121
|
+
boat: "#2563eb",
|
|
8122
|
+
train: "#1d4ed8",
|
|
8123
|
+
bird: "#14b8a6",
|
|
8124
|
+
dog: "#84cc16",
|
|
8125
|
+
cat: "#f97316",
|
|
8126
|
+
horse: "#a16207",
|
|
8127
|
+
sheep: "#a3a3a3",
|
|
8128
|
+
cow: "#78716c",
|
|
8129
|
+
elephant: "#6b7280",
|
|
8130
|
+
bear: "#7c2d12",
|
|
8131
|
+
zebra: "#404040",
|
|
8132
|
+
giraffe: "#d4a373"
|
|
8133
|
+
};
|
|
8134
|
+
function titleCase(id) {
|
|
8135
|
+
return id.split(/[-_ ]/).filter((p) => p.length > 0).map((p) => p.charAt(0).toUpperCase() + p.slice(1)).join(" ");
|
|
8136
|
+
}
|
|
8137
|
+
var entries = /* @__PURE__ */ new Map();
|
|
8138
|
+
function macro(kind, category, color, iconId, label) {
|
|
8139
|
+
entries.set(kind, {
|
|
8140
|
+
kind,
|
|
8141
|
+
parentKind: null,
|
|
8142
|
+
level: "macro",
|
|
8143
|
+
category,
|
|
8144
|
+
color,
|
|
8145
|
+
iconId,
|
|
8146
|
+
labelKey: `eventKind.${kind}`,
|
|
8147
|
+
label
|
|
8148
|
+
});
|
|
8149
|
+
}
|
|
8150
|
+
function sub(kind, parentKind, category, color, iconId, label) {
|
|
8151
|
+
entries.set(kind, {
|
|
8152
|
+
kind,
|
|
8153
|
+
parentKind,
|
|
8154
|
+
level: "sub",
|
|
8155
|
+
category,
|
|
8156
|
+
color,
|
|
8157
|
+
iconId,
|
|
8158
|
+
labelKey: `eventKind.${kind}`,
|
|
8159
|
+
label
|
|
8160
|
+
});
|
|
8161
|
+
}
|
|
8162
|
+
macro("motion", "motion", TAXONOMY_COLORS.motion, "motion", "Motion");
|
|
8163
|
+
macro("audio", "audio", TAXONOMY_COLORS.audio, "audio", "Audio");
|
|
8164
|
+
macro("person", "detection", TAXONOMY_COLORS.person, "person", "Person");
|
|
8165
|
+
macro("vehicle", "detection", TAXONOMY_COLORS.vehicle, "vehicle", "Vehicle");
|
|
8166
|
+
macro("animal", "detection", TAXONOMY_COLORS.animal, "animal", "Animal");
|
|
8167
|
+
macro("package", "package", TAXONOMY_COLORS.package, "package", "Package");
|
|
8168
|
+
macro("sensor", "sensor", TAXONOMY_COLORS.sensor, "sensor", "Sensor");
|
|
8169
|
+
macro("control", "control", TAXONOMY_COLORS.control, "control", "Control");
|
|
8170
|
+
for (const [cocoClass, macroClass] of Object.entries(COCO_TO_MACRO.mapping)) {
|
|
8171
|
+
if (macroClass !== "vehicle" && macroClass !== "animal") continue;
|
|
8172
|
+
if (entries.has(cocoClass)) continue;
|
|
8173
|
+
sub(cocoClass, macroClass, "detection", DETECTION_SUB_COLORS[cocoClass] ?? TAXONOMY_COLORS.genericDetection, cocoClass, titleCase(cocoClass));
|
|
8174
|
+
}
|
|
8175
|
+
sub("package-delivered", "package", "package", TAXONOMY_COLORS.package, "package", "Package delivered");
|
|
8176
|
+
sub("package-picked-up", "package", "package", TAXONOMY_COLORS.package, "package", "Package picked up");
|
|
8177
|
+
sub("contact", "sensor", "sensor", "#f59e0b", "door", "Contact");
|
|
8178
|
+
sub("motion-sensor", "sensor", "sensor", TAXONOMY_COLORS.sensor, "pir", "Motion sensor");
|
|
8179
|
+
sub("smoke", "sensor", "sensor", "#ef4444", "smoke", "Smoke");
|
|
8180
|
+
sub("flood", "sensor", "sensor", "#3b82f6", "water", "Water leak");
|
|
8181
|
+
sub("gas", "sensor", "sensor", "#ef4444", "gas", "Gas");
|
|
8182
|
+
sub("carbon-monoxide", "sensor", "sensor", "#dc2626", "smoke", "Carbon monoxide");
|
|
8183
|
+
sub("vibration", "sensor", "sensor", "#eab308", "vibration", "Vibration");
|
|
8184
|
+
sub("tamper", "sensor", "sensor", "#f97316", "tamper", "Tamper");
|
|
8185
|
+
sub("presence", "sensor", "sensor", "#22c55e", "presence", "Presence");
|
|
8186
|
+
sub("enum-sensor", "sensor", "sensor", TAXONOMY_COLORS.sensor, "generic", "Sensor state");
|
|
8187
|
+
sub("device-event", "sensor", "sensor", "#10b981", "button", "Device event");
|
|
8188
|
+
sub("lock", "control", "control", "#0ea5e9", "lock", "Lock");
|
|
8189
|
+
sub("switch", "control", "control", TAXONOMY_COLORS.control, "switch", "Switch");
|
|
8190
|
+
sub("siren", "control", "control", "#dc2626", "siren", "Siren");
|
|
8191
|
+
sub("button", "control", "control", "#10b981", "button", "Button");
|
|
8192
|
+
sub("doorbell", "control", "control", "#a855f7", "doorbell", "Doorbell");
|
|
8193
|
+
for (const l of AUDIO_MACRO_LABELS) {
|
|
8194
|
+
const kind = `audio-${l.id}`;
|
|
8195
|
+
if (entries.has(kind)) continue;
|
|
8196
|
+
sub(kind, "audio", "audio", TAXONOMY_COLORS.audio, kind, l.name);
|
|
8197
|
+
}
|
|
8198
|
+
/** The complete taxonomy dictionary, keyed by kind. */
|
|
8199
|
+
var EVENT_TAXONOMY = Object.freeze(Object.fromEntries(entries));
|
|
8200
|
+
/**
|
|
7872
8201
|
* Error types for the safe expression engine. Two distinct classes so callers
|
|
7873
8202
|
* can tell a compile-time (grammar) failure from a runtime (evaluation)
|
|
7874
8203
|
* failure — both are non-fatal to the host: read paths degrade to "skip link".
|
|
@@ -14823,9 +15152,10 @@ var DEVICE_LOCAL_STATE_CAPS = {
|
|
|
14823
15152
|
* `package` backs the package-drop detector — a package zone is a
|
|
14824
15153
|
* `ZoneRule` on the `'package'` stage referencing drawn polygons
|
|
14825
15154
|
* (see docs/superpowers/specs/2026-07-17-package-zones-design.md §3.1).
|
|
14826
|
-
* The orchestrator provider
|
|
14827
|
-
*
|
|
14828
|
-
* consumers read
|
|
15155
|
+
* The orchestrator provider writes this stage as a first-class slice
|
|
15156
|
+
* (Phase 4): every mutation mirrors the full `{motion, detection,
|
|
15157
|
+
* package}` shape, so consumers read the current package rules directly
|
|
15158
|
+
* off `device.state.zoneRules.value.package`.
|
|
14829
15159
|
*/
|
|
14830
15160
|
runtimeState: object({
|
|
14831
15161
|
motion: array(ZoneRuleSchema).readonly(),
|
|
@@ -18800,17 +19130,30 @@ var EventKindCategorySchema = _enum([
|
|
|
18800
19130
|
"audio",
|
|
18801
19131
|
"detection",
|
|
18802
19132
|
"sensor",
|
|
19133
|
+
"control",
|
|
18803
19134
|
"custom",
|
|
18804
19135
|
"package"
|
|
18805
19136
|
]);
|
|
19137
|
+
/** Taxonomy level — macro (timeline lane) vs sub (events-page leaf). */
|
|
19138
|
+
var EventKindLevelSchema = _enum(["macro", "sub"]);
|
|
18806
19139
|
var EventKindDescriptorSchema = object({
|
|
18807
|
-
/** Stable kind id (e.g. 'motion', '
|
|
19140
|
+
/** Stable kind id (e.g. 'motion', 'vehicle', 'car', 'lock'). */
|
|
18808
19141
|
kind: string(),
|
|
19142
|
+
/** i18n key resolved on the UI side; `label` is the English fallback. */
|
|
19143
|
+
labelKey: string(),
|
|
19144
|
+
/** English fallback label (kept for clients that don't translate). */
|
|
18809
19145
|
label: string(),
|
|
18810
19146
|
/** Hex color for timeline/legend rendering. */
|
|
18811
19147
|
color: string(),
|
|
19148
|
+
/** Dictionary id → lucide component on the UI side. */
|
|
19149
|
+
iconId: string(),
|
|
19150
|
+
/** Legacy closed-vocab glyph — fallback for `iconId`. */
|
|
18812
19151
|
icon: EventKindIconSchema,
|
|
18813
19152
|
category: EventKindCategorySchema,
|
|
19153
|
+
/** Macro parent for this kind ('car' → 'vehicle'); null for a macro. */
|
|
19154
|
+
parentKind: string().nullable(),
|
|
19155
|
+
/** Derived from `parentKind`, explicit for the client tree. */
|
|
19156
|
+
level: EventKindLevelSchema,
|
|
18814
19157
|
/** Which cap + device contributes this kind. For built-ins the camera
|
|
18815
19158
|
* itself; for sensor kinds the LINKED source device. */
|
|
18816
19159
|
source: object({
|
|
@@ -18883,11 +19226,21 @@ var TrackAudioLabelSchema = object({
|
|
|
18883
19226
|
firstAt: number(),
|
|
18884
19227
|
lastAt: number()
|
|
18885
19228
|
});
|
|
19229
|
+
/**
|
|
19230
|
+
* How a track was produced. `pipeline` (default / absent) = the spatial
|
|
19231
|
+
* detection+tracking pipeline. `sensor` = a SYNTHETIC track projected from a
|
|
19232
|
+
* linked sensor/control state change (no positions; carries a snapshot). The
|
|
19233
|
+
* spatial subsystems (tracker association, occupancy count, re-id/embedding,
|
|
19234
|
+
* resurrection) MUST skip `sensor` tracks — they have no bbox trajectory.
|
|
19235
|
+
*/
|
|
19236
|
+
var TrackSourceSchema = _enum(["pipeline", "sensor"]);
|
|
18886
19237
|
var TrackSchema = object({
|
|
18887
19238
|
trackId: string(),
|
|
18888
19239
|
deviceId: number(),
|
|
18889
19240
|
className: string(),
|
|
18890
19241
|
label: string().optional(),
|
|
19242
|
+
/** Track provenance. Absent ⇒ `pipeline` (legacy rows). */
|
|
19243
|
+
source: TrackSourceSchema.optional(),
|
|
18891
19244
|
firstSeen: number(),
|
|
18892
19245
|
lastSeen: number(),
|
|
18893
19246
|
/** Frame-rate position history (subject to maxPositionHistory cap). */
|
|
@@ -19142,6 +19495,26 @@ var TrackCascadeCountsSchema = object({
|
|
|
19142
19495
|
/** Per-track CLIP search vectors removed (best-effort). */
|
|
19143
19496
|
embeddings: number().int()
|
|
19144
19497
|
});
|
|
19498
|
+
/** Event-store footprint for one camera. */
|
|
19499
|
+
var EventStoreDeviceFootprintSchema = object({
|
|
19500
|
+
deviceId: number(),
|
|
19501
|
+
/** Persisted event rows (motion + object + audio) for the camera. */
|
|
19502
|
+
rows: number().int(),
|
|
19503
|
+
/** Event-owned media bytes on disk for the camera. */
|
|
19504
|
+
bytes: number().int()
|
|
19505
|
+
});
|
|
19506
|
+
/** Aggregate event-store footprint: global totals + per-camera breakdown. */
|
|
19507
|
+
var EventStoreFootprintSchema = object({
|
|
19508
|
+
totalRows: number().int(),
|
|
19509
|
+
totalBytes: number().int(),
|
|
19510
|
+
devices: array(EventStoreDeviceFootprintSchema).readonly()
|
|
19511
|
+
});
|
|
19512
|
+
/** Per-kind counts returned by the event-prune / device-delete mutations. */
|
|
19513
|
+
var EventPruneCountsSchema = object({
|
|
19514
|
+
motion: number().int(),
|
|
19515
|
+
object: number().int(),
|
|
19516
|
+
audio: number().int()
|
|
19517
|
+
});
|
|
19145
19518
|
DeviceType.Camera, method(object({ deviceId: number() }), array(TrackSchema).readonly()), method(object({
|
|
19146
19519
|
deviceId: number(),
|
|
19147
19520
|
trackId: string()
|
|
@@ -19205,6 +19578,21 @@ DeviceType.Camera, method(object({ deviceId: number() }), array(TrackSchema).rea
|
|
|
19205
19578
|
}), {
|
|
19206
19579
|
kind: "mutation",
|
|
19207
19580
|
auth: "admin"
|
|
19581
|
+
}), method(object({}), EventStoreFootprintSchema, {
|
|
19582
|
+
kind: "query",
|
|
19583
|
+
auth: "admin"
|
|
19584
|
+
}), method(object({
|
|
19585
|
+
olderThanMs: number(),
|
|
19586
|
+
reason: OpsLogReasonSchema.optional()
|
|
19587
|
+
}), EventPruneCountsSchema, {
|
|
19588
|
+
kind: "mutation",
|
|
19589
|
+
auth: "admin"
|
|
19590
|
+
}), method(object({ deviceId: number() }), EventPruneCountsSchema, {
|
|
19591
|
+
kind: "mutation",
|
|
19592
|
+
auth: "admin"
|
|
19593
|
+
}), method(OpsLogQueryInputSchema, array(OpsLogEntrySchema).readonly(), {
|
|
19594
|
+
kind: "query",
|
|
19595
|
+
auth: "admin"
|
|
19208
19596
|
}), method(object({
|
|
19209
19597
|
eventId: string(),
|
|
19210
19598
|
kind: MediaFileKindEnum.optional()
|
|
@@ -19229,6 +19617,76 @@ DeviceType.Camera, method(object({ deviceId: number() }), array(TrackSchema).rea
|
|
|
19229
19617
|
eventId: string(),
|
|
19230
19618
|
timestamp: number()
|
|
19231
19619
|
});
|
|
19620
|
+
/**
|
|
19621
|
+
* Cap → event-kind mapping for the SENSOR / CONTROL cap families — the table
|
|
19622
|
+
* `pipeline-analytics.listEventKinds` uses to turn a linked device's bound
|
|
19623
|
+
* caps into per-camera event-kind descriptors.
|
|
19624
|
+
*
|
|
19625
|
+
* The descriptor DATA (color / iconId / labelKey / parentKind / category)
|
|
19626
|
+
* is NOT duplicated here — every entry is derived from the single
|
|
19627
|
+
* `EVENT_TAXONOMY` dictionary (`catalogs/event-taxonomy.ts`). This file owns
|
|
19628
|
+
* ONLY the cap-name → taxonomy-kind mapping. Adding a new eventful sensor /
|
|
19629
|
+
* control cap means adding one line here (and a taxonomy entry); the anti-
|
|
19630
|
+
* drift guard `scripts/check-event-kind-coverage.ts` fails the build if an
|
|
19631
|
+
* eventful cap is missing.
|
|
19632
|
+
*/
|
|
19633
|
+
/** Map a taxonomy `iconId` onto the legacy closed `EventKindIcon` enum. */
|
|
19634
|
+
var LEGACY_ICON = {
|
|
19635
|
+
motion: "motion",
|
|
19636
|
+
audio: "audio",
|
|
19637
|
+
person: "person",
|
|
19638
|
+
vehicle: "vehicle",
|
|
19639
|
+
animal: "animal",
|
|
19640
|
+
package: "package",
|
|
19641
|
+
door: "door",
|
|
19642
|
+
pir: "pir",
|
|
19643
|
+
smoke: "smoke",
|
|
19644
|
+
water: "water",
|
|
19645
|
+
button: "button",
|
|
19646
|
+
generic: "generic",
|
|
19647
|
+
gas: "smoke",
|
|
19648
|
+
vibration: "generic",
|
|
19649
|
+
tamper: "generic",
|
|
19650
|
+
presence: "person",
|
|
19651
|
+
lock: "generic",
|
|
19652
|
+
siren: "generic",
|
|
19653
|
+
switch: "generic",
|
|
19654
|
+
doorbell: "button"
|
|
19655
|
+
};
|
|
19656
|
+
function legacyIcon(iconId) {
|
|
19657
|
+
return LEGACY_ICON[iconId] ?? "generic";
|
|
19658
|
+
}
|
|
19659
|
+
/**
|
|
19660
|
+
* Cap name → taxonomy kind id. Covers EVERY eventful sensor / control cap.
|
|
19661
|
+
* The anti-drift guard cross-checks this against the eventful caps declared
|
|
19662
|
+
* in `packages/types/src/capabilities/*.cap.ts`.
|
|
19663
|
+
*/
|
|
19664
|
+
var CAP_TO_KIND = {
|
|
19665
|
+
contact: "contact",
|
|
19666
|
+
motion: "motion-sensor",
|
|
19667
|
+
smoke: "smoke",
|
|
19668
|
+
flood: "flood",
|
|
19669
|
+
gas: "gas",
|
|
19670
|
+
"carbon-monoxide": "carbon-monoxide",
|
|
19671
|
+
vibration: "vibration",
|
|
19672
|
+
tamper: "tamper",
|
|
19673
|
+
presence: "presence",
|
|
19674
|
+
"enum-sensor": "enum-sensor",
|
|
19675
|
+
"event-emitter": "device-event",
|
|
19676
|
+
"lock-control": "lock",
|
|
19677
|
+
switch: "switch",
|
|
19678
|
+
button: "button",
|
|
19679
|
+
doorbell: "doorbell"
|
|
19680
|
+
};
|
|
19681
|
+
function buildDescriptor(capName, kind) {
|
|
19682
|
+
const t = EVENT_TAXONOMY[kind];
|
|
19683
|
+
if (t === void 0) throw new Error(`EVENT_KIND_BY_CAP: cap '${capName}' maps to unknown taxonomy kind '${kind}'`);
|
|
19684
|
+
return {
|
|
19685
|
+
...t,
|
|
19686
|
+
icon: legacyIcon(t.iconId)
|
|
19687
|
+
};
|
|
19688
|
+
}
|
|
19689
|
+
Object.freeze(Object.fromEntries(Object.entries(CAP_TO_KIND).map(([capName, kind]) => [capName, buildDescriptor(capName, kind)])));
|
|
19232
19690
|
var CameraPipelineConfigSchema = object({
|
|
19233
19691
|
engine: PipelineEngineChoiceSchema.optional(),
|
|
19234
19692
|
steps: array(PipelineStepInputSchema).readonly(),
|
|
@@ -22438,13 +22896,29 @@ method(object({
|
|
|
22438
22896
|
}), method(object({ deviceId: number() }), RecordingStatusSchema, {
|
|
22439
22897
|
kind: "mutation",
|
|
22440
22898
|
auth: "admin"
|
|
22441
|
-
}), method(object({
|
|
22899
|
+
}), method(object({
|
|
22900
|
+
deviceId: number(),
|
|
22901
|
+
reason: OpsLogReasonSchema.optional()
|
|
22902
|
+
}), object({
|
|
22442
22903
|
floorMs: number().nullable(),
|
|
22443
22904
|
deletedBuckets: number().int(),
|
|
22444
22905
|
reclaimedBytes: number().int()
|
|
22445
22906
|
}), {
|
|
22446
22907
|
kind: "mutation",
|
|
22447
22908
|
auth: "admin"
|
|
22909
|
+
}), method(object({
|
|
22910
|
+
deviceId: number(),
|
|
22911
|
+
fromMs: number().optional(),
|
|
22912
|
+
toMs: number().optional()
|
|
22913
|
+
}), object({
|
|
22914
|
+
deletedBuckets: number().int(),
|
|
22915
|
+
reclaimedBytes: number().int()
|
|
22916
|
+
}), {
|
|
22917
|
+
kind: "mutation",
|
|
22918
|
+
auth: "admin"
|
|
22919
|
+
}), method(OpsLogQueryInputSchema, array(OpsLogEntrySchema).readonly(), {
|
|
22920
|
+
kind: "query",
|
|
22921
|
+
auth: "admin"
|
|
22448
22922
|
});
|
|
22449
22923
|
/**
|
|
22450
22924
|
* `recordingExport` cap — render a footage time range into a single downloadable
|
|
@@ -25566,6 +26040,12 @@ Object.freeze({
|
|
|
25566
26040
|
addonId: null,
|
|
25567
26041
|
access: "delete"
|
|
25568
26042
|
},
|
|
26043
|
+
"pipelineAnalytics.deleteDeviceEvents": {
|
|
26044
|
+
capName: "pipeline-analytics",
|
|
26045
|
+
capScope: "device",
|
|
26046
|
+
addonId: null,
|
|
26047
|
+
access: "delete"
|
|
26048
|
+
},
|
|
25569
26049
|
"pipelineAnalytics.deleteTracks": {
|
|
25570
26050
|
capName: "pipeline-analytics",
|
|
25571
26051
|
capScope: "device",
|
|
@@ -25596,6 +26076,12 @@ Object.freeze({
|
|
|
25596
26076
|
addonId: null,
|
|
25597
26077
|
access: "view"
|
|
25598
26078
|
},
|
|
26079
|
+
"pipelineAnalytics.getEventStoreFootprint": {
|
|
26080
|
+
capName: "pipeline-analytics",
|
|
26081
|
+
capScope: "device",
|
|
26082
|
+
addonId: null,
|
|
26083
|
+
access: "view"
|
|
26084
|
+
},
|
|
25599
26085
|
"pipelineAnalytics.getKeyEvents": {
|
|
25600
26086
|
capName: "pipeline-analytics",
|
|
25601
26087
|
capScope: "device",
|
|
@@ -25638,6 +26124,12 @@ Object.freeze({
|
|
|
25638
26124
|
addonId: null,
|
|
25639
26125
|
access: "view"
|
|
25640
26126
|
},
|
|
26127
|
+
"pipelineAnalytics.listOpsLog": {
|
|
26128
|
+
capName: "pipeline-analytics",
|
|
26129
|
+
capScope: "device",
|
|
26130
|
+
addonId: null,
|
|
26131
|
+
access: "view"
|
|
26132
|
+
},
|
|
25641
26133
|
"pipelineAnalytics.listRecentTracks": {
|
|
25642
26134
|
capName: "pipeline-analytics",
|
|
25643
26135
|
capScope: "device",
|
|
@@ -25650,6 +26142,12 @@ Object.freeze({
|
|
|
25650
26142
|
addonId: null,
|
|
25651
26143
|
access: "view"
|
|
25652
26144
|
},
|
|
26145
|
+
"pipelineAnalytics.pruneEvents": {
|
|
26146
|
+
capName: "pipeline-analytics",
|
|
26147
|
+
capScope: "device",
|
|
26148
|
+
addonId: null,
|
|
26149
|
+
access: "create"
|
|
26150
|
+
},
|
|
25653
26151
|
"pipelineAnalytics.pruneEventsBefore": {
|
|
25654
26152
|
capName: "pipeline-analytics",
|
|
25655
26153
|
capScope: "device",
|
|
@@ -26412,6 +26910,12 @@ Object.freeze({
|
|
|
26412
26910
|
addonId: null,
|
|
26413
26911
|
access: "create"
|
|
26414
26912
|
},
|
|
26913
|
+
"recording.deleteFootprint": {
|
|
26914
|
+
capName: "recording",
|
|
26915
|
+
capScope: "system",
|
|
26916
|
+
addonId: null,
|
|
26917
|
+
access: "delete"
|
|
26918
|
+
},
|
|
26415
26919
|
"recording.getAvailability": {
|
|
26416
26920
|
capName: "recording",
|
|
26417
26921
|
capScope: "system",
|
|
@@ -26442,6 +26946,12 @@ Object.freeze({
|
|
|
26442
26946
|
addonId: null,
|
|
26443
26947
|
access: "view"
|
|
26444
26948
|
},
|
|
26949
|
+
"recording.listOpsLog": {
|
|
26950
|
+
capName: "recording",
|
|
26951
|
+
capScope: "system",
|
|
26952
|
+
addonId: null,
|
|
26953
|
+
access: "view"
|
|
26954
|
+
},
|
|
26445
26955
|
"recording.locateSegment": {
|
|
26446
26956
|
capName: "recording",
|
|
26447
26957
|
capScope: "system",
|
package/package.json
CHANGED