plaud 0.1.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/CONTRIBUTING.md +28 -0
- package/LICENSE +22 -0
- package/README.md +101 -0
- package/SECURITY.md +23 -0
- package/dist/auth.js +155 -0
- package/dist/auth.js.map +1 -0
- package/dist/cli.js +583 -0
- package/dist/cli.js.map +1 -0
- package/dist/config.js +52 -0
- package/dist/config.js.map +1 -0
- package/dist/download.js +88 -0
- package/dist/download.js.map +1 -0
- package/dist/export.js +164 -0
- package/dist/export.js.map +1 -0
- package/dist/output.js +52 -0
- package/dist/output.js.map +1 -0
- package/dist/plaud-api.js +145 -0
- package/dist/plaud-api.js.map +1 -0
- package/dist/recordings-format.js +46 -0
- package/dist/recordings-format.js.map +1 -0
- package/docs/CONTRACT_V1.md +218 -0
- package/package.json +53 -0
- package/skills/plaud/SKILL.md +41 -0
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"config.js","sourceRoot":"","sources":["../src/config.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,kBAAkB,CAAC;AAClC,OAAO,EAAE,MAAM,SAAS,CAAC;AACzB,OAAO,IAAI,MAAM,WAAW,CAAC;AAM7B,SAAS,YAAY;IACnB,MAAM,GAAG,GAAG,OAAO,CAAC,GAAG,CAAC,eAAe,CAAC;IACxC,OAAO,GAAG,IAAI,GAAG,CAAC,IAAI,EAAE,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,OAAO,EAAE,EAAE,SAAS,CAAC,CAAC;AACtE,CAAC;AAED,SAAS,aAAa;IACpB,OAAO,IAAI,CAAC,IAAI,CAAC,YAAY,EAAE,EAAE,OAAO,EAAE,aAAa,CAAC,CAAC;AAC3D,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,UAAU;IAC9B,MAAM,UAAU,GAAG,aAAa,EAAE,CAAC;IACnC,IAAI,CAAC;QACH,MAAM,GAAG,GAAG,MAAM,EAAE,CAAC,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC,CAAC;QAClD,MAAM,MAAM,GAAG,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC;QAC/B,OAAO,OAAO,MAAM,KAAK,QAAQ,IAAI,MAAM,CAAC,CAAC,CAAE,MAAsB,CAAC,CAAC,CAAC,EAAE,CAAC;IAC7E,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,EAAE,CAAC;IACZ,CAAC;AACH,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,WAAW,CAAC,MAAmB;IACnD,MAAM,UAAU,GAAG,aAAa,EAAE,CAAC;IACnC,MAAM,EAAE,CAAC,KAAK,CAAC,IAAI,CAAC,OAAO,CAAC,UAAU,CAAC,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;IAC9D,MAAM,IAAI,GAAG,IAAI,CAAC,SAAS,CAAC,MAAM,EAAE,IAAI,EAAE,CAAC,CAAC,CAAC;IAC7C,MAAM,EAAE,CAAC,SAAS,CAAC,UAAU,EAAE,IAAI,EAAE,EAAE,IAAI,EAAE,KAAK,EAAE,CAAC,CAAC;IACtD,iFAAiF;IACjF,IAAI,CAAC;QACH,MAAM,EAAE,CAAC,KAAK,CAAC,UAAU,EAAE,KAAK,CAAC,CAAC;IACpC,CAAC;IAAC,MAAM,CAAC;QACP,SAAS;IACX,CAAC;AACH,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,WAAW;IAC/B,MAAM,UAAU,GAAG,aAAa,EAAE,CAAC;IACnC,IAAI,CAAC;QACH,MAAM,EAAE,CAAC,MAAM,CAAC,UAAU,CAAC,CAAC;IAC9B,CAAC;IAAC,MAAM,CAAC;QACP,SAAS;IACX,CAAC;AACH,CAAC;AAED,MAAM,UAAU,WAAW,CAAC,KAAa;IACvC,IAAI,CAAC,KAAK;QAAE,OAAO,EAAE,CAAC;IACtB,MAAM,KAAK,GAAG,MAAM,CAAC,KAAK,CAAC,CAAC,IAAI,EAAE,CAAC,OAAO,CAAC,aAAa,EAAE,EAAE,CAAC,CAAC;IAC9D,IAAI,KAAK,CAAC,MAAM,IAAI,EAAE;QAAE,OAAO,GAAG,KAAK,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,GAAG,CAAC;IACvD,OAAO,GAAG,KAAK,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,IAAI,KAAK,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC;AACnD,CAAC"}
|
package/dist/download.js
ADDED
|
@@ -0,0 +1,88 @@
|
|
|
1
|
+
import fs from "node:fs/promises";
|
|
2
|
+
import { createWriteStream } from "node:fs";
|
|
3
|
+
import path from "node:path";
|
|
4
|
+
import { Readable } from "node:stream";
|
|
5
|
+
import { getRecordingTempUrls, getRecordingDetailsBatch } from "./plaud-api.js";
|
|
6
|
+
import { formatTranscript, getFilenameWithDate, sanitizeFilename } from "./recordings-format.js";
|
|
7
|
+
async function ensureDir(dir) {
|
|
8
|
+
await fs.mkdir(dir, { recursive: true });
|
|
9
|
+
}
|
|
10
|
+
async function streamToFile({ url, outPath, timeoutMs = 60_000, }) {
|
|
11
|
+
const controller = new AbortController();
|
|
12
|
+
const timeout = setTimeout(() => controller.abort(), timeoutMs);
|
|
13
|
+
try {
|
|
14
|
+
const res = await fetch(url, { signal: controller.signal });
|
|
15
|
+
if (!res.ok)
|
|
16
|
+
throw new Error(`Download failed: HTTP ${res.status} ${res.statusText}`);
|
|
17
|
+
if (!res.body)
|
|
18
|
+
throw new Error("Download failed: empty body");
|
|
19
|
+
await ensureDir(path.dirname(outPath));
|
|
20
|
+
const fileStream = createWriteStream(outPath);
|
|
21
|
+
await new Promise((resolve, reject) => {
|
|
22
|
+
fileStream.on("error", reject);
|
|
23
|
+
fileStream.on("close", resolve);
|
|
24
|
+
Readable.fromWeb(res.body).pipe(fileStream);
|
|
25
|
+
});
|
|
26
|
+
return { bytes: Number(res.headers.get("content-length") || 0) || null };
|
|
27
|
+
}
|
|
28
|
+
finally {
|
|
29
|
+
clearTimeout(timeout);
|
|
30
|
+
}
|
|
31
|
+
}
|
|
32
|
+
async function getDetails({ token, id }) {
|
|
33
|
+
const list = await getRecordingDetailsBatch({ token, ids: [id] });
|
|
34
|
+
const details = Array.isArray(list) ? list.find((d) => String(d?.id || "") === String(id)) : null;
|
|
35
|
+
if (!details)
|
|
36
|
+
throw new Error("Recording not found (or details unavailable)");
|
|
37
|
+
return details;
|
|
38
|
+
}
|
|
39
|
+
function parseWhat(what) {
|
|
40
|
+
const parts = String(what || "")
|
|
41
|
+
.split(",")
|
|
42
|
+
.map((s) => s.trim().toLowerCase())
|
|
43
|
+
.filter(Boolean);
|
|
44
|
+
return new Set(parts.length ? parts : ["transcript", "summary", "json"]);
|
|
45
|
+
}
|
|
46
|
+
export async function downloadRecording({ token, id, outDir, what = "transcript,summary,json", audioFormat = "opus", }) {
|
|
47
|
+
if (!token)
|
|
48
|
+
throw new Error("Missing token");
|
|
49
|
+
if (!id)
|
|
50
|
+
throw new Error("Missing id");
|
|
51
|
+
if (!outDir)
|
|
52
|
+
throw new Error("Missing outDir");
|
|
53
|
+
const whatSet = parseWhat(what);
|
|
54
|
+
const details = await getDetails({ token, id });
|
|
55
|
+
const baseFilename = getFilenameWithDate(details?.filename, { id }, details);
|
|
56
|
+
const written = [];
|
|
57
|
+
await ensureDir(outDir);
|
|
58
|
+
if (whatSet.has("json")) {
|
|
59
|
+
const jsonPath = path.join(outDir, `${baseFilename}.json`);
|
|
60
|
+
await fs.writeFile(jsonPath, JSON.stringify(details, null, 2), "utf8");
|
|
61
|
+
written.push({ kind: "json", path: jsonPath });
|
|
62
|
+
}
|
|
63
|
+
if (whatSet.has("transcript")) {
|
|
64
|
+
const transcript = formatTranscript(details?.trans_result);
|
|
65
|
+
const transcriptPath = path.join(outDir, `${baseFilename}.txt`);
|
|
66
|
+
await fs.writeFile(transcriptPath, transcript, "utf8");
|
|
67
|
+
written.push({ kind: "transcript", path: transcriptPath });
|
|
68
|
+
}
|
|
69
|
+
if (whatSet.has("summary")) {
|
|
70
|
+
const ai = details?.ai_content ? String(details.ai_content) : "";
|
|
71
|
+
const mdPath = path.join(outDir, `${baseFilename}_ai.md`);
|
|
72
|
+
await fs.writeFile(mdPath, ai, "utf8");
|
|
73
|
+
written.push({ kind: "summary", path: mdPath });
|
|
74
|
+
}
|
|
75
|
+
if (whatSet.has("audio")) {
|
|
76
|
+
const temp = await getRecordingTempUrls({ token, id });
|
|
77
|
+
const tempUrl = audioFormat === "original" ? temp?.temp_url : temp?.temp_url_opus || temp?.temp_url;
|
|
78
|
+
if (!tempUrl)
|
|
79
|
+
throw new Error("Audio temp URL not available for this recording");
|
|
80
|
+
const ext = audioFormat === "opus" ? "opus" : "m4a";
|
|
81
|
+
const audioName = sanitizeFilename(`${baseFilename}.${ext}`);
|
|
82
|
+
const audioPath = path.join(outDir, audioName);
|
|
83
|
+
const info = await streamToFile({ url: tempUrl, outPath: audioPath });
|
|
84
|
+
written.push({ kind: "audio", path: audioPath, bytes: info.bytes });
|
|
85
|
+
}
|
|
86
|
+
return { id: String(id), outDir, written };
|
|
87
|
+
}
|
|
88
|
+
//# sourceMappingURL=download.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"download.js","sourceRoot":"","sources":["../src/download.ts"],"names":[],"mappings":"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"}
|
package/dist/export.js
ADDED
|
@@ -0,0 +1,164 @@
|
|
|
1
|
+
import fs from "node:fs/promises";
|
|
2
|
+
import path from "node:path";
|
|
3
|
+
import archiver from "archiver";
|
|
4
|
+
import { createWriteStream } from "node:fs";
|
|
5
|
+
import { listRecordings, getRecordingDetailsBatch } from "./plaud-api.js";
|
|
6
|
+
import { formatTranscript, getFilenameWithDate } from "./recordings-format.js";
|
|
7
|
+
function sleep(ms) {
|
|
8
|
+
return new Promise((resolve) => setTimeout(resolve, ms));
|
|
9
|
+
}
|
|
10
|
+
function parseIsoDate(value) {
|
|
11
|
+
if (!value)
|
|
12
|
+
return null;
|
|
13
|
+
const d = new Date(value);
|
|
14
|
+
if (Number.isNaN(d.getTime()))
|
|
15
|
+
return null;
|
|
16
|
+
return d;
|
|
17
|
+
}
|
|
18
|
+
async function ensureDir(dir) {
|
|
19
|
+
await fs.mkdir(dir, { recursive: true });
|
|
20
|
+
}
|
|
21
|
+
async function exists(p) {
|
|
22
|
+
try {
|
|
23
|
+
await fs.stat(p);
|
|
24
|
+
return true;
|
|
25
|
+
}
|
|
26
|
+
catch {
|
|
27
|
+
return false;
|
|
28
|
+
}
|
|
29
|
+
}
|
|
30
|
+
export async function exportRecordings({ token, outDir, zipPath, includeTrash = false, formats = { txt: true, json: true, md: true }, batchSize = 10, delayMs = 300, max = Infinity, since, until, resume = false, onProgress, }) {
|
|
31
|
+
const sinceDate = parseIsoDate(since || null);
|
|
32
|
+
const untilDate = parseIsoDate(until || null);
|
|
33
|
+
const recordings = await listRecordings({ token, includeTrash, max });
|
|
34
|
+
const filtered = recordings.filter((r) => {
|
|
35
|
+
const ts = r?.start_time || r?.edit_time;
|
|
36
|
+
if (!ts)
|
|
37
|
+
return true;
|
|
38
|
+
const d = new Date(ts);
|
|
39
|
+
if (Number.isNaN(d.getTime()))
|
|
40
|
+
return true;
|
|
41
|
+
if (sinceDate && d < sinceDate)
|
|
42
|
+
return false;
|
|
43
|
+
if (untilDate && d > untilDate)
|
|
44
|
+
return false;
|
|
45
|
+
return true;
|
|
46
|
+
});
|
|
47
|
+
const progress = { current: 0, total: filtered.length };
|
|
48
|
+
const results = [];
|
|
49
|
+
let archive = null;
|
|
50
|
+
let archiveStream = null;
|
|
51
|
+
if (zipPath) {
|
|
52
|
+
await ensureDir(path.dirname(zipPath));
|
|
53
|
+
archiveStream = createWriteStream(zipPath);
|
|
54
|
+
archive = archiver("zip", { zlib: { level: 6 } });
|
|
55
|
+
archive.on("warning", (err) => {
|
|
56
|
+
// eslint-disable-next-line no-console
|
|
57
|
+
console.warn("zip warning:", err?.message || err);
|
|
58
|
+
});
|
|
59
|
+
archive.on("error", (err) => {
|
|
60
|
+
throw err;
|
|
61
|
+
});
|
|
62
|
+
archive.pipe(archiveStream);
|
|
63
|
+
}
|
|
64
|
+
else {
|
|
65
|
+
await ensureDir(outDir);
|
|
66
|
+
await ensureDir(path.join(outDir, "transcripts"));
|
|
67
|
+
await ensureDir(path.join(outDir, "json"));
|
|
68
|
+
await ensureDir(path.join(outDir, "ai-summaries"));
|
|
69
|
+
}
|
|
70
|
+
for (let i = 0; i < filtered.length; i += batchSize) {
|
|
71
|
+
const batch = filtered.slice(i, i + batchSize);
|
|
72
|
+
const ids = batch.map((f) => f.id).filter(Boolean);
|
|
73
|
+
let detailsList = [];
|
|
74
|
+
try {
|
|
75
|
+
detailsList = await getRecordingDetailsBatch({ token, ids });
|
|
76
|
+
}
|
|
77
|
+
catch {
|
|
78
|
+
// If the batch call fails, fall back to single-id requests for this batch.
|
|
79
|
+
detailsList = [];
|
|
80
|
+
for (const id of ids) {
|
|
81
|
+
try {
|
|
82
|
+
const single = await getRecordingDetailsBatch({ token, ids: [id] });
|
|
83
|
+
detailsList.push(...single);
|
|
84
|
+
}
|
|
85
|
+
catch {
|
|
86
|
+
// leave missing
|
|
87
|
+
}
|
|
88
|
+
}
|
|
89
|
+
}
|
|
90
|
+
const detailsById = new Map(detailsList.map((d) => [d.id, d]));
|
|
91
|
+
for (const file of batch) {
|
|
92
|
+
const details = detailsById.get(file.id) || null;
|
|
93
|
+
const filename = getFilenameWithDate(file.filename, file, details);
|
|
94
|
+
try {
|
|
95
|
+
const transcriptText = formats.txt ? formatTranscript(details?.trans_result) : null;
|
|
96
|
+
const jsonText = formats.json ? JSON.stringify(details ?? {}, null, 2) : null;
|
|
97
|
+
const aiText = formats.md ? (details?.ai_content ? String(details.ai_content) : "") : null;
|
|
98
|
+
const jsonRel = `json/${filename}.json`;
|
|
99
|
+
const txtRel = `transcripts/${filename}.txt`;
|
|
100
|
+
const mdRel = `ai-summaries/${filename}_ai.md`;
|
|
101
|
+
if (archive) {
|
|
102
|
+
if (formats.json)
|
|
103
|
+
archive.append(jsonText, { name: jsonRel });
|
|
104
|
+
if (formats.txt && transcriptText)
|
|
105
|
+
archive.append(transcriptText, { name: txtRel });
|
|
106
|
+
if (formats.md && aiText)
|
|
107
|
+
archive.append(aiText, { name: mdRel });
|
|
108
|
+
}
|
|
109
|
+
else {
|
|
110
|
+
const jsonPath = path.join(outDir, jsonRel);
|
|
111
|
+
const txtPath = path.join(outDir, txtRel);
|
|
112
|
+
const mdPath = path.join(outDir, mdRel);
|
|
113
|
+
if (formats.json) {
|
|
114
|
+
if (!resume || !(await exists(jsonPath)))
|
|
115
|
+
await fs.writeFile(jsonPath, jsonText || "{}", "utf8");
|
|
116
|
+
}
|
|
117
|
+
if (formats.txt && transcriptText) {
|
|
118
|
+
if (!resume || !(await exists(txtPath)))
|
|
119
|
+
await fs.writeFile(txtPath, transcriptText, "utf8");
|
|
120
|
+
}
|
|
121
|
+
if (formats.md && aiText) {
|
|
122
|
+
if (!resume || !(await exists(mdPath)))
|
|
123
|
+
await fs.writeFile(mdPath, aiText, "utf8");
|
|
124
|
+
}
|
|
125
|
+
}
|
|
126
|
+
results.push({ success: true, id: String(file.id), filename: file.filename });
|
|
127
|
+
}
|
|
128
|
+
catch (error) {
|
|
129
|
+
results.push({ success: false, id: String(file.id), filename: file.filename, error: error?.message });
|
|
130
|
+
}
|
|
131
|
+
progress.current++;
|
|
132
|
+
if (onProgress)
|
|
133
|
+
onProgress({ ...progress });
|
|
134
|
+
}
|
|
135
|
+
if (delayMs > 0)
|
|
136
|
+
await sleep(delayMs);
|
|
137
|
+
}
|
|
138
|
+
const summary = {
|
|
139
|
+
exportDate: new Date().toISOString(),
|
|
140
|
+
totalFiles: filtered.length,
|
|
141
|
+
successful: results.filter((r) => r.success).length,
|
|
142
|
+
failed: results.filter((r) => !r.success),
|
|
143
|
+
includesTrash: includeTrash,
|
|
144
|
+
since: since || null,
|
|
145
|
+
until: until || null,
|
|
146
|
+
};
|
|
147
|
+
if (archive) {
|
|
148
|
+
archive.append(JSON.stringify(summary, null, 2), { name: "export_summary.json" });
|
|
149
|
+
archive.finalize();
|
|
150
|
+
await new Promise((resolve, reject) => {
|
|
151
|
+
archiveStream.on("close", resolve);
|
|
152
|
+
archiveStream.on("error", reject);
|
|
153
|
+
});
|
|
154
|
+
}
|
|
155
|
+
else {
|
|
156
|
+
await fs.writeFile(path.join(outDir, "export_summary.json"), JSON.stringify(summary, null, 2), "utf8");
|
|
157
|
+
}
|
|
158
|
+
return {
|
|
159
|
+
...summary,
|
|
160
|
+
outDir: zipPath ? null : outDir,
|
|
161
|
+
zipPath: zipPath || null,
|
|
162
|
+
};
|
|
163
|
+
}
|
|
164
|
+
//# sourceMappingURL=export.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"export.js","sourceRoot":"","sources":["../src/export.ts"],"names":[],"mappings":"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"}
|
package/dist/output.js
ADDED
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
function isObject(value) {
|
|
2
|
+
return !!value && typeof value === "object" && !Array.isArray(value);
|
|
3
|
+
}
|
|
4
|
+
export function toErrorCode(err) {
|
|
5
|
+
const status = err?.status;
|
|
6
|
+
if (status === 401 || status === 403)
|
|
7
|
+
return "AUTH_INVALID";
|
|
8
|
+
if (status === 404)
|
|
9
|
+
return "NOT_FOUND";
|
|
10
|
+
if (status === 429)
|
|
11
|
+
return "RATE_LIMITED";
|
|
12
|
+
if (typeof status === "number" && status >= 500)
|
|
13
|
+
return "UPSTREAM_5XX";
|
|
14
|
+
if (err?.name === "AbortError")
|
|
15
|
+
return "TIMEOUT";
|
|
16
|
+
return "UNKNOWN";
|
|
17
|
+
}
|
|
18
|
+
export function isRetryable(err) {
|
|
19
|
+
const code = toErrorCode(err);
|
|
20
|
+
return code === "RATE_LIMITED" || code === "UPSTREAM_5XX" || code === "TIMEOUT";
|
|
21
|
+
}
|
|
22
|
+
export function makeError(err, { code, message } = {}) {
|
|
23
|
+
const status = err?.status;
|
|
24
|
+
const errorData = err?.data;
|
|
25
|
+
const resolvedCode = code || toErrorCode(err);
|
|
26
|
+
const resolvedMessage = message || err?.message || "Request failed";
|
|
27
|
+
const base = {
|
|
28
|
+
code: resolvedCode,
|
|
29
|
+
message: resolvedMessage,
|
|
30
|
+
retryable: isRetryable(err),
|
|
31
|
+
};
|
|
32
|
+
if (typeof status === "number")
|
|
33
|
+
base.http = { status };
|
|
34
|
+
// Keep error details small and non-sensitive.
|
|
35
|
+
if (isObject(errorData)) {
|
|
36
|
+
const detail = errorData.detail || errorData.msg || errorData.message;
|
|
37
|
+
if (detail && String(detail) !== resolvedMessage)
|
|
38
|
+
base.detail = String(detail);
|
|
39
|
+
}
|
|
40
|
+
return base;
|
|
41
|
+
}
|
|
42
|
+
export function printJson(obj) {
|
|
43
|
+
// eslint-disable-next-line no-console
|
|
44
|
+
console.log(JSON.stringify(obj, null, 2));
|
|
45
|
+
}
|
|
46
|
+
export function ok(data, meta) {
|
|
47
|
+
return meta ? { ok: true, data, meta } : { ok: true, data };
|
|
48
|
+
}
|
|
49
|
+
export function fail(error, meta) {
|
|
50
|
+
return meta ? { ok: false, error, meta } : { ok: false, error };
|
|
51
|
+
}
|
|
52
|
+
//# sourceMappingURL=output.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"output.js","sourceRoot":"","sources":["../src/output.ts"],"names":[],"mappings":"AAAA,SAAS,QAAQ,CAAC,KAAc;IAC9B,OAAO,CAAC,CAAC,KAAK,IAAI,OAAO,KAAK,KAAK,QAAQ,IAAI,CAAC,KAAK,CAAC,OAAO,CAAC,KAAK,CAAC,CAAC;AACvE,CAAC;AAUD,MAAM,UAAU,WAAW,CAAC,GAAQ;IAClC,MAAM,MAAM,GAAG,GAAG,EAAE,MAA4B,CAAC;IACjD,IAAI,MAAM,KAAK,GAAG,IAAI,MAAM,KAAK,GAAG;QAAE,OAAO,cAAc,CAAC;IAC5D,IAAI,MAAM,KAAK,GAAG;QAAE,OAAO,WAAW,CAAC;IACvC,IAAI,MAAM,KAAK,GAAG;QAAE,OAAO,cAAc,CAAC;IAC1C,IAAI,OAAO,MAAM,KAAK,QAAQ,IAAI,MAAM,IAAI,GAAG;QAAE,OAAO,cAAc,CAAC;IACvE,IAAI,GAAG,EAAE,IAAI,KAAK,YAAY;QAAE,OAAO,SAAS,CAAC;IACjD,OAAO,SAAS,CAAC;AACnB,CAAC;AAED,MAAM,UAAU,WAAW,CAAC,GAAQ;IAClC,MAAM,IAAI,GAAG,WAAW,CAAC,GAAG,CAAC,CAAC;IAC9B,OAAO,IAAI,KAAK,cAAc,IAAI,IAAI,KAAK,cAAc,IAAI,IAAI,KAAK,SAAS,CAAC;AAClF,CAAC;AAED,MAAM,UAAU,SAAS,CAAC,GAAQ,EAAE,EAAE,IAAI,EAAE,OAAO,KAA0C,EAAE;IAC7F,MAAM,MAAM,GAAG,GAAG,EAAE,MAA4B,CAAC;IACjD,MAAM,SAAS,GAAG,GAAG,EAAE,IAAe,CAAC;IACvC,MAAM,YAAY,GAAG,IAAI,IAAI,WAAW,CAAC,GAAG,CAAC,CAAC;IAC9C,MAAM,eAAe,GAAG,OAAO,IAAI,GAAG,EAAE,OAAO,IAAI,gBAAgB,CAAC;IAEpE,MAAM,IAAI,GAAa;QACrB,IAAI,EAAE,YAAY;QAClB,OAAO,EAAE,eAAe;QACxB,SAAS,EAAE,WAAW,CAAC,GAAG,CAAC;KAC5B,CAAC;IAEF,IAAI,OAAO,MAAM,KAAK,QAAQ;QAAE,IAAI,CAAC,IAAI,GAAG,EAAE,MAAM,EAAE,CAAC;IAEvD,8CAA8C;IAC9C,IAAI,QAAQ,CAAC,SAAS,CAAC,EAAE,CAAC;QACxB,MAAM,MAAM,GAAG,SAAS,CAAC,MAAM,IAAI,SAAS,CAAC,GAAG,IAAI,SAAS,CAAC,OAAO,CAAC;QACtE,IAAI,MAAM,IAAI,MAAM,CAAC,MAAM,CAAC,KAAK,eAAe;YAAE,IAAI,CAAC,MAAM,GAAG,MAAM,CAAC,MAAM,CAAC,CAAC;IACjF,CAAC;IAED,OAAO,IAAI,CAAC;AACd,CAAC;AAMD,MAAM,UAAU,SAAS,CAAC,GAAY;IACpC,sCAAsC;IACtC,OAAO,CAAC,GAAG,CAAC,IAAI,CAAC,SAAS,CAAC,GAAG,EAAE,IAAI,EAAE,CAAC,CAAC,CAAC,CAAC;AAC5C,CAAC;AAED,MAAM,UAAU,EAAE,CAAI,IAAO,EAAE,IAA8B;IAC3D,OAAO,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,IAAI,EAAE,IAAI,EAAE,CAAC;AAC9D,CAAC;AAED,MAAM,UAAU,IAAI,CAAC,KAAe,EAAE,IAA8B;IAClE,OAAO,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,KAAK,EAAE,KAAK,EAAE,IAAI,EAAE,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,KAAK,EAAE,KAAK,EAAE,CAAC;AAClE,CAAC"}
|
|
@@ -0,0 +1,145 @@
|
|
|
1
|
+
import { readConfig } from "./config.js";
|
|
2
|
+
const BASE_URL = "https://api.plaud.ai";
|
|
3
|
+
function sleep(ms) {
|
|
4
|
+
return new Promise((resolve) => setTimeout(resolve, ms));
|
|
5
|
+
}
|
|
6
|
+
function cleanToken(token) {
|
|
7
|
+
return String(token || "")
|
|
8
|
+
.trim()
|
|
9
|
+
.replace(/^bearer\s+/i, "");
|
|
10
|
+
}
|
|
11
|
+
export async function resolveAuthToken() {
|
|
12
|
+
if (process.env.PLAUD_AUTH_TOKEN)
|
|
13
|
+
return cleanToken(process.env.PLAUD_AUTH_TOKEN);
|
|
14
|
+
const config = await readConfig();
|
|
15
|
+
if (config?.authToken)
|
|
16
|
+
return cleanToken(config.authToken);
|
|
17
|
+
return "";
|
|
18
|
+
}
|
|
19
|
+
async function readJsonOrThrow(response) {
|
|
20
|
+
let data;
|
|
21
|
+
try {
|
|
22
|
+
data = await response.json();
|
|
23
|
+
}
|
|
24
|
+
catch {
|
|
25
|
+
data = null;
|
|
26
|
+
}
|
|
27
|
+
if (response.ok)
|
|
28
|
+
return data;
|
|
29
|
+
const detail = (data && typeof data === "object" && (data.detail || data.msg || data.message)) || "";
|
|
30
|
+
const message = detail ? String(detail) : `HTTP ${response.status} ${response.statusText}`;
|
|
31
|
+
const error = new Error(message);
|
|
32
|
+
error.status = response.status;
|
|
33
|
+
error.data = data;
|
|
34
|
+
throw error;
|
|
35
|
+
}
|
|
36
|
+
export async function plaudRequest({ token, endpoint, method = "GET", body, timeoutMs = 30_000, retries = 4, }) {
|
|
37
|
+
const url = `${BASE_URL}${endpoint}`;
|
|
38
|
+
const headers = {
|
|
39
|
+
accept: "application/json, text/plain, */*",
|
|
40
|
+
"accept-language": "en-US,en;q=0.9",
|
|
41
|
+
"app-platform": "web",
|
|
42
|
+
authorization: `bearer ${cleanToken(token)}`,
|
|
43
|
+
"content-type": "application/json",
|
|
44
|
+
dnt: "1",
|
|
45
|
+
"edit-from": "web",
|
|
46
|
+
origin: "https://app.plaud.ai",
|
|
47
|
+
referer: "https://app.plaud.ai/",
|
|
48
|
+
};
|
|
49
|
+
for (let attempt = 0; attempt <= retries; attempt++) {
|
|
50
|
+
const controller = new AbortController();
|
|
51
|
+
const timeout = setTimeout(() => controller.abort(), timeoutMs);
|
|
52
|
+
try {
|
|
53
|
+
const response = await fetch(url, {
|
|
54
|
+
method,
|
|
55
|
+
headers,
|
|
56
|
+
body: body === undefined ? undefined : JSON.stringify(body),
|
|
57
|
+
signal: controller.signal,
|
|
58
|
+
});
|
|
59
|
+
return await readJsonOrThrow(response);
|
|
60
|
+
}
|
|
61
|
+
catch (error) {
|
|
62
|
+
const isLast = attempt === retries;
|
|
63
|
+
const status = error?.status;
|
|
64
|
+
const transient = error?.name === "AbortError" ||
|
|
65
|
+
status === 429 ||
|
|
66
|
+
(typeof status === "number" && status >= 500);
|
|
67
|
+
if (isLast || !transient)
|
|
68
|
+
throw error;
|
|
69
|
+
const backoffMs = Math.min(10_000, 500 * 2 ** attempt);
|
|
70
|
+
await sleep(backoffMs);
|
|
71
|
+
}
|
|
72
|
+
finally {
|
|
73
|
+
clearTimeout(timeout);
|
|
74
|
+
}
|
|
75
|
+
}
|
|
76
|
+
// unreachable
|
|
77
|
+
throw new Error("Request failed");
|
|
78
|
+
}
|
|
79
|
+
export async function getMe({ token }) {
|
|
80
|
+
return await plaudRequest({ token, endpoint: "/user/me", timeoutMs: 15_000, retries: 1 });
|
|
81
|
+
}
|
|
82
|
+
export async function getRecordingTempUrls({ token, id }) {
|
|
83
|
+
if (!id)
|
|
84
|
+
throw new Error("Missing recording id");
|
|
85
|
+
return await plaudRequest({ token, endpoint: `/file/temp-url/${encodeURIComponent(String(id))}` });
|
|
86
|
+
}
|
|
87
|
+
function parseFileListResponse(listResponse) {
|
|
88
|
+
if (!listResponse || typeof listResponse !== "object")
|
|
89
|
+
return [];
|
|
90
|
+
if (listResponse.detail && String(listResponse.detail).toLowerCase().includes("token")) {
|
|
91
|
+
throw new Error("Auth token expired/invalid. Re-run `plaud auth set`.");
|
|
92
|
+
}
|
|
93
|
+
if (listResponse.status !== undefined && listResponse.status !== 0) {
|
|
94
|
+
throw new Error(listResponse.msg || listResponse.message || "API error");
|
|
95
|
+
}
|
|
96
|
+
const candidates = [
|
|
97
|
+
listResponse.data_file_list,
|
|
98
|
+
listResponse.files,
|
|
99
|
+
listResponse.data,
|
|
100
|
+
listResponse.dataFileList,
|
|
101
|
+
listResponse.list,
|
|
102
|
+
listResponse.file_list,
|
|
103
|
+
listResponse.items,
|
|
104
|
+
listResponse.records,
|
|
105
|
+
];
|
|
106
|
+
for (const c of candidates) {
|
|
107
|
+
if (Array.isArray(c))
|
|
108
|
+
return c;
|
|
109
|
+
}
|
|
110
|
+
return [];
|
|
111
|
+
}
|
|
112
|
+
export async function listRecordings({ token, includeTrash = false, pageSize = 200, max = Infinity, }) {
|
|
113
|
+
const isTrash = includeTrash ? 2 : 0;
|
|
114
|
+
const recordings = [];
|
|
115
|
+
let skip = 0;
|
|
116
|
+
while (recordings.length < max) {
|
|
117
|
+
const limit = Math.min(pageSize, max - recordings.length);
|
|
118
|
+
const res = await plaudRequest({
|
|
119
|
+
token,
|
|
120
|
+
endpoint: `/file/simple/web?skip=${skip}&limit=${limit}&is_trash=${isTrash}&sort_by=start_time&is_desc=true`,
|
|
121
|
+
});
|
|
122
|
+
const batch = parseFileListResponse(res);
|
|
123
|
+
if (batch.length === 0)
|
|
124
|
+
break;
|
|
125
|
+
recordings.push(...batch);
|
|
126
|
+
skip += batch.length;
|
|
127
|
+
if (batch.length < limit)
|
|
128
|
+
break;
|
|
129
|
+
}
|
|
130
|
+
return recordings;
|
|
131
|
+
}
|
|
132
|
+
export async function getRecordingDetailsBatch({ token, ids }) {
|
|
133
|
+
if (!Array.isArray(ids) || ids.length === 0)
|
|
134
|
+
return [];
|
|
135
|
+
const res = await plaudRequest({
|
|
136
|
+
token,
|
|
137
|
+
endpoint: "/file/list?support_mul_summ=true",
|
|
138
|
+
method: "POST",
|
|
139
|
+
body: ids,
|
|
140
|
+
});
|
|
141
|
+
if (res?.status === 0 && Array.isArray(res?.data_file_list))
|
|
142
|
+
return res.data_file_list;
|
|
143
|
+
return [];
|
|
144
|
+
}
|
|
145
|
+
//# sourceMappingURL=plaud-api.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"plaud-api.js","sourceRoot":"","sources":["../src/plaud-api.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAE,MAAM,aAAa,CAAC;AAEzC,MAAM,QAAQ,GAAG,sBAAsB,CAAC;AAIxC,SAAS,KAAK,CAAC,EAAU;IACvB,OAAO,IAAI,OAAO,CAAC,CAAC,OAAO,EAAE,EAAE,CAAC,UAAU,CAAC,OAAO,EAAE,EAAE,CAAC,CAAC,CAAC;AAC3D,CAAC;AAED,SAAS,UAAU,CAAC,KAAa;IAC/B,OAAO,MAAM,CAAC,KAAK,IAAI,EAAE,CAAC;SACvB,IAAI,EAAE;SACN,OAAO,CAAC,aAAa,EAAE,EAAE,CAAC,CAAC;AAChC,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,gBAAgB;IACpC,IAAI,OAAO,CAAC,GAAG,CAAC,gBAAgB;QAAE,OAAO,UAAU,CAAC,OAAO,CAAC,GAAG,CAAC,gBAAgB,CAAC,CAAC;IAElF,MAAM,MAAM,GAAG,MAAM,UAAU,EAAE,CAAC;IAClC,IAAI,MAAM,EAAE,SAAS;QAAE,OAAO,UAAU,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;IAE3D,OAAO,EAAE,CAAC;AACZ,CAAC;AAED,KAAK,UAAU,eAAe,CAAC,QAAkB;IAC/C,IAAI,IAAS,CAAC;IACd,IAAI,CAAC;QACH,IAAI,GAAG,MAAM,QAAQ,CAAC,IAAI,EAAE,CAAC;IAC/B,CAAC;IAAC,MAAM,CAAC;QACP,IAAI,GAAG,IAAI,CAAC;IACd,CAAC;IAED,IAAI,QAAQ,CAAC,EAAE;QAAE,OAAO,IAAI,CAAC;IAE7B,MAAM,MAAM,GACV,CAAC,IAAI,IAAI,OAAO,IAAI,KAAK,QAAQ,IAAI,CAAC,IAAI,CAAC,MAAM,IAAI,IAAI,CAAC,GAAG,IAAI,IAAI,CAAC,OAAO,CAAC,CAAC,IAAI,EAAE,CAAC;IACxF,MAAM,OAAO,GAAG,MAAM,CAAC,CAAC,CAAC,MAAM,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,QAAQ,QAAQ,CAAC,MAAM,IAAI,QAAQ,CAAC,UAAU,EAAE,CAAC;IAC3F,MAAM,KAAK,GAAG,IAAI,KAAK,CAAC,OAAO,CAAkB,CAAC;IAClD,KAAK,CAAC,MAAM,GAAG,QAAQ,CAAC,MAAM,CAAC;IAC/B,KAAK,CAAC,IAAI,GAAG,IAAI,CAAC;IAClB,MAAM,KAAK,CAAC;AACd,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,YAAY,CAAC,EACjC,KAAK,EACL,QAAQ,EACR,MAAM,GAAG,KAAK,EACd,IAAI,EACJ,SAAS,GAAG,MAAM,EAClB,OAAO,GAAG,CAAC,GAQZ;IACC,MAAM,GAAG,GAAG,GAAG,QAAQ,GAAG,QAAQ,EAAE,CAAC;IACrC,MAAM,OAAO,GAA2B;QACtC,MAAM,EAAE,mCAAmC;QAC3C,iBAAiB,EAAE,gBAAgB;QACnC,cAAc,EAAE,KAAK;QACrB,aAAa,EAAE,UAAU,UAAU,CAAC,KAAK,CAAC,EAAE;QAC5C,cAAc,EAAE,kBAAkB;QAClC,GAAG,EAAE,GAAG;QACR,WAAW,EAAE,KAAK;QAClB,MAAM,EAAE,sBAAsB;QAC9B,OAAO,EAAE,uBAAuB;KACjC,CAAC;IAEF,KAAK,IAAI,OAAO,GAAG,CAAC,EAAE,OAAO,IAAI,OAAO,EAAE,OAAO,EAAE,EAAE,CAAC;QACpD,MAAM,UAAU,GAAG,IAAI,eAAe,EAAE,CAAC;QACzC,MAAM,OAAO,GAAG,UAAU,CAAC,GAAG,EAAE,CAAC,UAAU,CAAC,KAAK,EAAE,EAAE,SAAS,CAAC,CAAC;QAChE,IAAI,CAAC;YACH,MAAM,QAAQ,GAAG,MAAM,KAAK,CAAC,GAAG,EAAE;gBAChC,MAAM;gBACN,OAAO;gBACP,IAAI,EAAE,IAAI,KAAK,SAAS,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC;gBAC3D,MAAM,EAAE,UAAU,CAAC,MAAM;aAC1B,CAAC,CAAC;YACH,OAAO,MAAM,eAAe,CAAC,QAAQ,CAAC,CAAC;QACzC,CAAC;QAAC,OAAO,KAAU,EAAE,CAAC;YACpB,MAAM,MAAM,GAAG,OAAO,KAAK,OAAO,CAAC;YACnC,MAAM,MAAM,GAAG,KAAK,EAAE,MAA4B,CAAC;YACnD,MAAM,SAAS,GACb,KAAK,EAAE,IAAI,KAAK,YAAY;gBAC5B,MAAM,KAAK,GAAG;gBACd,CAAC,OAAO,MAAM,KAAK,QAAQ,IAAI,MAAM,IAAI,GAAG,CAAC,CAAC;YAEhD,IAAI,MAAM,IAAI,CAAC,SAAS;gBAAE,MAAM,KAAK,CAAC;YAEtC,MAAM,SAAS,GAAG,IAAI,CAAC,GAAG,CAAC,MAAM,EAAE,GAAG,GAAG,CAAC,IAAI,OAAO,CAAC,CAAC;YACvD,MAAM,KAAK,CAAC,SAAS,CAAC,CAAC;QACzB,CAAC;gBAAS,CAAC;YACT,YAAY,CAAC,OAAO,CAAC,CAAC;QACxB,CAAC;IACH,CAAC;IAED,cAAc;IACd,MAAM,IAAI,KAAK,CAAC,gBAAgB,CAAC,CAAC;AACpC,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,KAAK,CAAC,EAAE,KAAK,EAAqB;IACtD,OAAO,MAAM,YAAY,CAAC,EAAE,KAAK,EAAE,QAAQ,EAAE,UAAU,EAAE,SAAS,EAAE,MAAM,EAAE,OAAO,EAAE,CAAC,EAAE,CAAC,CAAC;AAC5F,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,oBAAoB,CAAC,EAAE,KAAK,EAAE,EAAE,EAAiC;IACrF,IAAI,CAAC,EAAE;QAAE,MAAM,IAAI,KAAK,CAAC,sBAAsB,CAAC,CAAC;IACjD,OAAO,MAAM,YAAY,CAAC,EAAE,KAAK,EAAE,QAAQ,EAAE,kBAAkB,kBAAkB,CAAC,MAAM,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;AACrG,CAAC;AAED,SAAS,qBAAqB,CAAC,YAAiB;IAC9C,IAAI,CAAC,YAAY,IAAI,OAAO,YAAY,KAAK,QAAQ;QAAE,OAAO,EAAE,CAAC;IAEjE,IAAI,YAAY,CAAC,MAAM,IAAI,MAAM,CAAC,YAAY,CAAC,MAAM,CAAC,CAAC,WAAW,EAAE,CAAC,QAAQ,CAAC,OAAO,CAAC,EAAE,CAAC;QACvF,MAAM,IAAI,KAAK,CAAC,sDAAsD,CAAC,CAAC;IAC1E,CAAC;IAED,IAAI,YAAY,CAAC,MAAM,KAAK,SAAS,IAAI,YAAY,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;QACnE,MAAM,IAAI,KAAK,CAAC,YAAY,CAAC,GAAG,IAAI,YAAY,CAAC,OAAO,IAAI,WAAW,CAAC,CAAC;IAC3E,CAAC;IAED,MAAM,UAAU,GAAG;QACjB,YAAY,CAAC,cAAc;QAC3B,YAAY,CAAC,KAAK;QAClB,YAAY,CAAC,IAAI;QACjB,YAAY,CAAC,YAAY;QACzB,YAAY,CAAC,IAAI;QACjB,YAAY,CAAC,SAAS;QACtB,YAAY,CAAC,KAAK;QAClB,YAAY,CAAC,OAAO;KACrB,CAAC;IAEF,KAAK,MAAM,CAAC,IAAI,UAAU,EAAE,CAAC;QAC3B,IAAI,KAAK,CAAC,OAAO,CAAC,CAAC,CAAC;YAAE,OAAO,CAAC,CAAC;IACjC,CAAC;IAED,OAAO,EAAE,CAAC;AACZ,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,cAAc,CAAC,EACnC,KAAK,EACL,YAAY,GAAG,KAAK,EACpB,QAAQ,GAAG,GAAG,EACd,GAAG,GAAG,QAAQ,GAMf;IACC,MAAM,OAAO,GAAG,YAAY,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IACrC,MAAM,UAAU,GAAU,EAAE,CAAC;IAC7B,IAAI,IAAI,GAAG,CAAC,CAAC;IAEb,OAAO,UAAU,CAAC,MAAM,GAAG,GAAG,EAAE,CAAC;QAC/B,MAAM,KAAK,GAAG,IAAI,CAAC,GAAG,CAAC,QAAQ,EAAE,GAAG,GAAG,UAAU,CAAC,MAAM,CAAC,CAAC;QAC1D,MAAM,GAAG,GAAG,MAAM,YAAY,CAAC;YAC7B,KAAK;YACL,QAAQ,EAAE,yBAAyB,IAAI,UAAU,KAAK,aAAa,OAAO,kCAAkC;SAC7G,CAAC,CAAC;QACH,MAAM,KAAK,GAAG,qBAAqB,CAAC,GAAG,CAAC,CAAC;QACzC,IAAI,KAAK,CAAC,MAAM,KAAK,CAAC;YAAE,MAAM;QAC9B,UAAU,CAAC,IAAI,CAAC,GAAG,KAAK,CAAC,CAAC;QAC1B,IAAI,IAAI,KAAK,CAAC,MAAM,CAAC;QACrB,IAAI,KAAK,CAAC,MAAM,GAAG,KAAK;YAAE,MAAM;IAClC,CAAC;IAED,OAAO,UAAU,CAAC;AACpB,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,wBAAwB,CAAC,EAAE,KAAK,EAAE,GAAG,EAAoC;IAC7F,IAAI,CAAC,KAAK,CAAC,OAAO,CAAC,GAAG,CAAC,IAAI,GAAG,CAAC,MAAM,KAAK,CAAC;QAAE,OAAO,EAAE,CAAC;IACvD,MAAM,GAAG,GAAG,MAAM,YAAY,CAAC;QAC7B,KAAK;QACL,QAAQ,EAAE,kCAAkC;QAC5C,MAAM,EAAE,MAAM;QACd,IAAI,EAAE,GAAG;KACV,CAAC,CAAC;IAEH,IAAI,GAAG,EAAE,MAAM,KAAK,CAAC,IAAI,KAAK,CAAC,OAAO,CAAC,GAAG,EAAE,cAAc,CAAC;QAAE,OAAO,GAAG,CAAC,cAAc,CAAC;IACvF,OAAO,EAAE,CAAC;AACZ,CAAC"}
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
function formatTime(milliseconds) {
|
|
2
|
+
const totalSeconds = Math.floor(Number(milliseconds || 0) / 1000);
|
|
3
|
+
const hours = Math.floor(totalSeconds / 3600);
|
|
4
|
+
const minutes = Math.floor((totalSeconds % 3600) / 60);
|
|
5
|
+
const seconds = totalSeconds % 60;
|
|
6
|
+
if (hours > 0) {
|
|
7
|
+
return `${hours}:${String(minutes).padStart(2, "0")}:${String(seconds).padStart(2, "0")}`;
|
|
8
|
+
}
|
|
9
|
+
return `${String(minutes).padStart(2, "0")}:${String(seconds).padStart(2, "0")}`;
|
|
10
|
+
}
|
|
11
|
+
function formatDate(timestamp) {
|
|
12
|
+
if (!timestamp)
|
|
13
|
+
return "";
|
|
14
|
+
const date = new Date(timestamp);
|
|
15
|
+
if (Number.isNaN(date.getTime()))
|
|
16
|
+
return "";
|
|
17
|
+
const year = date.getFullYear();
|
|
18
|
+
const month = String(date.getMonth() + 1).padStart(2, "0");
|
|
19
|
+
const day = String(date.getDate()).padStart(2, "0");
|
|
20
|
+
return `${year}-${month}-${day}`;
|
|
21
|
+
}
|
|
22
|
+
export function sanitizeFilename(filename) {
|
|
23
|
+
return String(filename || "untitled")
|
|
24
|
+
.replace(/[<>:"/\\|?*]/g, "-")
|
|
25
|
+
.replace(/\s+/g, "_")
|
|
26
|
+
.slice(0, 200);
|
|
27
|
+
}
|
|
28
|
+
export function getFilenameWithDate(baseFilename, file, details) {
|
|
29
|
+
const timestamp = details?.start_time || file?.start_time || details?.edit_time || file?.edit_time;
|
|
30
|
+
const datePrefix = formatDate(timestamp);
|
|
31
|
+
const sanitized = sanitizeFilename(baseFilename || file?.id || "untitled");
|
|
32
|
+
return datePrefix ? `${datePrefix}_${sanitized}` : sanitized;
|
|
33
|
+
}
|
|
34
|
+
export function formatTranscript(segments) {
|
|
35
|
+
if (!Array.isArray(segments))
|
|
36
|
+
return "";
|
|
37
|
+
return segments
|
|
38
|
+
.map((segment) => {
|
|
39
|
+
const time = formatTime(segment.start_time);
|
|
40
|
+
const speaker = segment.speaker || "Speaker";
|
|
41
|
+
const content = segment.content || "";
|
|
42
|
+
return `[${time}] ${speaker}: ${content}`;
|
|
43
|
+
})
|
|
44
|
+
.join("\n\n");
|
|
45
|
+
}
|
|
46
|
+
//# sourceMappingURL=recordings-format.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"recordings-format.js","sourceRoot":"","sources":["../src/recordings-format.ts"],"names":[],"mappings":"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"}
|