@trillboards/edge-sdk 0.2.140 → 0.2.151
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/README.md +2 -2
- package/deploy/detector/pyproject.toml +20 -2
- package/deploy/detector/tests/test_execution.py +149 -0
- package/deploy/detector/tests/test_model_identity.py +80 -0
- package/deploy/detector/tests/test_registry.py +18 -0
- package/deploy/detector/tests/test_server.py +3 -1
- package/deploy/detector/tests/test_version_stamp.py +4 -1
- package/deploy/detector/trillboards_detector/_version.py +2 -2
- package/deploy/detector/trillboards_detector/cli.py +3 -0
- package/deploy/detector/trillboards_detector/detections.py +7 -0
- package/deploy/detector/trillboards_detector/errors.py +4 -0
- package/deploy/detector/trillboards_detector/execution.py +110 -0
- package/deploy/detector/trillboards_detector/loader.py +6 -3
- package/deploy/detector/trillboards_detector/registry.py +27 -5
- package/deploy/detector/trillboards_detector/server.py +29 -2
- package/deploy/detector/trillboards_detector/session.py +15 -3
- package/deploy/litertlm/test_trillboards_litertlm_shim.py +81 -0
- package/deploy/litertlm/test_verify_model_proof.py +30 -0
- package/deploy/litertlm/trillboards_litertlm_shim.py +150 -1
- package/deploy/litertlm/verify_model_proof.py +30 -0
- package/deploy/macos/build-macos-pkg.sh +10 -10
- package/deploy/macos/scripts/setup-detector.sh +2 -2
- package/deploy/macos/scripts/setup-litertlm.sh +66 -30
- package/deploy/macos/test-setup-litertlm-reinstall.sh +57 -4
- package/deploy/systemd/setup-detector.sh +2 -2
- package/deploy/systemd/setup-litertlm.sh +51 -27
- package/deploy/windows/build-windows.ps1 +10 -6
- package/deploy/windows/bundle-windows-installer.ps1 +3 -3
- package/deploy/windows/e2e/test-local-sense.ps1 +6 -5
- package/deploy/windows/install-update.ps1 +59 -14
- package/deploy/windows/set-executable-icon.ps1 +24 -5
- package/deploy/windows/setup-detector.ps1 +142 -4
- package/deploy/windows/setup-litertlm.ps1 +53 -10
- package/dist/AudienceAnalyzeClient.d.ts +10 -0
- package/dist/AudienceAnalyzeClient.d.ts.map +1 -1
- package/dist/AudienceAnalyzeClient.js +5 -4
- package/dist/AudienceAnalyzeClient.js.map +1 -1
- package/dist/CloudSensingManager.d.ts +38 -1
- package/dist/CloudSensingManager.d.ts.map +1 -1
- package/dist/CloudSensingManager.js +403 -25
- package/dist/CloudSensingManager.js.map +1 -1
- package/dist/DetectorFieldProducer.d.ts +5 -1
- package/dist/DetectorFieldProducer.d.ts.map +1 -1
- package/dist/DetectorFieldProducer.js +8 -1
- package/dist/DetectorFieldProducer.js.map +1 -1
- package/dist/DurableVlmCandidateSpool.d.ts +83 -2
- package/dist/DurableVlmCandidateSpool.d.ts.map +1 -1
- package/dist/DurableVlmCandidateSpool.js +596 -30
- package/dist/DurableVlmCandidateSpool.js.map +1 -1
- package/dist/EdgeAgent.js +1 -1
- package/dist/FrameGroupingShadow.d.ts +51 -0
- package/dist/FrameGroupingShadow.d.ts.map +1 -0
- package/dist/FrameGroupingShadow.js +158 -0
- package/dist/FrameGroupingShadow.js.map +1 -0
- package/dist/ImageClassifierFieldProducer.d.ts +36 -0
- package/dist/ImageClassifierFieldProducer.d.ts.map +1 -0
- package/dist/ImageClassifierFieldProducer.js +150 -0
- package/dist/ImageClassifierFieldProducer.js.map +1 -0
- package/dist/LiteRtVlmProvider.d.ts +5 -0
- package/dist/LiteRtVlmProvider.d.ts.map +1 -1
- package/dist/LiteRtVlmProvider.js +72 -7
- package/dist/LiteRtVlmProvider.js.map +1 -1
- package/dist/LocalDetectorClient.d.ts +6 -0
- package/dist/LocalDetectorClient.d.ts.map +1 -1
- package/dist/LocalDetectorClient.js +8 -0
- package/dist/LocalDetectorClient.js.map +1 -1
- package/dist/OrderedFrameReview.d.ts +57 -0
- package/dist/OrderedFrameReview.d.ts.map +1 -0
- package/dist/OrderedFrameReview.js +121 -0
- package/dist/OrderedFrameReview.js.map +1 -0
- package/dist/OrderedReviewClient.d.ts +38 -0
- package/dist/OrderedReviewClient.d.ts.map +1 -0
- package/dist/OrderedReviewClient.js +121 -0
- package/dist/OrderedReviewClient.js.map +1 -0
- package/dist/OrderedSequenceStore.d.ts +69 -0
- package/dist/OrderedSequenceStore.d.ts.map +1 -0
- package/dist/OrderedSequenceStore.js +257 -0
- package/dist/OrderedSequenceStore.js.map +1 -0
- package/dist/ProfileReviewWork.d.ts +68 -0
- package/dist/ProfileReviewWork.d.ts.map +1 -0
- package/dist/ProfileReviewWork.js +150 -0
- package/dist/ProfileReviewWork.js.map +1 -0
- package/dist/RetainedFieldContract.d.ts +21 -0
- package/dist/RetainedFieldContract.d.ts.map +1 -0
- package/dist/RetainedFieldContract.js +92 -0
- package/dist/RetainedFieldContract.js.map +1 -0
- package/dist/ReviewModelUse.d.ts +7 -0
- package/dist/ReviewModelUse.d.ts.map +1 -0
- package/dist/ReviewModelUse.js +30 -0
- package/dist/ReviewModelUse.js.map +1 -0
- package/dist/ReviewPriority.d.ts +12 -0
- package/dist/ReviewPriority.d.ts.map +1 -0
- package/dist/ReviewPriority.js +45 -0
- package/dist/ReviewPriority.js.map +1 -0
- package/dist/RuntimeModelSelection.d.ts +10 -0
- package/dist/RuntimeModelSelection.d.ts.map +1 -0
- package/dist/RuntimeModelSelection.js +58 -0
- package/dist/RuntimeModelSelection.js.map +1 -0
- package/dist/SceneChangeDetector.d.ts +1 -1
- package/dist/SceneChangeDetector.d.ts.map +1 -1
- package/dist/SceneChangeDetector.js +18 -6
- package/dist/SceneChangeDetector.js.map +1 -1
- package/dist/ScopedVlmReview.d.ts +76 -0
- package/dist/ScopedVlmReview.d.ts.map +1 -0
- package/dist/ScopedVlmReview.js +267 -0
- package/dist/ScopedVlmReview.js.map +1 -0
- package/dist/SensingProfileClient.d.ts +50 -0
- package/dist/SensingProfileClient.d.ts.map +1 -1
- package/dist/SensingProfileClient.js +58 -2
- package/dist/SensingProfileClient.js.map +1 -1
- package/dist/TemporalReviewClient.d.ts +43 -0
- package/dist/TemporalReviewClient.d.ts.map +1 -0
- package/dist/TemporalReviewClient.js +117 -0
- package/dist/TemporalReviewClient.js.map +1 -0
- package/dist/TemporalReviewJournal.d.ts +91 -0
- package/dist/TemporalReviewJournal.d.ts.map +1 -0
- package/dist/TemporalReviewJournal.js +337 -0
- package/dist/TemporalReviewJournal.js.map +1 -0
- package/dist/UrgentReviewTriage.d.ts +35 -0
- package/dist/UrgentReviewTriage.d.ts.map +1 -0
- package/dist/UrgentReviewTriage.js +52 -0
- package/dist/UrgentReviewTriage.js.map +1 -0
- package/dist/VideoSegmentUploader.d.ts +293 -0
- package/dist/VideoSegmentUploader.d.ts.map +1 -0
- package/dist/VideoSegmentUploader.js +1002 -0
- package/dist/VideoSegmentUploader.js.map +1 -0
- package/dist/VlmCandidateBuffer.d.ts +19 -0
- package/dist/VlmCandidateBuffer.d.ts.map +1 -1
- package/dist/VlmCandidateBuffer.js.map +1 -1
- package/dist/autoSense.d.ts +2 -2
- package/dist/autoSense.d.ts.map +1 -1
- package/dist/autoSense.js +16 -11
- package/dist/autoSense.js.map +1 -1
- package/dist/cli.js +1 -1
- package/dist/cli.js.map +1 -1
- package/dist/config.d.ts +2 -0
- package/dist/config.d.ts.map +1 -1
- package/dist/config.js.map +1 -1
- package/dist/continuousReview.d.ts +71 -0
- package/dist/continuousReview.d.ts.map +1 -0
- package/dist/continuousReview.js +53 -0
- package/dist/continuousReview.js.map +1 -0
- package/dist/detectorCountReview.d.ts +9 -0
- package/dist/detectorCountReview.d.ts.map +1 -0
- package/dist/detectorCountReview.js +79 -0
- package/dist/detectorCountReview.js.map +1 -0
- package/dist/diagnose.d.ts +1 -1
- package/dist/diagnose.js +1 -1
- package/dist/installerOnboardingMode.d.ts.map +1 -1
- package/dist/installerOnboardingMode.js +5 -3
- package/dist/installerOnboardingMode.js.map +1 -1
- package/dist/localInferenceSchema.d.ts +8 -0
- package/dist/localInferenceSchema.d.ts.map +1 -1
- package/dist/localInferenceSchema.js +3 -3
- package/dist/localInferenceSchema.js.map +1 -1
- package/dist/localSenseE2eHarness.d.ts +12 -0
- package/dist/localSenseE2eHarness.d.ts.map +1 -1
- package/dist/localSenseE2eHarness.js +77 -4
- package/dist/localSenseE2eHarness.js.map +1 -1
- package/dist/localSensing.d.ts +91 -18
- package/dist/localSensing.d.ts.map +1 -1
- package/dist/localSensing.js +678 -153
- package/dist/localSensing.js.map +1 -1
- package/dist/mixedScopedCounts.d.ts +17 -0
- package/dist/mixedScopedCounts.d.ts.map +1 -0
- package/dist/mixedScopedCounts.js +90 -0
- package/dist/mixedScopedCounts.js.map +1 -0
- package/dist/sensingCatchRate.d.ts +9 -5
- package/dist/sensingCatchRate.d.ts.map +1 -1
- package/dist/sensingCatchRate.js +10 -6
- package/dist/sensingCatchRate.js.map +1 -1
- package/dist/sensingRunMode.d.ts +5 -0
- package/dist/sensingRunMode.d.ts.map +1 -1
- package/dist/sensingRunMode.js +56 -0
- package/dist/sensingRunMode.js.map +1 -1
- package/package.json +7 -4
- package/retained/ArchiveLifecycle.cjs +79 -0
- package/retained/ModelStageScheduler.cjs +66 -0
- package/retained/ProfileAuthorityClient.cjs +88 -0
- package/retained/RetainedCaptureClient.cjs +164 -0
- package/retained/WaitRecheckCaptureClient.cjs +109 -0
- package/retained/__tests__/archive-lifecycle.test.cjs +117 -0
- package/retained/__tests__/runtime.test.cjs +384 -0
- package/retained/alert-rule-policy.cjs +37 -0
- package/retained/manager.cjs +133 -0
- package/retained/pilot-profile-client.cjs +82 -0
- package/retained/temporal-grouping.cjs +78 -0
- package/retained/website-api-capability.cjs +122 -0
|
@@ -0,0 +1,293 @@
|
|
|
1
|
+
import { type HttpPoster } from './AudienceAnalyzeClient';
|
|
2
|
+
import { type CctvVideoKnobs } from './SensingProfileClient';
|
|
3
|
+
/**
|
|
4
|
+
* VideoSegmentUploader — delivers the CCTV connector's recorded MP4 segments
|
|
5
|
+
* into the ONE video index, `video_segment`, over the same three calls a
|
|
6
|
+
* tablet uses:
|
|
7
|
+
*
|
|
8
|
+
* 1. `POST /v2/earner/video-segment-upload-url` {segment_id, bytes,
|
|
9
|
+
* content_type, capture_start_ms} → a presigned Put Block URL on the
|
|
10
|
+
* private media container (`<folder>/vision-video-private/…`);
|
|
11
|
+
* 2. `PUT` the file's bytes there with `Content-MD5`, which Azure verifies;
|
|
12
|
+
* 3. `POST /v2/earner/video-segment-finalize` with the segment's metadata.
|
|
13
|
+
* The server re-hashes the committed blob and indexes it.
|
|
14
|
+
*
|
|
15
|
+
* `segment_id` is the lowercase hex SHA-256 of the complete file, computed
|
|
16
|
+
* here after the file closed. A local file is deleted ONLY when finalize
|
|
17
|
+
* answers 200 (indexed) or 422 (the server read different bytes and deleted
|
|
18
|
+
* the blob). Every other outcome keeps the file and retries with backoff; the
|
|
19
|
+
* provider's ring is what bounds how much can wait.
|
|
20
|
+
*
|
|
21
|
+
* Device auth is the same header set every connector client sends
|
|
22
|
+
* (`DiscoveryReportClient`, `SensingProfileClient`): `X-Device-Token`, its
|
|
23
|
+
* alias, `X-Device-Timestamp` and a fresh `X-Device-Nonce` per request. Both
|
|
24
|
+
* the API calls and the Blob PUT go through the enterprise agent, so a venue
|
|
25
|
+
* proxy or TLS-inspecting root that works for sensing works for video.
|
|
26
|
+
*
|
|
27
|
+
* Nothing here re-encodes, blurs or filters: the segment is the camera's own
|
|
28
|
+
* bitstream, stream-copied by ffmpeg, delivered as recorded.
|
|
29
|
+
*/
|
|
30
|
+
/** Structurally the provider's `RecordedSegment` (edge-platform-rtsp is required at runtime, never imported). */
|
|
31
|
+
export interface RecordedSegmentLike {
|
|
32
|
+
file: string;
|
|
33
|
+
metaFile?: string;
|
|
34
|
+
startSec: number;
|
|
35
|
+
endSec: number;
|
|
36
|
+
captureStartMs: number;
|
|
37
|
+
captureEndMs: number;
|
|
38
|
+
bytes?: number;
|
|
39
|
+
stream?: {
|
|
40
|
+
codec: string;
|
|
41
|
+
width: number | null;
|
|
42
|
+
height: number | null;
|
|
43
|
+
fps: number | null;
|
|
44
|
+
} | null;
|
|
45
|
+
recovered?: boolean;
|
|
46
|
+
}
|
|
47
|
+
export type UploadNetwork = 'wifi' | 'cellular' | 'ethernet' | 'unknown';
|
|
48
|
+
/** The route's ceiling on one segment: 256 MiB (268,435,456 bytes). */
|
|
49
|
+
export declare const MAX_SEGMENT_BYTES = 268435456;
|
|
50
|
+
/** `max(60 s, 2 x bytes / 125,000 B/s)`, in ms. */
|
|
51
|
+
export declare function putTimeoutMs(bytes: number): number;
|
|
52
|
+
/** What a closed MP4 holds, read from its own boxes. */
|
|
53
|
+
export interface Mp4Probe {
|
|
54
|
+
/** `h264` for avc1/avc3, `hevc` for hvc1/hev1, else the sample entry's fourcc. */
|
|
55
|
+
codec: string;
|
|
56
|
+
sampleEntry: string;
|
|
57
|
+
width: number;
|
|
58
|
+
height: number;
|
|
59
|
+
frames: number;
|
|
60
|
+
durationMs: number;
|
|
61
|
+
fps: number;
|
|
62
|
+
/** Sum of the video track's sample sizes — the bitstream, without container. */
|
|
63
|
+
videoBytes: number;
|
|
64
|
+
hasAudio: boolean;
|
|
65
|
+
}
|
|
66
|
+
/**
|
|
67
|
+
* A CLOSED MP4 with a video track, measured from its own boxes — or null.
|
|
68
|
+
*
|
|
69
|
+
* Null is the "never upload this" answer: a file whose top-level boxes run
|
|
70
|
+
* past its end, or that has no `moov`, is a segment ffmpeg was still writing
|
|
71
|
+
* (measured: a SIGTERM'd segment is mdat with no moov). It is the last gate
|
|
72
|
+
* between a partial file and the corpus, after the provider's list check.
|
|
73
|
+
*/
|
|
74
|
+
export declare function probeMp4File(file: string): Mp4Probe | null;
|
|
75
|
+
/** SHA-256 (hex, the segment_id) and MD5 (base64, Content-MD5) in one read. */
|
|
76
|
+
export declare function hashFile(file: string): Promise<{
|
|
77
|
+
sha256: string;
|
|
78
|
+
md5Base64: string;
|
|
79
|
+
bytes: number;
|
|
80
|
+
}>;
|
|
81
|
+
export interface BlobPutter {
|
|
82
|
+
(url: string, file: string, options: {
|
|
83
|
+
bytes: number;
|
|
84
|
+
contentMd5: string;
|
|
85
|
+
contentType: string;
|
|
86
|
+
timeoutMs: number;
|
|
87
|
+
}): Promise<{
|
|
88
|
+
statusCode: number;
|
|
89
|
+
body: string;
|
|
90
|
+
}>;
|
|
91
|
+
}
|
|
92
|
+
/**
|
|
93
|
+
* Stream a file into a presigned PUT. Never buffers the file: a 256 MiB
|
|
94
|
+
* segment costs one 64 KB read buffer. Bounded twice — a total budget
|
|
95
|
+
* (`putTimeoutMs`) and an idle socket timeout — because a stalled upload must
|
|
96
|
+
* not hold the queue past the URL's own lifetime.
|
|
97
|
+
*/
|
|
98
|
+
export declare const defaultBlobPutter: BlobPutter;
|
|
99
|
+
/**
|
|
100
|
+
* macOS: the default route's interface, named by `networksetup`'s hardware
|
|
101
|
+
* port list (`Hardware Port: Wi-Fi` / `Device: en0`).
|
|
102
|
+
*/
|
|
103
|
+
export declare function macHardwarePortType(hardwarePorts: string, iface: string): UploadNetwork;
|
|
104
|
+
/** The host's uplink type, cached. Any probe failure is 'unknown', never a guess. */
|
|
105
|
+
export declare function hostUploadNetwork(nowMs?: number): Promise<UploadNetwork>;
|
|
106
|
+
/** Test seam. */
|
|
107
|
+
export declare function __resetHostUploadNetworkForTests(): void;
|
|
108
|
+
export interface VideoSegmentUploaderOptions {
|
|
109
|
+
apiBaseUrl: string;
|
|
110
|
+
/** The feed's device token: the server derives screen, device and source from it. */
|
|
111
|
+
deviceToken: string;
|
|
112
|
+
/** Default: this package's version (the connector's). */
|
|
113
|
+
agentVersion?: string;
|
|
114
|
+
/** API transport. Default: the shared `defaultHttpPoster`. */
|
|
115
|
+
poster?: HttpPoster;
|
|
116
|
+
/** Blob transport. Default: `defaultBlobPutter`. */
|
|
117
|
+
putBlob?: BlobPutter;
|
|
118
|
+
/** Default: `hostUploadNetwork`. */
|
|
119
|
+
network?: () => Promise<UploadNetwork> | UploadNetwork;
|
|
120
|
+
/** Default: `probeMp4File`. */
|
|
121
|
+
probe?: (file: string) => Mp4Probe | null;
|
|
122
|
+
now?: () => number;
|
|
123
|
+
retryBaseMs?: number;
|
|
124
|
+
retryMaxMs?: number;
|
|
125
|
+
log?: (level: 'info' | 'warn', message: string) => void;
|
|
126
|
+
}
|
|
127
|
+
export interface VideoUploadStats {
|
|
128
|
+
queued: number;
|
|
129
|
+
inFlight: boolean;
|
|
130
|
+
uploaded: number;
|
|
131
|
+
uploadedBytes: number;
|
|
132
|
+
uploadedSeconds: number;
|
|
133
|
+
/** Finalize 422s, by the server's reason. The local file was deleted. */
|
|
134
|
+
rejected: Record<string, number>;
|
|
135
|
+
/** Not a complete MP4 with a video track — never uploaded, deleted. */
|
|
136
|
+
invalid: number;
|
|
137
|
+
/** A codec `video_segment` does not hold — never uploaded, deleted. */
|
|
138
|
+
unsupportedCodec: number;
|
|
139
|
+
/** Larger than the route accepts — never uploaded, deleted. */
|
|
140
|
+
oversize: number;
|
|
141
|
+
/** Gone before its upload (the ring evicted it). */
|
|
142
|
+
missing: number;
|
|
143
|
+
failures: {
|
|
144
|
+
presign: number;
|
|
145
|
+
put: number;
|
|
146
|
+
finalize: number;
|
|
147
|
+
};
|
|
148
|
+
lastStatus: number | null;
|
|
149
|
+
lastError: string | null;
|
|
150
|
+
lastUploadAtMs: number | null;
|
|
151
|
+
}
|
|
152
|
+
export declare class VideoSegmentUploader {
|
|
153
|
+
private readonly apiBase;
|
|
154
|
+
private readonly deviceToken;
|
|
155
|
+
private readonly agentVersion;
|
|
156
|
+
private readonly poster;
|
|
157
|
+
private readonly putBlob;
|
|
158
|
+
private readonly network;
|
|
159
|
+
private readonly probe;
|
|
160
|
+
private readonly now;
|
|
161
|
+
private readonly retryBaseMs;
|
|
162
|
+
private readonly retryMaxMs;
|
|
163
|
+
private readonly log;
|
|
164
|
+
private readonly queue;
|
|
165
|
+
private inFlight;
|
|
166
|
+
private draining;
|
|
167
|
+
private timer;
|
|
168
|
+
private stopped;
|
|
169
|
+
private readonly stats;
|
|
170
|
+
constructor(options: VideoSegmentUploaderOptions);
|
|
171
|
+
/** Queue a closed segment. Oldest capture first; a file already queued is ignored. */
|
|
172
|
+
enqueue(segment: RecordedSegmentLike): void;
|
|
173
|
+
/** The ring deleted this file; stop trying to deliver it. */
|
|
174
|
+
forget(file: string): void;
|
|
175
|
+
stop(): void;
|
|
176
|
+
getStats(): VideoUploadStats;
|
|
177
|
+
/** Deliver every item that is due now, one at a time. Resolves when none is due. */
|
|
178
|
+
flush(): Promise<void>;
|
|
179
|
+
private kick;
|
|
180
|
+
/** One attempt at one segment: presign → PUT → finalize, resuming at finalize. */
|
|
181
|
+
private deliver;
|
|
182
|
+
/** C4, snake_case. Server-authoritative fields (screen, device, source, key) are never sent. */
|
|
183
|
+
private finalizeBody;
|
|
184
|
+
private postJson;
|
|
185
|
+
private noteFailure;
|
|
186
|
+
private discard;
|
|
187
|
+
private deleteLocal;
|
|
188
|
+
}
|
|
189
|
+
/** What the recorder needs from a provider (edge-platform-rtsp's RTSPStreamCameraProvider). */
|
|
190
|
+
export interface SegmentRecordingTarget {
|
|
191
|
+
on(event: string, listener: (...args: any[]) => void): unknown;
|
|
192
|
+
setSegmentRecording(config: {
|
|
193
|
+
dir: string;
|
|
194
|
+
segmentSeconds: number;
|
|
195
|
+
ringSeconds: number;
|
|
196
|
+
enabled?: boolean;
|
|
197
|
+
} | null): void;
|
|
198
|
+
}
|
|
199
|
+
export interface CctvVideoRecorderOptions {
|
|
200
|
+
provider: SegmentRecordingTarget;
|
|
201
|
+
/** The feed's own directory (the provider's segment dir; knob + budget state beside it). */
|
|
202
|
+
dir: string;
|
|
203
|
+
feedName: string;
|
|
204
|
+
profileClient: {
|
|
205
|
+
fetchProfile(): Promise<{
|
|
206
|
+
video?: CctvVideoKnobs | null;
|
|
207
|
+
} | null>;
|
|
208
|
+
};
|
|
209
|
+
uploader: VideoSegmentUploader;
|
|
210
|
+
pollMs?: number;
|
|
211
|
+
now?: () => number;
|
|
212
|
+
log?: (level: 'info' | 'warn', message: string) => void;
|
|
213
|
+
}
|
|
214
|
+
export interface CctvVideoRecorderStats {
|
|
215
|
+
knobs: CctvVideoKnobs | null;
|
|
216
|
+
/** Whether the provider was last told to record. */
|
|
217
|
+
recording: boolean;
|
|
218
|
+
day: string;
|
|
219
|
+
recordedSecondsToday: number;
|
|
220
|
+
polls: number;
|
|
221
|
+
/** Polls that kept the last applied knobs: no answer, no `video` key, or an unreadable one. */
|
|
222
|
+
keptOnFailedFetch: number;
|
|
223
|
+
keptOnSilence: number;
|
|
224
|
+
keptOnMalformed: number;
|
|
225
|
+
}
|
|
226
|
+
/**
|
|
227
|
+
* One per recording feed. Applies the server's knobs to the provider, keeps
|
|
228
|
+
* a per-UTC-day recorded-seconds budget, and hands every closed segment to
|
|
229
|
+
* the uploader.
|
|
230
|
+
*
|
|
231
|
+
* Knobs follow the deployedCadenceSource rule: a failed fetch, an API that
|
|
232
|
+
* does not send `video`, and an unreadable `video` all KEEP the last applied
|
|
233
|
+
* value — persisted beside the segments, so a restart with the API down
|
|
234
|
+
* records exactly as before. Until the server has ever answered, recording is
|
|
235
|
+
* off. Everything starts at the provider's first `open()`, so a recorder that
|
|
236
|
+
* is built and never opened makes no request and writes nothing.
|
|
237
|
+
*/
|
|
238
|
+
export declare class CctvVideoRecorder {
|
|
239
|
+
private readonly provider;
|
|
240
|
+
private readonly dir;
|
|
241
|
+
private readonly feedName;
|
|
242
|
+
private readonly profileClient;
|
|
243
|
+
readonly uploader: VideoSegmentUploader;
|
|
244
|
+
private readonly pollMs;
|
|
245
|
+
private readonly now;
|
|
246
|
+
private readonly log;
|
|
247
|
+
private knobs;
|
|
248
|
+
private daily;
|
|
249
|
+
private recording;
|
|
250
|
+
private started;
|
|
251
|
+
private stopped;
|
|
252
|
+
private pollTimer;
|
|
253
|
+
private dayTimer;
|
|
254
|
+
private readonly counts;
|
|
255
|
+
constructor(options: CctvVideoRecorderOptions);
|
|
256
|
+
/** Idempotent. Runs synchronously inside the provider's `open()`. */
|
|
257
|
+
start(): void;
|
|
258
|
+
stop(): void;
|
|
259
|
+
getStats(): CctvVideoRecorderStats;
|
|
260
|
+
/** One knob fetch. Only an explicit, readable `video` block changes anything. */
|
|
261
|
+
poll(): Promise<void>;
|
|
262
|
+
private apply;
|
|
263
|
+
private onSegment;
|
|
264
|
+
private rollDay;
|
|
265
|
+
private scheduleNextDay;
|
|
266
|
+
private loadState;
|
|
267
|
+
private persist;
|
|
268
|
+
}
|
|
269
|
+
export interface AttachCctvVideoRecorderArgs {
|
|
270
|
+
provider: unknown;
|
|
271
|
+
dir: string;
|
|
272
|
+
feedName: string;
|
|
273
|
+
apiBaseUrl: string;
|
|
274
|
+
deviceToken: string;
|
|
275
|
+
httpPoster?: HttpPoster;
|
|
276
|
+
/** Knob poll interval; the wiring passes the local profile cache TTL. */
|
|
277
|
+
pollMs?: number;
|
|
278
|
+
}
|
|
279
|
+
/**
|
|
280
|
+
* Attach a recorder to a freshly built provider. Returns null — and records
|
|
281
|
+
* nothing — when the installed edge-platform-rtsp predates segment recording
|
|
282
|
+
* (edge-sdk accepts any `^0.2.0`). A second recorder for the same directory
|
|
283
|
+
* replaces the first, so two managers can never deliver one ring twice.
|
|
284
|
+
*/
|
|
285
|
+
export declare function attachCctvVideoRecorder(args: AttachCctvVideoRecorderArgs): CctvVideoRecorder | null;
|
|
286
|
+
/** Every attached recorder, for diagnostics. */
|
|
287
|
+
export declare function activeCctvVideoRecorders(): Array<{
|
|
288
|
+
dir: string;
|
|
289
|
+
recorder: CctvVideoRecorder;
|
|
290
|
+
}>;
|
|
291
|
+
/** Test seam. */
|
|
292
|
+
export declare function __resetCctvVideoRecordersForTests(): void;
|
|
293
|
+
//# sourceMappingURL=VideoSegmentUploader.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"VideoSegmentUploader.d.ts","sourceRoot":"","sources":["../src/VideoSegmentUploader.ts"],"names":[],"mappings":"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"}
|