@recallai/desktop-sdk 2.0.6 → 2.0.8

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/CHANGELOG.md CHANGED
@@ -1,8 +1,28 @@
1
+ ### 2.0.8 [patch] (MacOS+Windows) - 2026-03-13
2
+ - Reduced blips/audio-glitches in the audio mixing process
3
+ - Fixed Windows audio latency during capture
4
+ - Added Windows network-status event and automatic recording stopping.
5
+ - More robust device switching and restarting on windows.
6
+ - Prevent google meet updated events after recording stopped on macOS.
7
+ - Fixed Brave detection on macOS
8
+ - Fixed Chrome fullscreen detection on macOS
9
+ - Fixed issue for Google Meet where compliance message would send to wrong input when different window is focused on macOS
10
+ - Fixed issue for Zoom where host would incorrectly get recognized as a separate participant on macOS
11
+ - Fixed issue for screenshare capturing where screen sharing indicator would sometimes persist after recording ended on macOS
12
+ - Added ZoomAudioDevice to mic capture blacklist on macOS
13
+ - Fixed Chrome title detection on macOS
14
+ - Supported title on MS Teams on macOS
15
+
16
+ ### 2.0.7 [patch] (MacOS+Windows) - 2026-02-26
17
+ - Fixed issues capturing audio when devices change on windows.
18
+ - Added a network shutdown event on macOS.
19
+ - Set recording id on SDK events on macOS and windows.
20
+ - Fix cases where stop recording would take a while and prevent any future commands.
21
+
1
22
  ### 2.0.6 [patch] (MacOS+Windows) - 2026-02-11
2
23
  - Fix case where recording-ended would not trigger on Windows
3
24
 
4
- ### 2.0.5 [patch] (MacOS+Windows) - 2026-02-11
5
-
25
+ ### 2.0.5 [patch] (MacOS+Windows) - 2026-02-11 (deprecated)
6
26
  - Support for Google Chrome 145.0.7632.46+
7
27
  - Improvements for Brave
8
28
  - Automatically detect which microphone is being used by the meeting platform
