@langchain/vue 0.4.7 → 1.0.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/README.md +84 -364
- package/dist/context.cjs +2 -2
- package/dist/context.cjs.map +1 -1
- package/dist/context.d.cts +4 -5
- package/dist/context.d.cts.map +1 -1
- package/dist/context.d.ts +4 -5
- package/dist/context.d.ts.map +1 -1
- package/dist/context.js +1 -1
- package/dist/context.js.map +1 -1
- package/dist/index.cjs +30 -222
- package/dist/index.d.cts +10 -24
- package/dist/index.d.ts +10 -24
- package/dist/index.js +9 -198
- package/dist/selectors.cjs +170 -0
- package/dist/selectors.cjs.map +1 -0
- package/dist/selectors.d.cts +133 -0
- package/dist/selectors.d.cts.map +1 -0
- package/dist/selectors.d.ts +133 -0
- package/dist/selectors.d.ts.map +1 -0
- package/dist/selectors.js +160 -0
- package/dist/selectors.js.map +1 -0
- package/dist/use-audio-player.cjs +591 -0
- package/dist/use-audio-player.cjs.map +1 -0
- package/dist/use-audio-player.d.cts +69 -0
- package/dist/use-audio-player.d.cts.map +1 -0
- package/dist/use-audio-player.d.ts +69 -0
- package/dist/use-audio-player.d.ts.map +1 -0
- package/dist/use-audio-player.js +591 -0
- package/dist/use-audio-player.js.map +1 -0
- package/dist/use-media-url.cjs +51 -0
- package/dist/use-media-url.cjs.map +1 -0
- package/dist/use-media-url.d.cts +29 -0
- package/dist/use-media-url.d.cts.map +1 -0
- package/dist/use-media-url.d.ts +29 -0
- package/dist/use-media-url.d.ts.map +1 -0
- package/dist/use-media-url.js +51 -0
- package/dist/use-media-url.js.map +1 -0
- package/dist/use-projection.cjs +66 -0
- package/dist/use-projection.cjs.map +1 -0
- package/dist/use-projection.d.cts +39 -0
- package/dist/use-projection.d.cts.map +1 -0
- package/dist/use-projection.d.ts +39 -0
- package/dist/use-projection.d.ts.map +1 -0
- package/dist/use-projection.js +66 -0
- package/dist/use-projection.js.map +1 -0
- package/dist/use-stream.cjs +169 -0
- package/dist/use-stream.cjs.map +1 -0
- package/dist/use-stream.d.cts +118 -0
- package/dist/use-stream.d.cts.map +1 -0
- package/dist/use-stream.d.ts +118 -0
- package/dist/use-stream.d.ts.map +1 -0
- package/dist/use-stream.js +167 -0
- package/dist/use-stream.js.map +1 -0
- package/dist/use-video-player.cjs +212 -0
- package/dist/use-video-player.cjs.map +1 -0
- package/dist/use-video-player.d.cts +57 -0
- package/dist/use-video-player.d.cts.map +1 -0
- package/dist/use-video-player.d.ts +57 -0
- package/dist/use-video-player.d.ts.map +1 -0
- package/dist/use-video-player.js +212 -0
- package/dist/use-video-player.js.map +1 -0
- package/package.json +10 -8
- package/dist/index.cjs.map +0 -1
- package/dist/index.d.cts.map +0 -1
- package/dist/index.d.ts.map +0 -1
- package/dist/index.js.map +0 -1
- package/dist/stream.custom.cjs +0 -133
- package/dist/stream.custom.cjs.map +0 -1
- package/dist/stream.custom.js +0 -133
- package/dist/stream.custom.js.map +0 -1
- package/dist/subagents.cjs +0 -76
- package/dist/subagents.cjs.map +0 -1
- package/dist/subagents.js +0 -76
- package/dist/subagents.js.map +0 -1
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
let vue = require("vue");
|
|
2
|
+
//#region src/use-media-url.ts
|
|
3
|
+
/**
|
|
4
|
+
* Resolve the lazy {@link MediaBase.objectURL} promise into a
|
|
5
|
+
* reactive string suitable for `<audio src>`, `<img src>`,
|
|
6
|
+
* `<video src>`, or `<a download href>`. Returns `undefined` until
|
|
7
|
+
* the URL is available.
|
|
8
|
+
*
|
|
9
|
+
* Lifecycle:
|
|
10
|
+
* - On setup (or whenever the supplied `media` value changes), the
|
|
11
|
+
* composable awaits `media.objectURL` and commits the resolved
|
|
12
|
+
* string to state.
|
|
13
|
+
* - On scope disposal (or when `media` changes), the composable
|
|
14
|
+
* calls `media.revoke()` to free the blob URL slot. The next
|
|
15
|
+
* consumer that accesses `media.objectURL` mints a fresh URL from
|
|
16
|
+
* the same `Blob`, so live re-renders just work.
|
|
17
|
+
* - If the underlying handle errored before settling, the URL stays
|
|
18
|
+
* `undefined`. Surface the failure via `media.error`.
|
|
19
|
+
*
|
|
20
|
+
* `media` accepts a raw handle, a `Ref<MediaBase | undefined>`, or a
|
|
21
|
+
* getter, so the composable can rebind automatically to the latest
|
|
22
|
+
* media without a manual watcher at the call site.
|
|
23
|
+
*/
|
|
24
|
+
function useMediaURL(media) {
|
|
25
|
+
const url = (0, vue.ref)();
|
|
26
|
+
let currentMedia;
|
|
27
|
+
let cancelled = false;
|
|
28
|
+
const detach = () => {
|
|
29
|
+
cancelled = true;
|
|
30
|
+
if (currentMedia != null) try {
|
|
31
|
+
currentMedia.revoke();
|
|
32
|
+
} catch {}
|
|
33
|
+
currentMedia = void 0;
|
|
34
|
+
url.value = void 0;
|
|
35
|
+
};
|
|
36
|
+
(0, vue.watch)(() => (0, vue.toValue)(media), (next) => {
|
|
37
|
+
detach();
|
|
38
|
+
if (next == null) return;
|
|
39
|
+
cancelled = false;
|
|
40
|
+
currentMedia = next;
|
|
41
|
+
next.objectURL.then((resolved) => {
|
|
42
|
+
if (!cancelled) url.value = resolved;
|
|
43
|
+
}, () => {});
|
|
44
|
+
}, { immediate: true });
|
|
45
|
+
(0, vue.onScopeDispose)(detach);
|
|
46
|
+
return url;
|
|
47
|
+
}
|
|
48
|
+
//#endregion
|
|
49
|
+
exports.useMediaURL = useMediaURL;
|
|
50
|
+
|
|
51
|
+
//# sourceMappingURL=use-media-url.cjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"use-media-url.cjs","names":[],"sources":["../src/use-media-url.ts"],"sourcesContent":["import {\n ref,\n watch,\n onScopeDispose,\n toValue,\n type MaybeRefOrGetter,\n type Ref,\n} from \"vue\";\nimport type { MediaBase } from \"@langchain/langgraph-sdk/stream\";\n\n/**\n * Resolve the lazy {@link MediaBase.objectURL} promise into a\n * reactive string suitable for `<audio src>`, `<img src>`,\n * `<video src>`, or `<a download href>`. Returns `undefined` until\n * the URL is available.\n *\n * Lifecycle:\n * - On setup (or whenever the supplied `media` value changes), the\n * composable awaits `media.objectURL` and commits the resolved\n * string to state.\n * - On scope disposal (or when `media` changes), the composable\n * calls `media.revoke()` to free the blob URL slot. The next\n * consumer that accesses `media.objectURL` mints a fresh URL from\n * the same `Blob`, so live re-renders just work.\n * - If the underlying handle errored before settling, the URL stays\n * `undefined`. Surface the failure via `media.error`.\n *\n * `media` accepts a raw handle, a `Ref<MediaBase | undefined>`, or a\n * getter, so the composable can rebind automatically to the latest\n * media without a manual watcher at the call site.\n */\nexport function useMediaURL(\n media: MaybeRefOrGetter<MediaBase | undefined>\n): Readonly<Ref<string | undefined>> {\n const url = ref<string | undefined>();\n\n let currentMedia: MediaBase | undefined;\n let cancelled = false;\n\n const detach = () => {\n cancelled = true;\n if (currentMedia != null) {\n try {\n currentMedia.revoke();\n } catch {\n // best-effort\n }\n }\n currentMedia = undefined;\n url.value = undefined;\n };\n\n watch(\n () => toValue(media),\n (next) => {\n detach();\n if (next == null) return;\n cancelled = false;\n currentMedia = next;\n next.objectURL.then(\n (resolved) => {\n if (!cancelled) url.value = resolved;\n },\n () => {\n // Errors surfaced via `media.error`; keep `url` undefined\n // so consumers fall through to a no-src render.\n }\n );\n },\n { immediate: true }\n );\n\n onScopeDispose(detach);\n\n return url;\n}\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;AA+BA,SAAgB,YACd,OACmC;CACnC,MAAM,OAAA,GAAA,IAAA,MAA+B;CAErC,IAAI;CACJ,IAAI,YAAY;CAEhB,MAAM,eAAe;AACnB,cAAY;AACZ,MAAI,gBAAgB,KAClB,KAAI;AACF,gBAAa,QAAQ;UACf;AAIV,iBAAe,KAAA;AACf,MAAI,QAAQ,KAAA;;AAGd,EAAA,GAAA,IAAA,cAAA,GAAA,IAAA,SACgB,MAAM,GACnB,SAAS;AACR,UAAQ;AACR,MAAI,QAAQ,KAAM;AAClB,cAAY;AACZ,iBAAe;AACf,OAAK,UAAU,MACZ,aAAa;AACZ,OAAI,CAAC,UAAW,KAAI,QAAQ;WAExB,GAIP;IAEH,EAAE,WAAW,MAAM,CACpB;AAED,EAAA,GAAA,IAAA,gBAAe,OAAO;AAEtB,QAAO"}
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
import { MaybeRefOrGetter, Ref } from "vue";
|
|
2
|
+
import { MediaBase } from "@langchain/langgraph-sdk/stream";
|
|
3
|
+
|
|
4
|
+
//#region src/use-media-url.d.ts
|
|
5
|
+
/**
|
|
6
|
+
* Resolve the lazy {@link MediaBase.objectURL} promise into a
|
|
7
|
+
* reactive string suitable for `<audio src>`, `<img src>`,
|
|
8
|
+
* `<video src>`, or `<a download href>`. Returns `undefined` until
|
|
9
|
+
* the URL is available.
|
|
10
|
+
*
|
|
11
|
+
* Lifecycle:
|
|
12
|
+
* - On setup (or whenever the supplied `media` value changes), the
|
|
13
|
+
* composable awaits `media.objectURL` and commits the resolved
|
|
14
|
+
* string to state.
|
|
15
|
+
* - On scope disposal (or when `media` changes), the composable
|
|
16
|
+
* calls `media.revoke()` to free the blob URL slot. The next
|
|
17
|
+
* consumer that accesses `media.objectURL` mints a fresh URL from
|
|
18
|
+
* the same `Blob`, so live re-renders just work.
|
|
19
|
+
* - If the underlying handle errored before settling, the URL stays
|
|
20
|
+
* `undefined`. Surface the failure via `media.error`.
|
|
21
|
+
*
|
|
22
|
+
* `media` accepts a raw handle, a `Ref<MediaBase | undefined>`, or a
|
|
23
|
+
* getter, so the composable can rebind automatically to the latest
|
|
24
|
+
* media without a manual watcher at the call site.
|
|
25
|
+
*/
|
|
26
|
+
declare function useMediaURL(media: MaybeRefOrGetter<MediaBase | undefined>): Readonly<Ref<string | undefined>>;
|
|
27
|
+
//#endregion
|
|
28
|
+
export { useMediaURL };
|
|
29
|
+
//# sourceMappingURL=use-media-url.d.cts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"use-media-url.d.cts","names":[],"sources":["../src/use-media-url.ts"],"mappings":";;;;;;AA+BA;;;;;;;;;;;;;;;;;;;iBAAgB,WAAA,CACd,KAAA,EAAO,gBAAA,CAAiB,SAAA,gBACvB,QAAA,CAAS,GAAA"}
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
import { MaybeRefOrGetter, Ref } from "vue";
|
|
2
|
+
import { MediaBase } from "@langchain/langgraph-sdk/stream";
|
|
3
|
+
|
|
4
|
+
//#region src/use-media-url.d.ts
|
|
5
|
+
/**
|
|
6
|
+
* Resolve the lazy {@link MediaBase.objectURL} promise into a
|
|
7
|
+
* reactive string suitable for `<audio src>`, `<img src>`,
|
|
8
|
+
* `<video src>`, or `<a download href>`. Returns `undefined` until
|
|
9
|
+
* the URL is available.
|
|
10
|
+
*
|
|
11
|
+
* Lifecycle:
|
|
12
|
+
* - On setup (or whenever the supplied `media` value changes), the
|
|
13
|
+
* composable awaits `media.objectURL` and commits the resolved
|
|
14
|
+
* string to state.
|
|
15
|
+
* - On scope disposal (or when `media` changes), the composable
|
|
16
|
+
* calls `media.revoke()` to free the blob URL slot. The next
|
|
17
|
+
* consumer that accesses `media.objectURL` mints a fresh URL from
|
|
18
|
+
* the same `Blob`, so live re-renders just work.
|
|
19
|
+
* - If the underlying handle errored before settling, the URL stays
|
|
20
|
+
* `undefined`. Surface the failure via `media.error`.
|
|
21
|
+
*
|
|
22
|
+
* `media` accepts a raw handle, a `Ref<MediaBase | undefined>`, or a
|
|
23
|
+
* getter, so the composable can rebind automatically to the latest
|
|
24
|
+
* media without a manual watcher at the call site.
|
|
25
|
+
*/
|
|
26
|
+
declare function useMediaURL(media: MaybeRefOrGetter<MediaBase | undefined>): Readonly<Ref<string | undefined>>;
|
|
27
|
+
//#endregion
|
|
28
|
+
export { useMediaURL };
|
|
29
|
+
//# sourceMappingURL=use-media-url.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"use-media-url.d.ts","names":[],"sources":["../src/use-media-url.ts"],"mappings":";;;;;;AA+BA;;;;;;;;;;;;;;;;;;;iBAAgB,WAAA,CACd,KAAA,EAAO,gBAAA,CAAiB,SAAA,gBACvB,QAAA,CAAS,GAAA"}
|
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
import { onScopeDispose, ref, toValue, watch } from "vue";
|
|
2
|
+
//#region src/use-media-url.ts
|
|
3
|
+
/**
|
|
4
|
+
* Resolve the lazy {@link MediaBase.objectURL} promise into a
|
|
5
|
+
* reactive string suitable for `<audio src>`, `<img src>`,
|
|
6
|
+
* `<video src>`, or `<a download href>`. Returns `undefined` until
|
|
7
|
+
* the URL is available.
|
|
8
|
+
*
|
|
9
|
+
* Lifecycle:
|
|
10
|
+
* - On setup (or whenever the supplied `media` value changes), the
|
|
11
|
+
* composable awaits `media.objectURL` and commits the resolved
|
|
12
|
+
* string to state.
|
|
13
|
+
* - On scope disposal (or when `media` changes), the composable
|
|
14
|
+
* calls `media.revoke()` to free the blob URL slot. The next
|
|
15
|
+
* consumer that accesses `media.objectURL` mints a fresh URL from
|
|
16
|
+
* the same `Blob`, so live re-renders just work.
|
|
17
|
+
* - If the underlying handle errored before settling, the URL stays
|
|
18
|
+
* `undefined`. Surface the failure via `media.error`.
|
|
19
|
+
*
|
|
20
|
+
* `media` accepts a raw handle, a `Ref<MediaBase | undefined>`, or a
|
|
21
|
+
* getter, so the composable can rebind automatically to the latest
|
|
22
|
+
* media without a manual watcher at the call site.
|
|
23
|
+
*/
|
|
24
|
+
function useMediaURL(media) {
|
|
25
|
+
const url = ref();
|
|
26
|
+
let currentMedia;
|
|
27
|
+
let cancelled = false;
|
|
28
|
+
const detach = () => {
|
|
29
|
+
cancelled = true;
|
|
30
|
+
if (currentMedia != null) try {
|
|
31
|
+
currentMedia.revoke();
|
|
32
|
+
} catch {}
|
|
33
|
+
currentMedia = void 0;
|
|
34
|
+
url.value = void 0;
|
|
35
|
+
};
|
|
36
|
+
watch(() => toValue(media), (next) => {
|
|
37
|
+
detach();
|
|
38
|
+
if (next == null) return;
|
|
39
|
+
cancelled = false;
|
|
40
|
+
currentMedia = next;
|
|
41
|
+
next.objectURL.then((resolved) => {
|
|
42
|
+
if (!cancelled) url.value = resolved;
|
|
43
|
+
}, () => {});
|
|
44
|
+
}, { immediate: true });
|
|
45
|
+
onScopeDispose(detach);
|
|
46
|
+
return url;
|
|
47
|
+
}
|
|
48
|
+
//#endregion
|
|
49
|
+
export { useMediaURL };
|
|
50
|
+
|
|
51
|
+
//# sourceMappingURL=use-media-url.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"use-media-url.js","names":[],"sources":["../src/use-media-url.ts"],"sourcesContent":["import {\n ref,\n watch,\n onScopeDispose,\n toValue,\n type MaybeRefOrGetter,\n type Ref,\n} from \"vue\";\nimport type { MediaBase } from \"@langchain/langgraph-sdk/stream\";\n\n/**\n * Resolve the lazy {@link MediaBase.objectURL} promise into a\n * reactive string suitable for `<audio src>`, `<img src>`,\n * `<video src>`, or `<a download href>`. Returns `undefined` until\n * the URL is available.\n *\n * Lifecycle:\n * - On setup (or whenever the supplied `media` value changes), the\n * composable awaits `media.objectURL` and commits the resolved\n * string to state.\n * - On scope disposal (or when `media` changes), the composable\n * calls `media.revoke()` to free the blob URL slot. The next\n * consumer that accesses `media.objectURL` mints a fresh URL from\n * the same `Blob`, so live re-renders just work.\n * - If the underlying handle errored before settling, the URL stays\n * `undefined`. Surface the failure via `media.error`.\n *\n * `media` accepts a raw handle, a `Ref<MediaBase | undefined>`, or a\n * getter, so the composable can rebind automatically to the latest\n * media without a manual watcher at the call site.\n */\nexport function useMediaURL(\n media: MaybeRefOrGetter<MediaBase | undefined>\n): Readonly<Ref<string | undefined>> {\n const url = ref<string | undefined>();\n\n let currentMedia: MediaBase | undefined;\n let cancelled = false;\n\n const detach = () => {\n cancelled = true;\n if (currentMedia != null) {\n try {\n currentMedia.revoke();\n } catch {\n // best-effort\n }\n }\n currentMedia = undefined;\n url.value = undefined;\n };\n\n watch(\n () => toValue(media),\n (next) => {\n detach();\n if (next == null) return;\n cancelled = false;\n currentMedia = next;\n next.objectURL.then(\n (resolved) => {\n if (!cancelled) url.value = resolved;\n },\n () => {\n // Errors surfaced via `media.error`; keep `url` undefined\n // so consumers fall through to a no-src render.\n }\n );\n },\n { immediate: true }\n );\n\n onScopeDispose(detach);\n\n return url;\n}\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;AA+BA,SAAgB,YACd,OACmC;CACnC,MAAM,MAAM,KAAyB;CAErC,IAAI;CACJ,IAAI,YAAY;CAEhB,MAAM,eAAe;AACnB,cAAY;AACZ,MAAI,gBAAgB,KAClB,KAAI;AACF,gBAAa,QAAQ;UACf;AAIV,iBAAe,KAAA;AACf,MAAI,QAAQ,KAAA;;AAGd,aACQ,QAAQ,MAAM,GACnB,SAAS;AACR,UAAQ;AACR,MAAI,QAAQ,KAAM;AAClB,cAAY;AACZ,iBAAe;AACf,OAAK,UAAU,MACZ,aAAa;AACZ,OAAI,CAAC,UAAW,KAAI,QAAQ;WAExB,GAIP;IAEH,EAAE,WAAW,MAAM,CACpB;AAED,gBAAe,OAAO;AAEtB,QAAO"}
|
|
@@ -0,0 +1,66 @@
|
|
|
1
|
+
let vue = require("vue");
|
|
2
|
+
//#region src/use-projection.ts
|
|
3
|
+
/**
|
|
4
|
+
* Vue primitive that composes {@link ChannelRegistry.acquire} with
|
|
5
|
+
* Vue's reactivity system.
|
|
6
|
+
*
|
|
7
|
+
* Contract (mirrors the React `useProjection` hook but adapted to
|
|
8
|
+
* Vue's `setup` + `onScopeDispose` lifecycle):
|
|
9
|
+
*
|
|
10
|
+
* - On `setup()` (or whenever `registry` / `key` change) the
|
|
11
|
+
* composable acquires a ref-counted projection from the registry
|
|
12
|
+
* and subscribes to its store. Vue re-renders automatically
|
|
13
|
+
* whenever the store's snapshot changes.
|
|
14
|
+
* - On `onScopeDispose` (or when `registry` / `key` change) the
|
|
15
|
+
* previous acquisition is released. If this was the last consumer
|
|
16
|
+
* of that spec, the registry closes the underlying server
|
|
17
|
+
* subscription.
|
|
18
|
+
* - When `registry` is `null`/`undefined` the composable stays at
|
|
19
|
+
* `initialValue`. This is the happy path for root-served
|
|
20
|
+
* projections (`useMessages`, `useToolCalls`, `useValues`) which
|
|
21
|
+
* delegate to the always-on root store instead of acquiring a new
|
|
22
|
+
* registry projection.
|
|
23
|
+
*
|
|
24
|
+
* `registry` and `key` accept `MaybeRefOrGetter` so selector
|
|
25
|
+
* composables can pass a reactive target (e.g. a computed subagent
|
|
26
|
+
* snapshot) and have the projection rebind automatically.
|
|
27
|
+
*
|
|
28
|
+
* Returns a `Readonly<ShallowRef<T>>` so templates auto-unwrap and
|
|
29
|
+
* scripts can `computed(() => proj.value)`. The underlying ref is
|
|
30
|
+
* `shallowRef` — consumers that mutate the snapshot get undefined
|
|
31
|
+
* behaviour; stream projections should always be treated as
|
|
32
|
+
* immutable snapshots.
|
|
33
|
+
*/
|
|
34
|
+
function useProjection(registry, specFactory, key, initialValue) {
|
|
35
|
+
const state = (0, vue.shallowRef)(initialValue);
|
|
36
|
+
let currentRelease = null;
|
|
37
|
+
let currentUnsubscribe = null;
|
|
38
|
+
const detach = () => {
|
|
39
|
+
currentUnsubscribe?.();
|
|
40
|
+
currentUnsubscribe = null;
|
|
41
|
+
currentRelease?.();
|
|
42
|
+
currentRelease = null;
|
|
43
|
+
};
|
|
44
|
+
(0, vue.watch)(() => [(0, vue.toValue)(registry), (0, vue.toValue)(key)], ([nextRegistry]) => {
|
|
45
|
+
detach();
|
|
46
|
+
if (nextRegistry == null) {
|
|
47
|
+
state.value = initialValue;
|
|
48
|
+
return;
|
|
49
|
+
}
|
|
50
|
+
const acquired = nextRegistry.acquire(specFactory());
|
|
51
|
+
state.value = acquired.store.getSnapshot();
|
|
52
|
+
currentUnsubscribe = acquired.store.subscribe(() => {
|
|
53
|
+
state.value = acquired.store.getSnapshot();
|
|
54
|
+
});
|
|
55
|
+
currentRelease = acquired.release;
|
|
56
|
+
}, {
|
|
57
|
+
immediate: true,
|
|
58
|
+
flush: "sync"
|
|
59
|
+
});
|
|
60
|
+
(0, vue.onScopeDispose)(detach);
|
|
61
|
+
return (0, vue.readonly)(state);
|
|
62
|
+
}
|
|
63
|
+
//#endregion
|
|
64
|
+
exports.useProjection = useProjection;
|
|
65
|
+
|
|
66
|
+
//# sourceMappingURL=use-projection.cjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"use-projection.cjs","names":[],"sources":["../src/use-projection.ts"],"sourcesContent":["import {\n onScopeDispose,\n readonly,\n shallowRef,\n toValue,\n watch,\n type MaybeRefOrGetter,\n type ShallowRef,\n} from \"vue\";\nimport type {\n ChannelRegistry,\n ProjectionSpec,\n} from \"@langchain/langgraph-sdk/stream\";\n\n/**\n * Vue primitive that composes {@link ChannelRegistry.acquire} with\n * Vue's reactivity system.\n *\n * Contract (mirrors the React `useProjection` hook but adapted to\n * Vue's `setup` + `onScopeDispose` lifecycle):\n *\n * - On `setup()` (or whenever `registry` / `key` change) the\n * composable acquires a ref-counted projection from the registry\n * and subscribes to its store. Vue re-renders automatically\n * whenever the store's snapshot changes.\n * - On `onScopeDispose` (or when `registry` / `key` change) the\n * previous acquisition is released. If this was the last consumer\n * of that spec, the registry closes the underlying server\n * subscription.\n * - When `registry` is `null`/`undefined` the composable stays at\n * `initialValue`. This is the happy path for root-served\n * projections (`useMessages`, `useToolCalls`, `useValues`) which\n * delegate to the always-on root store instead of acquiring a new\n * registry projection.\n *\n * `registry` and `key` accept `MaybeRefOrGetter` so selector\n * composables can pass a reactive target (e.g. a computed subagent\n * snapshot) and have the projection rebind automatically.\n *\n * Returns a `Readonly<ShallowRef<T>>` so templates auto-unwrap and\n * scripts can `computed(() => proj.value)`. The underlying ref is\n * `shallowRef` — consumers that mutate the snapshot get undefined\n * behaviour; stream projections should always be treated as\n * immutable snapshots.\n */\nexport function useProjection<T>(\n registry: MaybeRefOrGetter<ChannelRegistry | null | undefined>,\n specFactory: () => ProjectionSpec<T>,\n key: MaybeRefOrGetter<string>,\n initialValue: T\n): Readonly<ShallowRef<T>> {\n const state = shallowRef<T>(initialValue);\n let currentRelease: (() => void) | null = null;\n let currentUnsubscribe: (() => void) | null = null;\n\n const detach = () => {\n currentUnsubscribe?.();\n currentUnsubscribe = null;\n currentRelease?.();\n currentRelease = null;\n };\n\n watch(\n () => [toValue(registry), toValue(key)] as const,\n ([nextRegistry]) => {\n detach();\n if (nextRegistry == null) {\n state.value = initialValue;\n return;\n }\n const acquired = nextRegistry.acquire(specFactory());\n state.value = acquired.store.getSnapshot();\n currentUnsubscribe = acquired.store.subscribe(() => {\n state.value = acquired.store.getSnapshot();\n });\n currentRelease = acquired.release;\n },\n { immediate: true, flush: \"sync\" }\n );\n\n onScopeDispose(detach);\n\n return readonly(state) as Readonly<ShallowRef<T>>;\n}\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AA6CA,SAAgB,cACd,UACA,aACA,KACA,cACyB;CACzB,MAAM,SAAA,GAAA,IAAA,YAAsB,aAAa;CACzC,IAAI,iBAAsC;CAC1C,IAAI,qBAA0C;CAE9C,MAAM,eAAe;AACnB,wBAAsB;AACtB,uBAAqB;AACrB,oBAAkB;AAClB,mBAAiB;;AAGnB,EAAA,GAAA,IAAA,aACQ,EAAA,GAAA,IAAA,SAAS,SAAS,GAAA,GAAA,IAAA,SAAU,IAAI,CAAC,GACtC,CAAC,kBAAkB;AAClB,UAAQ;AACR,MAAI,gBAAgB,MAAM;AACxB,SAAM,QAAQ;AACd;;EAEF,MAAM,WAAW,aAAa,QAAQ,aAAa,CAAC;AACpD,QAAM,QAAQ,SAAS,MAAM,aAAa;AAC1C,uBAAqB,SAAS,MAAM,gBAAgB;AAClD,SAAM,QAAQ,SAAS,MAAM,aAAa;IAC1C;AACF,mBAAiB,SAAS;IAE5B;EAAE,WAAW;EAAM,OAAO;EAAQ,CACnC;AAED,EAAA,GAAA,IAAA,gBAAe,OAAO;AAEtB,SAAA,GAAA,IAAA,UAAgB,MAAM"}
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
import { MaybeRefOrGetter, ShallowRef } from "vue";
|
|
2
|
+
import { ChannelRegistry, ProjectionSpec } from "@langchain/langgraph-sdk/stream";
|
|
3
|
+
|
|
4
|
+
//#region src/use-projection.d.ts
|
|
5
|
+
/**
|
|
6
|
+
* Vue primitive that composes {@link ChannelRegistry.acquire} with
|
|
7
|
+
* Vue's reactivity system.
|
|
8
|
+
*
|
|
9
|
+
* Contract (mirrors the React `useProjection` hook but adapted to
|
|
10
|
+
* Vue's `setup` + `onScopeDispose` lifecycle):
|
|
11
|
+
*
|
|
12
|
+
* - On `setup()` (or whenever `registry` / `key` change) the
|
|
13
|
+
* composable acquires a ref-counted projection from the registry
|
|
14
|
+
* and subscribes to its store. Vue re-renders automatically
|
|
15
|
+
* whenever the store's snapshot changes.
|
|
16
|
+
* - On `onScopeDispose` (or when `registry` / `key` change) the
|
|
17
|
+
* previous acquisition is released. If this was the last consumer
|
|
18
|
+
* of that spec, the registry closes the underlying server
|
|
19
|
+
* subscription.
|
|
20
|
+
* - When `registry` is `null`/`undefined` the composable stays at
|
|
21
|
+
* `initialValue`. This is the happy path for root-served
|
|
22
|
+
* projections (`useMessages`, `useToolCalls`, `useValues`) which
|
|
23
|
+
* delegate to the always-on root store instead of acquiring a new
|
|
24
|
+
* registry projection.
|
|
25
|
+
*
|
|
26
|
+
* `registry` and `key` accept `MaybeRefOrGetter` so selector
|
|
27
|
+
* composables can pass a reactive target (e.g. a computed subagent
|
|
28
|
+
* snapshot) and have the projection rebind automatically.
|
|
29
|
+
*
|
|
30
|
+
* Returns a `Readonly<ShallowRef<T>>` so templates auto-unwrap and
|
|
31
|
+
* scripts can `computed(() => proj.value)`. The underlying ref is
|
|
32
|
+
* `shallowRef` — consumers that mutate the snapshot get undefined
|
|
33
|
+
* behaviour; stream projections should always be treated as
|
|
34
|
+
* immutable snapshots.
|
|
35
|
+
*/
|
|
36
|
+
declare function useProjection<T>(registry: MaybeRefOrGetter<ChannelRegistry | null | undefined>, specFactory: () => ProjectionSpec<T>, key: MaybeRefOrGetter<string>, initialValue: T): Readonly<ShallowRef<T>>;
|
|
37
|
+
//#endregion
|
|
38
|
+
export { useProjection };
|
|
39
|
+
//# sourceMappingURL=use-projection.d.cts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"use-projection.d.cts","names":[],"sources":["../src/use-projection.ts"],"mappings":";;;;;;AA6CA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;iBAAgB,aAAA,GAAA,CACd,QAAA,EAAU,gBAAA,CAAiB,eAAA,sBAC3B,WAAA,QAAmB,cAAA,CAAe,CAAA,GAClC,GAAA,EAAK,gBAAA,UACL,YAAA,EAAc,CAAA,GACb,QAAA,CAAS,UAAA,CAAW,CAAA"}
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
import { MaybeRefOrGetter, ShallowRef } from "vue";
|
|
2
|
+
import { ChannelRegistry, ProjectionSpec } from "@langchain/langgraph-sdk/stream";
|
|
3
|
+
|
|
4
|
+
//#region src/use-projection.d.ts
|
|
5
|
+
/**
|
|
6
|
+
* Vue primitive that composes {@link ChannelRegistry.acquire} with
|
|
7
|
+
* Vue's reactivity system.
|
|
8
|
+
*
|
|
9
|
+
* Contract (mirrors the React `useProjection` hook but adapted to
|
|
10
|
+
* Vue's `setup` + `onScopeDispose` lifecycle):
|
|
11
|
+
*
|
|
12
|
+
* - On `setup()` (or whenever `registry` / `key` change) the
|
|
13
|
+
* composable acquires a ref-counted projection from the registry
|
|
14
|
+
* and subscribes to its store. Vue re-renders automatically
|
|
15
|
+
* whenever the store's snapshot changes.
|
|
16
|
+
* - On `onScopeDispose` (or when `registry` / `key` change) the
|
|
17
|
+
* previous acquisition is released. If this was the last consumer
|
|
18
|
+
* of that spec, the registry closes the underlying server
|
|
19
|
+
* subscription.
|
|
20
|
+
* - When `registry` is `null`/`undefined` the composable stays at
|
|
21
|
+
* `initialValue`. This is the happy path for root-served
|
|
22
|
+
* projections (`useMessages`, `useToolCalls`, `useValues`) which
|
|
23
|
+
* delegate to the always-on root store instead of acquiring a new
|
|
24
|
+
* registry projection.
|
|
25
|
+
*
|
|
26
|
+
* `registry` and `key` accept `MaybeRefOrGetter` so selector
|
|
27
|
+
* composables can pass a reactive target (e.g. a computed subagent
|
|
28
|
+
* snapshot) and have the projection rebind automatically.
|
|
29
|
+
*
|
|
30
|
+
* Returns a `Readonly<ShallowRef<T>>` so templates auto-unwrap and
|
|
31
|
+
* scripts can `computed(() => proj.value)`. The underlying ref is
|
|
32
|
+
* `shallowRef` — consumers that mutate the snapshot get undefined
|
|
33
|
+
* behaviour; stream projections should always be treated as
|
|
34
|
+
* immutable snapshots.
|
|
35
|
+
*/
|
|
36
|
+
declare function useProjection<T>(registry: MaybeRefOrGetter<ChannelRegistry | null | undefined>, specFactory: () => ProjectionSpec<T>, key: MaybeRefOrGetter<string>, initialValue: T): Readonly<ShallowRef<T>>;
|
|
37
|
+
//#endregion
|
|
38
|
+
export { useProjection };
|
|
39
|
+
//# sourceMappingURL=use-projection.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"use-projection.d.ts","names":[],"sources":["../src/use-projection.ts"],"mappings":";;;;;;AA6CA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;iBAAgB,aAAA,GAAA,CACd,QAAA,EAAU,gBAAA,CAAiB,eAAA,sBAC3B,WAAA,QAAmB,cAAA,CAAe,CAAA,GAClC,GAAA,EAAK,gBAAA,UACL,YAAA,EAAc,CAAA,GACb,QAAA,CAAS,UAAA,CAAW,CAAA"}
|
|
@@ -0,0 +1,66 @@
|
|
|
1
|
+
import { onScopeDispose, readonly, shallowRef, toValue, watch } from "vue";
|
|
2
|
+
//#region src/use-projection.ts
|
|
3
|
+
/**
|
|
4
|
+
* Vue primitive that composes {@link ChannelRegistry.acquire} with
|
|
5
|
+
* Vue's reactivity system.
|
|
6
|
+
*
|
|
7
|
+
* Contract (mirrors the React `useProjection` hook but adapted to
|
|
8
|
+
* Vue's `setup` + `onScopeDispose` lifecycle):
|
|
9
|
+
*
|
|
10
|
+
* - On `setup()` (or whenever `registry` / `key` change) the
|
|
11
|
+
* composable acquires a ref-counted projection from the registry
|
|
12
|
+
* and subscribes to its store. Vue re-renders automatically
|
|
13
|
+
* whenever the store's snapshot changes.
|
|
14
|
+
* - On `onScopeDispose` (or when `registry` / `key` change) the
|
|
15
|
+
* previous acquisition is released. If this was the last consumer
|
|
16
|
+
* of that spec, the registry closes the underlying server
|
|
17
|
+
* subscription.
|
|
18
|
+
* - When `registry` is `null`/`undefined` the composable stays at
|
|
19
|
+
* `initialValue`. This is the happy path for root-served
|
|
20
|
+
* projections (`useMessages`, `useToolCalls`, `useValues`) which
|
|
21
|
+
* delegate to the always-on root store instead of acquiring a new
|
|
22
|
+
* registry projection.
|
|
23
|
+
*
|
|
24
|
+
* `registry` and `key` accept `MaybeRefOrGetter` so selector
|
|
25
|
+
* composables can pass a reactive target (e.g. a computed subagent
|
|
26
|
+
* snapshot) and have the projection rebind automatically.
|
|
27
|
+
*
|
|
28
|
+
* Returns a `Readonly<ShallowRef<T>>` so templates auto-unwrap and
|
|
29
|
+
* scripts can `computed(() => proj.value)`. The underlying ref is
|
|
30
|
+
* `shallowRef` — consumers that mutate the snapshot get undefined
|
|
31
|
+
* behaviour; stream projections should always be treated as
|
|
32
|
+
* immutable snapshots.
|
|
33
|
+
*/
|
|
34
|
+
function useProjection(registry, specFactory, key, initialValue) {
|
|
35
|
+
const state = shallowRef(initialValue);
|
|
36
|
+
let currentRelease = null;
|
|
37
|
+
let currentUnsubscribe = null;
|
|
38
|
+
const detach = () => {
|
|
39
|
+
currentUnsubscribe?.();
|
|
40
|
+
currentUnsubscribe = null;
|
|
41
|
+
currentRelease?.();
|
|
42
|
+
currentRelease = null;
|
|
43
|
+
};
|
|
44
|
+
watch(() => [toValue(registry), toValue(key)], ([nextRegistry]) => {
|
|
45
|
+
detach();
|
|
46
|
+
if (nextRegistry == null) {
|
|
47
|
+
state.value = initialValue;
|
|
48
|
+
return;
|
|
49
|
+
}
|
|
50
|
+
const acquired = nextRegistry.acquire(specFactory());
|
|
51
|
+
state.value = acquired.store.getSnapshot();
|
|
52
|
+
currentUnsubscribe = acquired.store.subscribe(() => {
|
|
53
|
+
state.value = acquired.store.getSnapshot();
|
|
54
|
+
});
|
|
55
|
+
currentRelease = acquired.release;
|
|
56
|
+
}, {
|
|
57
|
+
immediate: true,
|
|
58
|
+
flush: "sync"
|
|
59
|
+
});
|
|
60
|
+
onScopeDispose(detach);
|
|
61
|
+
return readonly(state);
|
|
62
|
+
}
|
|
63
|
+
//#endregion
|
|
64
|
+
export { useProjection };
|
|
65
|
+
|
|
66
|
+
//# sourceMappingURL=use-projection.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"use-projection.js","names":[],"sources":["../src/use-projection.ts"],"sourcesContent":["import {\n onScopeDispose,\n readonly,\n shallowRef,\n toValue,\n watch,\n type MaybeRefOrGetter,\n type ShallowRef,\n} from \"vue\";\nimport type {\n ChannelRegistry,\n ProjectionSpec,\n} from \"@langchain/langgraph-sdk/stream\";\n\n/**\n * Vue primitive that composes {@link ChannelRegistry.acquire} with\n * Vue's reactivity system.\n *\n * Contract (mirrors the React `useProjection` hook but adapted to\n * Vue's `setup` + `onScopeDispose` lifecycle):\n *\n * - On `setup()` (or whenever `registry` / `key` change) the\n * composable acquires a ref-counted projection from the registry\n * and subscribes to its store. Vue re-renders automatically\n * whenever the store's snapshot changes.\n * - On `onScopeDispose` (or when `registry` / `key` change) the\n * previous acquisition is released. If this was the last consumer\n * of that spec, the registry closes the underlying server\n * subscription.\n * - When `registry` is `null`/`undefined` the composable stays at\n * `initialValue`. This is the happy path for root-served\n * projections (`useMessages`, `useToolCalls`, `useValues`) which\n * delegate to the always-on root store instead of acquiring a new\n * registry projection.\n *\n * `registry` and `key` accept `MaybeRefOrGetter` so selector\n * composables can pass a reactive target (e.g. a computed subagent\n * snapshot) and have the projection rebind automatically.\n *\n * Returns a `Readonly<ShallowRef<T>>` so templates auto-unwrap and\n * scripts can `computed(() => proj.value)`. The underlying ref is\n * `shallowRef` — consumers that mutate the snapshot get undefined\n * behaviour; stream projections should always be treated as\n * immutable snapshots.\n */\nexport function useProjection<T>(\n registry: MaybeRefOrGetter<ChannelRegistry | null | undefined>,\n specFactory: () => ProjectionSpec<T>,\n key: MaybeRefOrGetter<string>,\n initialValue: T\n): Readonly<ShallowRef<T>> {\n const state = shallowRef<T>(initialValue);\n let currentRelease: (() => void) | null = null;\n let currentUnsubscribe: (() => void) | null = null;\n\n const detach = () => {\n currentUnsubscribe?.();\n currentUnsubscribe = null;\n currentRelease?.();\n currentRelease = null;\n };\n\n watch(\n () => [toValue(registry), toValue(key)] as const,\n ([nextRegistry]) => {\n detach();\n if (nextRegistry == null) {\n state.value = initialValue;\n return;\n }\n const acquired = nextRegistry.acquire(specFactory());\n state.value = acquired.store.getSnapshot();\n currentUnsubscribe = acquired.store.subscribe(() => {\n state.value = acquired.store.getSnapshot();\n });\n currentRelease = acquired.release;\n },\n { immediate: true, flush: \"sync\" }\n );\n\n onScopeDispose(detach);\n\n return readonly(state) as Readonly<ShallowRef<T>>;\n}\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AA6CA,SAAgB,cACd,UACA,aACA,KACA,cACyB;CACzB,MAAM,QAAQ,WAAc,aAAa;CACzC,IAAI,iBAAsC;CAC1C,IAAI,qBAA0C;CAE9C,MAAM,eAAe;AACnB,wBAAsB;AACtB,uBAAqB;AACrB,oBAAkB;AAClB,mBAAiB;;AAGnB,aACQ,CAAC,QAAQ,SAAS,EAAE,QAAQ,IAAI,CAAC,GACtC,CAAC,kBAAkB;AAClB,UAAQ;AACR,MAAI,gBAAgB,MAAM;AACxB,SAAM,QAAQ;AACd;;EAEF,MAAM,WAAW,aAAa,QAAQ,aAAa,CAAC;AACpD,QAAM,QAAQ,SAAS,MAAM,aAAa;AAC1C,uBAAqB,SAAS,MAAM,gBAAgB;AAClD,SAAM,QAAQ,SAAS,MAAM,aAAa;IAC1C;AACF,mBAAiB,SAAS;IAE5B;EAAE,WAAW;EAAM,OAAO;EAAQ,CACnC;AAED,gBAAe,OAAO;AAEtB,QAAO,SAAS,MAAM"}
|
|
@@ -0,0 +1,169 @@
|
|
|
1
|
+
const require_context = require("./context.cjs");
|
|
2
|
+
let vue = require("vue");
|
|
3
|
+
let _langchain_langgraph_sdk = require("@langchain/langgraph-sdk");
|
|
4
|
+
let _langchain_langgraph_sdk_client = require("@langchain/langgraph-sdk/client");
|
|
5
|
+
let _langchain_langgraph_sdk_stream = require("@langchain/langgraph-sdk/stream");
|
|
6
|
+
//#region src/use-stream.ts
|
|
7
|
+
/**
|
|
8
|
+
* Private field on the handle that carries the {@link StreamController}
|
|
9
|
+
* reference. Selector composables read this to reach the shared
|
|
10
|
+
* {@link ChannelRegistry}. Use the selector composables (`useMessages`,
|
|
11
|
+
* `useToolCalls`, `useValues`, …) instead of reading this directly.
|
|
12
|
+
*/
|
|
13
|
+
const STREAM_CONTROLLER = Symbol.for("@langchain/vue/controller");
|
|
14
|
+
/**
|
|
15
|
+
* Vue Composition API binding for the v2-native stream runtime.
|
|
16
|
+
*
|
|
17
|
+
* Returns a handle whose projections are Vue refs so templates
|
|
18
|
+
* auto-unwrap and scripts can feed them into `computed`/`watch`.
|
|
19
|
+
* Scoped views (subagents, subgraphs, any namespaced projection) are
|
|
20
|
+
* surfaced via the companion selector composables (`useMessages`,
|
|
21
|
+
* `useToolCalls`, `useValues`, `useMessageMetadata`,
|
|
22
|
+
* `useSubmissionQueue`, `useExtension`, `useChannel`, plus media
|
|
23
|
+
* composables).
|
|
24
|
+
*
|
|
25
|
+
* @example
|
|
26
|
+
* ```vue
|
|
27
|
+
* <script setup lang="ts">
|
|
28
|
+
* import { useStream } from "@langchain/vue";
|
|
29
|
+
*
|
|
30
|
+
* const stream = useStream({
|
|
31
|
+
* assistantId: "agent",
|
|
32
|
+
* apiUrl: "http://localhost:2024",
|
|
33
|
+
* });
|
|
34
|
+
* <\/script>
|
|
35
|
+
*
|
|
36
|
+
* <template>
|
|
37
|
+
* <div v-for="msg in stream.messages.value" :key="msg.id">
|
|
38
|
+
* {{ msg.content }}
|
|
39
|
+
* </div>
|
|
40
|
+
* <button @click="stream.submit({ messages: [{ type: 'human', content: 'Hi' }] })">
|
|
41
|
+
* Send
|
|
42
|
+
* </button>
|
|
43
|
+
* </template>
|
|
44
|
+
* ```
|
|
45
|
+
*
|
|
46
|
+
* `assistantId`, `client`, and `transport` are captured at setup time.
|
|
47
|
+
* To bind a new assistant/transport, remount the component. Reactive
|
|
48
|
+
* inputs (`threadId`, `apiUrl`, `apiKey`) trigger in-place behaviour
|
|
49
|
+
* changes on the active controller.
|
|
50
|
+
*/
|
|
51
|
+
function useStream(options) {
|
|
52
|
+
const asBag = options;
|
|
53
|
+
const pluginOptions = (0, vue.inject)(require_context.LANGCHAIN_OPTIONS, void 0) ?? {};
|
|
54
|
+
const hasCustomAdapter = asBag.transport != null && typeof asBag.transport !== "string";
|
|
55
|
+
const transport = asBag.transport;
|
|
56
|
+
const resolveApiUrl = () => (0, vue.toValue)(asBag.apiUrl) ?? pluginOptions.apiUrl;
|
|
57
|
+
const resolveApiKey = () => (0, vue.toValue)(asBag.apiKey) ?? pluginOptions.apiKey;
|
|
58
|
+
const client = (0, vue.shallowRef)(asBag.client ?? pluginOptions.client ?? new _langchain_langgraph_sdk_client.Client({
|
|
59
|
+
apiUrl: resolveApiUrl(),
|
|
60
|
+
apiKey: resolveApiKey(),
|
|
61
|
+
callerOptions: asBag.callerOptions,
|
|
62
|
+
defaultHeaders: asBag.defaultHeaders
|
|
63
|
+
})).value;
|
|
64
|
+
const sentinel = "_";
|
|
65
|
+
const assistantId = "assistantId" in options ? options.assistantId ?? sentinel : sentinel;
|
|
66
|
+
const controller = new _langchain_langgraph_sdk_stream.StreamController({
|
|
67
|
+
assistantId,
|
|
68
|
+
client,
|
|
69
|
+
threadId: (0, vue.toValue)(asBag.threadId) ?? null,
|
|
70
|
+
transport,
|
|
71
|
+
fetch: hasCustomAdapter ? void 0 : asBag.fetch,
|
|
72
|
+
webSocketFactory: hasCustomAdapter ? void 0 : asBag.webSocketFactory,
|
|
73
|
+
onThreadId: options.onThreadId,
|
|
74
|
+
onCreated: options.onCreated,
|
|
75
|
+
initialValues: options.initialValues,
|
|
76
|
+
messagesKey: options.messagesKey
|
|
77
|
+
});
|
|
78
|
+
(0, vue.onScopeDispose)(controller.activate());
|
|
79
|
+
function bindStore(subscribe, getSnapshot) {
|
|
80
|
+
const ref = (0, vue.shallowRef)(getSnapshot());
|
|
81
|
+
(0, vue.onScopeDispose)(subscribe(() => {
|
|
82
|
+
ref.value = getSnapshot();
|
|
83
|
+
}));
|
|
84
|
+
return (0, vue.readonly)(ref);
|
|
85
|
+
}
|
|
86
|
+
const rootRef = bindStore(controller.rootStore.subscribe, controller.rootStore.getSnapshot);
|
|
87
|
+
const subagentRef = bindStore(controller.subagentStore.subscribe, controller.subagentStore.getSnapshot);
|
|
88
|
+
const subgraphRef = bindStore(controller.subgraphStore.subscribe, controller.subgraphStore.getSnapshot);
|
|
89
|
+
const subgraphByNodeRef = bindStore(controller.subgraphByNodeStore.subscribe, controller.subgraphByNodeStore.getSnapshot);
|
|
90
|
+
const values = (0, vue.computed)(() => rootRef.value.values);
|
|
91
|
+
const messages = (0, vue.computed)(() => rootRef.value.messages);
|
|
92
|
+
const toolCalls = (0, vue.computed)(() => rootRef.value.toolCalls);
|
|
93
|
+
const interrupts = (0, vue.computed)(() => (0, _langchain_langgraph_sdk.filterOutHeadlessToolInterrupts)(rootRef.value.interrupts));
|
|
94
|
+
const interrupt = (0, vue.computed)(() => interrupts.value[0]);
|
|
95
|
+
const isLoading = (0, vue.computed)(() => rootRef.value.isLoading);
|
|
96
|
+
const isThreadLoading = (0, vue.computed)(() => rootRef.value.isThreadLoading);
|
|
97
|
+
const error = (0, vue.computed)(() => rootRef.value.error);
|
|
98
|
+
const threadId = (0, vue.computed)(() => rootRef.value.threadId);
|
|
99
|
+
const hydrationPromise = (0, vue.computed)(() => controller.hydrationPromise);
|
|
100
|
+
const asShallow = (c) => c;
|
|
101
|
+
let skipFirstThreadIdWatch = true;
|
|
102
|
+
(0, vue.watch)(() => (0, vue.toValue)(asBag.threadId) ?? null, (next) => {
|
|
103
|
+
if (skipFirstThreadIdWatch) {
|
|
104
|
+
skipFirstThreadIdWatch = false;
|
|
105
|
+
return;
|
|
106
|
+
}
|
|
107
|
+
controller.hydrate(next);
|
|
108
|
+
});
|
|
109
|
+
const handledTools = /* @__PURE__ */ new Set();
|
|
110
|
+
(0, vue.watch)(() => (0, vue.toValue)(asBag.threadId) ?? null, () => handledTools.clear());
|
|
111
|
+
const tools = options.tools;
|
|
112
|
+
const onTool = options.onTool;
|
|
113
|
+
if (tools?.length) (0, vue.watch)(() => [rootRef.value.values, rootRef.value.interrupts], ([rootValues, rootInterrupts]) => {
|
|
114
|
+
const bag = rootValues;
|
|
115
|
+
const combined = [...Array.isArray(bag?.__interrupt__) ? bag.__interrupt__ : [], ...rootInterrupts];
|
|
116
|
+
if (combined.length === 0) return;
|
|
117
|
+
(0, _langchain_langgraph_sdk.flushPendingHeadlessToolInterrupts)({
|
|
118
|
+
...bag,
|
|
119
|
+
__interrupt__: combined
|
|
120
|
+
}, tools, handledTools, {
|
|
121
|
+
onTool,
|
|
122
|
+
defer: (run) => {
|
|
123
|
+
Promise.resolve().then(run);
|
|
124
|
+
},
|
|
125
|
+
resumeSubmit: (command) => controller.submit(null, { command })
|
|
126
|
+
});
|
|
127
|
+
}, {
|
|
128
|
+
immediate: true,
|
|
129
|
+
flush: "sync"
|
|
130
|
+
});
|
|
131
|
+
return {
|
|
132
|
+
values: asShallow(values),
|
|
133
|
+
messages: asShallow(messages),
|
|
134
|
+
toolCalls: asShallow(toolCalls),
|
|
135
|
+
interrupts: asShallow(interrupts),
|
|
136
|
+
interrupt,
|
|
137
|
+
isLoading,
|
|
138
|
+
isThreadLoading,
|
|
139
|
+
error,
|
|
140
|
+
threadId,
|
|
141
|
+
hydrationPromise,
|
|
142
|
+
subagents: subagentRef,
|
|
143
|
+
subgraphs: subgraphRef,
|
|
144
|
+
subgraphsByNode: subgraphByNodeRef,
|
|
145
|
+
submit: (input, submitOptions) => controller.submit(input, submitOptions),
|
|
146
|
+
stop: () => controller.stop(),
|
|
147
|
+
respond: (response, target) => controller.respond(response, target),
|
|
148
|
+
getThread: () => controller.getThread(),
|
|
149
|
+
client,
|
|
150
|
+
assistantId,
|
|
151
|
+
[STREAM_CONTROLLER]: controller
|
|
152
|
+
};
|
|
153
|
+
}
|
|
154
|
+
/**
|
|
155
|
+
* Helper used by the selector composables to reach the underlying
|
|
156
|
+
* {@link ChannelRegistry} from a stream handle. Kept internal —
|
|
157
|
+
* application code should call `useMessages`, `useToolCalls`, etc.
|
|
158
|
+
*
|
|
159
|
+
* @internal
|
|
160
|
+
*/
|
|
161
|
+
function getRegistry(stream) {
|
|
162
|
+
return stream[STREAM_CONTROLLER].registry;
|
|
163
|
+
}
|
|
164
|
+
//#endregion
|
|
165
|
+
exports.STREAM_CONTROLLER = STREAM_CONTROLLER;
|
|
166
|
+
exports.getRegistry = getRegistry;
|
|
167
|
+
exports.useStream = useStream;
|
|
168
|
+
|
|
169
|
+
//# sourceMappingURL=use-stream.cjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"use-stream.cjs","names":["LANGCHAIN_OPTIONS","ClientCtor","StreamController"],"sources":["../src/use-stream.ts"],"sourcesContent":["import {\n computed,\n onScopeDispose,\n readonly,\n shallowRef,\n toValue,\n watch,\n type ComputedRef,\n type MaybeRefOrGetter,\n type ShallowRef,\n} from \"vue\";\nimport type { BaseMessage } from \"@langchain/core/messages\";\nimport type { Client, Interrupt } from \"@langchain/langgraph-sdk\";\nimport {\n filterOutHeadlessToolInterrupts,\n flushPendingHeadlessToolInterrupts,\n type AnyHeadlessToolImplementation,\n type OnToolCallback,\n} from \"@langchain/langgraph-sdk\";\nimport {\n Client as ClientCtor,\n type ClientConfig,\n type ThreadStream,\n} from \"@langchain/langgraph-sdk/client\";\nimport {\n StreamController,\n type AgentServerAdapter,\n type AgentServerOptions as StreamAgentServerOptions,\n type AssembledToolCall,\n type ChannelRegistry,\n type CustomAdapterOptions as StreamCustomAdapterOptions,\n type InferStateType,\n type InferSubagentStates,\n type RootSnapshot,\n type StateOf as StreamStateOf,\n type StreamSubmitOptions,\n type SubagentDiscoverySnapshot,\n type SubagentMap,\n type SubgraphByNodeMap,\n type SubgraphDiscoverySnapshot,\n type SubgraphMap,\n type UseStreamOptions as StreamUseStreamOptions,\n type WidenUpdateMessages,\n} from \"@langchain/langgraph-sdk/stream\";\nimport { inject } from \"vue\";\nimport { LANGCHAIN_OPTIONS } from \"./context.js\";\n\n/** @deprecated Prefer {@link InferStateType}. */\nexport type StateOf<T> = StreamStateOf<T>;\n\ntype VueThreadId = MaybeRefOrGetter<string | null | undefined>;\ntype VueApiString = MaybeRefOrGetter<string | undefined>;\n\nexport type AgentServerOptions<StateType extends object> =\n StreamAgentServerOptions<StateType, VueThreadId, VueApiString, VueApiString>;\n\nexport type CustomAdapterOptions<StateType extends object> =\n StreamCustomAdapterOptions<StateType, VueThreadId, string>;\n\nexport type UseStreamOptions<\n StateType extends object = Record<string, unknown>,\n> = StreamUseStreamOptions<\n StateType,\n VueThreadId,\n VueApiString,\n VueApiString,\n string\n>;\n\n/**\n * Private field on the handle that carries the {@link StreamController}\n * reference. Selector composables read this to reach the shared\n * {@link ChannelRegistry}. Use the selector composables (`useMessages`,\n * `useToolCalls`, `useValues`, …) instead of reading this directly.\n */\nexport const STREAM_CONTROLLER: unique symbol = Symbol.for(\n \"@langchain/vue/controller\"\n);\n\n/**\n * Vue binding return type for {@link useStream}.\n *\n * Reactive primitives follow Vue conventions:\n *\n * - Data projections are `Readonly<ShallowRef<T>>` / `ComputedRef<T>`\n * so templates auto-unwrap via `msg.value` in `<script setup>`\n * and directly in templates. They are snapshots — never mutate.\n * - Imperative methods (`submit` / `stop` / `respond`) are plain\n * functions — no refs involved.\n * - Identity values captured at setup time (`client` / `assistantId`)\n * are exposed as plain values; if you need to swap the bound agent\n * or client, remount the composable.\n */\nexport interface UseStreamReturn<\n T = Record<string, unknown>,\n InterruptType = unknown,\n ConfigurableType extends object = Record<string, unknown>,\n StateType extends object = InferStateType<T>,\n SubagentStates = InferSubagentStates<T>,\n> {\n readonly values: Readonly<ShallowRef<StateType>>;\n readonly messages: Readonly<ShallowRef<BaseMessage[]>>;\n readonly toolCalls: Readonly<ShallowRef<AssembledToolCall[]>>;\n readonly interrupts: Readonly<ShallowRef<Interrupt<InterruptType>[]>>;\n readonly interrupt: ComputedRef<Interrupt<InterruptType> | undefined>;\n readonly isLoading: ComputedRef<boolean>;\n readonly isThreadLoading: ComputedRef<boolean>;\n readonly error: ComputedRef<unknown>;\n readonly threadId: ComputedRef<string | null>;\n\n /**\n * Promise that settles when the active thread's initial hydration\n * completes. Exposed so `async setup()` sites can\n * `await stream.hydrationPromise` to implement a Suspense-like\n * boundary.\n */\n readonly hydrationPromise: ComputedRef<Promise<void>>;\n\n readonly subagents: Readonly<\n ShallowRef<\n ReadonlyMap<\n keyof SubagentStates & string extends never\n ? string\n : keyof SubagentStates & string,\n SubagentDiscoverySnapshot\n >\n >\n >;\n readonly subgraphs: Readonly<\n ShallowRef<ReadonlyMap<string, SubgraphDiscoverySnapshot>>\n >;\n readonly subgraphsByNode: Readonly<\n ShallowRef<ReadonlyMap<string, readonly SubgraphDiscoverySnapshot[]>>\n >;\n\n submit(\n input: WidenUpdateMessages<Partial<StateType>> | null | undefined,\n options?: StreamSubmitOptions<StateType, ConfigurableType>\n ): Promise<void>;\n stop(): Promise<void>;\n respond(\n response: unknown,\n target?: { interruptId: string; namespace?: string[] }\n ): Promise<void>;\n\n readonly client: Client;\n readonly assistantId: string;\n\n /** v2 escape hatch — returns the bound {@link ThreadStream}. */\n getThread(): ThreadStream | undefined;\n\n /** @internal Used by selector composables. */\n readonly [STREAM_CONTROLLER]: StreamController<\n StateType,\n InterruptType,\n ConfigurableType\n >;\n}\n\n/**\n * Erased handle useful as a parameter type for helpers and wrapper\n * components that pass a `stream` through to selector composables\n * without reading `values` directly. Mirrors the React\n * `AnyStream` alias.\n */\n// eslint-disable-next-line @typescript-eslint/no-explicit-any\nexport type AnyStream = UseStreamReturn<any, any, any>;\n\n/** Convenience alias for the fully-resolved stream handle type. */\nexport type UseStreamResult<\n T = Record<string, unknown>,\n InterruptType = unknown,\n ConfigurableType extends object = Record<string, unknown>,\n> = UseStreamReturn<T, InterruptType, ConfigurableType>;\n\n/**\n * Vue Composition API binding for the v2-native stream runtime.\n *\n * Returns a handle whose projections are Vue refs so templates\n * auto-unwrap and scripts can feed them into `computed`/`watch`.\n * Scoped views (subagents, subgraphs, any namespaced projection) are\n * surfaced via the companion selector composables (`useMessages`,\n * `useToolCalls`, `useValues`, `useMessageMetadata`,\n * `useSubmissionQueue`, `useExtension`, `useChannel`, plus media\n * composables).\n *\n * @example\n * ```vue\n * <script setup lang=\"ts\">\n * import { useStream } from \"@langchain/vue\";\n *\n * const stream = useStream({\n * assistantId: \"agent\",\n * apiUrl: \"http://localhost:2024\",\n * });\n * </script>\n *\n * <template>\n * <div v-for=\"msg in stream.messages.value\" :key=\"msg.id\">\n * {{ msg.content }}\n * </div>\n * <button @click=\"stream.submit({ messages: [{ type: 'human', content: 'Hi' }] })\">\n * Send\n * </button>\n * </template>\n * ```\n *\n * `assistantId`, `client`, and `transport` are captured at setup time.\n * To bind a new assistant/transport, remount the component. Reactive\n * inputs (`threadId`, `apiUrl`, `apiKey`) trigger in-place behaviour\n * changes on the active controller.\n */\nexport function useStream<\n T = Record<string, unknown>,\n InterruptType = unknown,\n ConfigurableType extends object = Record<string, unknown>,\n>(\n options: UseStreamOptions<InferStateType<T>>\n): UseStreamReturn<T, InterruptType, ConfigurableType> {\n type StateType = InferStateType<T>;\n\n interface OptionsBag {\n assistantId?: string;\n threadId?: MaybeRefOrGetter<string | null | undefined>;\n client?: Client;\n apiUrl?: MaybeRefOrGetter<string | undefined>;\n apiKey?: MaybeRefOrGetter<string | undefined>;\n callerOptions?: ClientConfig[\"callerOptions\"];\n defaultHeaders?: ClientConfig[\"defaultHeaders\"];\n transport?: \"sse\" | \"websocket\" | AgentServerAdapter;\n fetch?: typeof fetch;\n webSocketFactory?: (url: string) => WebSocket;\n onThreadId?: (threadId: string) => void;\n onCreated?: (meta: { run_id: string; thread_id: string }) => void;\n initialValues?: StateType;\n messagesKey?: string;\n tools?: AnyHeadlessToolImplementation[];\n onTool?: OnToolCallback;\n }\n const asBag = options as OptionsBag;\n\n // Inherit missing apiUrl / apiKey / client from any LangChainPlugin\n // installed on the app. Vue's `inject` returns `undefined` if the\n // key was never provided; that's fine — we only merge when the\n // caller didn't set a value.\n const pluginOptions =\n inject(LANGCHAIN_OPTIONS, undefined) ?? ({} as Record<string, unknown>);\n\n const hasCustomAdapter =\n asBag.transport != null && typeof asBag.transport !== \"string\";\n const transport = asBag.transport;\n\n // ─── Client construction ────────────────────────────────────────────\n //\n // Identity-stable per setup. Watches apiUrl/apiKey refs so callers\n // that flip a backend at runtime get a fresh client without a full\n // remount — the controller is swapped in lock-step below.\n const resolveApiUrl = () =>\n toValue(asBag.apiUrl) ?? (pluginOptions as { apiUrl?: string }).apiUrl;\n const resolveApiKey = () =>\n toValue(asBag.apiKey) ?? (pluginOptions as { apiKey?: string }).apiKey;\n const explicitClient =\n asBag.client ?? (pluginOptions as { client?: Client }).client;\n\n const clientRef = shallowRef<Client>(\n explicitClient ??\n (new ClientCtor({\n apiUrl: resolveApiUrl(),\n apiKey: resolveApiKey(),\n callerOptions: asBag.callerOptions,\n defaultHeaders: asBag.defaultHeaders,\n }) as unknown as Client)\n );\n\n // Note: we intentionally bind the controller to the *initial* client\n // instance. A dynamic client swap would require tearing the\n // controller down (in-flight subscriptions, queue, hydration), so we\n // keep the rule simple: client is captured at setup. Mirrors React\n // v1 which bakes `useMemo` on `[client, assistantId, transport]`.\n const client = clientRef.value;\n\n // Custom adapters may omit `assistantId`; the controller still\n // requires one so it has something to forward to `threads.stream`.\n const sentinel = \"_\";\n const assistantId =\n \"assistantId\" in options ? (options.assistantId ?? sentinel) : sentinel;\n\n const initialThreadId = toValue(asBag.threadId) ?? null;\n\n // ─── Controller construction ────────────────────────────────────────\n const controller = new StreamController<\n StateType,\n InterruptType,\n ConfigurableType\n >({\n assistantId,\n client: client as unknown as Client<StateType>,\n threadId: initialThreadId,\n transport,\n fetch: hasCustomAdapter ? undefined : asBag.fetch,\n webSocketFactory: hasCustomAdapter ? undefined : asBag.webSocketFactory,\n onThreadId: options.onThreadId,\n onCreated: options.onCreated,\n initialValues: options.initialValues,\n messagesKey: options.messagesKey,\n });\n\n // Deferred dispose: on the next microtask after the owning scope\n // disappears. Mirrors React's StrictMode-safe activate/deactivate\n // pattern — HMR and other scope-reuse scenarios stay clean because\n // `activate()` cancels the pending dispose if the scope survives.\n const deactivate = controller.activate();\n onScopeDispose(deactivate);\n\n // ─── Reactivity adapters — StreamStore → shallowRef ─────────────────\n function bindStore<S>(\n subscribe: (listener: () => void) => () => void,\n getSnapshot: () => S\n ): Readonly<ShallowRef<S>> {\n const ref = shallowRef<S>(getSnapshot());\n const unsubscribe = subscribe(() => {\n ref.value = getSnapshot();\n });\n onScopeDispose(unsubscribe);\n return readonly(ref) as Readonly<ShallowRef<S>>;\n }\n\n const rootRef = bindStore<RootSnapshot<StateType, InterruptType>>(\n controller.rootStore.subscribe,\n controller.rootStore.getSnapshot\n );\n const subagentRef = bindStore<SubagentMap>(\n controller.subagentStore.subscribe,\n controller.subagentStore.getSnapshot\n );\n const subgraphRef = bindStore<SubgraphMap>(\n controller.subgraphStore.subscribe,\n controller.subgraphStore.getSnapshot\n );\n const subgraphByNodeRef = bindStore<SubgraphByNodeMap>(\n controller.subgraphByNodeStore.subscribe,\n controller.subgraphByNodeStore.getSnapshot\n );\n\n // Derived refs for individual root-snapshot fields. Using computed\n // means templates that read `values.value` only retrigger when the\n // root snapshot's identity actually changes — we can't split further\n // because `StreamStore` fans the whole snapshot out on every update.\n const values = computed(() => rootRef.value.values);\n const messages = computed(() => rootRef.value.messages);\n const toolCalls = computed(() => rootRef.value.toolCalls);\n const interrupts = computed(() =>\n filterOutHeadlessToolInterrupts(rootRef.value.interrupts)\n );\n const interrupt = computed(() => interrupts.value[0]);\n const isLoading = computed(() => rootRef.value.isLoading);\n const isThreadLoading = computed(() => rootRef.value.isThreadLoading);\n const error = computed(() => rootRef.value.error);\n const threadId = computed(() => rootRef.value.threadId);\n const hydrationPromise = computed(() => controller.hydrationPromise);\n\n // Expose the derived refs through a `readonly(shallowRef)` shape to\n // match the rest of the public surface. `computed` already gives us\n // read-only semantics but templates type-check more cleanly when the\n // fully-typed return claims `Readonly<ShallowRef<T>>` everywhere.\n // The cast is safe — a ComputedRef<T> is structurally a\n // Readonly<Ref<T>>.\n const asShallow = <V>(c: ComputedRef<V>): Readonly<ShallowRef<V>> =>\n c as unknown as Readonly<ShallowRef<V>>;\n\n // ─── threadId reactivity ────────────────────────────────────────────\n //\n // Re-hydrate whenever the caller's threadId input changes post-setup.\n // The initial hydrate already fired synchronously in the controller\n // constructor, so we skip that first tick; otherwise we'd double-fetch\n // `thread.state.get()`.\n let skipFirstThreadIdWatch = true;\n watch(\n () => toValue(asBag.threadId) ?? null,\n (next) => {\n if (skipFirstThreadIdWatch) {\n skipFirstThreadIdWatch = false;\n return;\n }\n void controller.hydrate(next);\n }\n );\n\n // ─── Headless-tool handling ─────────────────────────────────────────\n //\n // Watch root values + protocol interrupts for items targeting a\n // registered tool, invoke the handler, and resume the run with the\n // handler's return value. Dedup via an id set so StrictMode /\n // rerenders don't replay a tool call twice.\n const handledTools = new Set<string>();\n watch(\n () => toValue(asBag.threadId) ?? null,\n () => handledTools.clear()\n );\n const tools = options.tools;\n const onTool = options.onTool;\n if (tools?.length) {\n watch(\n () => [rootRef.value.values, rootRef.value.interrupts] as const,\n ([rootValues, rootInterrupts]) => {\n const bag = rootValues as unknown as Record<string, unknown>;\n const existing = Array.isArray(bag?.__interrupt__)\n ? (bag.__interrupt__ as Interrupt[])\n : [];\n const combined: Interrupt[] = [\n ...existing,\n ...(rootInterrupts as unknown as Interrupt[]),\n ];\n if (combined.length === 0) return;\n flushPendingHeadlessToolInterrupts(\n { ...bag, __interrupt__: combined },\n tools,\n handledTools,\n {\n onTool,\n defer: (run) => {\n void Promise.resolve().then(run);\n },\n resumeSubmit: (command) =>\n controller.submit(null, {\n command,\n } as StreamSubmitOptions<StateType, ConfigurableType>),\n }\n );\n },\n { immediate: true, flush: \"sync\" }\n );\n }\n\n const handle: UseStreamReturn<T, InterruptType, ConfigurableType> = {\n values: asShallow(values) as UseStreamReturn<\n T,\n InterruptType,\n ConfigurableType\n >[\"values\"],\n messages: asShallow(messages),\n toolCalls: asShallow(toolCalls),\n interrupts: asShallow(interrupts),\n interrupt,\n isLoading,\n isThreadLoading,\n error,\n threadId,\n hydrationPromise,\n subagents: subagentRef as UseStreamReturn<\n T,\n InterruptType,\n ConfigurableType\n >[\"subagents\"],\n subgraphs: subgraphRef,\n subgraphsByNode: subgraphByNodeRef,\n submit: (input, submitOptions) => controller.submit(input, submitOptions),\n stop: () => controller.stop(),\n respond: (response, target) => controller.respond(response, target),\n getThread: () => controller.getThread(),\n client,\n assistantId,\n [STREAM_CONTROLLER]: controller,\n };\n\n return handle;\n}\n\n/**\n * Helper used by the selector composables to reach the underlying\n * {@link ChannelRegistry} from a stream handle. Kept internal —\n * application code should call `useMessages`, `useToolCalls`, etc.\n *\n * @internal\n */\nexport function getRegistry(\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n stream: UseStreamReturn<any, any, any>\n): ChannelRegistry {\n return stream[STREAM_CONTROLLER].registry;\n}\n\nexport type { ThreadStream };\n"],"mappings":"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"}
|