assemblyai 4.5.0-beta.0 → 4.6.0
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 +41 -0
- package/README.md +53 -9
- package/dist/assemblyai.streaming.umd.js +317 -0
- package/dist/assemblyai.streaming.umd.min.js +1 -0
- package/dist/assemblyai.umd.js +160 -12
- package/dist/assemblyai.umd.min.js +1 -1
- package/dist/browser.mjs +154 -11
- package/dist/bun.mjs +154 -11
- package/dist/deno.mjs +154 -11
- package/dist/exports/index.d.ts +2 -0
- package/dist/exports/streaming.d.ts +4 -0
- package/dist/index.cjs +160 -12
- package/dist/index.mjs +160 -12
- package/dist/node.cjs +154 -11
- package/dist/node.mjs +154 -11
- package/dist/polyfills/fetch/default.d.ts +1 -0
- package/dist/polyfills/fetch/workerd.d.ts +1 -0
- package/dist/services/base.d.ts +1 -0
- package/dist/services/lemur/index.d.ts +8 -1
- package/dist/services/realtime/service.d.ts +60 -0
- package/dist/services/transcripts/index.d.ts +16 -3
- package/dist/streaming.browser.mjs +268 -0
- package/dist/streaming.cjs +306 -0
- package/dist/streaming.mjs +303 -0
- package/dist/types/index.d.ts +7 -0
- package/dist/types/openapi.generated.d.ts +75 -29
- package/dist/types/services/index.d.ts +7 -0
- package/dist/types/transcripts/index.d.ts +9 -0
- package/dist/utils/userAgent.d.ts +2 -0
- package/dist/workerd.mjs +751 -0
- package/docs/reference-types-from-js.md +27 -0
- package/package.json +57 -25
- package/src/exports/index.ts +2 -0
- package/src/exports/streaming.ts +4 -0
- package/src/polyfills/fetch/default.ts +3 -0
- package/src/polyfills/fetch/workerd.ts +1 -0
- package/src/services/base.ts +27 -7
- package/src/services/files/index.ts +19 -2
- package/src/services/index.ts +2 -1
- package/src/services/lemur/index.ts +12 -0
- package/src/services/realtime/service.ts +65 -0
- package/src/services/transcripts/index.ts +41 -4
- package/src/types/index.ts +9 -0
- package/src/types/openapi.generated.ts +224 -48
- package/src/types/services/index.ts +8 -0
- package/src/types/transcripts/index.ts +10 -0
- package/src/utils/path.ts +1 -0
- package/src/utils/userAgent.ts +51 -0
package/dist/assemblyai.umd.js
CHANGED
|
@@ -48,6 +48,45 @@
|
|
|
48
48
|
return e.name = "SuppressedError", e.error = error, e.suppressed = suppressed, e;
|
|
49
49
|
};
|
|
50
50
|
|
|
51
|
+
const DEFAULT_FETCH_INIT = {
|
|
52
|
+
cache: "no-store",
|
|
53
|
+
};
|
|
54
|
+
|
|
55
|
+
const buildUserAgent = (userAgent) => defaultUserAgentString +
|
|
56
|
+
(userAgent === false
|
|
57
|
+
? ""
|
|
58
|
+
: " AssemblyAI/1.0 (" +
|
|
59
|
+
Object.entries(Object.assign(Object.assign({}, defaultUserAgent), userAgent))
|
|
60
|
+
.map(([key, item]) => item ? `${key}=${item.name}/${item.version}` : "")
|
|
61
|
+
.join(" ") +
|
|
62
|
+
")");
|
|
63
|
+
let defaultUserAgentString = "";
|
|
64
|
+
if (typeof navigator !== "undefined" && navigator.userAgent) {
|
|
65
|
+
defaultUserAgentString += navigator.userAgent;
|
|
66
|
+
}
|
|
67
|
+
const defaultUserAgent = {
|
|
68
|
+
sdk: { name: "JavaScript", version: "4.6.0" },
|
|
69
|
+
};
|
|
70
|
+
if (typeof process !== "undefined") {
|
|
71
|
+
if (process.versions.node && defaultUserAgentString.indexOf("Node") === -1) {
|
|
72
|
+
defaultUserAgent.runtime_env = {
|
|
73
|
+
name: "Node",
|
|
74
|
+
version: process.versions.node,
|
|
75
|
+
};
|
|
76
|
+
}
|
|
77
|
+
if (process.versions.bun && defaultUserAgentString.indexOf("Bun") === -1) {
|
|
78
|
+
defaultUserAgent.runtime_env = {
|
|
79
|
+
name: "Bun",
|
|
80
|
+
version: process.versions.bun,
|
|
81
|
+
};
|
|
82
|
+
}
|
|
83
|
+
}
|
|
84
|
+
if (typeof Deno !== "undefined") {
|
|
85
|
+
if (process.versions.bun && defaultUserAgentString.indexOf("Deno") === -1) {
|
|
86
|
+
defaultUserAgent.runtime_env = { name: "Deno", version: Deno.version.deno };
|
|
87
|
+
}
|
|
88
|
+
}
|
|
89
|
+
|
|
51
90
|
/**
|
|
52
91
|
* Base class for services that communicate with the API.
|
|
53
92
|
*/
|
|
@@ -58,13 +97,33 @@
|
|
|
58
97
|
*/
|
|
59
98
|
constructor(params) {
|
|
60
99
|
this.params = params;
|
|
100
|
+
if (params.userAgent === false) {
|
|
101
|
+
this.userAgent = undefined;
|
|
102
|
+
}
|
|
103
|
+
else {
|
|
104
|
+
this.userAgent = buildUserAgent(params.userAgent || {});
|
|
105
|
+
}
|
|
61
106
|
}
|
|
62
107
|
fetch(input, init) {
|
|
63
108
|
return __awaiter(this, void 0, void 0, function* () {
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
109
|
+
init = Object.assign(Object.assign({}, DEFAULT_FETCH_INIT), init);
|
|
110
|
+
let headers = {
|
|
111
|
+
Authorization: this.params.apiKey,
|
|
112
|
+
"Content-Type": "application/json",
|
|
113
|
+
};
|
|
114
|
+
if (DEFAULT_FETCH_INIT === null || DEFAULT_FETCH_INIT === void 0 ? void 0 : DEFAULT_FETCH_INIT.headers)
|
|
115
|
+
headers = Object.assign(Object.assign({}, headers), DEFAULT_FETCH_INIT.headers);
|
|
116
|
+
if (init === null || init === void 0 ? void 0 : init.headers)
|
|
117
|
+
headers = Object.assign(Object.assign({}, headers), init.headers);
|
|
118
|
+
if (this.userAgent) {
|
|
119
|
+
headers["User-Agent"] = this.userAgent;
|
|
120
|
+
// chromium browsers have a bug where the user agent can't be modified
|
|
121
|
+
if (typeof window !== "undefined" && "chrome" in window) {
|
|
122
|
+
headers["AssemblyAI-Agent"] =
|
|
123
|
+
this.userAgent;
|
|
124
|
+
}
|
|
125
|
+
}
|
|
126
|
+
init.headers = headers;
|
|
68
127
|
if (!input.startsWith("http"))
|
|
69
128
|
input = this.params.baseUrl + input;
|
|
70
129
|
const response = yield fetch(input, init);
|
|
@@ -75,7 +134,7 @@
|
|
|
75
134
|
try {
|
|
76
135
|
json = JSON.parse(text);
|
|
77
136
|
}
|
|
78
|
-
catch (
|
|
137
|
+
catch (_a) {
|
|
79
138
|
/* empty */
|
|
80
139
|
}
|
|
81
140
|
if (json === null || json === void 0 ? void 0 : json.error)
|
|
@@ -120,6 +179,9 @@
|
|
|
120
179
|
body: JSON.stringify(params),
|
|
121
180
|
});
|
|
122
181
|
}
|
|
182
|
+
getResponse(id) {
|
|
183
|
+
return this.fetchJson(`/lemur/v3/${id}`);
|
|
184
|
+
}
|
|
123
185
|
/**
|
|
124
186
|
* Delete the data for a previously submitted LeMUR request.
|
|
125
187
|
* @param id - ID of the LeMUR request
|
|
@@ -190,7 +252,14 @@
|
|
|
190
252
|
const defaultRealtimeUrl = "wss://api.assemblyai.com/v2/realtime/ws";
|
|
191
253
|
const forceEndOfUtteranceMessage = `{"force_end_utterance":true}`;
|
|
192
254
|
const terminateSessionMessage = `{"terminate_session":true}`;
|
|
255
|
+
/**
|
|
256
|
+
* RealtimeTranscriber connects to the Streaming Speech-to-Text API and lets you transcribe audio in real-time.
|
|
257
|
+
*/
|
|
193
258
|
class RealtimeTranscriber {
|
|
259
|
+
/**
|
|
260
|
+
* Create a new RealtimeTranscriber.
|
|
261
|
+
* @param params - Parameters to configure the RealtimeTranscriber
|
|
262
|
+
*/
|
|
194
263
|
constructor(params) {
|
|
195
264
|
var _a, _b;
|
|
196
265
|
this.listeners = {};
|
|
@@ -231,10 +300,19 @@
|
|
|
231
300
|
url.search = searchParams.toString();
|
|
232
301
|
return url;
|
|
233
302
|
}
|
|
303
|
+
/**
|
|
304
|
+
* Add a listener for an event.
|
|
305
|
+
* @param event - The event to listen for.
|
|
306
|
+
* @param listener - The function to call when the event is emitted.
|
|
307
|
+
*/
|
|
234
308
|
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
235
309
|
on(event, listener) {
|
|
236
310
|
this.listeners[event] = listener;
|
|
237
311
|
}
|
|
312
|
+
/**
|
|
313
|
+
* Connect to the server and begin a new session.
|
|
314
|
+
* @returns A promise that resolves when the connection is established and the session begins.
|
|
315
|
+
*/
|
|
238
316
|
connect() {
|
|
239
317
|
return new Promise((resolve) => {
|
|
240
318
|
if (this.socket) {
|
|
@@ -316,9 +394,17 @@
|
|
|
316
394
|
};
|
|
317
395
|
});
|
|
318
396
|
}
|
|
397
|
+
/**
|
|
398
|
+
* Send audio data to the server.
|
|
399
|
+
* @param audio - The audio data to send to the server.
|
|
400
|
+
*/
|
|
319
401
|
sendAudio(audio) {
|
|
320
402
|
this.send(audio);
|
|
321
403
|
}
|
|
404
|
+
/**
|
|
405
|
+
* Create a writable stream that can be used to send audio data to the server.
|
|
406
|
+
* @returns A writable stream that can be used to send audio data to the server.
|
|
407
|
+
*/
|
|
322
408
|
stream() {
|
|
323
409
|
return new WritableStream({
|
|
324
410
|
write: (chunk) => {
|
|
@@ -346,6 +432,11 @@
|
|
|
346
432
|
}
|
|
347
433
|
this.socket.send(data);
|
|
348
434
|
}
|
|
435
|
+
/**
|
|
436
|
+
* Close the connection to the server.
|
|
437
|
+
* @param waitForSessionTermination - If true, the method will wait for the session to be terminated before closing the connection.
|
|
438
|
+
* While waiting for the session to be terminated, you will receive the final transcript and session information.
|
|
439
|
+
*/
|
|
349
440
|
close() {
|
|
350
441
|
return __awaiter(this, arguments, void 0, function* (waitForSessionTermination = true) {
|
|
351
442
|
var _a;
|
|
@@ -416,6 +507,8 @@
|
|
|
416
507
|
return null;
|
|
417
508
|
if (path.startsWith("https"))
|
|
418
509
|
return null;
|
|
510
|
+
if (path.startsWith("data:"))
|
|
511
|
+
return null;
|
|
419
512
|
if (path.startsWith("file://"))
|
|
420
513
|
return path.substring(7);
|
|
421
514
|
if (path.startsWith("file:"))
|
|
@@ -460,8 +553,13 @@
|
|
|
460
553
|
audioUrl = yield this.files.upload(path);
|
|
461
554
|
}
|
|
462
555
|
else {
|
|
463
|
-
|
|
464
|
-
|
|
556
|
+
if (audio.startsWith("data:")) {
|
|
557
|
+
audioUrl = yield this.files.upload(audio);
|
|
558
|
+
}
|
|
559
|
+
else {
|
|
560
|
+
// audio is not a local path, and not a data-URI, assume it's a normal URL
|
|
561
|
+
audioUrl = audio;
|
|
562
|
+
}
|
|
465
563
|
}
|
|
466
564
|
}
|
|
467
565
|
else {
|
|
@@ -626,13 +724,45 @@
|
|
|
626
724
|
});
|
|
627
725
|
}
|
|
628
726
|
/**
|
|
629
|
-
* Retrieve
|
|
727
|
+
* Retrieve the redacted audio URL of a transcript.
|
|
630
728
|
* @param id - The identifier of the transcript.
|
|
631
|
-
* @returns A promise that resolves to the
|
|
729
|
+
* @returns A promise that resolves to the details of the redacted audio.
|
|
730
|
+
* @deprecated Use `redactedAudio` instead.
|
|
632
731
|
*/
|
|
633
732
|
redactions(id) {
|
|
733
|
+
return this.redactedAudio(id);
|
|
734
|
+
}
|
|
735
|
+
/**
|
|
736
|
+
* Retrieve the redacted audio URL of a transcript.
|
|
737
|
+
* @param id - The identifier of the transcript.
|
|
738
|
+
* @returns A promise that resolves to the details of the redacted audio.
|
|
739
|
+
*/
|
|
740
|
+
redactedAudio(id) {
|
|
634
741
|
return this.fetchJson(`/v2/transcript/${id}/redacted-audio`);
|
|
635
742
|
}
|
|
743
|
+
/**
|
|
744
|
+
* Retrieve the redacted audio file of a transcript.
|
|
745
|
+
* @param id - The identifier of the transcript.
|
|
746
|
+
* @returns A promise that resolves to the fetch HTTP response of the redacted audio file.
|
|
747
|
+
*/
|
|
748
|
+
redactedAudioFile(id) {
|
|
749
|
+
return __awaiter(this, void 0, void 0, function* () {
|
|
750
|
+
const { redacted_audio_url, status } = yield this.redactedAudio(id);
|
|
751
|
+
if (status !== "redacted_audio_ready") {
|
|
752
|
+
throw new Error(`Redacted audio status is ${status}`);
|
|
753
|
+
}
|
|
754
|
+
const response = yield fetch(redacted_audio_url);
|
|
755
|
+
if (!response.ok) {
|
|
756
|
+
throw new Error(`Failed to fetch redacted audio: ${response.statusText}`);
|
|
757
|
+
}
|
|
758
|
+
return {
|
|
759
|
+
arrayBuffer: response.arrayBuffer.bind(response),
|
|
760
|
+
blob: response.blob.bind(response),
|
|
761
|
+
body: response.body,
|
|
762
|
+
bodyUsed: response.bodyUsed,
|
|
763
|
+
};
|
|
764
|
+
});
|
|
765
|
+
}
|
|
636
766
|
}
|
|
637
767
|
function deprecateConformer2(params) {
|
|
638
768
|
if (!params)
|
|
@@ -659,8 +789,14 @@
|
|
|
659
789
|
upload(input) {
|
|
660
790
|
return __awaiter(this, void 0, void 0, function* () {
|
|
661
791
|
let fileData;
|
|
662
|
-
if (typeof input === "string")
|
|
663
|
-
|
|
792
|
+
if (typeof input === "string") {
|
|
793
|
+
if (input.startsWith("data:")) {
|
|
794
|
+
fileData = dataUrlToBlob(input);
|
|
795
|
+
}
|
|
796
|
+
else {
|
|
797
|
+
fileData = yield readFile();
|
|
798
|
+
}
|
|
799
|
+
}
|
|
664
800
|
else
|
|
665
801
|
fileData = input;
|
|
666
802
|
const data = yield this.fetchJson("/v2/upload", {
|
|
@@ -675,6 +811,17 @@
|
|
|
675
811
|
});
|
|
676
812
|
}
|
|
677
813
|
}
|
|
814
|
+
function dataUrlToBlob(dataUrl) {
|
|
815
|
+
const arr = dataUrl.split(",");
|
|
816
|
+
const mime = arr[0].match(/:(.*?);/)[1];
|
|
817
|
+
const bstr = atob(arr[1]);
|
|
818
|
+
let n = bstr.length;
|
|
819
|
+
const u8arr = new Uint8Array(n);
|
|
820
|
+
while (n--) {
|
|
821
|
+
u8arr[n] = bstr.charCodeAt(n);
|
|
822
|
+
}
|
|
823
|
+
return new Blob([u8arr], { type: mime });
|
|
824
|
+
}
|
|
678
825
|
|
|
679
826
|
const defaultBaseUrl = "https://api.assemblyai.com";
|
|
680
827
|
class AssemblyAI {
|
|
@@ -684,8 +831,9 @@
|
|
|
684
831
|
*/
|
|
685
832
|
constructor(params) {
|
|
686
833
|
params.baseUrl = params.baseUrl || defaultBaseUrl;
|
|
687
|
-
if (params.baseUrl && params.baseUrl.endsWith("/"))
|
|
834
|
+
if (params.baseUrl && params.baseUrl.endsWith("/")) {
|
|
688
835
|
params.baseUrl = params.baseUrl.slice(0, -1);
|
|
836
|
+
}
|
|
689
837
|
this.files = new FileService(params);
|
|
690
838
|
this.transcripts = new TranscriptService(params, this.files);
|
|
691
839
|
this.lemur = new LemurService(params);
|
|
@@ -1 +1 @@
|
|
|
1
|
-
!function(e,t){"object"==typeof exports&&"undefined"!=typeof module?t(exports):"function"==typeof define&&define.amd?define(["exports"],t):t((e="undefined"!=typeof globalThis?globalThis:e||self).assemblyai={})}(this,(function(e){"use strict";function t(e,t,s,i){return new(s||(s=Promise))((function(n,o){function r(e){try{l(i.next(e))}catch(e){o(e)}}function a(e){try{l(i.throw(e))}catch(e){o(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof s?t:new s((function(e){e(t)}))).then(r,a)}l((i=i.apply(e,t||[])).next())}))}"function"==typeof SuppressedError&&SuppressedError;class s{constructor(e){this.params=e}fetch(e,s){return t(this,void 0,void 0,(function*(){var t;(s=null!=s?s:{}).headers=null!==(t=s.headers)&&void 0!==t?t:{},s.headers=Object.assign({Authorization:this.params.apiKey,"Content-Type":"application/json"},s.headers),e.startsWith("http")||(e=this.params.baseUrl+e);const i=yield fetch(e,s);if(i.status>=400){let e;const t=yield i.text();if(t){try{e=JSON.parse(t)}catch(e){}if(null==e?void 0:e.error)throw new Error(e.error);throw new Error(t)}throw new Error(`HTTP Error: ${i.status} ${i.statusText}`)}return i}))}fetchJson(e,s){return t(this,void 0,void 0,(function*(){return(yield this.fetch(e,s)).json()}))}}class i extends s{summary(e){return this.fetchJson("/lemur/v3/generate/summary",{method:"POST",body:JSON.stringify(e)})}questionAnswer(e){return this.fetchJson("/lemur/v3/generate/question-answer",{method:"POST",body:JSON.stringify(e)})}actionItems(e){return this.fetchJson("/lemur/v3/generate/action-items",{method:"POST",body:JSON.stringify(e)})}task(e){return this.fetchJson("/lemur/v3/generate/task",{method:"POST",body:JSON.stringify(e)})}purgeRequestData(e){return this.fetchJson(`/lemur/v3/${e}`,{method:"DELETE"})}}const{WritableStream:n}="undefined"!=typeof window?window:"undefined"!=typeof global?global:globalThis;var o,r;const a=null!==(r=null!==(o=null!==WebSocket&&void 0!==WebSocket?WebSocket:null===global||void 0===global?void 0:global.WebSocket)&&void 0!==o?o:null===window||void 0===window?void 0:window.WebSocket)&&void 0!==r?r:null===self||void 0===self?void 0:self.WebSocket,l=(e,t)=>t?new a(e,t):new a(e);var c;!function(e){e[e.BadSampleRate=4e3]="BadSampleRate",e[e.AuthFailed=4001]="AuthFailed",e[e.InsufficientFundsOrFreeAccount=4002]="InsufficientFundsOrFreeAccount",e[e.NonexistentSessionId=4004]="NonexistentSessionId",e[e.SessionExpired=4008]="SessionExpired",e[e.ClosedSession=4010]="ClosedSession",e[e.RateLimited=4029]="RateLimited",e[e.UniqueSessionViolation=4030]="UniqueSessionViolation",e[e.SessionTimeout=4031]="SessionTimeout",e[e.AudioTooShort=4032]="AudioTooShort",e[e.AudioTooLong=4033]="AudioTooLong",e[e.BadJson=4100]="BadJson",e[e.BadSchema=4101]="BadSchema",e[e.TooManyStreams=4102]="TooManyStreams",e[e.Reconnected=4103]="Reconnected",e[e.ReconnectAttemptsExhausted=1013]="ReconnectAttemptsExhausted"}(c||(c={}));const d={[c.BadSampleRate]:"Sample rate must be a positive integer",[c.AuthFailed]:"Not Authorized",[c.InsufficientFundsOrFreeAccount]:"Insufficient funds or you are using a free account. This feature is paid-only and requires you to add a credit card. Please visit https://assemblyai.com/dashboard/ to add a credit card to your account.",[c.NonexistentSessionId]:"Session ID does not exist",[c.SessionExpired]:"Session has expired",[c.ClosedSession]:"Session is closed",[c.RateLimited]:"Rate limited",[c.UniqueSessionViolation]:"Unique session violation",[c.SessionTimeout]:"Session Timeout",[c.AudioTooShort]:"Audio too short",[c.AudioTooLong]:"Audio too long",[c.BadJson]:"Bad JSON",[c.BadSchema]:"Bad schema",[c.TooManyStreams]:"Too many streams",[c.Reconnected]:"Reconnected",[c.ReconnectAttemptsExhausted]:"Reconnect attempts exhausted"};class h extends Error{}const u='{"terminate_session":true}';class p{constructor(e){var t,s;if(this.listeners={},this.realtimeUrl=null!==(t=e.realtimeUrl)&&void 0!==t?t:"wss://api.assemblyai.com/v2/realtime/ws",this.sampleRate=null!==(s=e.sampleRate)&&void 0!==s?s:16e3,this.wordBoost=e.wordBoost,this.encoding=e.encoding,this.endUtteranceSilenceThreshold=e.endUtteranceSilenceThreshold,this.disablePartialTranscripts=e.disablePartialTranscripts,"token"in e&&e.token&&(this.token=e.token),"apiKey"in e&&e.apiKey&&(this.apiKey=e.apiKey),!this.token&&!this.apiKey)throw new Error("API key or temporary token is required.")}connectionUrl(){const e=new URL(this.realtimeUrl);if("wss:"!==e.protocol)throw new Error("Invalid protocol, must be wss");const t=new URLSearchParams;return this.token&&t.set("token",this.token),t.set("sample_rate",this.sampleRate.toString()),this.wordBoost&&this.wordBoost.length>0&&t.set("word_boost",JSON.stringify(this.wordBoost)),this.encoding&&t.set("encoding",this.encoding),t.set("enable_extra_session_information","true"),this.disablePartialTranscripts&&t.set("disable_partial_transcripts",this.disablePartialTranscripts.toString()),e.search=t.toString(),e}on(e,t){this.listeners[e]=t}connect(){return new Promise((e=>{if(this.socket)throw new Error("Already connected");const t=this.connectionUrl();this.token?this.socket=l(t.toString()):this.socket=l(t.toString(),{headers:{Authorization:this.apiKey}}),this.socket.binaryType="arraybuffer",this.socket.onopen=()=>{void 0!==this.endUtteranceSilenceThreshold&&null!==this.endUtteranceSilenceThreshold&&this.configureEndUtteranceSilenceThreshold(this.endUtteranceSilenceThreshold)},this.socket.onclose=({code:e,reason:t})=>{var s,i;t||e in c&&(t=d[e]),null===(i=(s=this.listeners).close)||void 0===i||i.call(s,e,t)},this.socket.onerror=e=>{var t,s,i,n;e.error?null===(s=(t=this.listeners).error)||void 0===s||s.call(t,e.error):null===(n=(i=this.listeners).error)||void 0===n||n.call(i,new Error(e.message))},this.socket.onmessage=({data:t})=>{var s,i,n,o,r,a,l,c,d,u,p,f,m,v,y;const S=JSON.parse(t.toString());if("error"in S)null===(i=(s=this.listeners).error)||void 0===i||i.call(s,new h(S.error));else switch(S.message_type){case"SessionBegins":{const t={sessionId:S.session_id,expiresAt:new Date(S.expires_at)};e(t),null===(o=(n=this.listeners).open)||void 0===o||o.call(n,t);break}case"PartialTranscript":S.created=new Date(S.created),null===(a=(r=this.listeners).transcript)||void 0===a||a.call(r,S),null===(c=(l=this.listeners)["transcript.partial"])||void 0===c||c.call(l,S);break;case"FinalTranscript":S.created=new Date(S.created),null===(u=(d=this.listeners).transcript)||void 0===u||u.call(d,S),null===(f=(p=this.listeners)["transcript.final"])||void 0===f||f.call(p,S);break;case"SessionInformation":null===(v=(m=this.listeners).session_information)||void 0===v||v.call(m,S);break;case"SessionTerminated":null===(y=this.sessionTerminatedResolve)||void 0===y||y.call(this)}}}))}sendAudio(e){this.send(e)}stream(){return new n({write:e=>{this.sendAudio(e)}})}forceEndUtterance(){this.send('{"force_end_utterance":true}')}configureEndUtteranceSilenceThreshold(e){this.send(`{"end_utterance_silence_threshold":${e}}`)}send(e){if(!this.socket||this.socket.readyState!==this.socket.OPEN)throw new Error("Socket is not open for communication");this.socket.send(e)}close(){return t(this,arguments,void 0,(function*(e=!0){var t;if(this.socket){if(this.socket.readyState===this.socket.OPEN)if(e){const e=new Promise((e=>{this.sessionTerminatedResolve=e}));this.socket.send(u),yield e}else this.socket.send(u);(null===(t=this.socket)||void 0===t?void 0:t.removeAllListeners)&&this.socket.removeAllListeners(),this.socket.close()}this.listeners={},this.socket=void 0}))}}class f extends s{constructor(e){super(e),this.rtFactoryParams=e}createService(e){return this.transcriber(e)}transcriber(e){const t=Object.assign({},e);return t.token||t.apiKey||(t.apiKey=this.rtFactoryParams.apiKey),new p(t)}createTemporaryToken(e){return t(this,void 0,void 0,(function*(){return(yield this.fetchJson("/v2/realtime/token",{method:"POST",body:JSON.stringify(e)})).token}))}}function m(e){return e.startsWith("http")||e.startsWith("https")?null:e.startsWith("file://")?e.substring(7):e.startsWith("file:")?e.substring(5):e}class v extends s{constructor(e,t){super(e),this.files=t}transcribe(e,s){return t(this,void 0,void 0,(function*(){y(e);const t=yield this.submit(e);return yield this.waitUntilReady(t.id,s)}))}submit(e){return t(this,void 0,void 0,(function*(){let t,s;if(y(e),"audio"in e){const{audio:i}=e,n=function(e,t){var s={};for(var i in e)Object.prototype.hasOwnProperty.call(e,i)&&t.indexOf(i)<0&&(s[i]=e[i]);if(null!=e&&"function"==typeof Object.getOwnPropertySymbols){var n=0;for(i=Object.getOwnPropertySymbols(e);n<i.length;n++)t.indexOf(i[n])<0&&Object.prototype.propertyIsEnumerable.call(e,i[n])&&(s[i[n]]=e[i[n]])}return s}(e,["audio"]);if("string"==typeof i){const e=m(i);t=null!==e?yield this.files.upload(e):i}else t=yield this.files.upload(i);s=Object.assign(Object.assign({},n),{audio_url:t})}else s=e;return yield this.fetchJson("/v2/transcript",{method:"POST",body:JSON.stringify(s)})}))}create(e,s){return t(this,void 0,void 0,(function*(){var t;y(e);const i=m(e.audio_url);if(null!==i){const t=yield this.files.upload(i);e.audio_url=t}const n=yield this.fetchJson("/v2/transcript",{method:"POST",body:JSON.stringify(e)});return null===(t=null==s?void 0:s.poll)||void 0===t||t?yield this.waitUntilReady(n.id,s):n}))}waitUntilReady(e,s){return t(this,void 0,void 0,(function*(){var t,i;const n=null!==(t=null==s?void 0:s.pollingInterval)&&void 0!==t?t:3e3,o=null!==(i=null==s?void 0:s.pollingTimeout)&&void 0!==i?i:-1,r=Date.now();for(;;){const t=yield this.get(e);if("completed"===t.status||"error"===t.status)return t;if(o>0&&Date.now()-r>o)throw new Error("Polling timeout");yield new Promise((e=>setTimeout(e,n)))}}))}get(e){return this.fetchJson(`/v2/transcript/${e}`)}list(e){return t(this,void 0,void 0,(function*(){let t="/v2/transcript";"string"==typeof e?t=e:e&&(t=`${t}?${new URLSearchParams(Object.keys(e).map((t=>{var s;return[t,(null===(s=e[t])||void 0===s?void 0:s.toString())||""]})))}`);const s=yield this.fetchJson(t);for(const e of s.transcripts)e.created=new Date(e.created),e.completed&&(e.completed=new Date(e.completed));return s}))}delete(e){return this.fetchJson(`/v2/transcript/${e}`,{method:"DELETE"})}wordSearch(e,t){const s=new URLSearchParams({words:t.join(",")});return this.fetchJson(`/v2/transcript/${e}/word-search?${s.toString()}`)}sentences(e){return this.fetchJson(`/v2/transcript/${e}/sentences`)}paragraphs(e){return this.fetchJson(`/v2/transcript/${e}/paragraphs`)}subtitles(e){return t(this,arguments,void 0,(function*(e,t="srt",s){let i=`/v2/transcript/${e}/${t}`;if(s){const e=new URLSearchParams;e.set("chars_per_caption",s.toString()),i+=`?${e.toString()}`}const n=yield this.fetch(i);return yield n.text()}))}redactions(e){return this.fetchJson(`/v2/transcript/${e}/redacted-audio`)}}function y(e){e&&"conformer-2"===e.speech_model&&console.warn("The speech_model conformer-2 option is deprecated and will stop working in the near future. Use best or nano instead.")}class S extends s{upload(e){return t(this,void 0,void 0,(function*(){let s;s="string"==typeof e?yield function(e){return t(this,void 0,void 0,(function*(){throw new Error("Interacting with the file system is not supported in this environment.")}))}():e;return(yield this.fetchJson("/v2/upload",{method:"POST",body:s,headers:{"Content-Type":"application/octet-stream"},duplex:"half"})).upload_url}))}}e.AssemblyAI=class{constructor(e){e.baseUrl=e.baseUrl||"https://api.assemblyai.com",e.baseUrl&&e.baseUrl.endsWith("/")&&(e.baseUrl=e.baseUrl.slice(0,-1)),this.files=new S(e),this.transcripts=new v(e,this.files),this.lemur=new i(e),this.realtime=new f(e)}},e.FileService=S,e.LemurService=i,e.RealtimeService=class extends p{},e.RealtimeServiceFactory=class extends f{},e.RealtimeTranscriber=p,e.RealtimeTranscriberFactory=f,e.TranscriptService=v}));
|
|
1
|
+
!function(e,t){"object"==typeof exports&&"undefined"!=typeof module?t(exports):"function"==typeof define&&define.amd?define(["exports"],t):t((e="undefined"!=typeof globalThis?globalThis:e||self).assemblyai={})}(this,(function(e){"use strict";function t(e,t,s,i){return new(s||(s=Promise))((function(n,o){function r(e){try{c(i.next(e))}catch(e){o(e)}}function a(e){try{c(i.throw(e))}catch(e){o(e)}}function c(e){var t;e.done?n(e.value):(t=e.value,t instanceof s?t:new s((function(e){e(t)}))).then(r,a)}c((i=i.apply(e,t||[])).next())}))}"function"==typeof SuppressedError&&SuppressedError;const s={cache:"no-store"};let i="";"undefined"!=typeof navigator&&navigator.userAgent&&(i+=navigator.userAgent);const n={sdk:{name:"JavaScript",version:"4.6.0"}};"undefined"!=typeof process&&(process.versions.node&&-1===i.indexOf("Node")&&(n.runtime_env={name:"Node",version:process.versions.node}),process.versions.bun&&-1===i.indexOf("Bun")&&(n.runtime_env={name:"Bun",version:process.versions.bun})),"undefined"!=typeof Deno&&process.versions.bun&&-1===i.indexOf("Deno")&&(n.runtime_env={name:"Deno",version:Deno.version.deno});class o{constructor(e){var t;this.params=e,!1===e.userAgent?this.userAgent=void 0:this.userAgent=(t=e.userAgent||{},i+(!1===t?"":" AssemblyAI/1.0 ("+Object.entries(Object.assign(Object.assign({},n),t)).map((([e,t])=>t?`${e}=${t.name}/${t.version}`:"")).join(" ")+")"))}fetch(e,i){return t(this,void 0,void 0,(function*(){i=Object.assign(Object.assign({},s),i);let t={Authorization:this.params.apiKey,"Content-Type":"application/json"};(null==s?void 0:s.headers)&&(t=Object.assign(Object.assign({},t),s.headers)),(null==i?void 0:i.headers)&&(t=Object.assign(Object.assign({},t),i.headers)),this.userAgent&&(t["User-Agent"]=this.userAgent,"undefined"!=typeof window&&"chrome"in window&&(t["AssemblyAI-Agent"]=this.userAgent)),i.headers=t,e.startsWith("http")||(e=this.params.baseUrl+e);const n=yield fetch(e,i);if(n.status>=400){let e;const t=yield n.text();if(t){try{e=JSON.parse(t)}catch(e){}if(null==e?void 0:e.error)throw new Error(e.error);throw new Error(t)}throw new Error(`HTTP Error: ${n.status} ${n.statusText}`)}return n}))}fetchJson(e,s){return t(this,void 0,void 0,(function*(){return(yield this.fetch(e,s)).json()}))}}class r extends o{summary(e){return this.fetchJson("/lemur/v3/generate/summary",{method:"POST",body:JSON.stringify(e)})}questionAnswer(e){return this.fetchJson("/lemur/v3/generate/question-answer",{method:"POST",body:JSON.stringify(e)})}actionItems(e){return this.fetchJson("/lemur/v3/generate/action-items",{method:"POST",body:JSON.stringify(e)})}task(e){return this.fetchJson("/lemur/v3/generate/task",{method:"POST",body:JSON.stringify(e)})}getResponse(e){return this.fetchJson(`/lemur/v3/${e}`)}purgeRequestData(e){return this.fetchJson(`/lemur/v3/${e}`,{method:"DELETE"})}}const{WritableStream:a}="undefined"!=typeof window?window:"undefined"!=typeof global?global:globalThis;var c,d;const l=null!==(d=null!==(c=null!==WebSocket&&void 0!==WebSocket?WebSocket:null===global||void 0===global?void 0:global.WebSocket)&&void 0!==c?c:null===window||void 0===window?void 0:window.WebSocket)&&void 0!==d?d:null===self||void 0===self?void 0:self.WebSocket,u=(e,t)=>t?new l(e,t):new l(e);var h;!function(e){e[e.BadSampleRate=4e3]="BadSampleRate",e[e.AuthFailed=4001]="AuthFailed",e[e.InsufficientFundsOrFreeAccount=4002]="InsufficientFundsOrFreeAccount",e[e.NonexistentSessionId=4004]="NonexistentSessionId",e[e.SessionExpired=4008]="SessionExpired",e[e.ClosedSession=4010]="ClosedSession",e[e.RateLimited=4029]="RateLimited",e[e.UniqueSessionViolation=4030]="UniqueSessionViolation",e[e.SessionTimeout=4031]="SessionTimeout",e[e.AudioTooShort=4032]="AudioTooShort",e[e.AudioTooLong=4033]="AudioTooLong",e[e.BadJson=4100]="BadJson",e[e.BadSchema=4101]="BadSchema",e[e.TooManyStreams=4102]="TooManyStreams",e[e.Reconnected=4103]="Reconnected",e[e.ReconnectAttemptsExhausted=1013]="ReconnectAttemptsExhausted"}(h||(h={}));const f={[h.BadSampleRate]:"Sample rate must be a positive integer",[h.AuthFailed]:"Not Authorized",[h.InsufficientFundsOrFreeAccount]:"Insufficient funds or you are using a free account. This feature is paid-only and requires you to add a credit card. Please visit https://assemblyai.com/dashboard/ to add a credit card to your account.",[h.NonexistentSessionId]:"Session ID does not exist",[h.SessionExpired]:"Session has expired",[h.ClosedSession]:"Session is closed",[h.RateLimited]:"Rate limited",[h.UniqueSessionViolation]:"Unique session violation",[h.SessionTimeout]:"Session Timeout",[h.AudioTooShort]:"Audio too short",[h.AudioTooLong]:"Audio too long",[h.BadJson]:"Bad JSON",[h.BadSchema]:"Bad schema",[h.TooManyStreams]:"Too many streams",[h.Reconnected]:"Reconnected",[h.ReconnectAttemptsExhausted]:"Reconnect attempts exhausted"};class p extends Error{}const m='{"terminate_session":true}';class v{constructor(e){var t,s;if(this.listeners={},this.realtimeUrl=null!==(t=e.realtimeUrl)&&void 0!==t?t:"wss://api.assemblyai.com/v2/realtime/ws",this.sampleRate=null!==(s=e.sampleRate)&&void 0!==s?s:16e3,this.wordBoost=e.wordBoost,this.encoding=e.encoding,this.endUtteranceSilenceThreshold=e.endUtteranceSilenceThreshold,this.disablePartialTranscripts=e.disablePartialTranscripts,"token"in e&&e.token&&(this.token=e.token),"apiKey"in e&&e.apiKey&&(this.apiKey=e.apiKey),!this.token&&!this.apiKey)throw new Error("API key or temporary token is required.")}connectionUrl(){const e=new URL(this.realtimeUrl);if("wss:"!==e.protocol)throw new Error("Invalid protocol, must be wss");const t=new URLSearchParams;return this.token&&t.set("token",this.token),t.set("sample_rate",this.sampleRate.toString()),this.wordBoost&&this.wordBoost.length>0&&t.set("word_boost",JSON.stringify(this.wordBoost)),this.encoding&&t.set("encoding",this.encoding),t.set("enable_extra_session_information","true"),this.disablePartialTranscripts&&t.set("disable_partial_transcripts",this.disablePartialTranscripts.toString()),e.search=t.toString(),e}on(e,t){this.listeners[e]=t}connect(){return new Promise((e=>{if(this.socket)throw new Error("Already connected");const t=this.connectionUrl();this.token?this.socket=u(t.toString()):this.socket=u(t.toString(),{headers:{Authorization:this.apiKey}}),this.socket.binaryType="arraybuffer",this.socket.onopen=()=>{void 0!==this.endUtteranceSilenceThreshold&&null!==this.endUtteranceSilenceThreshold&&this.configureEndUtteranceSilenceThreshold(this.endUtteranceSilenceThreshold)},this.socket.onclose=({code:e,reason:t})=>{var s,i;t||e in h&&(t=f[e]),null===(i=(s=this.listeners).close)||void 0===i||i.call(s,e,t)},this.socket.onerror=e=>{var t,s,i,n;e.error?null===(s=(t=this.listeners).error)||void 0===s||s.call(t,e.error):null===(n=(i=this.listeners).error)||void 0===n||n.call(i,new Error(e.message))},this.socket.onmessage=({data:t})=>{var s,i,n,o,r,a,c,d,l,u,h,f,m,v,y;const b=JSON.parse(t.toString());if("error"in b)null===(i=(s=this.listeners).error)||void 0===i||i.call(s,new p(b.error));else switch(b.message_type){case"SessionBegins":{const t={sessionId:b.session_id,expiresAt:new Date(b.expires_at)};e(t),null===(o=(n=this.listeners).open)||void 0===o||o.call(n,t);break}case"PartialTranscript":b.created=new Date(b.created),null===(a=(r=this.listeners).transcript)||void 0===a||a.call(r,b),null===(d=(c=this.listeners)["transcript.partial"])||void 0===d||d.call(c,b);break;case"FinalTranscript":b.created=new Date(b.created),null===(u=(l=this.listeners).transcript)||void 0===u||u.call(l,b),null===(f=(h=this.listeners)["transcript.final"])||void 0===f||f.call(h,b);break;case"SessionInformation":null===(v=(m=this.listeners).session_information)||void 0===v||v.call(m,b);break;case"SessionTerminated":null===(y=this.sessionTerminatedResolve)||void 0===y||y.call(this)}}}))}sendAudio(e){this.send(e)}stream(){return new a({write:e=>{this.sendAudio(e)}})}forceEndUtterance(){this.send('{"force_end_utterance":true}')}configureEndUtteranceSilenceThreshold(e){this.send(`{"end_utterance_silence_threshold":${e}}`)}send(e){if(!this.socket||this.socket.readyState!==this.socket.OPEN)throw new Error("Socket is not open for communication");this.socket.send(e)}close(){return t(this,arguments,void 0,(function*(e=!0){var t;if(this.socket){if(this.socket.readyState===this.socket.OPEN)if(e){const e=new Promise((e=>{this.sessionTerminatedResolve=e}));this.socket.send(m),yield e}else this.socket.send(m);(null===(t=this.socket)||void 0===t?void 0:t.removeAllListeners)&&this.socket.removeAllListeners(),this.socket.close()}this.listeners={},this.socket=void 0}))}}class y extends o{constructor(e){super(e),this.rtFactoryParams=e}createService(e){return this.transcriber(e)}transcriber(e){const t=Object.assign({},e);return t.token||t.apiKey||(t.apiKey=this.rtFactoryParams.apiKey),new v(t)}createTemporaryToken(e){return t(this,void 0,void 0,(function*(){return(yield this.fetchJson("/v2/realtime/token",{method:"POST",body:JSON.stringify(e)})).token}))}}function b(e){return e.startsWith("http")||e.startsWith("https")||e.startsWith("data:")?null:e.startsWith("file://")?e.substring(7):e.startsWith("file:")?e.substring(5):e}class S extends o{constructor(e,t){super(e),this.files=t}transcribe(e,s){return t(this,void 0,void 0,(function*(){g(e);const t=yield this.submit(e);return yield this.waitUntilReady(t.id,s)}))}submit(e){return t(this,void 0,void 0,(function*(){let t,s;if(g(e),"audio"in e){const{audio:i}=e,n=function(e,t){var s={};for(var i in e)Object.prototype.hasOwnProperty.call(e,i)&&t.indexOf(i)<0&&(s[i]=e[i]);if(null!=e&&"function"==typeof Object.getOwnPropertySymbols){var n=0;for(i=Object.getOwnPropertySymbols(e);n<i.length;n++)t.indexOf(i[n])<0&&Object.prototype.propertyIsEnumerable.call(e,i[n])&&(s[i[n]]=e[i[n]])}return s}(e,["audio"]);if("string"==typeof i){const e=b(i);t=null!==e?yield this.files.upload(e):i.startsWith("data:")?yield this.files.upload(i):i}else t=yield this.files.upload(i);s=Object.assign(Object.assign({},n),{audio_url:t})}else s=e;return yield this.fetchJson("/v2/transcript",{method:"POST",body:JSON.stringify(s)})}))}create(e,s){return t(this,void 0,void 0,(function*(){var t;g(e);const i=b(e.audio_url);if(null!==i){const t=yield this.files.upload(i);e.audio_url=t}const n=yield this.fetchJson("/v2/transcript",{method:"POST",body:JSON.stringify(e)});return null===(t=null==s?void 0:s.poll)||void 0===t||t?yield this.waitUntilReady(n.id,s):n}))}waitUntilReady(e,s){return t(this,void 0,void 0,(function*(){var t,i;const n=null!==(t=null==s?void 0:s.pollingInterval)&&void 0!==t?t:3e3,o=null!==(i=null==s?void 0:s.pollingTimeout)&&void 0!==i?i:-1,r=Date.now();for(;;){const t=yield this.get(e);if("completed"===t.status||"error"===t.status)return t;if(o>0&&Date.now()-r>o)throw new Error("Polling timeout");yield new Promise((e=>setTimeout(e,n)))}}))}get(e){return this.fetchJson(`/v2/transcript/${e}`)}list(e){return t(this,void 0,void 0,(function*(){let t="/v2/transcript";"string"==typeof e?t=e:e&&(t=`${t}?${new URLSearchParams(Object.keys(e).map((t=>{var s;return[t,(null===(s=e[t])||void 0===s?void 0:s.toString())||""]})))}`);const s=yield this.fetchJson(t);for(const e of s.transcripts)e.created=new Date(e.created),e.completed&&(e.completed=new Date(e.completed));return s}))}delete(e){return this.fetchJson(`/v2/transcript/${e}`,{method:"DELETE"})}wordSearch(e,t){const s=new URLSearchParams({words:t.join(",")});return this.fetchJson(`/v2/transcript/${e}/word-search?${s.toString()}`)}sentences(e){return this.fetchJson(`/v2/transcript/${e}/sentences`)}paragraphs(e){return this.fetchJson(`/v2/transcript/${e}/paragraphs`)}subtitles(e){return t(this,arguments,void 0,(function*(e,t="srt",s){let i=`/v2/transcript/${e}/${t}`;if(s){const e=new URLSearchParams;e.set("chars_per_caption",s.toString()),i+=`?${e.toString()}`}const n=yield this.fetch(i);return yield n.text()}))}redactions(e){return this.redactedAudio(e)}redactedAudio(e){return this.fetchJson(`/v2/transcript/${e}/redacted-audio`)}redactedAudioFile(e){return t(this,void 0,void 0,(function*(){const{redacted_audio_url:t,status:s}=yield this.redactedAudio(e);if("redacted_audio_ready"!==s)throw new Error(`Redacted audio status is ${s}`);const i=yield fetch(t);if(!i.ok)throw new Error(`Failed to fetch redacted audio: ${i.statusText}`);return{arrayBuffer:i.arrayBuffer.bind(i),blob:i.blob.bind(i),body:i.body,bodyUsed:i.bodyUsed}}))}}function g(e){e&&"conformer-2"===e.speech_model&&console.warn("The speech_model conformer-2 option is deprecated and will stop working in the near future. Use best or nano instead.")}class w extends o{upload(e){return t(this,void 0,void 0,(function*(){let s;s="string"==typeof e?e.startsWith("data:")?function(e){const t=e.split(","),s=t[0].match(/:(.*?);/)[1],i=atob(t[1]);let n=i.length;const o=new Uint8Array(n);for(;n--;)o[n]=i.charCodeAt(n);return new Blob([o],{type:s})}(e):yield function(e){return t(this,void 0,void 0,(function*(){throw new Error("Interacting with the file system is not supported in this environment.")}))}():e;return(yield this.fetchJson("/v2/upload",{method:"POST",body:s,headers:{"Content-Type":"application/octet-stream"},duplex:"half"})).upload_url}))}}e.AssemblyAI=class{constructor(e){e.baseUrl=e.baseUrl||"https://api.assemblyai.com",e.baseUrl&&e.baseUrl.endsWith("/")&&(e.baseUrl=e.baseUrl.slice(0,-1)),this.files=new w(e),this.transcripts=new S(e,this.files),this.lemur=new r(e),this.realtime=new y(e)}},e.FileService=w,e.LemurService=r,e.RealtimeService=class extends v{},e.RealtimeServiceFactory=class extends y{},e.RealtimeTranscriber=v,e.RealtimeTranscriberFactory=y,e.TranscriptService=S}));
|
package/dist/browser.mjs
CHANGED
|
@@ -1,3 +1,42 @@
|
|
|
1
|
+
const DEFAULT_FETCH_INIT = {
|
|
2
|
+
cache: "no-store",
|
|
3
|
+
};
|
|
4
|
+
|
|
5
|
+
const buildUserAgent = (userAgent) => defaultUserAgentString +
|
|
6
|
+
(userAgent === false
|
|
7
|
+
? ""
|
|
8
|
+
: " AssemblyAI/1.0 (" +
|
|
9
|
+
Object.entries({ ...defaultUserAgent, ...userAgent })
|
|
10
|
+
.map(([key, item]) => item ? `${key}=${item.name}/${item.version}` : "")
|
|
11
|
+
.join(" ") +
|
|
12
|
+
")");
|
|
13
|
+
let defaultUserAgentString = "";
|
|
14
|
+
if (typeof navigator !== "undefined" && navigator.userAgent) {
|
|
15
|
+
defaultUserAgentString += navigator.userAgent;
|
|
16
|
+
}
|
|
17
|
+
const defaultUserAgent = {
|
|
18
|
+
sdk: { name: "JavaScript", version: "4.6.0" },
|
|
19
|
+
};
|
|
20
|
+
if (typeof process !== "undefined") {
|
|
21
|
+
if (process.versions.node && defaultUserAgentString.indexOf("Node") === -1) {
|
|
22
|
+
defaultUserAgent.runtime_env = {
|
|
23
|
+
name: "Node",
|
|
24
|
+
version: process.versions.node,
|
|
25
|
+
};
|
|
26
|
+
}
|
|
27
|
+
if (process.versions.bun && defaultUserAgentString.indexOf("Bun") === -1) {
|
|
28
|
+
defaultUserAgent.runtime_env = {
|
|
29
|
+
name: "Bun",
|
|
30
|
+
version: process.versions.bun,
|
|
31
|
+
};
|
|
32
|
+
}
|
|
33
|
+
}
|
|
34
|
+
if (typeof Deno !== "undefined") {
|
|
35
|
+
if (process.versions.bun && defaultUserAgentString.indexOf("Deno") === -1) {
|
|
36
|
+
defaultUserAgent.runtime_env = { name: "Deno", version: Deno.version.deno };
|
|
37
|
+
}
|
|
38
|
+
}
|
|
39
|
+
|
|
1
40
|
/**
|
|
2
41
|
* Base class for services that communicate with the API.
|
|
3
42
|
*/
|
|
@@ -8,15 +47,32 @@ class BaseService {
|
|
|
8
47
|
*/
|
|
9
48
|
constructor(params) {
|
|
10
49
|
this.params = params;
|
|
50
|
+
if (params.userAgent === false) {
|
|
51
|
+
this.userAgent = undefined;
|
|
52
|
+
}
|
|
53
|
+
else {
|
|
54
|
+
this.userAgent = buildUserAgent(params.userAgent || {});
|
|
55
|
+
}
|
|
11
56
|
}
|
|
12
57
|
async fetch(input, init) {
|
|
13
|
-
init = init
|
|
14
|
-
|
|
15
|
-
init.headers = {
|
|
58
|
+
init = { ...DEFAULT_FETCH_INIT, ...init };
|
|
59
|
+
let headers = {
|
|
16
60
|
Authorization: this.params.apiKey,
|
|
17
61
|
"Content-Type": "application/json",
|
|
18
|
-
...init.headers,
|
|
19
62
|
};
|
|
63
|
+
if (DEFAULT_FETCH_INIT?.headers)
|
|
64
|
+
headers = { ...headers, ...DEFAULT_FETCH_INIT.headers };
|
|
65
|
+
if (init?.headers)
|
|
66
|
+
headers = { ...headers, ...init.headers };
|
|
67
|
+
if (this.userAgent) {
|
|
68
|
+
headers["User-Agent"] = this.userAgent;
|
|
69
|
+
// chromium browsers have a bug where the user agent can't be modified
|
|
70
|
+
if (typeof window !== "undefined" && "chrome" in window) {
|
|
71
|
+
headers["AssemblyAI-Agent"] =
|
|
72
|
+
this.userAgent;
|
|
73
|
+
}
|
|
74
|
+
}
|
|
75
|
+
init.headers = headers;
|
|
20
76
|
if (!input.startsWith("http"))
|
|
21
77
|
input = this.params.baseUrl + input;
|
|
22
78
|
const response = await fetch(input, init);
|
|
@@ -69,6 +125,9 @@ class LemurService extends BaseService {
|
|
|
69
125
|
body: JSON.stringify(params),
|
|
70
126
|
});
|
|
71
127
|
}
|
|
128
|
+
getResponse(id) {
|
|
129
|
+
return this.fetchJson(`/lemur/v3/${id}`);
|
|
130
|
+
}
|
|
72
131
|
/**
|
|
73
132
|
* Delete the data for a previously submitted LeMUR request.
|
|
74
133
|
* @param id - ID of the LeMUR request
|
|
@@ -138,7 +197,14 @@ class RealtimeError extends Error {
|
|
|
138
197
|
const defaultRealtimeUrl = "wss://api.assemblyai.com/v2/realtime/ws";
|
|
139
198
|
const forceEndOfUtteranceMessage = `{"force_end_utterance":true}`;
|
|
140
199
|
const terminateSessionMessage = `{"terminate_session":true}`;
|
|
200
|
+
/**
|
|
201
|
+
* RealtimeTranscriber connects to the Streaming Speech-to-Text API and lets you transcribe audio in real-time.
|
|
202
|
+
*/
|
|
141
203
|
class RealtimeTranscriber {
|
|
204
|
+
/**
|
|
205
|
+
* Create a new RealtimeTranscriber.
|
|
206
|
+
* @param params - Parameters to configure the RealtimeTranscriber
|
|
207
|
+
*/
|
|
142
208
|
constructor(params) {
|
|
143
209
|
this.listeners = {};
|
|
144
210
|
this.realtimeUrl = params.realtimeUrl ?? defaultRealtimeUrl;
|
|
@@ -178,10 +244,19 @@ class RealtimeTranscriber {
|
|
|
178
244
|
url.search = searchParams.toString();
|
|
179
245
|
return url;
|
|
180
246
|
}
|
|
247
|
+
/**
|
|
248
|
+
* Add a listener for an event.
|
|
249
|
+
* @param event - The event to listen for.
|
|
250
|
+
* @param listener - The function to call when the event is emitted.
|
|
251
|
+
*/
|
|
181
252
|
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
182
253
|
on(event, listener) {
|
|
183
254
|
this.listeners[event] = listener;
|
|
184
255
|
}
|
|
256
|
+
/**
|
|
257
|
+
* Connect to the server and begin a new session.
|
|
258
|
+
* @returns A promise that resolves when the connection is established and the session begins.
|
|
259
|
+
*/
|
|
185
260
|
connect() {
|
|
186
261
|
return new Promise((resolve) => {
|
|
187
262
|
if (this.socket) {
|
|
@@ -260,9 +335,17 @@ class RealtimeTranscriber {
|
|
|
260
335
|
};
|
|
261
336
|
});
|
|
262
337
|
}
|
|
338
|
+
/**
|
|
339
|
+
* Send audio data to the server.
|
|
340
|
+
* @param audio - The audio data to send to the server.
|
|
341
|
+
*/
|
|
263
342
|
sendAudio(audio) {
|
|
264
343
|
this.send(audio);
|
|
265
344
|
}
|
|
345
|
+
/**
|
|
346
|
+
* Create a writable stream that can be used to send audio data to the server.
|
|
347
|
+
* @returns A writable stream that can be used to send audio data to the server.
|
|
348
|
+
*/
|
|
266
349
|
stream() {
|
|
267
350
|
return new WritableStream({
|
|
268
351
|
write: (chunk) => {
|
|
@@ -290,6 +373,11 @@ class RealtimeTranscriber {
|
|
|
290
373
|
}
|
|
291
374
|
this.socket.send(data);
|
|
292
375
|
}
|
|
376
|
+
/**
|
|
377
|
+
* Close the connection to the server.
|
|
378
|
+
* @param waitForSessionTermination - If true, the method will wait for the session to be terminated before closing the connection.
|
|
379
|
+
* While waiting for the session to be terminated, you will receive the final transcript and session information.
|
|
380
|
+
*/
|
|
293
381
|
async close(waitForSessionTermination = true) {
|
|
294
382
|
if (this.socket) {
|
|
295
383
|
if (this.socket.readyState === this.socket.OPEN) {
|
|
@@ -355,6 +443,8 @@ function getPath(path) {
|
|
|
355
443
|
return null;
|
|
356
444
|
if (path.startsWith("https"))
|
|
357
445
|
return null;
|
|
446
|
+
if (path.startsWith("data:"))
|
|
447
|
+
return null;
|
|
358
448
|
if (path.startsWith("file://"))
|
|
359
449
|
return path.substring(7);
|
|
360
450
|
if (path.startsWith("file:"))
|
|
@@ -396,8 +486,13 @@ class TranscriptService extends BaseService {
|
|
|
396
486
|
audioUrl = await this.files.upload(path);
|
|
397
487
|
}
|
|
398
488
|
else {
|
|
399
|
-
|
|
400
|
-
|
|
489
|
+
if (audio.startsWith("data:")) {
|
|
490
|
+
audioUrl = await this.files.upload(audio);
|
|
491
|
+
}
|
|
492
|
+
else {
|
|
493
|
+
// audio is not a local path, and not a data-URI, assume it's a normal URL
|
|
494
|
+
audioUrl = audio;
|
|
495
|
+
}
|
|
401
496
|
}
|
|
402
497
|
}
|
|
403
498
|
else {
|
|
@@ -548,13 +643,43 @@ class TranscriptService extends BaseService {
|
|
|
548
643
|
return await response.text();
|
|
549
644
|
}
|
|
550
645
|
/**
|
|
551
|
-
* Retrieve
|
|
646
|
+
* Retrieve the redacted audio URL of a transcript.
|
|
552
647
|
* @param id - The identifier of the transcript.
|
|
553
|
-
* @returns A promise that resolves to the
|
|
648
|
+
* @returns A promise that resolves to the details of the redacted audio.
|
|
649
|
+
* @deprecated Use `redactedAudio` instead.
|
|
554
650
|
*/
|
|
555
651
|
redactions(id) {
|
|
652
|
+
return this.redactedAudio(id);
|
|
653
|
+
}
|
|
654
|
+
/**
|
|
655
|
+
* Retrieve the redacted audio URL of a transcript.
|
|
656
|
+
* @param id - The identifier of the transcript.
|
|
657
|
+
* @returns A promise that resolves to the details of the redacted audio.
|
|
658
|
+
*/
|
|
659
|
+
redactedAudio(id) {
|
|
556
660
|
return this.fetchJson(`/v2/transcript/${id}/redacted-audio`);
|
|
557
661
|
}
|
|
662
|
+
/**
|
|
663
|
+
* Retrieve the redacted audio file of a transcript.
|
|
664
|
+
* @param id - The identifier of the transcript.
|
|
665
|
+
* @returns A promise that resolves to the fetch HTTP response of the redacted audio file.
|
|
666
|
+
*/
|
|
667
|
+
async redactedAudioFile(id) {
|
|
668
|
+
const { redacted_audio_url, status } = await this.redactedAudio(id);
|
|
669
|
+
if (status !== "redacted_audio_ready") {
|
|
670
|
+
throw new Error(`Redacted audio status is ${status}`);
|
|
671
|
+
}
|
|
672
|
+
const response = await fetch(redacted_audio_url);
|
|
673
|
+
if (!response.ok) {
|
|
674
|
+
throw new Error(`Failed to fetch redacted audio: ${response.statusText}`);
|
|
675
|
+
}
|
|
676
|
+
return {
|
|
677
|
+
arrayBuffer: response.arrayBuffer.bind(response),
|
|
678
|
+
blob: response.blob.bind(response),
|
|
679
|
+
body: response.body,
|
|
680
|
+
bodyUsed: response.bodyUsed,
|
|
681
|
+
};
|
|
682
|
+
}
|
|
558
683
|
}
|
|
559
684
|
function deprecateConformer2(params) {
|
|
560
685
|
if (!params)
|
|
@@ -578,8 +703,14 @@ class FileService extends BaseService {
|
|
|
578
703
|
*/
|
|
579
704
|
async upload(input) {
|
|
580
705
|
let fileData;
|
|
581
|
-
if (typeof input === "string")
|
|
582
|
-
|
|
706
|
+
if (typeof input === "string") {
|
|
707
|
+
if (input.startsWith("data:")) {
|
|
708
|
+
fileData = dataUrlToBlob(input);
|
|
709
|
+
}
|
|
710
|
+
else {
|
|
711
|
+
fileData = await readFile();
|
|
712
|
+
}
|
|
713
|
+
}
|
|
583
714
|
else
|
|
584
715
|
fileData = input;
|
|
585
716
|
const data = await this.fetchJson("/v2/upload", {
|
|
@@ -593,6 +724,17 @@ class FileService extends BaseService {
|
|
|
593
724
|
return data.upload_url;
|
|
594
725
|
}
|
|
595
726
|
}
|
|
727
|
+
function dataUrlToBlob(dataUrl) {
|
|
728
|
+
const arr = dataUrl.split(",");
|
|
729
|
+
const mime = arr[0].match(/:(.*?);/)[1];
|
|
730
|
+
const bstr = atob(arr[1]);
|
|
731
|
+
let n = bstr.length;
|
|
732
|
+
const u8arr = new Uint8Array(n);
|
|
733
|
+
while (n--) {
|
|
734
|
+
u8arr[n] = bstr.charCodeAt(n);
|
|
735
|
+
}
|
|
736
|
+
return new Blob([u8arr], { type: mime });
|
|
737
|
+
}
|
|
596
738
|
|
|
597
739
|
const defaultBaseUrl = "https://api.assemblyai.com";
|
|
598
740
|
class AssemblyAI {
|
|
@@ -602,8 +744,9 @@ class AssemblyAI {
|
|
|
602
744
|
*/
|
|
603
745
|
constructor(params) {
|
|
604
746
|
params.baseUrl = params.baseUrl || defaultBaseUrl;
|
|
605
|
-
if (params.baseUrl && params.baseUrl.endsWith("/"))
|
|
747
|
+
if (params.baseUrl && params.baseUrl.endsWith("/")) {
|
|
606
748
|
params.baseUrl = params.baseUrl.slice(0, -1);
|
|
749
|
+
}
|
|
607
750
|
this.files = new FileService(params);
|
|
608
751
|
this.transcripts = new TranscriptService(params, this.files);
|
|
609
752
|
this.lemur = new LemurService(params);
|