package/index.d.ts CHANGED
@@ -1,4 +1,4 @@
1
- export type RecallAiSdkEvent = RecordingStartEvent | RecordingStopEvent | UploadProgressEvent | MeetingDetectedEvent | MeetingUpdatedEvent | MeetingClosedEvent | SdkStateChangeEvent | ErrorEvent | MediaCaptureStatusEvent | ParticipantCaptureStatusEvent | PermissionsGrantedEvent | RealtimeEvent | ShutdownEvent | LogEvent;
1
+ export type RecallAiSdkEvent = RecordingStartEvent | RecordingStopEvent | UploadProgressEvent | MeetingDetectedEvent | MeetingUpdatedEvent | MeetingClosedEvent | SdkStateChangeEvent | ErrorEvent | MediaCaptureStatusEvent | ParticipantCaptureStatusEvent | PermissionsGrantedEvent | RealtimeEvent | ShutdownEvent | LogEvent | NetworkStatusEvent;
2
2
  export type EventTypeToPayloadMap = {
3
3
  'recording-started': RecordingStartEvent;
4
4
  'recording-ended': RecordingStopEvent;
@@ -18,6 +18,7 @@ export type EventTypeToPayloadMap = {
18
18
  'realtime-event': RealtimeEvent;
19
19
  'shutdown': ShutdownEvent;
20
20
  'log': LogEvent;
21
+ 'network-status': NetworkStatusEvent;
21
22
  };
22
23
  export type Permission = 'accessibility' | 'screen-capture' | 'microphone' | 'system-audio' | 'full-disk-access';
23
24
  export interface RecallAiSdkWindow {
@@ -32,6 +33,10 @@ export interface RecallAiSdkConfig {
32
33
  acquirePermissionsOnStartup?: Permission[];
33
34
  restartOnError?: boolean;
34
35
  dev?: boolean;
36
+ testMode?: boolean;
37
+ testSpeedModifier?: string;
38
+ testTargetBundleId?: string;
39
+ testTargetBundleIdRemapped?: string;
35
40
  }
36
41
  export interface StartRecordingConfig {
37
42
  windowId: string;
@@ -110,6 +115,9 @@ export interface ShutdownEvent {
110
115
  code: number;
111
116
  signal: string;
112
117
  }
118
+ export interface NetworkStatusEvent {
119
+ status: 'reconnected' | 'disconnected';
120
+ }
113
121
  export interface LogEvent {
114
122
  level: 'debug' | 'info' | 'warning' | 'error';
115
123
  message: string;
package/index.js CHANGED
@@ -185,6 +185,9 @@ async function doLog(level, log, echo = true) {
185
185
  }
186
186
  }
187
187
  catch (e) {
188
+ if (proc?.exitCode === 0 || exiting) {
189
+ return;
190
+ }
188
191
  console.error("Failed to send log to Desktop SDK", e.stack, e.message);
189
192
  }
190
193
  }
@@ -227,6 +230,12 @@ function startProcess() {
227
230
  return;
228
231
  }
229
232
  let envExtra = {};
233
+ // forward all env starting with RECALL_
234
+ Object.keys(process.env).forEach(key => {
235
+ if (key.startsWith("RECALL_")) {
236
+ envExtra[key] = process.env[key];
237
+ }
238
+ });
230
239
  if (process.platform === "win32" && process.env.GLOBAL_GST_RECALL !== "1") {
231
240
  envExtra["GST_PLUGIN_PATH"] = path.join(path.dirname(exe_path), "gstreamer-1.0");
232
241
  }
@@ -244,6 +253,18 @@ function startProcess() {
244
253
  if (sdk_version) {
245
254
  envExtra["SDK_VERSION"] = sdk_version;
246
255
  }
256
+ if (lastOptions?.testMode) {
257
+ envExtra["TEST_MODE"] = "1";
258
+ }
259
+ if (lastOptions?.testTargetBundleId) {
260
+ envExtra["TEST_TARGET_BUNDLE_ID"] = lastOptions.testTargetBundleId;
261
+ }
262
+ if (lastOptions?.testTargetBundleIdRemapped) {
263
+ envExtra["TEST_TARGET_BUNDLE_ID_REMAP"] = lastOptions.testTargetBundleIdRemapped;
264
+ }
265
+ if (lastOptions?.testSpeedModifier) {
266
+ envExtra["TEST_SPEED_MODIFIER"] = String(lastOptions.testSpeedModifier);
267
+ }
247
268
  const gst_dump_dir = process.env.RECALLAI_DESKTOP_SDK_DEV ? path.join(os.tmpdir(), "gst.nocommit") : os.tmpdir();
248
269
  if (!fs.existsSync(gst_dump_dir)) {
249
270
  try {
@@ -257,7 +278,7 @@ function startProcess() {
257
278
  stdio: (process.platform === "darwin" ? ["pipe", "pipe", "pipe", "pipe"] : "pipe"),
258
279
  env: {
259
280
  GST_RECALL_DEBUG: "2,transcriber:4,rtewebsocketsink:4,rtewebhooksink:4,audiomixer:4,galleryview:4,dsdks3sink:5",
260
- GST_DEBUG: "3,GST_CAPS:5,GST_SCHEDULING:5,GST_PADS:5,video-scaler:1,transcriber:4,filebuffereds3sink:4,seekables3sink:4,rtpsession:1,videodecoder:2,basesink:2,webrtcbin:2,websocketsink:4,audiomixer:4,galleryview:4,removeonsinkeosbin:4,fallbackswitch:6,sendmessageonsinkeosbin:4,dsdks3sink:5",
281
+ GST_DEBUG: "3,GST_CAPS:5,GST_SCHEDULING:5,GST_PADS:5,video-scaler:1,transcriber:4,filebuffereds3sink:4,seekables3sink:4,rtpsession:1,audioresample:1,videodecoder:2,basesink:2,webrtcbin:2,websocketsink:4,audiomixer:4,galleryview:4,removeonsinkeosbin:4,fallbackswitch:6,sendmessageonsinkeosbin:4,dsdks3sink:5",
261
282
  GST_DEBUG_DUMP_DOT_DIR: gst_dump_dir,
262
283
  RUST_BACKTRACE: "1",
263
284
  // "DYLD_INSERT_LIBRARIES":"/opt/homebrew/lib/libjemalloc.dylib",
@@ -404,11 +425,19 @@ async function shutdown() {
404
425
  const result = await sendCommand("shutdown");
405
426
  if (proc) {
406
427
  const currentProc = proc;
407
- setTimeout(() => {
408
- if (!currentProc.killed) {
409
- currentProc.kill();
428
+ await new Promise((resolve) => {
429
+ if (currentProc.exitCode !== null) {
430
+ resolve();
431
+ return;
410
432
  }
411
- }, 5000);
433
+ currentProc.once("close", () => resolve());
434
+ setTimeout(() => {
435
+ if (!currentProc.killed) {
436
+ currentProc.kill();
437
+ }
438
+ resolve();
439
+ }, 5000);
440
+ });
412
441
  }
413
442
  return result;
414
443
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@recallai/desktop-sdk",
3
- "version": "2.0.6",
3
+ "version": "2.0.8",
4
4
  "description": "Recall Desktop SDK",
5
5
  "main": "./index.js",
6
6
  "types": "./index.d.ts",
@@ -20,5 +20,5 @@
20
20
  "@types/node": "^24.2.0",
21
21
  "typescript": "^5.3.3"
22
22
  },
23
- "commit_sha": "7c6147d6d2f3a05c7a2fb7582ea702d7de563b46"
23
+ "commit_sha": "b7a1c938d0de3e558014e49d4e79299e71d84f17"
24
24
  }
package/setup.js CHANGED
@@ -1,6 +1,5 @@
1
1
  const fs = require("fs");
2
2
  const path = require("path");
3
- const tar = require("tar");
4
3
  const { Readable } = require("stream");
5
4
  const { finished } = require("stream/promises");
6
5
 
@@ -39,6 +38,7 @@ async function setupMacOS(version) {
39
38
  }
40
39
 
41
40
  try {
41
+ const tar = require("tar");
42
42
  await tar.extract({ file: nativeTarPathMacOS, cwd: __dirname });
43
43
  } catch (e) {
44
44
  console.error("Error extracting tar file:", e);
@@ -63,6 +63,7 @@ async function setupWin32(version) {
63
63
  }
64
64
 
65
65
  try {
66
+ const tar = require("tar");
66
67
  await tar.extract({ file: nativeTarPathWin32, cwd: __dirname });
67
68
  } catch (e) {
68
69
  console.error("Error extracting tar file:", e);