@olares/lares-core 0.15.6 → 0.15.9
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +2 -1
- package/brand/identity.js +33 -3
- package/drive/cat.js +62 -0
- package/drive/download.js +3 -3
- package/drive/execute.js +8 -2
- package/drive/files-path.js +33 -0
- package/drive/flowstudio-files.js +87 -0
- package/drive/ls.js +3 -3
- package/drive/paths.js +23 -13
- package/drive/tools.js +4 -2
- package/entrance/surface.js +96 -0
- package/files/app-link.js +64 -0
- package/files/backend-client.js +266 -0
- package/files/deliverables.js +55 -1
- package/files/intake.js +0 -63
- package/files/mention.js +1 -51
- package/files/preview-groups.js +71 -3
- package/files/preview-local.js +69 -0
- package/files/preview-workspace.js +114 -13
- package/files/preview.js +171 -16
- package/files/produced-gate.js +197 -0
- package/files/produced-mentions.js +19 -0
- package/files/published-tools.js +69 -0
- package/files/published-turn-data.js +84 -0
- package/i18n/chat-model.js +5 -5
- package/i18n/mcp.js +83 -0
- package/i18n/mobile.js +100 -2
- package/i18n/preview.js +10 -0
- package/i18n/search.js +13 -7
- package/i18n/skills.js +31 -0
- package/i18n/voice.js +88 -19
- package/larepass/chat.js +9 -0
- package/larepass/host.js +7 -2
- package/larepass/mux.js +210 -2
- package/larepass/process-fold.js +239 -0
- package/larepass/queue.js +44 -0
- package/larepass/rpc.js +50 -3
- package/larepass/runtime.js +215 -83
- package/larepass/session-cache.js +6 -0
- package/larepass/settings.js +15 -7
- package/larepass/transcript.js +49 -11
- package/mcp/approval.js +152 -0
- package/mcp/client.js +38 -0
- package/mcp/config.js +139 -0
- package/media/catalog-row.js +244 -0
- package/media/generation.js +707 -0
- package/media/tool.js +92 -0
- package/olares/entrance.js +67 -15
- package/olares/identity.js +13 -136
- package/olares/session-identity.js +12 -12
- package/olares/trusted-host.js +0 -29
- package/package.json +48 -4
- package/router/catalog-cache.d.ts +1 -1
- package/router/catalog-cache.js +25 -14
- package/router/catalog-sync.js +8 -3
- package/router/catalog.d.ts +6 -1
- package/router/catalog.js +18 -2
- package/router/gateway.d.ts +9 -1
- package/router/gateway.js +40 -4
- package/router/gemini-schema.js +125 -0
- package/router/generation-guard.js +82 -0
- package/router/models.d.ts +6 -0
- package/router/models.js +22 -3
- package/router/search.js +10 -2
- package/router/session-model.js +53 -0
- package/router/shim.js +104 -3
- package/router/sref.js +126 -0
- package/router/stt.js +43 -12
- package/router/tts.js +118 -0
- package/search/client.js +5 -3
- package/search/config.js +53 -39
- package/search/menu.js +45 -10
- package/skills/client.js +42 -0
- package/skills/packs.js +40 -0
- package/skills/state.d.ts +22 -0
- package/skills/state.js +142 -0
- package/tools/crypto-uuid.js +3 -6
- package/tools/head-script.js +15 -0
- package/voice/agent.js +50 -0
- package/voice/capture.js +250 -0
- package/voice/client.js +126 -24
- package/voice/config.js +11 -1
- package/voice/duplex.js +44 -0
- package/voice/endpoint.js +57 -0
- package/voice/host/bluetooth-ready.py +1196 -0
- package/voice/host/install-host.sh +102 -0
- package/voice/input.js +4 -0
- package/voice/install.js +146 -0
- package/voice/languages.js +11 -1
- package/voice/link.js +86 -0
- package/voice/pcm.js +100 -0
- package/voice/playback.js +7 -0
- package/voice/problem.js +46 -0
- package/voice/recorder.js +79 -4
- package/voice/script.js +35 -0
- package/voice/service.js +253 -10
- package/voice/session.js +128 -0
- package/voice/speech.js +93 -0
- package/files/preview-cache.js +0 -100
package/voice/duplex.js
ADDED
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* One headset call link is half duplex. The newest recording owns it and
|
|
3
|
+
* invalidates synthesis that has not reached the speaker yet.
|
|
4
|
+
*/
|
|
5
|
+
export function createDuplexCoordinator(stopPlayback = async () => {}) {
|
|
6
|
+
let speech = null;
|
|
7
|
+
|
|
8
|
+
function beginSpeech(externalSignal) {
|
|
9
|
+
if (speech) {
|
|
10
|
+
speech.controller.abort();
|
|
11
|
+
void Promise.resolve(stopPlayback()).catch(() => {});
|
|
12
|
+
}
|
|
13
|
+
const controller = new AbortController();
|
|
14
|
+
const lease = {
|
|
15
|
+
controller,
|
|
16
|
+
active() {
|
|
17
|
+
return speech === lease && !controller.signal.aborted;
|
|
18
|
+
},
|
|
19
|
+
finish() {
|
|
20
|
+
if (speech === lease) speech = null;
|
|
21
|
+
},
|
|
22
|
+
};
|
|
23
|
+
speech = lease;
|
|
24
|
+
if (externalSignal) {
|
|
25
|
+
const abort = () => {
|
|
26
|
+
if (speech === lease) speech = null;
|
|
27
|
+
controller.abort();
|
|
28
|
+
void Promise.resolve(stopPlayback()).catch(() => {});
|
|
29
|
+
};
|
|
30
|
+
if (externalSignal.aborted) abort();
|
|
31
|
+
else externalSignal.addEventListener("abort", abort, { once: true });
|
|
32
|
+
}
|
|
33
|
+
return { signal: controller.signal, active: lease.active, finish: lease.finish };
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
async function interrupt() {
|
|
37
|
+
const current = speech;
|
|
38
|
+
speech = null;
|
|
39
|
+
current?.controller.abort();
|
|
40
|
+
await stopPlayback();
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
return { beginSpeech, interrupt };
|
|
44
|
+
}
|
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Decide when a take is over from Silero's per-frame speech probability and the
|
|
3
|
+
* frame's loudness. A conference mic hears the whole room, so a frame only
|
|
4
|
+
* counts as the speaker when it is human speech and within `relative` of the
|
|
5
|
+
* loudest speech already heard in this take. Farther voices then do not hold
|
|
6
|
+
* the recording open.
|
|
7
|
+
*/
|
|
8
|
+
export const ENDPOINT = {
|
|
9
|
+
speechProb: 0.5,
|
|
10
|
+
// Phrase endpointing, the same default speech platforms use for a request
|
|
11
|
+
// (Azure end-of-silence is 500ms). Dictation waits 1.5–2s; a chat turn should not.
|
|
12
|
+
silenceMs: 500,
|
|
13
|
+
minSpeechMs: 250,
|
|
14
|
+
relative: 0.3,
|
|
15
|
+
floor: 0.004,
|
|
16
|
+
smoothFrames: 5,
|
|
17
|
+
};
|
|
18
|
+
|
|
19
|
+
export function frameRms(frame) {
|
|
20
|
+
if (!frame?.length) return 0;
|
|
21
|
+
let sum = 0;
|
|
22
|
+
for (let i = 0; i < frame.length; i += 1) sum += frame[i] * frame[i];
|
|
23
|
+
return Math.sqrt(sum / frame.length);
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
export function createSpeechEndpoint(options = {}) {
|
|
27
|
+
const o = { ...ENDPOINT, ...options };
|
|
28
|
+
const recent = [];
|
|
29
|
+
let reference = 0;
|
|
30
|
+
let speechMs = 0;
|
|
31
|
+
let quietMs = 0;
|
|
32
|
+
let ended = false;
|
|
33
|
+
|
|
34
|
+
return {
|
|
35
|
+
/** @returns {boolean} true once, on the frame that ends the take */
|
|
36
|
+
push(prob, rms, frameMs) {
|
|
37
|
+
if (ended) return false;
|
|
38
|
+
recent.push(rms);
|
|
39
|
+
if (recent.length > o.smoothFrames) recent.shift();
|
|
40
|
+
const level = recent.reduce((sum, value) => sum + value, 0) / recent.length;
|
|
41
|
+
const human = prob >= o.speechProb;
|
|
42
|
+
if (human && level > reference) reference = level;
|
|
43
|
+
const near = human && level >= Math.max(o.floor, reference * o.relative);
|
|
44
|
+
if (near) {
|
|
45
|
+
speechMs += frameMs;
|
|
46
|
+
quietMs = 0;
|
|
47
|
+
} else {
|
|
48
|
+
quietMs += frameMs;
|
|
49
|
+
}
|
|
50
|
+
if (speechMs >= o.minSpeechMs && quietMs >= o.silenceMs) {
|
|
51
|
+
ended = true;
|
|
52
|
+
return true;
|
|
53
|
+
}
|
|
54
|
+
return false;
|
|
55
|
+
},
|
|
56
|
+
};
|
|
57
|
+
}
|