@apocaliss92/nodelink-js 0.4.26 → 0.4.28
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 +4 -2
- package/dist/{chunk-F3XCYKYT.js → chunk-NQ7D5TLR.js} +145 -26
- package/dist/chunk-NQ7D5TLR.js.map +1 -0
- package/dist/cli/rtsp-server.cjs +105 -25
- package/dist/cli/rtsp-server.cjs.map +1 -1
- package/dist/cli/rtsp-server.js +1 -1
- package/dist/index.cjs +473 -74
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +217 -6
- package/dist/index.d.ts +221 -5
- package/dist/index.js +290 -5
- package/dist/index.js.map +1 -1
- package/package.json +5 -1
- package/dist/chunk-F3XCYKYT.js.map +0 -1
package/dist/index.d.ts
CHANGED
|
@@ -2978,6 +2978,8 @@ export declare function buildStartZoomFocusXml(channelId: number, movePos: numbe
|
|
|
2978
2978
|
*/
|
|
2979
2979
|
export declare function buildWhiteLedStateXml(channelId: number, state: number): string;
|
|
2980
2980
|
|
|
2981
|
+
declare type CameraResolver = (recipient: string) => string | undefined;
|
|
2982
|
+
|
|
2981
2983
|
/**
|
|
2982
2984
|
* Capture all relevant API responses from a single device (or NVR channel)
|
|
2983
2985
|
* and write them as JSON/XML fixtures into `outDir`.
|
|
@@ -4079,6 +4081,27 @@ export declare function createDiagnosticsBundle(params: {
|
|
|
4079
4081
|
diagnosticsPath: string;
|
|
4080
4082
|
}>;
|
|
4081
4083
|
|
|
4084
|
+
export declare function createEmailPushServer(params: CreateEmailPushServerParams): EmailPushServerInstance;
|
|
4085
|
+
|
|
4086
|
+
export declare interface CreateEmailPushServerParams {
|
|
4087
|
+
config: EmailPushServerConfig;
|
|
4088
|
+
/**
|
|
4089
|
+
* Resolver mapping the `cam-<id>` localpart (the part before `@domain`)
|
|
4090
|
+
* to the consumer's internal camera identifier. Return `undefined` to
|
|
4091
|
+
* reject the recipient at RCPT TO.
|
|
4092
|
+
*/
|
|
4093
|
+
cameraResolver: (localCameraId: string) => string | undefined;
|
|
4094
|
+
/** Optional logger; defaults to no-op. */
|
|
4095
|
+
logger?: EmailPushLogger;
|
|
4096
|
+
/**
|
|
4097
|
+
* Optional TLS loader override. Default uses `loadEmailPushTls` which
|
|
4098
|
+
* reads `cert.pem` + `key.pem` from `config.tlsDir`. Consumers (e.g.
|
|
4099
|
+
* Scrypted) can pass their own loader to source the material from a
|
|
4100
|
+
* different store.
|
|
4101
|
+
*/
|
|
4102
|
+
loadTls?: (dir: string, warn: (m: string) => void) => Promise<EmailPushTlsOptions | undefined>;
|
|
4103
|
+
}
|
|
4104
|
+
|
|
4082
4105
|
export declare function createLogger(options?: {
|
|
4083
4106
|
base?: LoggerLike;
|
|
4084
4107
|
level?: LogLevel;
|
|
@@ -4773,6 +4796,115 @@ export declare interface EmailConfig {
|
|
|
4773
4796
|
/** Patch payload accepted by SetEmail. All fields optional — only supplied ones are written. */
|
|
4774
4797
|
export declare type EmailConfigPatch = Partial<Omit<EmailConfig, "senderMaxLen" | "pwdMaxLen" | "emailAttachAbility">>;
|
|
4775
4798
|
|
|
4799
|
+
export declare interface EmailPushEvent {
|
|
4800
|
+
cameraId: string;
|
|
4801
|
+
/** Original recipient address that matched this camera. */
|
|
4802
|
+
recipient: string;
|
|
4803
|
+
inferredType: EmailPushInferredType;
|
|
4804
|
+
/** Reception timestamp on the manager (ms since epoch). */
|
|
4805
|
+
receivedAtMs: number;
|
|
4806
|
+
subject: string;
|
|
4807
|
+
from: string;
|
|
4808
|
+
/** Raw body text excerpt (max 500 chars). */
|
|
4809
|
+
bodyExcerpt: string;
|
|
4810
|
+
}
|
|
4811
|
+
|
|
4812
|
+
/**
|
|
4813
|
+
* Email push event bus.
|
|
4814
|
+
*
|
|
4815
|
+
* Stateless in-memory dispatcher. Lives in the library so any consumer
|
|
4816
|
+
* (the manager app, the Scrypted plugin, integration tests) can subscribe
|
|
4817
|
+
* and emit through the same surface without dragging in the
|
|
4818
|
+
* `smtp-server` / `mailparser` native deps.
|
|
4819
|
+
*
|
|
4820
|
+
* The bus is intentionally:
|
|
4821
|
+
* - **Process-local** — every consumer has its own bus instance (the
|
|
4822
|
+
* module-level state below). No cross-process or cross-import sharing.
|
|
4823
|
+
* - **Bounded** — keeps the last `MAX_GLOBAL_EVENTS` (default 300) for
|
|
4824
|
+
* the "recent emails" panel, and a single-event reference per camera
|
|
4825
|
+
* for the verifyDelivery race short-circuit. Footprint is O(cameras)
|
|
4826
|
+
* plus O(MAX_GLOBAL_EVENTS).
|
|
4827
|
+
* - **Attachment-free** — only metadata (subject, from, body excerpt,
|
|
4828
|
+
* classified type) is retained; the actual JPEG/MP4 payloads from the
|
|
4829
|
+
* camera are never persisted by the bus.
|
|
4830
|
+
*/
|
|
4831
|
+
/** Trigger classification produced by parsing the camera's email body. */
|
|
4832
|
+
export declare type EmailPushInferredType = "motion" | "people" | "vehicle" | "animal" | "face" | "package" | "doorbell" | "other";
|
|
4833
|
+
|
|
4834
|
+
export declare interface EmailPushLogger {
|
|
4835
|
+
debug?: (msg: string) => void;
|
|
4836
|
+
info?: (msg: string) => void;
|
|
4837
|
+
warn?: (msg: string) => void;
|
|
4838
|
+
error?: (msg: string) => void;
|
|
4839
|
+
}
|
|
4840
|
+
|
|
4841
|
+
export declare interface EmailPushServerConfig {
|
|
4842
|
+
/** SMTP listen port. */
|
|
4843
|
+
port: number;
|
|
4844
|
+
/** Bind host (`0.0.0.0` to accept on LAN). */
|
|
4845
|
+
bindHost: string;
|
|
4846
|
+
/** Virtual mail domain — used to extract the camera id from RCPT TO. */
|
|
4847
|
+
domain: string;
|
|
4848
|
+
/** Require AUTH PLAIN / AUTH LOGIN. */
|
|
4849
|
+
requireAuth: boolean;
|
|
4850
|
+
/** Expected AUTH username (stored bare, e.g. `nodelink-abcd`). */
|
|
4851
|
+
authUsername: string;
|
|
4852
|
+
/** Expected AUTH password. */
|
|
4853
|
+
authPassword: string;
|
|
4854
|
+
/** Enable STARTTLS using cert+key under `tlsDir`. */
|
|
4855
|
+
tls: boolean;
|
|
4856
|
+
/** Directory holding cert.pem + key.pem when `tls: true`. */
|
|
4857
|
+
tlsDir?: string;
|
|
4858
|
+
/** Maximum accepted message size in bytes. */
|
|
4859
|
+
maxMessageBytes: number;
|
|
4860
|
+
}
|
|
4861
|
+
|
|
4862
|
+
export declare interface EmailPushServerInstance {
|
|
4863
|
+
start(): Promise<void>;
|
|
4864
|
+
stop(): Promise<void>;
|
|
4865
|
+
restart(): Promise<void>;
|
|
4866
|
+
getStatus(): EmailPushServerStatus;
|
|
4867
|
+
/**
|
|
4868
|
+
* Replace the current config; the next `start` / `restart` picks it up.
|
|
4869
|
+
* Hot updates of config without restart are not supported on purpose —
|
|
4870
|
+
* SMTP server bind options need a fresh `listen()`.
|
|
4871
|
+
*/
|
|
4872
|
+
updateConfig(next: EmailPushServerConfig): void;
|
|
4873
|
+
}
|
|
4874
|
+
|
|
4875
|
+
export declare interface EmailPushServerStatus {
|
|
4876
|
+
enabled: boolean;
|
|
4877
|
+
running: boolean;
|
|
4878
|
+
port: number;
|
|
4879
|
+
bindHost: string;
|
|
4880
|
+
domain: string;
|
|
4881
|
+
requireAuth: boolean;
|
|
4882
|
+
tls: boolean;
|
|
4883
|
+
/** Cumulative messages accepted since start. */
|
|
4884
|
+
messagesAccepted: number;
|
|
4885
|
+
/** Cumulative messages rejected (unknown recipient, parse fail, etc.). */
|
|
4886
|
+
messagesRejected: number;
|
|
4887
|
+
startedAtMs: number | undefined;
|
|
4888
|
+
lastErrorMessage: string | undefined;
|
|
4889
|
+
}
|
|
4890
|
+
|
|
4891
|
+
/**
|
|
4892
|
+
* Optional STARTTLS support for the email-push SMTP server.
|
|
4893
|
+
*
|
|
4894
|
+
* The library does NOT auto-generate a self-signed cert: doing so portably
|
|
4895
|
+
* across Node versions requires a heavy dependency (`selfsigned` /
|
|
4896
|
+
* `node-forge`), and Reolink cameras typically accept self-signed certs
|
|
4897
|
+
* only when the user has consciously opted into TLS.
|
|
4898
|
+
*
|
|
4899
|
+
* Consumers point `loadEmailPushTls` at a directory containing `cert.pem`
|
|
4900
|
+
* and `key.pem`. When either is missing the function returns `undefined`
|
|
4901
|
+
* and logs through the provided logger (or `console.warn` by default).
|
|
4902
|
+
*/
|
|
4903
|
+
export declare interface EmailPushTlsOptions {
|
|
4904
|
+
cert: Buffer;
|
|
4905
|
+
key: Buffer;
|
|
4906
|
+
}
|
|
4907
|
+
|
|
4776
4908
|
/** Email schedule configuration (cmdId=216/217). */
|
|
4777
4909
|
export declare interface EmailTaskConfig {
|
|
4778
4910
|
channelId: number;
|
|
@@ -4799,6 +4931,9 @@ export declare interface EmailTaskScheduleItem {
|
|
|
4799
4931
|
/** Whether the alert body carries the standard human-readable text. */
|
|
4800
4932
|
export declare type EmailTextType = "withText" | "noText";
|
|
4801
4933
|
|
|
4934
|
+
/** Internal: SMTP server uses this to dispatch an event into the bus. */
|
|
4935
|
+
export declare function emitEmailPushEvent(event: EmailPushEvent): void;
|
|
4936
|
+
|
|
4802
4937
|
/**
|
|
4803
4938
|
* Encoding configuration (getEnc response).
|
|
4804
4939
|
* cmdId=56 (GetEnc) — payload is wrapped in `Compression`, not `Enc`.
|
|
@@ -4959,6 +5094,8 @@ export declare interface EncStreamPatch {
|
|
|
4959
5094
|
*/
|
|
4960
5095
|
export declare function ensureXmlHeader(xml: string): string;
|
|
4961
5096
|
|
|
5097
|
+
declare type EventHandler = (event: EmailPushEvent) => void;
|
|
5098
|
+
|
|
4962
5099
|
export declare interface Events {
|
|
4963
5100
|
channel?: number;
|
|
4964
5101
|
ai?: AIState;
|
|
@@ -5076,6 +5213,9 @@ export declare interface FtpTaskConfig {
|
|
|
5076
5213
|
*/
|
|
5077
5214
|
export declare function fullCoverageScope(columns: number, rows: number, width?: number, height?: number): MotionZoneScope;
|
|
5078
5215
|
|
|
5216
|
+
/** Build the recipient address assigned to a given camera. */
|
|
5217
|
+
export declare function getCameraEmailAddress(cameraId: string, domain: string): string;
|
|
5218
|
+
|
|
5079
5219
|
/**
|
|
5080
5220
|
* Get constructed video stream options for all available profiles.
|
|
5081
5221
|
*
|
|
@@ -5083,6 +5223,8 @@ export declare function fullCoverageScope(columns: number, rows: number, width?:
|
|
|
5083
5223
|
*/
|
|
5084
5224
|
export declare function getConstructedVideoStreamOptions(channel: number, api: ReolinkBaichuanApi, rtspHost: string, rtspPort?: number, rtspUsername?: string, rtspPassword?: string): Promise<ResponseMediaStreamOptions[]>;
|
|
5085
5225
|
|
|
5226
|
+
export declare function getEmailPushCameraResolver(): CameraResolver;
|
|
5227
|
+
|
|
5086
5228
|
export declare function getGlobalLogger(): Logger_2;
|
|
5087
5229
|
|
|
5088
5230
|
/**
|
|
@@ -5091,8 +5233,23 @@ export declare function getGlobalLogger(): Logger_2;
|
|
|
5091
5233
|
*/
|
|
5092
5234
|
export declare function getH265NalType(nalPayload: Buffer): number | null;
|
|
5093
5235
|
|
|
5236
|
+
/**
|
|
5237
|
+
* Read the most recent event observed for a camera. Returns `undefined`
|
|
5238
|
+
* when no email-push event has been received since the consumer started.
|
|
5239
|
+
*/
|
|
5240
|
+
export declare function getLastEmailPushEvent(cameraId: string): EmailPushEvent | undefined;
|
|
5241
|
+
|
|
5094
5242
|
export declare function getMjpegContentType(boundary: string): string;
|
|
5095
5243
|
|
|
5244
|
+
/**
|
|
5245
|
+
* Return a snapshot of the most recent email-push events across all
|
|
5246
|
+
* cameras (most recent first). Capped at `MAX_GLOBAL_EVENTS` (300).
|
|
5247
|
+
*
|
|
5248
|
+
* `limit` is clamped to the buffer cap so callers can ask for a smaller
|
|
5249
|
+
* page without juggling the storage limit.
|
|
5250
|
+
*/
|
|
5251
|
+
export declare function getRecentEmailPushEvents(limit?: number): EmailPushEvent[];
|
|
5252
|
+
|
|
5096
5253
|
/**
|
|
5097
5254
|
* Result of getRecordingVideo() - a fully muxed MP4 with stats.
|
|
5098
5255
|
*/
|
|
@@ -5770,6 +5927,19 @@ export declare type LastSleepProbe = {
|
|
|
5770
5927
|
status: SleepStatus;
|
|
5771
5928
|
};
|
|
5772
5929
|
|
|
5930
|
+
/**
|
|
5931
|
+
* Read the user-provided cert/key pair. Returns `undefined` (and logs a
|
|
5932
|
+
* warning) when either file is missing.
|
|
5933
|
+
*/
|
|
5934
|
+
export declare function loadEmailPushTls(params: LoadTlsParams): Promise<EmailPushTlsOptions | undefined>;
|
|
5935
|
+
|
|
5936
|
+
export declare interface LoadTlsParams {
|
|
5937
|
+
/** Directory holding `cert.pem` + `key.pem`. */
|
|
5938
|
+
dir: string;
|
|
5939
|
+
/** Optional logger; defaults to console-based warn. */
|
|
5940
|
+
warn?: (msg: string) => void;
|
|
5941
|
+
}
|
|
5942
|
+
|
|
5773
5943
|
export declare type Logger = Logger_2;
|
|
5774
5944
|
|
|
5775
5945
|
declare interface Logger_2 {
|
|
@@ -5796,6 +5966,15 @@ export declare type LoginResponseValue = {
|
|
|
5796
5966
|
|
|
5797
5967
|
export declare type LogLevel = "silent" | "error" | "warn" | "info" | "debug";
|
|
5798
5968
|
|
|
5969
|
+
/**
|
|
5970
|
+
* Map the email-push classifier output onto the lib's broader
|
|
5971
|
+
* ReolinkSimpleEvent type union. Shared by `ReolinkBaichuanApi
|
|
5972
|
+
* .subscribeEmailPushEvents` (the per-camera bridge) and any consumer
|
|
5973
|
+
* that wants the same mapping at the global bus level (e.g. the
|
|
5974
|
+
* manager-app's events-manager) so both code paths stay in sync.
|
|
5975
|
+
*/
|
|
5976
|
+
export declare function mapEmailPushInferredType(inferred: EmailPushInferredType): "motion" | "doorbell" | "people" | "vehicle" | "animal" | "face" | "package";
|
|
5977
|
+
|
|
5799
5978
|
/**
|
|
5800
5979
|
* Privacy mask configuration (`getMask`). The `Shelter` block always
|
|
5801
5980
|
* contains `enable` + `maxNum` + `shelterList`; tracked-shelter sub-
|
|
@@ -6168,6 +6347,12 @@ export declare type NvrChannelsSummaryCacheEntry = {
|
|
|
6168
6347
|
devices: ReolinkBaichuanDeviceSummary[];
|
|
6169
6348
|
};
|
|
6170
6349
|
|
|
6350
|
+
/**
|
|
6351
|
+
* Register a handler invoked for every accepted email-push event. Returns
|
|
6352
|
+
* an `off` function.
|
|
6353
|
+
*/
|
|
6354
|
+
export declare function onEmailPushEvent(handler: EventHandler): () => void;
|
|
6355
|
+
|
|
6171
6356
|
/**
|
|
6172
6357
|
* Online user list response.
|
|
6173
6358
|
*/
|
|
@@ -6556,7 +6741,7 @@ export declare class ReolinkBaichuanApi {
|
|
|
6556
6741
|
* general socket is created, logged in, and all event/push/guard listeners
|
|
6557
6742
|
* are re-attached automatically.
|
|
6558
6743
|
*
|
|
6559
|
-
* This is a **no-op** when the API is already
|
|
6744
|
+
* This is a **no-op** when the API is already ready (see `isReadyState()`).
|
|
6560
6745
|
*
|
|
6561
6746
|
* @throws If `close()` was called — the API is permanently closed and a new
|
|
6562
6747
|
* instance must be created.
|
|
@@ -6570,7 +6755,7 @@ export declare class ReolinkBaichuanApi {
|
|
|
6570
6755
|
/**
|
|
6571
6756
|
* Attach event, push, channelInfo, and guard listeners to the current
|
|
6572
6757
|
* "general" client. Called from the constructor and from
|
|
6573
|
-
*
|
|
6758
|
+
* `reconnectGeneralSocket()`.
|
|
6574
6759
|
*/
|
|
6575
6760
|
private setupGeneralClientListeners;
|
|
6576
6761
|
/**
|
|
@@ -7093,6 +7278,27 @@ export declare class ReolinkBaichuanApi {
|
|
|
7093
7278
|
* Called on every socket close event.
|
|
7094
7279
|
*/
|
|
7095
7280
|
private maybeRebootOnEconnresetStorm;
|
|
7281
|
+
/**
|
|
7282
|
+
* Bind this API instance to the global email-push bus so that incoming
|
|
7283
|
+
* SMTP-delivered motion / AI events for the matching camera surface on
|
|
7284
|
+
* this instance's standard `onSimpleEvent` channel. The consumer keeps
|
|
7285
|
+
* a single subscription (`onSimpleEvent`) and gets both the native
|
|
7286
|
+
* Baichuan push and the email-push transport on the same stream.
|
|
7287
|
+
*
|
|
7288
|
+
* - `cameraId` shorthand: match events with `event.cameraId === cameraId`.
|
|
7289
|
+
* - `match`: arbitrary predicate (e.g. when the consumer uses a
|
|
7290
|
+
* nickname-based mapping or wants to handle multiple recipients).
|
|
7291
|
+
*
|
|
7292
|
+
* Returns an `off()` handle. Safe to call repeatedly — each call
|
|
7293
|
+
* registers its own listener.
|
|
7294
|
+
*/
|
|
7295
|
+
subscribeEmailPushEvents(params: {
|
|
7296
|
+
cameraId: string;
|
|
7297
|
+
channel?: number;
|
|
7298
|
+
} | {
|
|
7299
|
+
match: (event: EmailPushEvent) => boolean;
|
|
7300
|
+
channel?: number;
|
|
7301
|
+
}): () => void;
|
|
7096
7302
|
/**
|
|
7097
7303
|
* Subscribe to minimal high-level events.
|
|
7098
7304
|
* The API manages Baichuan subscribe/unsubscribe automatically.
|
|
@@ -7109,7 +7315,7 @@ export declare class ReolinkBaichuanApi {
|
|
|
7109
7315
|
* Subscribe to per-frame detection events sourced from the BcMedia
|
|
7110
7316
|
* `additionalHeader` block on active video streams.
|
|
7111
7317
|
*
|
|
7112
|
-
* Mirrors
|
|
7318
|
+
* Mirrors `onSimpleEvent()` but is fed by the streaming side-channel:
|
|
7113
7319
|
* one event fires for every I-frame / P-frame that carries an overlay block.
|
|
7114
7320
|
* Coordinates are reported in normalized [0, 1] fractions of the source
|
|
7115
7321
|
* frame, so the same box renders correctly on mainStream, subStream, and
|
|
@@ -7128,7 +7334,7 @@ export declare class ReolinkBaichuanApi {
|
|
|
7128
7334
|
* Subscribe to AI object detections (people / vehicle / animal / face boxes
|
|
7129
7335
|
* with class label and confidence) without managing a video stream yourself.
|
|
7130
7336
|
*
|
|
7131
|
-
* Mirrors
|
|
7337
|
+
* Mirrors `onSimpleEvent()` end-to-end: on the first listener for a given
|
|
7132
7338
|
* `(channel, profile)` tuple the API ensures the corresponding video stream
|
|
7133
7339
|
* is running (the pool socket may already be shared with a regular consumer),
|
|
7134
7340
|
* forwards every box-bearing `additionalHeader` to your callback, and tears
|
|
@@ -8745,7 +8951,7 @@ export declare class ReolinkBaichuanApi {
|
|
|
8745
8951
|
* Field meaning per stream:
|
|
8746
8952
|
* - `audio` — 0/1 toggle
|
|
8747
8953
|
* - `width`/`height` — resolution in pixels. Must be one of the
|
|
8748
|
-
* resolutions returned by
|
|
8954
|
+
* resolutions returned by `getStreamInfoList()`.
|
|
8749
8955
|
* - `bitRate` — kbps. Must match the table from `getStreamInfoList`.
|
|
8750
8956
|
* - `frameRate` — fps. Must match the table from `getStreamInfoList`.
|
|
8751
8957
|
* - `videoEncType` — `"h264"` or `"h265"`
|
|
@@ -10848,6 +11054,9 @@ export declare interface ReplayHttpServerOptions {
|
|
|
10848
11054
|
isNvr?: boolean;
|
|
10849
11055
|
}
|
|
10850
11056
|
|
|
11057
|
+
/** Test hook: drop all subscribers, recent events, and reset the resolver. */
|
|
11058
|
+
export declare function _resetEmailPushBusForTests(): void;
|
|
11059
|
+
|
|
10851
11060
|
/**
|
|
10852
11061
|
* ResponseMediaStreamOptions - Stream profile metadata
|
|
10853
11062
|
*/
|
|
@@ -11220,6 +11429,13 @@ export declare function sampleStreams(opts: StreamSamplingOptions): Promise<void
|
|
|
11220
11429
|
*/
|
|
11221
11430
|
export declare function sanitizeFixtureData(value: unknown): unknown;
|
|
11222
11431
|
|
|
11432
|
+
/**
|
|
11433
|
+
* Set the callback that maps a recipient address (e.g.
|
|
11434
|
+
* `cam-abc@nodelink.local`) to a known cameraId. Returning `undefined`
|
|
11435
|
+
* rejects the recipient at RCPT TO.
|
|
11436
|
+
*/
|
|
11437
|
+
export declare function setEmailPushCameraResolver(resolver: CameraResolver): void;
|
|
11438
|
+
|
|
11223
11439
|
export declare function setGlobalLogger(logger: LoggerLike | Logger_2 | undefined): void;
|
|
11224
11440
|
|
|
11225
11441
|
/**
|