@dxos/plugin-transcription 0.8.2-staging.7ac8446 → 0.8.2
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/lib/browser/TranscriptContainer-PFKLKRPQ.mjs +11 -0
- package/dist/lib/browser/{chunk-YCZISX63.mjs → chunk-4KCUYW2F.mjs} +139 -95
- package/dist/lib/browser/chunk-4KCUYW2F.mjs.map +7 -0
- package/dist/lib/browser/{chunk-6ZR5MDK3.mjs → chunk-GOF7MJNV.mjs} +3 -3
- package/dist/lib/browser/{chunk-6ZR5MDK3.mjs.map → chunk-GOF7MJNV.mjs.map} +1 -1
- package/dist/lib/browser/{chunk-K7FOYAXO.mjs → chunk-IGEKO7ZU.mjs} +2 -2
- package/dist/lib/browser/chunk-NODIXNQP.mjs +54 -0
- package/dist/lib/browser/chunk-NODIXNQP.mjs.map +7 -0
- package/dist/lib/browser/chunk-TJPJBE45.mjs +764 -0
- package/dist/lib/browser/chunk-TJPJBE45.mjs.map +7 -0
- package/dist/lib/browser/{chunk-YEPT334A.mjs → chunk-W2KNYJD6.mjs} +4 -4
- package/dist/lib/browser/chunk-W2KNYJD6.mjs.map +7 -0
- package/dist/lib/browser/index.mjs +30 -216
- package/dist/lib/browser/index.mjs.map +4 -4
- package/dist/lib/browser/{intent-resolver-4R66ZCKT.mjs → intent-resolver-I2LJSQDR.mjs} +7 -11
- package/dist/lib/browser/intent-resolver-I2LJSQDR.mjs.map +7 -0
- package/dist/lib/browser/meta.json +1 -1
- package/dist/lib/browser/{react-surface-FQUHU5G7.mjs → react-surface-ID2MLJHZ.mjs} +11 -9
- package/dist/lib/browser/react-surface-ID2MLJHZ.mjs.map +7 -0
- package/dist/lib/browser/transcriber-NA7CIFIT.mjs +56 -0
- package/dist/lib/browser/transcriber-NA7CIFIT.mjs.map +7 -0
- package/dist/lib/browser/types/index.mjs +4 -8
- package/dist/lib/node/{TranscriptContainer-QEYTTT2V.cjs → TranscriptContainer-LHMC7553.cjs} +9 -8
- package/dist/lib/node/TranscriptContainer-LHMC7553.cjs.map +7 -0
- package/dist/lib/node/chunk-3GS5UNO5.cjs +778 -0
- package/dist/lib/node/chunk-3GS5UNO5.cjs.map +7 -0
- package/dist/lib/node/{chunk-LP4FG423.cjs → chunk-5J3FBCON.cjs} +5 -5
- package/dist/lib/node/{chunk-NVZWGFJL.cjs → chunk-AFUZI63A.cjs} +6 -6
- package/dist/lib/node/{chunk-NVZWGFJL.cjs.map → chunk-AFUZI63A.cjs.map} +1 -1
- package/dist/lib/node/chunk-EIMUQYCZ.cjs +74 -0
- package/dist/lib/node/chunk-EIMUQYCZ.cjs.map +7 -0
- package/dist/lib/node/{chunk-CZMLKKWT.cjs → chunk-FKDJNJ57.cjs} +8 -8
- package/dist/lib/node/chunk-FKDJNJ57.cjs.map +7 -0
- package/dist/lib/node/{chunk-FCCJALOT.cjs → chunk-ZFTXJZXH.cjs} +138 -95
- package/dist/lib/node/chunk-ZFTXJZXH.cjs.map +7 -0
- package/dist/lib/node/index.cjs +59 -251
- package/dist/lib/node/index.cjs.map +4 -4
- package/dist/lib/node/{intent-resolver-WMMCOUEH.cjs → intent-resolver-LLMGF5I5.cjs} +10 -11
- package/dist/lib/node/intent-resolver-LLMGF5I5.cjs.map +7 -0
- package/dist/lib/node/meta.json +1 -1
- package/dist/lib/node/{react-surface-WI2MGWCC.cjs → react-surface-SEQLEL4K.cjs} +13 -11
- package/dist/lib/node/react-surface-SEQLEL4K.cjs.map +7 -0
- package/dist/lib/node/transcriber-RKKN7LDU.cjs +68 -0
- package/dist/lib/node/transcriber-RKKN7LDU.cjs.map +7 -0
- package/dist/lib/node/types/index.cjs +7 -11
- package/dist/lib/node/types/index.cjs.map +2 -2
- package/dist/lib/node-esm/{TranscriptContainer-ZXUCOWGY.mjs → TranscriptContainer-DLNRFVTA.mjs} +4 -3
- package/dist/lib/node-esm/chunk-BRPFVRAD.mjs +55 -0
- package/dist/lib/node-esm/chunk-BRPFVRAD.mjs.map +7 -0
- package/dist/lib/node-esm/{chunk-YQYBLFNI.mjs → chunk-EFIWBQDF.mjs} +139 -95
- package/dist/lib/node-esm/chunk-EFIWBQDF.mjs.map +7 -0
- package/dist/lib/node-esm/{chunk-J4D2RBBH.mjs → chunk-KUWWHMOA.mjs} +2 -2
- package/dist/lib/node-esm/{chunk-PTZHDZ36.mjs → chunk-MFJPEIVB.mjs} +4 -4
- package/dist/lib/node-esm/chunk-MFJPEIVB.mjs.map +7 -0
- package/dist/lib/node-esm/chunk-PR7EYODX.mjs +765 -0
- package/dist/lib/node-esm/chunk-PR7EYODX.mjs.map +7 -0
- package/dist/lib/node-esm/{chunk-X4DDJIVL.mjs → chunk-TXMDLLBR.mjs} +3 -3
- package/dist/lib/node-esm/{chunk-X4DDJIVL.mjs.map → chunk-TXMDLLBR.mjs.map} +1 -1
- package/dist/lib/node-esm/index.mjs +30 -216
- package/dist/lib/node-esm/index.mjs.map +4 -4
- package/dist/lib/node-esm/{intent-resolver-QN2LO5TX.mjs → intent-resolver-WOZKOEBW.mjs} +7 -11
- package/dist/lib/node-esm/intent-resolver-WOZKOEBW.mjs.map +7 -0
- package/dist/lib/node-esm/meta.json +1 -1
- package/dist/lib/node-esm/{react-surface-PCH6NTVB.mjs → react-surface-7MXUUTAL.mjs} +11 -9
- package/dist/lib/node-esm/react-surface-7MXUUTAL.mjs.map +7 -0
- package/dist/lib/node-esm/transcriber-5WSI6DYK.mjs +57 -0
- package/dist/lib/node-esm/transcriber-5WSI6DYK.mjs.map +7 -0
- package/dist/lib/node-esm/types/index.mjs +4 -8
- package/dist/types/src/TranscriptionPlugin.d.ts.map +1 -1
- package/dist/types/src/capabilities/capabilities.d.ts +8 -10
- package/dist/types/src/capabilities/capabilities.d.ts.map +1 -1
- package/dist/types/src/capabilities/index.d.ts +2 -183
- package/dist/types/src/capabilities/index.d.ts.map +1 -1
- package/dist/types/src/capabilities/intent-resolver.d.ts +2 -2
- package/dist/types/src/capabilities/intent-resolver.d.ts.map +1 -1
- package/dist/types/src/capabilities/react-surface.d.ts.map +1 -1
- package/dist/types/src/capabilities/transcriber.d.ts +2 -1
- package/dist/types/src/capabilities/transcriber.d.ts.map +1 -1
- package/dist/types/src/components/Transcript/Transcript.d.ts +14 -4
- package/dist/types/src/components/Transcript/Transcript.d.ts.map +1 -1
- package/dist/types/src/components/Transcript/Transcript.stories.d.ts +19 -4
- package/dist/types/src/components/Transcript/Transcript.stories.d.ts.map +1 -1
- package/dist/types/src/components/Transcript/deprecated/OldTranscript.d.ts +27 -0
- package/dist/types/src/components/Transcript/deprecated/OldTranscript.d.ts.map +1 -0
- package/dist/types/src/components/Transcript/transcript-extension.d.ts +19 -0
- package/dist/types/src/components/Transcript/transcript-extension.d.ts.map +1 -0
- package/dist/types/src/components/TranscriptContainer.d.ts.map +1 -1
- package/dist/types/src/components/stories/FileTranscription.stories.d.ts +17 -0
- package/dist/types/src/components/stories/FileTranscription.stories.d.ts.map +1 -0
- package/dist/types/src/components/stories/KeyWordRecognition.stories.d.ts +10 -0
- package/dist/types/src/components/stories/KeyWordRecognition.stories.d.ts.map +1 -0
- package/dist/types/src/components/stories/MicrophoneTranscription.stories.d.ts +19 -0
- package/dist/types/src/components/stories/MicrophoneTranscription.stories.d.ts.map +1 -0
- package/dist/types/src/components/stories/TranscriptionStory.d.ts +11 -0
- package/dist/types/src/components/stories/TranscriptionStory.d.ts.map +1 -0
- package/dist/types/src/components/stories/useIsSpeaking.d.ts +3 -0
- package/dist/types/src/components/stories/useIsSpeaking.d.ts.map +1 -0
- package/dist/types/src/hooks/index.d.ts +1 -0
- package/dist/types/src/hooks/index.d.ts.map +1 -1
- package/dist/types/src/hooks/useAudioFile.d.ts +1 -1
- package/dist/types/src/hooks/useAudioFile.d.ts.map +1 -1
- package/dist/types/src/hooks/useAudioTrack.d.ts +1 -1
- package/dist/types/src/hooks/useAudioTrack.d.ts.map +1 -1
- package/dist/types/src/hooks/useQueueModelAdapter.d.ts +7 -0
- package/dist/types/src/hooks/useQueueModelAdapter.d.ts.map +1 -0
- package/dist/types/src/hooks/useTranscriber.d.ts +1 -1
- package/dist/types/src/hooks/useTranscriber.d.ts.map +1 -1
- package/dist/types/src/hooks/useVoiceInput.d.ts.map +1 -1
- package/dist/types/src/model/index.d.ts +2 -0
- package/dist/types/src/model/index.d.ts.map +1 -0
- package/dist/types/src/model/model.d.ts +68 -0
- package/dist/types/src/model/model.d.ts.map +1 -0
- package/dist/types/src/model/model.test.d.ts +2 -0
- package/dist/types/src/model/model.test.d.ts.map +1 -0
- package/dist/types/src/segments-normalization/index.d.ts +4 -0
- package/dist/types/src/segments-normalization/index.d.ts.map +1 -0
- package/dist/types/src/segments-normalization/message-normalizer.d.ts +26 -0
- package/dist/types/src/segments-normalization/message-normalizer.d.ts.map +1 -0
- package/dist/types/src/segments-normalization/normalization.d.ts +520 -0
- package/dist/types/src/segments-normalization/normalization.d.ts.map +1 -0
- package/dist/types/src/segments-normalization/normalization.test.d.ts +2 -0
- package/dist/types/src/segments-normalization/normalization.test.d.ts.map +1 -0
- package/dist/types/src/segments-normalization/utils.d.ts +3 -0
- package/dist/types/src/segments-normalization/utils.d.ts.map +1 -0
- package/dist/types/src/testing/index.d.ts +2 -0
- package/dist/types/src/testing/index.d.ts.map +1 -0
- package/dist/types/src/testing/testing.d.ts +40 -0
- package/dist/types/src/testing/testing.d.ts.map +1 -0
- package/dist/types/src/transcriber/media-stream-recorder.d.ts +8 -5
- package/dist/types/src/transcriber/media-stream-recorder.d.ts.map +1 -1
- package/dist/types/src/transcriber/transcriber.browser.test.d.ts +2 -0
- package/dist/types/src/transcriber/transcriber.browser.test.d.ts.map +1 -0
- package/dist/types/src/transcriber/transcriber.d.ts +6 -2
- package/dist/types/src/transcriber/transcriber.d.ts.map +1 -1
- package/dist/types/src/transcriber/transcription-manager.d.ts +19 -15
- package/dist/types/src/transcriber/transcription-manager.d.ts.map +1 -1
- package/dist/types/src/translations.d.ts +3 -20
- package/dist/types/src/translations.d.ts.map +1 -1
- package/dist/types/src/types/schema.d.ts +23 -40
- package/dist/types/src/types/schema.d.ts.map +1 -1
- package/dist/types/src/types/types.d.ts +15 -8
- package/dist/types/src/types/types.d.ts.map +1 -1
- package/dist/types/src/util/array.d.ts.map +1 -1
- package/dist/types/src/util/get-time-str.d.ts.map +1 -1
- package/dist/types/src/util/index.d.ts +0 -1
- package/dist/types/src/util/index.d.ts.map +1 -1
- package/dist/types/src/util/monitor-audio-level.d.ts.map +1 -1
- package/dist/types/tsconfig.tsbuildinfo +1 -1
- package/package.json +62 -41
- package/src/TranscriptionPlugin.tsx +13 -18
- package/src/capabilities/capabilities.ts +15 -8
- package/src/capabilities/index.ts +0 -2
- package/src/capabilities/intent-resolver.ts +7 -8
- package/src/capabilities/react-surface.tsx +5 -4
- package/src/capabilities/transcriber.ts +34 -6
- package/src/components/Transcript/Transcript.stories.tsx +201 -43
- package/src/components/Transcript/Transcript.tsx +83 -208
- package/src/components/Transcript/deprecated/OldTranscript.tsx +260 -0
- package/src/components/Transcript/transcript-extension.ts +236 -0
- package/src/components/TranscriptContainer.tsx +11 -6
- package/src/components/stories/FileTranscription.stories.tsx +240 -0
- package/src/components/stories/KeyWordRecognition.stories.tsx +128 -0
- package/src/components/stories/MicrophoneTranscription.stories.tsx +274 -0
- package/src/components/stories/TranscriptionStory.tsx +41 -0
- package/src/components/stories/useIsSpeaking.tsx +40 -0
- package/src/hooks/index.ts +1 -0
- package/src/hooks/useAudioFile.ts +39 -9
- package/src/hooks/useAudioTrack.ts +2 -2
- package/src/hooks/useQueueModelAdapter.ts +65 -0
- package/src/hooks/useTranscriber.ts +4 -2
- package/src/meta.ts +2 -2
- package/src/model/index.ts +5 -0
- package/src/model/model.test.ts +169 -0
- package/src/model/model.ts +229 -0
- package/src/segments-normalization/index.ts +7 -0
- package/src/segments-normalization/message-normalizer.ts +108 -0
- package/src/segments-normalization/normalization.test.ts +142 -0
- package/src/segments-normalization/normalization.ts +103 -0
- package/src/segments-normalization/utils.ts +9 -0
- package/src/testing/index.ts +5 -0
- package/src/testing/testing.ts +216 -0
- package/src/transcriber/media-stream-recorder.ts +14 -7
- package/src/transcriber/{transcriber.test.ts → transcriber.browser.test.ts} +7 -7
- package/src/transcriber/transcriber.ts +33 -20
- package/src/transcriber/transcription-manager.ts +87 -71
- package/src/translations.ts +2 -3
- package/src/types/schema.ts +11 -33
- package/src/types/types.ts +8 -12
- package/src/util/index.ts +0 -1
- package/dist/lib/browser/TranscriptContainer-JQ3HFHLQ.mjs +0 -10
- package/dist/lib/browser/app-graph-builder-VDQOVX7P.mjs +0 -191
- package/dist/lib/browser/app-graph-builder-VDQOVX7P.mjs.map +0 -7
- package/dist/lib/browser/chunk-G4B6CPC2.mjs +0 -253
- package/dist/lib/browser/chunk-G4B6CPC2.mjs.map +0 -7
- package/dist/lib/browser/chunk-GU2BNYKZ.mjs +0 -35
- package/dist/lib/browser/chunk-GU2BNYKZ.mjs.map +0 -7
- package/dist/lib/browser/chunk-OGNXNGJB.mjs +0 -73
- package/dist/lib/browser/chunk-OGNXNGJB.mjs.map +0 -7
- package/dist/lib/browser/chunk-YCZISX63.mjs.map +0 -7
- package/dist/lib/browser/chunk-YEPT334A.mjs.map +0 -7
- package/dist/lib/browser/intent-resolver-4R66ZCKT.mjs.map +0 -7
- package/dist/lib/browser/meeting-transcription-state-DLFHQK72.mjs +0 -18
- package/dist/lib/browser/meeting-transcription-state-DLFHQK72.mjs.map +0 -7
- package/dist/lib/browser/react-surface-FQUHU5G7.mjs.map +0 -7
- package/dist/lib/browser/transcriber-LGMIWDYI.mjs +0 -36
- package/dist/lib/browser/transcriber-LGMIWDYI.mjs.map +0 -7
- package/dist/lib/node/TranscriptContainer-QEYTTT2V.cjs.map +0 -7
- package/dist/lib/node/app-graph-builder-IFSIVNUR.cjs +0 -200
- package/dist/lib/node/app-graph-builder-IFSIVNUR.cjs.map +0 -7
- package/dist/lib/node/chunk-3KHUSQNW.cjs +0 -55
- package/dist/lib/node/chunk-3KHUSQNW.cjs.map +0 -7
- package/dist/lib/node/chunk-CZMLKKWT.cjs.map +0 -7
- package/dist/lib/node/chunk-FCCJALOT.cjs.map +0 -7
- package/dist/lib/node/chunk-P4VVD6ZO.cjs +0 -95
- package/dist/lib/node/chunk-P4VVD6ZO.cjs.map +0 -7
- package/dist/lib/node/chunk-UOFHT4GZ.cjs +0 -280
- package/dist/lib/node/chunk-UOFHT4GZ.cjs.map +0 -7
- package/dist/lib/node/intent-resolver-WMMCOUEH.cjs.map +0 -7
- package/dist/lib/node/meeting-transcription-state-URIYILEQ.cjs +0 -34
- package/dist/lib/node/meeting-transcription-state-URIYILEQ.cjs.map +0 -7
- package/dist/lib/node/react-surface-WI2MGWCC.cjs.map +0 -7
- package/dist/lib/node/transcriber-QG5WPKX4.cjs +0 -49
- package/dist/lib/node/transcriber-QG5WPKX4.cjs.map +0 -7
- package/dist/lib/node-esm/app-graph-builder-UL6XLIZY.mjs +0 -192
- package/dist/lib/node-esm/app-graph-builder-UL6XLIZY.mjs.map +0 -7
- package/dist/lib/node-esm/chunk-6X7X2UZF.mjs +0 -254
- package/dist/lib/node-esm/chunk-6X7X2UZF.mjs.map +0 -7
- package/dist/lib/node-esm/chunk-GIO6J6FE.mjs +0 -74
- package/dist/lib/node-esm/chunk-GIO6J6FE.mjs.map +0 -7
- package/dist/lib/node-esm/chunk-HKATMD34.mjs +0 -37
- package/dist/lib/node-esm/chunk-HKATMD34.mjs.map +0 -7
- package/dist/lib/node-esm/chunk-PTZHDZ36.mjs.map +0 -7
- package/dist/lib/node-esm/chunk-YQYBLFNI.mjs.map +0 -7
- package/dist/lib/node-esm/intent-resolver-QN2LO5TX.mjs.map +0 -7
- package/dist/lib/node-esm/meeting-transcription-state-ZYVRAW6Y.mjs +0 -19
- package/dist/lib/node-esm/meeting-transcription-state-ZYVRAW6Y.mjs.map +0 -7
- package/dist/lib/node-esm/react-surface-PCH6NTVB.mjs.map +0 -7
- package/dist/lib/node-esm/transcriber-TMPYZ5L4.mjs +0 -37
- package/dist/lib/node-esm/transcriber-TMPYZ5L4.mjs.map +0 -7
- package/dist/types/src/capabilities/app-graph-builder.d.ts +0 -181
- package/dist/types/src/capabilities/app-graph-builder.d.ts.map +0 -1
- package/dist/types/src/capabilities/meeting-transcription-state.d.ts +0 -6
- package/dist/types/src/capabilities/meeting-transcription-state.d.ts.map +0 -1
- package/dist/types/src/components/transcription.stories.d.ts +0 -15
- package/dist/types/src/components/transcription.stories.d.ts.map +0 -1
- package/dist/types/src/transcriber/transcriber.test.d.ts +0 -2
- package/dist/types/src/transcriber/transcriber.test.d.ts.map +0 -1
- package/dist/types/src/util/random-queue-dxn.d.ts +0 -3
- package/dist/types/src/util/random-queue-dxn.d.ts.map +0 -1
- package/src/capabilities/app-graph-builder.ts +0 -152
- package/src/capabilities/meeting-transcription-state.ts +0 -16
- package/src/components/transcription.stories.tsx +0 -196
- package/src/util/random-queue-dxn.ts +0 -9
- /package/dist/lib/browser/{TranscriptContainer-JQ3HFHLQ.mjs.map → TranscriptContainer-PFKLKRPQ.mjs.map} +0 -0
- /package/dist/lib/browser/{chunk-K7FOYAXO.mjs.map → chunk-IGEKO7ZU.mjs.map} +0 -0
- /package/dist/lib/node/{chunk-LP4FG423.cjs.map → chunk-5J3FBCON.cjs.map} +0 -0
- /package/dist/lib/node-esm/{TranscriptContainer-ZXUCOWGY.mjs.map → TranscriptContainer-DLNRFVTA.mjs.map} +0 -0
- /package/dist/lib/node-esm/{chunk-J4D2RBBH.mjs.map → chunk-KUWWHMOA.mjs.map} +0 -0
|
@@ -1,11 +1,7 @@
|
|
|
1
1
|
import { createRequire } from 'node:module';const require = createRequire(import.meta.url);
|
|
2
2
|
import {
|
|
3
|
-
|
|
4
|
-
} from "./chunk-
|
|
5
|
-
import {
|
|
6
|
-
TRANSCRIPTION_URL,
|
|
7
|
-
TranscriptBlock
|
|
8
|
-
} from "./chunk-GIO6J6FE.mjs";
|
|
3
|
+
TRANSCRIPTION_URL
|
|
4
|
+
} from "./chunk-BRPFVRAD.mjs";
|
|
9
5
|
|
|
10
6
|
// packages/plugins/plugin-transcription/src/transcriber/media-stream-recorder.ts
|
|
11
7
|
import { MediaRecorder, register } from "extendable-media-recorder";
|
|
@@ -27,11 +23,11 @@ var initializeExtendableMediaRecorder = async () => {
|
|
|
27
23
|
await register(await connect());
|
|
28
24
|
};
|
|
29
25
|
var MediaStreamRecorder = class {
|
|
30
|
-
constructor({ mediaStreamTrack,
|
|
26
|
+
constructor({ mediaStreamTrack, config }) {
|
|
31
27
|
this._mediaRecorder = void 0;
|
|
32
28
|
this._header = void 0;
|
|
33
29
|
this._mediaStreamTrack = mediaStreamTrack;
|
|
34
|
-
this.
|
|
30
|
+
this._config = config;
|
|
35
31
|
}
|
|
36
32
|
get wavConfig() {
|
|
37
33
|
const settings = this._mediaStreamTrack.getSettings();
|
|
@@ -52,7 +48,7 @@ var MediaStreamRecorder = class {
|
|
|
52
48
|
err
|
|
53
49
|
}, {
|
|
54
50
|
F: __dxlog_file,
|
|
55
|
-
L:
|
|
51
|
+
L: 69,
|
|
56
52
|
S: this,
|
|
57
53
|
C: (f, a) => f(...a)
|
|
58
54
|
}));
|
|
@@ -69,7 +65,7 @@ var MediaStreamRecorder = class {
|
|
|
69
65
|
}
|
|
70
66
|
invariant(this._onChunk, "MediaStreamRecorder: onChunk is not set", {
|
|
71
67
|
F: __dxlog_file,
|
|
72
|
-
L:
|
|
68
|
+
L: 80,
|
|
73
69
|
S: this,
|
|
74
70
|
A: [
|
|
75
71
|
"this._onChunk",
|
|
@@ -77,7 +73,7 @@ var MediaStreamRecorder = class {
|
|
|
77
73
|
]
|
|
78
74
|
});
|
|
79
75
|
this._mediaRecorder.ondataavailable = (event) => this._ondataavailable(event);
|
|
80
|
-
this._mediaRecorder.start(this.
|
|
76
|
+
this._mediaRecorder.start(this._config.interval);
|
|
81
77
|
}
|
|
82
78
|
async stop() {
|
|
83
79
|
if (this._mediaRecorder?.state !== "recording") {
|
|
@@ -104,7 +100,7 @@ var MediaStreamRecorder = class {
|
|
|
104
100
|
} else {
|
|
105
101
|
log.warn("MediaStreamRecorder: no header", void 0, {
|
|
106
102
|
F: __dxlog_file,
|
|
107
|
-
L:
|
|
103
|
+
L: 111,
|
|
108
104
|
S: this,
|
|
109
105
|
C: (f, a) => f(...a)
|
|
110
106
|
});
|
|
@@ -129,6 +125,19 @@ import { DeferredTask, Trigger } from "@dxos/async";
|
|
|
129
125
|
import { LifecycleState, Resource } from "@dxos/context";
|
|
130
126
|
import { log as log2 } from "@dxos/log";
|
|
131
127
|
import { trace as trace2 } from "@dxos/tracing";
|
|
128
|
+
|
|
129
|
+
// packages/plugins/plugin-transcription/src/util/array.ts
|
|
130
|
+
var mergeFloat64Arrays = (arrays) => {
|
|
131
|
+
const newArray = new Float64Array(arrays.reduce((acc, array) => array.length + acc, 0));
|
|
132
|
+
let offset = 0;
|
|
133
|
+
for (const array of arrays) {
|
|
134
|
+
newArray.set(array, offset);
|
|
135
|
+
offset += array.length;
|
|
136
|
+
}
|
|
137
|
+
return newArray;
|
|
138
|
+
};
|
|
139
|
+
|
|
140
|
+
// packages/plugins/plugin-transcription/src/transcriber/transcriber.ts
|
|
132
141
|
function _ts_decorate2(decorators, target, key, desc) {
|
|
133
142
|
var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
|
|
134
143
|
if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
|
|
@@ -151,17 +160,35 @@ var Transcriber = class extends Resource {
|
|
|
151
160
|
this._onSegments = onSegments;
|
|
152
161
|
}
|
|
153
162
|
async _open(ctx) {
|
|
163
|
+
log2.info("opening", void 0, {
|
|
164
|
+
F: __dxlog_file2,
|
|
165
|
+
L: 101,
|
|
166
|
+
S: this,
|
|
167
|
+
C: (f, a) => f(...a)
|
|
168
|
+
});
|
|
154
169
|
this._recorder.setOnChunk((chunk) => this._saveAudioChunk(chunk));
|
|
155
170
|
await this._recorder.start();
|
|
156
171
|
this._transcribeTask = new DeferredTask(ctx, async () => this._transcribe());
|
|
157
172
|
this._openTrigger.wake();
|
|
158
173
|
}
|
|
159
174
|
async _close() {
|
|
175
|
+
log2.info("closing", void 0, {
|
|
176
|
+
F: __dxlog_file2,
|
|
177
|
+
L: 109,
|
|
178
|
+
S: this,
|
|
179
|
+
C: (f, a) => f(...a)
|
|
180
|
+
});
|
|
160
181
|
this._recording = false;
|
|
161
182
|
this._transcribeTask = void 0;
|
|
162
183
|
await this._recorder.stop();
|
|
163
184
|
}
|
|
164
185
|
startChunksRecording() {
|
|
186
|
+
log2.info("starting", void 0, {
|
|
187
|
+
F: __dxlog_file2,
|
|
188
|
+
L: 116,
|
|
189
|
+
S: this,
|
|
190
|
+
C: (f, a) => f(...a)
|
|
191
|
+
});
|
|
165
192
|
if (this._lifecycleState !== LifecycleState.OPEN) {
|
|
166
193
|
return;
|
|
167
194
|
}
|
|
@@ -173,13 +200,19 @@ var Transcriber = class extends Resource {
|
|
|
173
200
|
}
|
|
174
201
|
this._recording = false;
|
|
175
202
|
this._transcribeTask?.schedule();
|
|
203
|
+
log2.info("stopped", void 0, {
|
|
204
|
+
F: __dxlog_file2,
|
|
205
|
+
L: 131,
|
|
206
|
+
S: this,
|
|
207
|
+
C: (f, a) => f(...a)
|
|
208
|
+
});
|
|
176
209
|
}
|
|
177
210
|
_saveAudioChunk(chunk) {
|
|
178
211
|
log2("saving audio chunk", {
|
|
179
212
|
chunk
|
|
180
213
|
}, {
|
|
181
214
|
F: __dxlog_file2,
|
|
182
|
-
L:
|
|
215
|
+
L: 135,
|
|
183
216
|
S: this,
|
|
184
217
|
C: (f, a) => f(...a)
|
|
185
218
|
});
|
|
@@ -195,7 +228,7 @@ var Transcriber = class extends Resource {
|
|
|
195
228
|
chunks: this._audioChunks.length
|
|
196
229
|
}, {
|
|
197
230
|
F: __dxlog_file2,
|
|
198
|
-
L:
|
|
231
|
+
L: 151,
|
|
199
232
|
S: this,
|
|
200
233
|
C: (f, a) => f(...a)
|
|
201
234
|
});
|
|
@@ -239,15 +272,15 @@ var Transcriber = class extends Resource {
|
|
|
239
272
|
});
|
|
240
273
|
if (!response.ok) {
|
|
241
274
|
this._audioChunks = [];
|
|
242
|
-
throw new Error(
|
|
275
|
+
throw new Error(`Transcription failed: ${response.statusText}`);
|
|
243
276
|
}
|
|
244
277
|
const { segments } = await response.json();
|
|
245
278
|
log2.info("transcription response", {
|
|
246
|
-
segments,
|
|
279
|
+
segments: segments.length,
|
|
247
280
|
string: segments.map((segments2) => segments2.text).join(" ")
|
|
248
281
|
}, {
|
|
249
282
|
F: __dxlog_file2,
|
|
250
|
-
L:
|
|
283
|
+
L: 215,
|
|
251
284
|
S: this,
|
|
252
285
|
C: (f, a) => f(...a)
|
|
253
286
|
});
|
|
@@ -269,8 +302,9 @@ var Transcriber = class extends Resource {
|
|
|
269
302
|
}
|
|
270
303
|
this._lastUsedTimestamp = zeroTimestamp + filteredSegments.at(-1).end * 1e3;
|
|
271
304
|
return filteredSegments.map((segment) => ({
|
|
272
|
-
|
|
273
|
-
|
|
305
|
+
type: "transcription",
|
|
306
|
+
started: new Date(zeroTimestamp + segment.start * 1e3).toISOString(),
|
|
307
|
+
text: segment.text.trim()
|
|
274
308
|
}));
|
|
275
309
|
}
|
|
276
310
|
};
|
|
@@ -286,12 +320,13 @@ _ts_decorate2([
|
|
|
286
320
|
], Transcriber.prototype, "_fetchTranscription", null);
|
|
287
321
|
|
|
288
322
|
// packages/plugins/plugin-transcription/src/transcriber/transcription-manager.ts
|
|
323
|
+
import { signal } from "@preact/signals-core";
|
|
289
324
|
import { synchronized as synchronized2 } from "@dxos/async";
|
|
290
325
|
import { Resource as Resource2 } from "@dxos/context";
|
|
291
326
|
import { QueueImpl } from "@dxos/echo-db";
|
|
292
|
-
import {
|
|
293
|
-
import {
|
|
294
|
-
import {
|
|
327
|
+
import { create } from "@dxos/echo-schema";
|
|
328
|
+
import { log as log3 } from "@dxos/log";
|
|
329
|
+
import { DataType } from "@dxos/schema";
|
|
295
330
|
function _ts_decorate3(decorators, target, key, desc) {
|
|
296
331
|
var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
|
|
297
332
|
if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
|
|
@@ -303,16 +338,16 @@ var RECORD_INTERVAL = 200;
|
|
|
303
338
|
var PREFIXED_CHUNKS_AMOUNT = 10;
|
|
304
339
|
var TRANSCRIBE_AFTER_CHUNKS_AMOUNT = 50;
|
|
305
340
|
var TranscriptionManager = class extends Resource2 {
|
|
306
|
-
constructor(
|
|
341
|
+
constructor(options) {
|
|
307
342
|
super();
|
|
308
343
|
this._audioStreamTrack = void 0;
|
|
309
|
-
this.
|
|
310
|
-
this._hue = void 0;
|
|
344
|
+
this._identityDid = void 0;
|
|
311
345
|
this._mediaRecorder = void 0;
|
|
312
346
|
this._transcriber = void 0;
|
|
313
|
-
this._enabled = false;
|
|
314
347
|
this._queue = void 0;
|
|
315
|
-
this.
|
|
348
|
+
this._enabled = signal(false);
|
|
349
|
+
this._edgeClient = options.edgeClient;
|
|
350
|
+
this._messageEnricher = options.messageEnricher;
|
|
316
351
|
}
|
|
317
352
|
async _open() {
|
|
318
353
|
await this._toggleTranscriber();
|
|
@@ -320,25 +355,50 @@ var TranscriptionManager = class extends Resource2 {
|
|
|
320
355
|
async _close() {
|
|
321
356
|
void this._transcriber?.close();
|
|
322
357
|
}
|
|
358
|
+
/** @reactive */
|
|
359
|
+
get enabled() {
|
|
360
|
+
return this._enabled.value;
|
|
361
|
+
}
|
|
362
|
+
setQueue(queueDxn) {
|
|
363
|
+
if (this._queue?.dxn.toString() !== queueDxn.toString()) {
|
|
364
|
+
log3.info("setQueue", {
|
|
365
|
+
queueDxn: queueDxn.toString()
|
|
366
|
+
}, {
|
|
367
|
+
F: __dxlog_file3,
|
|
368
|
+
L: 80,
|
|
369
|
+
S: this,
|
|
370
|
+
C: (f, a) => f(...a)
|
|
371
|
+
});
|
|
372
|
+
this._queue = new QueueImpl(this._edgeClient, queueDxn);
|
|
373
|
+
}
|
|
374
|
+
return this;
|
|
375
|
+
}
|
|
376
|
+
setIdentityDid(did) {
|
|
377
|
+
if (this._identityDid !== did) {
|
|
378
|
+
this._identityDid = did;
|
|
379
|
+
}
|
|
380
|
+
return this;
|
|
381
|
+
}
|
|
323
382
|
setRecording(recording) {
|
|
324
|
-
if (!this.isOpen || !this._enabled) {
|
|
325
|
-
return;
|
|
383
|
+
if (!this.isOpen || !this._enabled.value) {
|
|
384
|
+
return this;
|
|
326
385
|
}
|
|
327
386
|
if (recording) {
|
|
328
387
|
this._transcriber?.startChunksRecording();
|
|
329
388
|
} else {
|
|
330
389
|
this._transcriber?.stopChunksRecording();
|
|
331
390
|
}
|
|
391
|
+
return this;
|
|
332
392
|
}
|
|
333
393
|
/**
|
|
334
394
|
* Enable or disable transcription.
|
|
335
395
|
* @param enabled - Whether to enable transcription.
|
|
336
396
|
*/
|
|
337
397
|
async setEnabled(enabled) {
|
|
338
|
-
if (this._enabled === enabled) {
|
|
398
|
+
if (this._enabled.value === enabled) {
|
|
339
399
|
return;
|
|
340
400
|
}
|
|
341
|
-
this._enabled = enabled ?? false;
|
|
401
|
+
this._enabled.value = enabled ?? false;
|
|
342
402
|
this.isOpen && await this._toggleTranscriber();
|
|
343
403
|
}
|
|
344
404
|
async setAudioTrack(track) {
|
|
@@ -348,67 +408,58 @@ var TranscriptionManager = class extends Resource2 {
|
|
|
348
408
|
this._audioStreamTrack = track;
|
|
349
409
|
this.isOpen && await this._toggleTranscriber();
|
|
350
410
|
}
|
|
351
|
-
|
|
352
|
-
* Set the queue to save the transcription to.
|
|
353
|
-
* @param queue - The queue to save the transcription to or the DXN of the queue.
|
|
354
|
-
*/
|
|
355
|
-
setQueue(queue) {
|
|
356
|
-
switch (typeof queue) {
|
|
357
|
-
case "string":
|
|
358
|
-
if (this._queue?.dxn.toString() === queue) {
|
|
359
|
-
return;
|
|
360
|
-
}
|
|
361
|
-
this._queue = new QueueImpl(this._edgeClient, DXN.parse(queue));
|
|
362
|
-
break;
|
|
363
|
-
case "object":
|
|
364
|
-
if (this._queue === queue) {
|
|
365
|
-
return;
|
|
366
|
-
}
|
|
367
|
-
invariant2(queue instanceof QueueImpl, void 0, {
|
|
368
|
-
F: __dxlog_file3,
|
|
369
|
-
L: 113,
|
|
370
|
-
S: this,
|
|
371
|
-
A: [
|
|
372
|
-
"queue instanceof QueueImpl",
|
|
373
|
-
""
|
|
374
|
-
]
|
|
375
|
-
});
|
|
376
|
-
this._queue = queue;
|
|
377
|
-
break;
|
|
378
|
-
case "undefined":
|
|
379
|
-
this._queue = void 0;
|
|
380
|
-
break;
|
|
381
|
-
}
|
|
382
|
-
}
|
|
383
|
-
setName(name) {
|
|
384
|
-
if (this._name === name) {
|
|
385
|
-
return;
|
|
386
|
-
}
|
|
387
|
-
this._name = name;
|
|
388
|
-
}
|
|
389
|
-
setHue(hue) {
|
|
390
|
-
if (this._hue === hue) {
|
|
391
|
-
return;
|
|
392
|
-
}
|
|
393
|
-
this._hue = hue;
|
|
394
|
-
}
|
|
411
|
+
// TODO(burdon): Change this to setEnables (explicit), not toggle.
|
|
395
412
|
async _toggleTranscriber() {
|
|
396
413
|
await this._maybeReinitTranscriber();
|
|
397
|
-
if (this._enabled) {
|
|
414
|
+
if (this._enabled.value) {
|
|
398
415
|
await this._transcriber?.open();
|
|
416
|
+
const block = create(DataType.Message, {
|
|
417
|
+
created: (/* @__PURE__ */ new Date()).toISOString(),
|
|
418
|
+
blocks: [
|
|
419
|
+
{
|
|
420
|
+
type: "transcription",
|
|
421
|
+
text: "Started",
|
|
422
|
+
started: (/* @__PURE__ */ new Date()).toISOString()
|
|
423
|
+
}
|
|
424
|
+
],
|
|
425
|
+
sender: {
|
|
426
|
+
role: "assistant"
|
|
427
|
+
}
|
|
428
|
+
});
|
|
429
|
+
this._queue?.append([
|
|
430
|
+
block
|
|
431
|
+
]);
|
|
399
432
|
} else {
|
|
400
433
|
await this._transcriber?.close();
|
|
434
|
+
const block = create(DataType.Message, {
|
|
435
|
+
created: (/* @__PURE__ */ new Date()).toISOString(),
|
|
436
|
+
blocks: [
|
|
437
|
+
{
|
|
438
|
+
type: "transcription",
|
|
439
|
+
text: "Stopped",
|
|
440
|
+
started: (/* @__PURE__ */ new Date()).toISOString()
|
|
441
|
+
}
|
|
442
|
+
],
|
|
443
|
+
sender: {
|
|
444
|
+
role: "assistant"
|
|
445
|
+
}
|
|
446
|
+
});
|
|
447
|
+
this._queue?.append([
|
|
448
|
+
block
|
|
449
|
+
]);
|
|
401
450
|
}
|
|
402
451
|
}
|
|
403
452
|
async _maybeReinitTranscriber() {
|
|
404
|
-
if (!this._audioStreamTrack || !this._enabled) {
|
|
453
|
+
if (!this._audioStreamTrack || !this._enabled.value) {
|
|
405
454
|
return;
|
|
406
455
|
}
|
|
407
456
|
let needReinit = false;
|
|
408
457
|
if (this._audioStreamTrack !== this._mediaRecorder?.mediaStreamTrack) {
|
|
409
458
|
this._mediaRecorder = new MediaStreamRecorder({
|
|
410
459
|
mediaStreamTrack: this._audioStreamTrack,
|
|
411
|
-
|
|
460
|
+
config: {
|
|
461
|
+
interval: RECORD_INTERVAL
|
|
462
|
+
}
|
|
412
463
|
});
|
|
413
464
|
needReinit = true;
|
|
414
465
|
}
|
|
@@ -428,38 +479,31 @@ var TranscriptionManager = class extends Resource2 {
|
|
|
428
479
|
if (!this.isOpen || !this._queue) {
|
|
429
480
|
return;
|
|
430
481
|
}
|
|
431
|
-
|
|
432
|
-
|
|
433
|
-
|
|
434
|
-
|
|
482
|
+
let block = create(DataType.Message, {
|
|
483
|
+
created: (/* @__PURE__ */ new Date()).toISOString(),
|
|
484
|
+
blocks: segments,
|
|
485
|
+
sender: {
|
|
486
|
+
identityDid: this._identityDid
|
|
487
|
+
}
|
|
435
488
|
});
|
|
489
|
+
if (this._messageEnricher) {
|
|
490
|
+
block = await this._messageEnricher(block);
|
|
491
|
+
}
|
|
436
492
|
this._queue.append([
|
|
437
493
|
block
|
|
438
494
|
]);
|
|
439
495
|
}
|
|
440
496
|
};
|
|
441
|
-
_ts_decorate3([
|
|
442
|
-
synchronized2
|
|
443
|
-
], TranscriptionManager.prototype, "setRecording", null);
|
|
444
497
|
_ts_decorate3([
|
|
445
498
|
synchronized2
|
|
446
499
|
], TranscriptionManager.prototype, "setEnabled", null);
|
|
447
500
|
_ts_decorate3([
|
|
448
501
|
synchronized2
|
|
449
502
|
], TranscriptionManager.prototype, "setAudioTrack", null);
|
|
450
|
-
_ts_decorate3([
|
|
451
|
-
synchronized2
|
|
452
|
-
], TranscriptionManager.prototype, "setQueue", null);
|
|
453
|
-
_ts_decorate3([
|
|
454
|
-
synchronized2
|
|
455
|
-
], TranscriptionManager.prototype, "setName", null);
|
|
456
|
-
_ts_decorate3([
|
|
457
|
-
synchronized2
|
|
458
|
-
], TranscriptionManager.prototype, "setHue", null);
|
|
459
503
|
|
|
460
504
|
export {
|
|
461
505
|
MediaStreamRecorder,
|
|
462
506
|
Transcriber,
|
|
463
507
|
TranscriptionManager
|
|
464
508
|
};
|
|
465
|
-
//# sourceMappingURL=chunk-
|
|
509
|
+
//# sourceMappingURL=chunk-EFIWBQDF.mjs.map
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
{
|
|
2
|
+
"version": 3,
|
|
3
|
+
"sources": ["../../../src/transcriber/media-stream-recorder.ts", "../../../src/transcriber/transcriber.ts", "../../../src/util/array.ts", "../../../src/transcriber/transcription-manager.ts"],
|
|
4
|
+
"sourcesContent": ["//\n// Copyright 2025 DXOS.org\n//\n\nimport { type IBlobEvent, type IMediaRecorder, MediaRecorder, register } from 'extendable-media-recorder';\nimport { WaveFile } from 'wavefile';\n\nimport { synchronized } from '@dxos/async';\nimport { invariant } from '@dxos/invariant';\nimport { log } from '@dxos/log';\nimport { trace } from '@dxos/tracing';\n\nimport { type WavConfig, type AudioChunk, type AudioRecorder } from './audio-recorder';\n\nlet initializingPromise: Promise<void> | undefined;\n\nconst initializeExtendableMediaRecorder = async () => {\n const { connect } = await import('extendable-media-recorder-wav-encoder');\n await register(await connect());\n};\n\nexport type MediaStreamRecorderParams = {\n mediaStreamTrack: MediaStreamTrack;\n config: {\n interval: number;\n };\n};\n\n/**\n * Recorder that uses the MediaContext API and AudioNode API to record audio.\n *\n * It records MediaStream using https://www.npmjs.com/package/extendable-media-recorder.\n */\n@trace.resource()\nexport class MediaStreamRecorder implements AudioRecorder {\n private readonly _mediaStreamTrack: MediaStreamTrack;\n /**\n * Default MediaRecorder implementation do not support wav encoding.\n */\n private readonly _config: MediaStreamRecorderParams['config'];\n private _mediaRecorder?: IMediaRecorder = undefined;\n private _header?: Uint8Array = undefined;\n private _onChunk?: (chunk: AudioChunk) => void;\n\n constructor({ mediaStreamTrack, config }: MediaStreamRecorderParams) {\n this._mediaStreamTrack = mediaStreamTrack;\n this._config = config;\n }\n\n get wavConfig(): WavConfig {\n const settings = this._mediaStreamTrack.getSettings();\n return {\n channels: settings.channelCount ?? 1,\n sampleRate: settings.sampleRate ?? 16000,\n bitDepthCode: settings.sampleSize ? String(settings.sampleSize) : '16',\n };\n }\n\n get mediaStreamTrack() {\n return this._mediaStreamTrack;\n }\n\n setOnChunk(onChunk: (chunk: AudioChunk) => void): void {\n this._onChunk = onChunk;\n }\n\n async start(): Promise<void> {\n await (initializingPromise ??= initializeExtendableMediaRecorder()).catch((err) =>\n log.info('initializeExtendableMediaRecorder', { err }),\n );\n\n if (!this._mediaRecorder) {\n const stream = new MediaStream([this._mediaStreamTrack]);\n this._mediaRecorder = new MediaRecorder(stream, { mimeType: 'audio/wav' });\n }\n\n if (this._mediaRecorder.state === 'recording') {\n return;\n }\n invariant(this._onChunk, 'MediaStreamRecorder: onChunk is not set');\n this._mediaRecorder.ondataavailable = (event) => this._ondataavailable(event);\n this._mediaRecorder.start(this._config.interval);\n }\n\n async stop(): Promise<void> {\n if (this._mediaRecorder?.state !== 'recording') {\n return;\n }\n this._mediaRecorder.stop();\n }\n\n @synchronized\n private async _ondataavailable(event: IBlobEvent): Promise<void> {\n const blob = event.data;\n const uint8Array = new Uint8Array(await blob.arrayBuffer());\n\n // First chunk from the MediaRecorder has a header.\n const isHeader =\n uint8Array[0] === 0x52 && // R\n uint8Array[1] === 0x49 && // I\n uint8Array[2] === 0x46 && // F\n uint8Array[3] === 0x46; // F\n let wav: WaveFile;\n\n if (isHeader) {\n wav = new WaveFile(uint8Array);\n this._header = uint8Array.slice(0, 44);\n } else if (this._header) {\n wav = new WaveFile(new Uint8Array([...this._header, ...uint8Array]));\n } else {\n log.warn('MediaStreamRecorder: no header');\n return;\n }\n\n this._onChunk!({\n timestamp: Date.now(),\n data: wav.getSamples(),\n });\n }\n}\n", "//\n// Copyright 2025 DXOS.org\n//\n\nimport { WaveFile } from 'wavefile';\n\nimport { DeferredTask, Trigger } from '@dxos/async';\nimport { type Context, LifecycleState, Resource } from '@dxos/context';\nimport { log } from '@dxos/log';\nimport { type DataType } from '@dxos/schema';\nimport { trace } from '@dxos/tracing';\n\nimport { type AudioRecorder, type AudioChunk } from './audio-recorder';\nimport { TRANSCRIPTION_URL } from '../types';\nimport { mergeFloat64Arrays } from '../util';\n\ntype WhisperWord = {\n word: string;\n\n /**\n * Time in seconds from the start of the audio.\n */\n start: number;\n\n /**\n * Time in seconds from the start of the audio.\n */\n end: number;\n};\n\ntype WhisperSegment = {\n text: string;\n\n /**\n * Time in seconds from the start of the audio.\n */\n start: number;\n\n /**\n * Time in seconds from the start of the audio.\n */\n end: number;\n\n /**\n * Probability of no speech in the segment.\n */\n no_speech_prob: number;\n\n words: WhisperWord[];\n};\n\nexport type TranscribeConfig = {\n /**\n * Number of chunks to transcribe automatically after.\n */\n transcribeAfterChunksAmount: number;\n\n /**\n * Number of chunks to save before the user starts speaking.\n * This is needed to catch the beginning of the user's speech.\n */\n prefixBufferChunksAmount: number;\n};\n\nexport type TranscriberParams = {\n config: TranscribeConfig;\n recorder: AudioRecorder;\n /**\n * Callback to handle the transcribed segments, after all segment transformers are applied.\n * @param segments - The transcribed segments.\n */\n onSegments: (segments: DataType.MessageBlock.Transcription[]) => Promise<void>;\n};\n\n/**\n * Handles transcription of audio chunks.\n * If user is not speaking, the last `minChunksAmount` chunks are saved and transcribed.\n * If user is speaking, the chunks are added to the buffer until the user is done talking.\n */\nexport class Transcriber extends Resource {\n private _audioChunks: AudioChunk[] = [];\n private _lastUsedTimestamp = 0;\n\n private readonly _openTrigger = new Trigger({ autoReset: true });\n\n private readonly _config: TranscribeConfig;\n private readonly _recorder: AudioRecorder;\n private readonly _onSegments: TranscriberParams['onSegments'];\n\n private _recording = false;\n private _transcribeTask?: DeferredTask = undefined;\n\n constructor({ config, recorder, onSegments }: TranscriberParams) {\n super();\n this._config = config;\n this._recorder = recorder;\n this._onSegments = onSegments;\n }\n\n protected override async _open(ctx: Context): Promise<void> {\n log.info('opening');\n this._recorder.setOnChunk((chunk) => this._saveAudioChunk(chunk));\n await this._recorder.start();\n this._transcribeTask = new DeferredTask(ctx, async () => this._transcribe());\n this._openTrigger.wake();\n }\n\n protected override async _close(): Promise<void> {\n log.info('closing');\n this._recording = false;\n this._transcribeTask = undefined;\n await this._recorder.stop();\n }\n\n startChunksRecording(): void {\n log.info('starting');\n if (this._lifecycleState !== LifecycleState.OPEN) {\n return;\n }\n\n this._recording = true;\n }\n\n stopChunksRecording(): void {\n if (this._lifecycleState !== LifecycleState.OPEN || !this._recording) {\n return;\n }\n\n this._recording = false;\n this._transcribeTask?.schedule();\n log.info('stopped');\n }\n\n private _saveAudioChunk(chunk: AudioChunk): void {\n log('saving audio chunk', { chunk });\n this._audioChunks.push(chunk);\n\n // Clean the buffer if the user is not speaking and the transcription task is not scheduled.\n if (\n !this._recording &&\n (!this._transcribeTask || !this._transcribeTask.scheduled) &&\n this._audioChunks.length >= this._config.prefixBufferChunksAmount\n ) {\n this._audioChunks = this._dropOldChunks();\n } else if (this._audioChunks.length >= this._config.transcribeAfterChunksAmount && this._recording) {\n this._transcribeTask?.schedule();\n }\n }\n\n private async _transcribe(): Promise<void> {\n log('transcribing', { chunks: this._audioChunks.length });\n const chunks = this._audioChunks;\n this._audioChunks = this._dropOldChunks();\n if (chunks.length === 0) {\n return;\n }\n\n const audio = await this._mergeAudioChunks(chunks);\n const segments = await this._fetchTranscription(audio);\n if (!Array.isArray(segments) || segments.length === 0) {\n return;\n }\n\n const alignedSegments = this._alignSegments(segments, chunks);\n if (alignedSegments.length > 0) {\n await this._onSegments(alignedSegments);\n }\n }\n\n private _dropOldChunks(): AudioChunk[] {\n return this._config.prefixBufferChunksAmount > 0\n ? this._audioChunks.slice(-this._config.prefixBufferChunksAmount)\n : [];\n }\n\n @trace.span({ showInBrowserTimeline: true })\n private async _mergeAudioChunks(chunks: AudioChunk[]): Promise<string> {\n const file = new WaveFile();\n const wavConfig = this._recorder.wavConfig;\n\n file.fromScratch(\n wavConfig.channels,\n wavConfig.sampleRate,\n wavConfig.bitDepthCode,\n mergeFloat64Arrays(chunks.map(({ data }) => data)),\n );\n\n return file.toBase64();\n }\n\n @trace.span({ showInBrowserTimeline: true })\n private async _fetchTranscription(audio: string): Promise<WhisperSegment[]> {\n if (audio.length === 0) {\n this._audioChunks = [];\n throw new Error('No audio to send for transcribing');\n }\n\n const response = await fetch(`${TRANSCRIPTION_URL}/transcribe`, {\n method: 'POST',\n body: JSON.stringify({ audio }),\n headers: {\n 'Content-Type': 'application/json',\n },\n });\n\n if (!response.ok) {\n this._audioChunks = [];\n throw new Error(`Transcription failed: ${response.statusText}`);\n }\n\n const { segments } = (await response.json()) as {\n segments: WhisperSegment[];\n };\n\n log.info('transcription response', {\n segments: segments.length,\n string: segments.map((segments) => segments.text).join(' '),\n });\n\n return segments;\n }\n\n private _alignSegments(\n segments: WhisperSegment[],\n originalChunks: AudioChunk[],\n ): DataType.MessageBlock.Transcription[] {\n // Absolute zero for all relative timestamps in the segments.\n const zeroTimestamp = originalChunks.at(0)!.timestamp;\n\n const filteredSegments = segments\n // Use segments that end after the last used timestamp.\n // Segments could overlap, so we need to filter words that starts after the last used timestamp.\n .filter((segment) => zeroTimestamp + segment.end * 1_000 >= this._lastUsedTimestamp)\n // Use words that starts after the last used timestamp.\n .map((segment) => {\n const words = segment.words.filter((word) => zeroTimestamp + word.start * 1_000 >= this._lastUsedTimestamp);\n return {\n ...segment,\n words,\n text: words.map((word) => word.word).join(''),\n start: words.at(0)?.start ?? segment.end,\n };\n })\n .filter((segment) => segment.words.length > 0);\n\n if (filteredSegments.length === 0) {\n return [];\n }\n\n // Update last timestamp.\n this._lastUsedTimestamp = zeroTimestamp + filteredSegments.at(-1)!.end * 1_000;\n\n // Add absolute timestamp to each segment.\n return filteredSegments.map((segment) => ({\n type: 'transcription',\n started: new Date(zeroTimestamp + segment.start * 1_000).toISOString(),\n text: segment.text.trim(),\n }));\n }\n}\n", "//\n// Copyright 2025 DXOS.org\n//\n\nexport const mergeFloat64Arrays = (arrays: Float64Array[]) => {\n const newArray = new Float64Array(arrays.reduce((acc, array) => array.length + acc, 0));\n let offset = 0;\n for (const array of arrays) {\n newArray.set(array, offset);\n offset += array.length;\n }\n\n return newArray;\n};\n", "//\n// Copyright 2025 DXOS.org\n//\n\nimport { signal } from '@preact/signals-core';\n\nimport { synchronized } from '@dxos/async';\nimport { Resource } from '@dxos/context';\nimport { QueueImpl, type Queue } from '@dxos/echo-db';\nimport { create } from '@dxos/echo-schema';\nimport { type DXN } from '@dxos/keys';\nimport { log } from '@dxos/log';\nimport { type EdgeHttpClient } from '@dxos/react-edge-client';\nimport { DataType } from '@dxos/schema';\n\nimport { MediaStreamRecorder } from './media-stream-recorder';\nimport { Transcriber } from './transcriber';\n\n/**\n * Length of the chunk in ms.\n */\nconst RECORD_INTERVAL = 200;\n\n/**\n * Number of chunks to save before the user starts speaking.\n */\nconst PREFIXED_CHUNKS_AMOUNT = 10;\n\n/**\n * Number of chunks to transcribe automatically after.\n * Combined should be mess than 25MB or whisper would fail.\n */\nconst TRANSCRIBE_AFTER_CHUNKS_AMOUNT = 50;\n\nexport type TranscriptMessageEnricher = (message: DataType.Message) => Promise<DataType.Message>;\n\nexport type TranscriptionManagerOptions = {\n edgeClient: EdgeHttpClient;\n\n /**\n * Enrich the message before it is written to the transcription queue.\n */\n messageEnricher?: TranscriptMessageEnricher;\n};\n\n/**\n * Manages transcription state for a meeting.\n */\nexport class TranscriptionManager extends Resource {\n private readonly _edgeClient: EdgeHttpClient;\n private readonly _messageEnricher?: TranscriptMessageEnricher;\n private _audioStreamTrack?: MediaStreamTrack = undefined;\n private _identityDid?: string = undefined;\n private _mediaRecorder?: MediaStreamRecorder = undefined;\n private _transcriber?: Transcriber = undefined;\n private _queue?: Queue<DataType.Message> = undefined;\n private _enabled = signal(false);\n\n constructor(options: TranscriptionManagerOptions) {\n super();\n this._edgeClient = options.edgeClient;\n this._messageEnricher = options.messageEnricher;\n }\n\n protected override async _open(): Promise<void> {\n await this._toggleTranscriber();\n }\n\n protected override async _close(): Promise<void> {\n void this._transcriber?.close();\n }\n\n /** @reactive */\n get enabled() {\n return this._enabled.value;\n }\n\n setQueue(queueDxn: DXN): TranscriptionManager {\n if (this._queue?.dxn.toString() !== queueDxn.toString()) {\n log.info('setQueue', { queueDxn: queueDxn.toString() });\n this._queue = new QueueImpl<DataType.Message>(this._edgeClient, queueDxn);\n }\n return this;\n }\n\n setIdentityDid(did: string): TranscriptionManager {\n if (this._identityDid !== did) {\n this._identityDid = did;\n }\n return this;\n }\n\n setRecording(recording?: boolean): TranscriptionManager {\n if (!this.isOpen || !this._enabled.value) {\n return this;\n }\n\n if (recording) {\n this._transcriber?.startChunksRecording();\n } else {\n this._transcriber?.stopChunksRecording();\n }\n return this;\n }\n\n /**\n * Enable or disable transcription.\n * @param enabled - Whether to enable transcription.\n */\n @synchronized\n async setEnabled(enabled?: boolean): Promise<void> {\n if (this._enabled.value === enabled) {\n return;\n }\n\n this._enabled.value = enabled ?? false;\n // TODO(burdon): Why is toggle called here?\n this.isOpen && (await this._toggleTranscriber());\n }\n\n @synchronized\n async setAudioTrack(track?: MediaStreamTrack): Promise<void> {\n if (this._audioStreamTrack === track) {\n return;\n }\n\n this._audioStreamTrack = track;\n this.isOpen && (await this._toggleTranscriber());\n }\n\n // TODO(burdon): Change this to setEnables (explicit), not toggle.\n private async _toggleTranscriber(): Promise<void> {\n await this._maybeReinitTranscriber();\n\n // Open or close transcriber if transcription is enabled or disabled.\n if (this._enabled.value) {\n await this._transcriber?.open();\n // TODO(burdon): Started and stopped blocks appear twice.\n const block = create(DataType.Message, {\n created: new Date().toISOString(),\n blocks: [{ type: 'transcription', text: 'Started', started: new Date().toISOString() }],\n sender: { role: 'assistant' },\n });\n this._queue?.append([block]);\n } else {\n await this._transcriber?.close();\n const block = create(DataType.Message, {\n created: new Date().toISOString(),\n blocks: [{ type: 'transcription', text: 'Stopped', started: new Date().toISOString() }],\n sender: { role: 'assistant' },\n });\n this._queue?.append([block]);\n }\n }\n\n private async _maybeReinitTranscriber(): Promise<void> {\n if (!this._audioStreamTrack || !this._enabled.value) {\n return;\n }\n\n // Reinitialize transcriber if queue or media stream track has changed.\n let needReinit = false;\n if (this._audioStreamTrack !== this._mediaRecorder?.mediaStreamTrack) {\n this._mediaRecorder = new MediaStreamRecorder({\n mediaStreamTrack: this._audioStreamTrack,\n config: { interval: RECORD_INTERVAL },\n });\n needReinit = true;\n }\n if (needReinit) {\n await this._transcriber?.close();\n this._transcriber = new Transcriber({\n config: {\n transcribeAfterChunksAmount: TRANSCRIBE_AFTER_CHUNKS_AMOUNT,\n prefixBufferChunksAmount: PREFIXED_CHUNKS_AMOUNT,\n },\n recorder: this._mediaRecorder,\n onSegments: (segments) => this._onSegments(segments),\n });\n }\n }\n\n private async _onSegments(segments: DataType.MessageBlock.Transcription[]): Promise<void> {\n if (!this.isOpen || !this._queue) {\n return;\n }\n\n let block = create(DataType.Message, {\n created: new Date().toISOString(),\n blocks: segments,\n sender: { identityDid: this._identityDid },\n });\n\n if (this._messageEnricher) {\n block = await this._messageEnricher(block);\n }\n\n this._queue.append([block]);\n }\n}\n"],
|
|
5
|
+
"mappings": "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",
|
|
6
|
+
"names": ["MediaRecorder", "register", "WaveFile", "synchronized", "invariant", "log", "trace", "initializingPromise", "initializeExtendableMediaRecorder", "connect", "MediaStreamRecorder", "mediaStreamTrack", "config", "_mediaRecorder", "undefined", "_header", "_mediaStreamTrack", "_config", "wavConfig", "settings", "getSettings", "channels", "channelCount", "sampleRate", "bitDepthCode", "sampleSize", "String", "setOnChunk", "onChunk", "_onChunk", "start", "catch", "err", "info", "stream", "MediaStream", "mimeType", "state", "ondataavailable", "event", "_ondataavailable", "interval", "stop", "blob", "data", "uint8Array", "Uint8Array", "arrayBuffer", "isHeader", "wav", "slice", "warn", "timestamp", "Date", "now", "getSamples", "resource", "WaveFile", "DeferredTask", "Trigger", "LifecycleState", "Resource", "log", "trace", "mergeFloat64Arrays", "arrays", "newArray", "Float64Array", "reduce", "acc", "array", "length", "offset", "set", "Transcriber", "Resource", "config", "recorder", "onSegments", "_audioChunks", "_lastUsedTimestamp", "_openTrigger", "Trigger", "autoReset", "_recording", "_transcribeTask", "undefined", "_config", "_recorder", "_onSegments", "_open", "ctx", "log", "info", "setOnChunk", "chunk", "_saveAudioChunk", "start", "DeferredTask", "_transcribe", "wake", "_close", "stop", "startChunksRecording", "_lifecycleState", "LifecycleState", "OPEN", "stopChunksRecording", "schedule", "push", "scheduled", "length", "prefixBufferChunksAmount", "_dropOldChunks", "transcribeAfterChunksAmount", "chunks", "audio", "_mergeAudioChunks", "segments", "_fetchTranscription", "Array", "isArray", "alignedSegments", "_alignSegments", "slice", "file", "WaveFile", "wavConfig", "fromScratch", "channels", "sampleRate", "bitDepthCode", "mergeFloat64Arrays", "map", "data", "toBase64", "Error", "response", "fetch", "TRANSCRIPTION_URL", "method", "body", "JSON", "stringify", "headers", "ok", "statusText", "json", "string", "text", "join", "originalChunks", "zeroTimestamp", "at", "timestamp", "filteredSegments", "filter", "segment", "end", "words", "word", "type", "started", "Date", "toISOString", "trim", "span", "showInBrowserTimeline", "signal", "synchronized", "Resource", "QueueImpl", "create", "log", "DataType", "RECORD_INTERVAL", "PREFIXED_CHUNKS_AMOUNT", "TRANSCRIBE_AFTER_CHUNKS_AMOUNT", "TranscriptionManager", "Resource", "options", "_audioStreamTrack", "undefined", "_identityDid", "_mediaRecorder", "_transcriber", "_queue", "_enabled", "signal", "_edgeClient", "edgeClient", "_messageEnricher", "messageEnricher", "_open", "_toggleTranscriber", "_close", "close", "enabled", "value", "setQueue", "queueDxn", "dxn", "toString", "log", "info", "QueueImpl", "setIdentityDid", "did", "setRecording", "recording", "isOpen", "startChunksRecording", "stopChunksRecording", "setEnabled", "setAudioTrack", "track", "_maybeReinitTranscriber", "open", "block", "create", "DataType", "Message", "created", "Date", "toISOString", "blocks", "type", "text", "started", "sender", "role", "append", "needReinit", "mediaStreamTrack", "MediaStreamRecorder", "config", "interval", "Transcriber", "transcribeAfterChunksAmount", "prefixBufferChunksAmount", "recorder", "onSegments", "segments", "_onSegments", "identityDid"]
|
|
7
|
+
}
|
|
@@ -2,9 +2,9 @@ import { createRequire } from 'node:module';const require = createRequire(import
|
|
|
2
2
|
|
|
3
3
|
// packages/plugins/plugin-transcription/src/components/index.ts
|
|
4
4
|
import { lazy } from "react";
|
|
5
|
-
var TranscriptContainer = lazy(() => import("./TranscriptContainer-
|
|
5
|
+
var TranscriptContainer = lazy(() => import("./TranscriptContainer-DLNRFVTA.mjs"));
|
|
6
6
|
|
|
7
7
|
export {
|
|
8
8
|
TranscriptContainer
|
|
9
9
|
};
|
|
10
|
-
//# sourceMappingURL=chunk-
|
|
10
|
+
//# sourceMappingURL=chunk-KUWWHMOA.mjs.map
|
|
@@ -1,17 +1,17 @@
|
|
|
1
1
|
import { createRequire } from 'node:module';const require = createRequire(import.meta.url);
|
|
2
2
|
import {
|
|
3
3
|
TRANSCRIPTION_PLUGIN
|
|
4
|
-
} from "./chunk-
|
|
4
|
+
} from "./chunk-TXMDLLBR.mjs";
|
|
5
5
|
|
|
6
6
|
// packages/plugins/plugin-transcription/src/capabilities/capabilities.ts
|
|
7
7
|
import { defineCapability } from "@dxos/app-framework";
|
|
8
|
-
var TranscriptionCapabilities;
|
|
9
8
|
(function(TranscriptionCapabilities2) {
|
|
10
9
|
TranscriptionCapabilities2.Transcriber = defineCapability(`${TRANSCRIPTION_PLUGIN}/capability/transcriber`);
|
|
11
|
-
TranscriptionCapabilities2.
|
|
10
|
+
TranscriptionCapabilities2.TranscriptionManager = defineCapability(`${TRANSCRIPTION_PLUGIN}/capability/transcription-manager`);
|
|
12
11
|
})(TranscriptionCapabilities || (TranscriptionCapabilities = {}));
|
|
12
|
+
var TranscriptionCapabilities;
|
|
13
13
|
|
|
14
14
|
export {
|
|
15
15
|
TranscriptionCapabilities
|
|
16
16
|
};
|
|
17
|
-
//# sourceMappingURL=chunk-
|
|
17
|
+
//# sourceMappingURL=chunk-MFJPEIVB.mjs.map
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
{
|
|
2
|
+
"version": 3,
|
|
3
|
+
"sources": ["../../../src/capabilities/capabilities.ts"],
|
|
4
|
+
"sourcesContent": ["//\n// Copyright 2025 DXOS.org\n//\n\nimport { defineCapability } from '@dxos/app-framework';\n\nimport { TRANSCRIPTION_PLUGIN } from '../meta';\nimport {\n type TranscriberParams,\n type Transcriber,\n type TranscriptionManager,\n type TranscriptMessageEnricher,\n type MediaStreamRecorderParams,\n} from '../transcriber';\n\nexport namespace TranscriptionCapabilities {\n export type GetTranscriberProps = {\n audioStreamTrack: MediaStreamTrack;\n onSegments: TranscriberParams['onSegments'];\n transcriberConfig?: Partial<TranscriberParams['config']>;\n recorderConfig?: Partial<MediaStreamRecorderParams['config']>;\n };\n export type GetTranscriber = (props: GetTranscriberProps) => Transcriber;\n export const Transcriber = defineCapability<GetTranscriber>(`${TRANSCRIPTION_PLUGIN}/capability/transcriber`);\n\n export type GetTranscriptionManagerProps = {\n messageEnricher?: TranscriptMessageEnricher;\n };\n export type GetTranscriptionManager = (props: GetTranscriptionManagerProps) => TranscriptionManager;\n export const TranscriptionManager = defineCapability<GetTranscriptionManager>(\n `${TRANSCRIPTION_PLUGIN}/capability/transcription-manager`,\n );\n}\n"],
|
|
5
|
+
"mappings": ";;;;;;AAIA,SAASA,wBAAwB;UAWhBC,4BAAAA;6BAQFC,cAAcC,iBAAiC,GAAGC,oBAAAA,yBAA6C;6BAM/FC,uBAAuBF,iBAClC,GAAGC,oBAAAA,mCAAuD;AAE9D,GAjBiBH,8BAAAA,4BAAAA,CAAAA,EAAAA;;",
|
|
6
|
+
"names": ["defineCapability", "TranscriptionCapabilities", "Transcriber", "defineCapability", "TRANSCRIPTION_PLUGIN", "TranscriptionManager"]
|
|
7
|
+
}
|