@langgraph-js/sdk
Version:
The UI SDK for LangGraph - seamlessly integrate your AI agents with frontend interfaces
64 lines (63 loc) • 2.62 kB
JavaScript
import { createElement, createContext, useContext, useMemo, useEffect, useRef } from "react";
import { createChatStore, useUnionStore } from "../ui-store/index.js";
import { useStore } from "@nanostores/react";
const ChatContext = createContext(undefined);
export const useChat = () => {
const context = useContext(ChatContext);
if (!context) {
throw new Error("useChat must be used within a ChatProvider");
}
return context;
};
export const ChatProvider = ({ children, defaultAgent = "", apiUrl = "http://localhost:8123", defaultHeaders, withCredentials = false, fetch, showHistory = false, showGraph = false, fallbackToAvailableAssistants = false, autoRestoreLastSession = false, onInitError, client, legacyMode = false, }) => {
// 使用 useMemo 稳定 defaultHeaders 的引用
const stableHeaders = useMemo(() => defaultHeaders || {}, [defaultHeaders]);
// 使用 useRef 保存 onInitError 的最新引用
const onInitErrorRef = useRef(onInitError);
useEffect(() => {
onInitErrorRef.current = onInitError;
}, [onInitError]);
const store = useMemo(() => {
const baseFetch = fetch || globalThis.fetch;
const F = withCredentials
? (url, options) => {
options.credentials = "include";
return baseFetch(url, options);
}
: baseFetch;
const config = {
apiUrl,
defaultHeaders: stableHeaders,
callerOptions: {
fetch: F,
maxRetries: 1,
},
legacyMode,
};
/** @ts-ignore */
if (client)
config.client = client;
return createChatStore(defaultAgent, config, {
showHistory,
showGraph,
fallbackToAvailableAssistants,
autoRestoreLastSession,
});
}, [defaultAgent, apiUrl, stableHeaders, withCredentials, fetch, showHistory, showGraph, fallbackToAvailableAssistants, autoRestoreLastSession]);
const unionStore = useUnionStore(store, useStore);
// 使用 ref 标记是否已初始化
const initializedRef = useRef(false);
useEffect(() => {
if (initializedRef.current) {
return;
}
initializedRef.current = true;
unionStore.initClient().catch((err) => {
console.error(err);
if (onInitErrorRef.current) {
onInitErrorRef.current(err, unionStore.currentAgent);
}
});
}, [unionStore]);
return createElement(ChatContext.Provider, { value: unionStore }, children);
};