@sinas/sdk 0.5.0 → 0.8.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/dist/{chunk-IABVF56L.js → chunk-RHQVV5O6.js} +344 -99
- package/dist/chunk-RHQVV5O6.js.map +1 -0
- package/dist/client.cjs +356 -98
- package/dist/client.cjs.map +1 -1
- package/dist/client.d.cts +330 -5
- package/dist/client.d.ts +330 -5
- package/dist/client.js +29 -1
- package/dist/index.cjs +624 -244
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +62 -4
- package/dist/index.d.ts +62 -4
- package/dist/index.js +298 -147
- package/dist/index.js.map +1 -1
- package/dist/sinas-sdk.umd.js +610 -244
- package/dist/sinas-sdk.umd.js.map +1 -1
- package/package.json +6 -3
- package/dist/chunk-IABVF56L.js.map +0 -1
package/dist/index.cjs.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/index.ts","../src/client/errors.ts","../src/client/auth.ts","../src/client/SinasClient.ts","../src/client/queries.ts","../src/client/functions.ts","../src/client/states.ts","../src/client/chat.ts","../src/client/collections.ts","../src/hooks/useQuery.ts","../src/hooks/context.ts","../src/hooks/useExecute.ts","../src/hooks/useStateStore.ts","../src/hooks/useChat.ts","../src/hooks/useSinas.ts","../src/hooks/useAuth.ts"],"sourcesContent":["// Client\nexport { SinasClient, SinasClientAuth, type SinasClientOptions } from './client/SinasClient';\nexport { executeQuery } from './client/queries';\nexport { executeFunction } from './client/functions';\nexport { stateGet, stateSet, stateDelete, stateList } from './client/states';\nexport { createChat, sendMessage, streamMessage, getChat, approveToolCall, streamFromChannel } from './client/chat';\nexport { listCollections, listFiles, uploadFile, generateFileUrl } from './client/collections';\nexport {\n getInfo,\n login,\n verifyOTP,\n refresh,\n logout,\n getMe,\n checkPermissions,\n} from './client/auth';\nexport {\n SinasError,\n SinasAuthError,\n SinasPermissionError,\n SinasNotFoundError,\n SinasTimeoutError,\n} from './client/errors';\n\n// Hooks\nexport { useQuery } from './hooks/useQuery';\nexport { useExecute } from './hooks/useExecute';\nexport { useStateStore } from './hooks/useStateStore';\nexport { useChat } from './hooks/useChat';\nexport { useSinas } from './hooks/useSinas';\nexport { useAuth } from './hooks/useAuth';\nexport { SinasProvider, useClient } from './hooks/context';\n\n// Types\nexport type {\n SinasConfig,\n QueryResult,\n FunctionResult,\n StateGetResult,\n StateListResult,\n ChatCreateResult,\n ChatMessage,\n ChatMessageFull,\n ToolCallInfo,\n ChatDetail,\n ApprovalRequest,\n ApprovalResult,\n ContentPart,\n TextContentPart,\n ImageContentPart,\n AudioContentPart,\n FileContentPart,\n ComponentContentPart,\n MessageContent,\n SSEChunk,\n Collection,\n FileInfo,\n FileUploadRequest,\n FileUrlResult,\n AuthMode,\n AuthUser,\n InfoResponse,\n LoginRequest,\n LoginResponse,\n OTPVerifyRequest,\n OTPVerifyResponse,\n RefreshResponse,\n PermissionCheckRequest,\n PermissionCheckResult,\n PermissionCheckResponse,\n} from './client/types';\nexport type { UseQueryOptions, UseQueryResult } from './hooks/useQuery';\nexport type { UseExecuteResult } from './hooks/useExecute';\nexport type { UseStateStoreResult, UseStateStoreOptions } from './hooks/useStateStore';\nexport type { ChatSessionMessage, ToolResult, ToolStatus, UseChatResult, UseChatOptions } from './hooks/useChat';\nexport type { UseSinasResult } from './hooks/useSinas';\nexport type { UseAuthResult, UseAuthOptions, AuthStatus } from './hooks/useAuth';\nexport type { SinasProviderProps } from './hooks/context';\n","export class SinasError extends Error {\n public readonly status: number;\n public readonly detail: string;\n\n constructor(message: string, status: number = 0, detail?: string) {\n super(message);\n this.name = 'SinasError';\n this.status = status;\n this.detail = detail || message;\n }\n}\n\nexport class SinasAuthError extends SinasError {\n constructor(message: string = 'Authentication required') {\n super(message, 401);\n this.name = 'SinasAuthError';\n }\n}\n\nexport class SinasPermissionError extends SinasError {\n constructor(message: string = 'Permission denied') {\n super(message, 403);\n this.name = 'SinasPermissionError';\n }\n}\n\nexport class SinasNotFoundError extends SinasError {\n constructor(resource: string) {\n super(`${resource} not found`, 404);\n this.name = 'SinasNotFoundError';\n }\n}\n\nexport class SinasTimeoutError extends SinasError {\n constructor(message: string = 'Request timed out') {\n super(message, 408);\n this.name = 'SinasTimeoutError';\n }\n}\n","import {\n SinasError,\n SinasAuthError,\n SinasPermissionError,\n SinasNotFoundError,\n} from './errors';\nimport type {\n AuthUser,\n InfoResponse,\n LoginRequest,\n LoginResponse,\n OTPVerifyRequest,\n OTPVerifyResponse,\n PermissionCheckRequest,\n PermissionCheckResponse,\n RefreshResponse,\n} from './types';\n\nfunction trimBase(baseUrl: string): string {\n return baseUrl.replace(/\\/+$/, '');\n}\n\nasync function authFetch(\n baseUrl: string,\n path: string,\n init: RequestInit = {},\n accessToken?: string | null,\n): Promise<Response> {\n const headers = new Headers(init.headers);\n if (!headers.has('Content-Type') && init.body !== undefined) {\n headers.set('Content-Type', 'application/json');\n }\n if (accessToken) headers.set('Authorization', `Bearer ${accessToken}`);\n\n const res = await fetch(`${trimBase(baseUrl)}${path}`, { ...init, headers });\n if (res.ok || res.status === 204) return res;\n\n let detail: string = res.statusText;\n try {\n const body = await res.clone().json();\n detail = body.detail || body.message || detail;\n } catch {\n // body wasn't JSON\n }\n if (res.status === 401) throw new SinasAuthError(detail);\n if (res.status === 403) throw new SinasPermissionError(detail);\n if (res.status === 404) throw new SinasNotFoundError(detail);\n throw new SinasError(detail, res.status, detail);\n}\n\n/** Fetch unauthenticated instance info. Use before showing a login screen. */\nexport async function getInfo(baseUrl: string): Promise<InfoResponse> {\n const res = await authFetch(baseUrl, '/info');\n return (await res.json()) as InfoResponse;\n}\n\n/**\n * Start a login. Response shape depends on the workspace's auth_mode:\n * - \"password\": access_token + refresh_token are set → done.\n * - \"otp\" or \"password+otp\": session_id is set → call verifyOTP next.\n */\nexport async function login(\n baseUrl: string,\n request: LoginRequest,\n): Promise<LoginResponse> {\n const res = await authFetch(baseUrl, '/auth/login', {\n method: 'POST',\n body: JSON.stringify(request),\n });\n return (await res.json()) as LoginResponse;\n}\n\n/** Second step for \"otp\" / \"password+otp\" modes. Returns final tokens. */\nexport async function verifyOTP(\n baseUrl: string,\n request: OTPVerifyRequest,\n): Promise<OTPVerifyResponse> {\n const res = await authFetch(baseUrl, '/auth/verify-otp', {\n method: 'POST',\n body: JSON.stringify(request),\n });\n return (await res.json()) as OTPVerifyResponse;\n}\n\n/** Exchange a refresh token for a new access token. */\nexport async function refresh(\n baseUrl: string,\n refreshToken: string,\n): Promise<RefreshResponse> {\n const res = await authFetch(baseUrl, '/auth/refresh', {\n method: 'POST',\n body: JSON.stringify({ refresh_token: refreshToken }),\n });\n return (await res.json()) as RefreshResponse;\n}\n\n/** Revoke a refresh token. Best-effort; ignore 404. */\nexport async function logout(\n baseUrl: string,\n refreshToken: string,\n): Promise<void> {\n try {\n await authFetch(baseUrl, '/auth/logout', {\n method: 'POST',\n body: JSON.stringify({ refresh_token: refreshToken }),\n });\n } catch (e) {\n if (e instanceof SinasNotFoundError) return;\n throw e;\n }\n}\n\n/** Return the authenticated user (id, email, roles). */\nexport async function getMe(\n baseUrl: string,\n accessToken: string,\n): Promise<AuthUser> {\n const res = await authFetch(baseUrl, '/auth/me', { method: 'GET' }, accessToken);\n return (await res.json()) as AuthUser;\n}\n\n/** Check whether the authenticated user has the given permissions. */\nexport async function checkPermissions(\n baseUrl: string,\n accessToken: string,\n request: PermissionCheckRequest,\n): Promise<PermissionCheckResponse> {\n const res = await authFetch(\n baseUrl,\n '/auth/check-permissions',\n {\n method: 'POST',\n body: JSON.stringify({ logic: 'AND', ...request }),\n },\n accessToken,\n );\n return (await res.json()) as PermissionCheckResponse;\n}\n","import {\n SinasError,\n SinasAuthError,\n SinasPermissionError,\n SinasNotFoundError,\n} from './errors';\nimport * as authApi from './auth';\nimport type {\n SinasConfig,\n InfoResponse,\n LoginRequest,\n LoginResponse,\n OTPVerifyRequest,\n OTPVerifyResponse,\n PermissionCheckRequest,\n PermissionCheckResponse,\n RefreshResponse,\n AuthUser,\n} from './types';\n\ndeclare global {\n interface Window {\n __SINAS_CONFIG__?: SinasConfig;\n __SINAS_AUTH_TOKEN__?: string | null;\n }\n}\n\nexport interface SinasClientOptions {\n /** Embedded-component config. Falls back to window.__SINAS_CONFIG__. */\n config?: SinasConfig;\n /** Workspace base URL for standalone use. Overrides config.apiBase for non-proxy calls. */\n baseUrl?: string;\n /** Returns the current access token, or null. Falls back to window.__SINAS_AUTH_TOKEN__. */\n getAccessToken?: () => string | null;\n /** Returns the current refresh token. Required for auto-refresh on 401. */\n getRefreshToken?: () => string | null;\n /** Called with the new access token after a successful /auth/refresh. */\n onTokenRefresh?: (accessToken: string) => void;\n /** Called when a request remains unauthenticated after a refresh attempt. */\n onUnauthenticated?: () => void;\n}\n\nfunction hasWindow(): boolean {\n return typeof window !== 'undefined';\n}\n\nfunction trim(url: string): string {\n return url.replace(/\\/+$/, '');\n}\n\n/**\n * Auth namespace on SinasClient. Standalone counterparts live in client/auth.ts.\n */\nexport class SinasClientAuth {\n constructor(private readonly client: SinasClient) {}\n\n getInfo(): Promise<InfoResponse> {\n return authApi.getInfo(this.client.requireBaseUrl());\n }\n\n login(request: LoginRequest): Promise<LoginResponse> {\n return authApi.login(this.client.requireBaseUrl(), request);\n }\n\n verifyOTP(request: OTPVerifyRequest): Promise<OTPVerifyResponse> {\n return authApi.verifyOTP(this.client.requireBaseUrl(), request);\n }\n\n refresh(refreshToken: string): Promise<RefreshResponse> {\n return authApi.refresh(this.client.requireBaseUrl(), refreshToken);\n }\n\n logout(refreshToken: string): Promise<void> {\n return authApi.logout(this.client.requireBaseUrl(), refreshToken);\n }\n\n getMe(): Promise<AuthUser> {\n const token = this.client.getAccessToken();\n if (!token) throw new SinasAuthError('No access token available');\n return authApi.getMe(this.client.requireBaseUrl(), token);\n }\n\n checkPermissions(request: PermissionCheckRequest): Promise<PermissionCheckResponse> {\n const token = this.client.getAccessToken();\n if (!token) throw new SinasAuthError('No access token available');\n return authApi.checkPermissions(this.client.requireBaseUrl(), token, request);\n }\n}\n\nexport class SinasClient {\n readonly auth: SinasClientAuth;\n\n private readonly options: SinasClientOptions;\n private refreshInFlight: Promise<string | null> | null = null;\n\n constructor(options: SinasClientOptions = {}) {\n this.options = options;\n this.auth = new SinasClientAuth(this);\n }\n\n // ─── Config / base URL ───\n\n getConfig(): SinasConfig {\n const config =\n this.options.config || (hasWindow() ? window.__SINAS_CONFIG__ : undefined);\n if (!config) {\n return {\n apiBase: this.options.baseUrl ? `${trim(this.options.baseUrl)}/api/v1` : '',\n component: { namespace: '', name: '', version: '' },\n resources: {\n enabledAgents: [],\n enabledFunctions: [],\n enabledQueries: [],\n enabledComponents: [],\n enabledStores: [],\n },\n input: {},\n };\n }\n return config;\n }\n\n getInput(): Record<string, unknown> {\n return this.getConfig().input || {};\n }\n\n /** Workspace base URL (root of the Sinas instance). Throws if unset. */\n requireBaseUrl(): string {\n const url = this.getBaseUrl();\n if (!url) {\n throw new SinasError(\n 'No baseUrl configured. Construct with `new SinasClient({ baseUrl })` for standalone use.',\n 0,\n );\n }\n return url;\n }\n\n getBaseUrl(): string | null {\n if (this.options.baseUrl) return trim(this.options.baseUrl);\n // Embedded mode: derive from config.apiBase by stripping /api/v1\n const apiBase = this.getConfig().apiBase;\n if (!apiBase) return null;\n return trim(apiBase).replace(/\\/api\\/v1$/, '');\n }\n\n // ─── Tokens ───\n\n getAccessToken(): string | null {\n if (this.options.getAccessToken) return this.options.getAccessToken();\n if (hasWindow()) return window.__SINAS_AUTH_TOKEN__ ?? null;\n return null;\n }\n\n private getRefreshToken(): string | null {\n return this.options.getRefreshToken ? this.options.getRefreshToken() : null;\n }\n\n private async tryRefresh(): Promise<string | null> {\n const refreshToken = this.getRefreshToken();\n if (!refreshToken) return null;\n if (this.refreshInFlight) return this.refreshInFlight;\n const baseUrl = this.getBaseUrl();\n if (!baseUrl) return null;\n\n this.refreshInFlight = (async () => {\n try {\n const resp = await authApi.refresh(baseUrl, refreshToken);\n this.options.onTokenRefresh?.(resp.access_token);\n return resp.access_token;\n } catch {\n return null;\n } finally {\n this.refreshInFlight = null;\n }\n })();\n return this.refreshInFlight;\n }\n\n // ─── Headers / proxy ───\n\n getAuthHeaders(): Record<string, string> {\n const token = this.getAccessToken();\n const headers: Record<string, string> = { 'Content-Type': 'application/json' };\n if (token) headers['Authorization'] = `Bearer ${token}`;\n return headers;\n }\n\n getProxyBase(): string {\n const config = this.getConfig();\n const comp = config.component;\n return `${config.apiBase}/components/${comp.namespace}/${comp.name}/proxy`;\n }\n\n // ─── Fetch with refresh-on-401 ───\n\n async fetch(url: string, options: RequestInit = {}, _retried = false): Promise<Response> {\n const res = await fetch(url, {\n ...options,\n headers: {\n ...this.getAuthHeaders(),\n ...((options.headers as Record<string, string>) || {}),\n },\n });\n\n if (res.ok || res.status === 204) return res;\n\n if (res.status === 401 && !_retried) {\n const newToken = await this.tryRefresh();\n if (newToken) return this.fetch(url, options, true);\n this.options.onUnauthenticated?.();\n }\n\n const body = await res.json().catch(() => ({ detail: res.statusText }));\n const message = body.detail || body.message || res.statusText;\n\n if (res.status === 401) throw new SinasAuthError(message);\n if (res.status === 403) throw new SinasPermissionError(message);\n if (res.status === 404) throw new SinasNotFoundError(message);\n throw new SinasError(message, res.status);\n }\n}\n","import type { SinasClient } from './SinasClient';\nimport type { QueryResult } from './types';\n\nfunction parseRef(ref: string): [string, string] {\n const parts = ref.split('/');\n if (parts.length !== 2) {\n throw new Error(`Invalid query ref \"${ref}\": expected \"namespace/name\"`);\n }\n return [parts[0], parts[1]];\n}\n\nexport async function executeQuery(\n client: SinasClient,\n ref: string,\n input: Record<string, unknown> = {}\n): Promise<QueryResult> {\n const [ns, name] = parseRef(ref);\n const base = client.getProxyBase();\n const res = await client.fetch(`${base}/queries/${ns}/${name}/execute`, {\n method: 'POST',\n body: JSON.stringify({ input }),\n });\n const data = await res.json();\n return {\n success: data.success,\n operation: data.operation,\n data: data.data,\n rowCount: data.row_count,\n affectedRows: data.affected_rows,\n durationMs: data.duration_ms,\n };\n}\n","import type { SinasClient } from './SinasClient';\nimport type { FunctionResult } from './types';\n\nfunction parseRef(ref: string): [string, string] {\n const parts = ref.split('/');\n if (parts.length !== 2) {\n throw new Error(`Invalid function ref \"${ref}\": expected \"namespace/name\"`);\n }\n return [parts[0], parts[1]];\n}\n\nexport async function executeFunction(\n client: SinasClient,\n ref: string,\n input: Record<string, unknown> = {},\n timeout?: number\n): Promise<FunctionResult> {\n const [ns, name] = parseRef(ref);\n const base = client.getProxyBase();\n const body: Record<string, unknown> = { input };\n if (timeout !== undefined) {\n body.timeout = timeout;\n }\n const res = await client.fetch(`${base}/functions/${ns}/${name}/execute`, {\n method: 'POST',\n body: JSON.stringify(body),\n });\n const data = await res.json();\n return {\n status: data.status,\n executionId: data.execution_id,\n result: data.result,\n error: data.error,\n };\n}\n","import type { SinasClient } from './SinasClient';\nimport type { StateGetResult, StateListResult } from './types';\n\nexport async function stateGet(\n client: SinasClient,\n ns: string,\n key: string\n): Promise<StateGetResult> {\n const base = client.getProxyBase();\n const res = await client.fetch(`${base}/states/${ns}`, {\n method: 'POST',\n body: JSON.stringify({ action: 'get', key }),\n });\n return res.json();\n}\n\nexport async function stateSet(\n client: SinasClient,\n ns: string,\n key: string,\n value: unknown,\n visibility: 'private' | 'shared' = 'private'\n): Promise<void> {\n const base = client.getProxyBase();\n await client.fetch(`${base}/states/${ns}`, {\n method: 'POST',\n body: JSON.stringify({ action: 'set', key, value, visibility }),\n });\n}\n\nexport async function stateDelete(\n client: SinasClient,\n ns: string,\n key: string\n): Promise<void> {\n const base = client.getProxyBase();\n await client.fetch(`${base}/states/${ns}`, {\n method: 'POST',\n body: JSON.stringify({ action: 'delete', key }),\n });\n}\n\nexport async function stateList(\n client: SinasClient,\n ns: string\n): Promise<StateListResult> {\n const base = client.getProxyBase();\n const res = await client.fetch(`${base}/states/${ns}`, {\n method: 'POST',\n body: JSON.stringify({ action: 'list' }),\n });\n return res.json();\n}\n","import type { SinasClient } from './SinasClient';\nimport type { ChatCreateResult, ChatMessage, ChatDetail, ChatMessageFull, ApprovalRequest, ApprovalResult, SSEChunk, MessageContent } from './types';\n\nexport async function createChat(\n client: SinasClient,\n agentRef: string,\n input?: Record<string, unknown>\n): Promise<ChatCreateResult> {\n const [ns, name] = agentRef.split('/');\n if (!ns || !name) {\n throw new Error(`Invalid agent ref \"${agentRef}\": expected \"namespace/name\"`);\n }\n const config = client.getConfig();\n const res = await client.fetch(`${config.apiBase}/agents/${ns}/${name}/chats`, {\n method: 'POST',\n body: JSON.stringify({ input: input || {} }),\n });\n const data = await res.json();\n return {\n id: data.id,\n agentNamespace: data.agent_namespace,\n agentName: data.agent_name,\n title: data.title,\n };\n}\n\nexport async function sendMessage(\n client: SinasClient,\n chatId: string,\n content: MessageContent\n): Promise<ChatMessage> {\n const config = client.getConfig();\n const res = await client.fetch(`${config.apiBase}/chats/${chatId}/messages`, {\n method: 'POST',\n body: JSON.stringify({ content }),\n });\n const data = await res.json();\n return {\n id: data.id,\n chatId: data.chat_id,\n role: data.role,\n content: data.content,\n createdAt: data.created_at,\n };\n}\n\nfunction mapMessage(data: Record<string, unknown>): ChatMessageFull {\n const toolCalls = data.tool_calls as ChatMessageFull['toolCalls'] | undefined;\n return {\n id: data.id as string,\n chatId: data.chat_id as string,\n role: data.role as ChatMessageFull['role'],\n content: (data.content as string) ?? null,\n toolCalls: toolCalls ?? null,\n toolCallId: (data.tool_call_id as string) ?? null,\n name: (data.name as string) ?? null,\n createdAt: data.created_at as string,\n };\n}\n\nexport async function getChat(\n client: SinasClient,\n chatId: string,\n): Promise<ChatDetail> {\n const config = client.getConfig();\n const res = await client.fetch(`${config.apiBase}/chats/${chatId}`);\n const data = await res.json();\n return {\n id: data.id,\n agentNamespace: data.agent_namespace,\n agentName: data.agent_name,\n title: data.title,\n messages: (data.messages || []).map(mapMessage),\n pendingApprovals: (data.pending_approvals || []).map((pa: Record<string, unknown>): ApprovalRequest => ({\n type: 'approval_required',\n toolCallId: pa.tool_call_id as string,\n functionNamespace: pa.function_namespace as string,\n functionName: pa.function_name as string,\n arguments: (pa.arguments as Record<string, unknown>) || {},\n })),\n };\n}\n\nexport async function approveToolCall(\n client: SinasClient,\n chatId: string,\n toolCallId: string,\n approved: boolean,\n): Promise<ApprovalResult> {\n const config = client.getConfig();\n const res = await client.fetch(\n `${config.apiBase}/chats/${chatId}/approve-tool/${toolCallId}`,\n { method: 'POST', body: JSON.stringify({ approved }) },\n );\n const data = await res.json();\n return {\n status: data.status,\n toolCallId: data.tool_call_id,\n channelId: data.channel_id,\n };\n}\n\nexport function streamFromChannel(\n client: SinasClient,\n chatId: string,\n channelId: string,\n onChunk: (chunk: SSEChunk) => void,\n onDone?: () => void,\n onError?: (error: Error) => void,\n): AbortController {\n const controller = new AbortController();\n const config = client.getConfig();\n\n (async () => {\n try {\n const res = await fetch(\n `${config.apiBase}/chats/${chatId}/stream/${channelId}?last_id=0`,\n { headers: client.getAuthHeaders(), signal: controller.signal },\n );\n\n if (!res.ok) {\n const body = await res.json().catch(() => ({ detail: res.statusText }));\n throw new Error(body.detail || 'Stream reconnect failed');\n }\n\n const reader = res.body!.getReader();\n const decoder = new TextDecoder();\n let buffer = '';\n\n while (true) {\n const { done, value } = await reader.read();\n if (done) break;\n\n buffer += decoder.decode(value, { stream: true });\n const { chunks, remaining } = parseSSE(buffer);\n buffer = remaining;\n\n for (const chunk of chunks) {\n onChunk(chunk);\n if (chunk.event === 'done') {\n onDone?.();\n return;\n }\n }\n }\n\n if (buffer.trim()) {\n const { chunks } = parseSSE(buffer + '\\n\\n');\n for (const chunk of chunks) {\n onChunk(chunk);\n }\n }\n\n onDone?.();\n } catch (err) {\n if ((err as Error).name === 'AbortError') return;\n onError?.(err as Error);\n }\n })();\n\n return controller;\n}\n\nfunction parseSSE(buffer: string): { chunks: SSEChunk[]; remaining: string } {\n const chunks: SSEChunk[] = [];\n // Normalize \\r\\n to \\n (sse_starlette uses \\r\\n line endings)\n const normalized = buffer.replace(/\\r\\n/g, '\\n');\n const lines = normalized.split('\\n');\n let event = '';\n let data = '';\n let remaining = '';\n\n for (let i = 0; i < lines.length; i++) {\n const line = lines[i];\n\n // If last line and doesn't end with newline, it's incomplete\n if (i === lines.length - 1 && !normalized.endsWith('\\n')) {\n remaining = line;\n break;\n }\n\n if (line.startsWith('event:')) {\n event = line.slice(6).trim();\n } else if (line.startsWith('data:')) {\n data = line.slice(5).trim();\n } else if (line === '') {\n if (event || data) {\n chunks.push({ event: event || 'message', data });\n event = '';\n data = '';\n }\n }\n }\n\n return { chunks, remaining };\n}\n\nexport function streamMessage(\n client: SinasClient,\n chatId: string,\n content: MessageContent,\n onChunk: (chunk: SSEChunk) => void,\n onDone?: () => void,\n onError?: (error: Error) => void\n): AbortController {\n const controller = new AbortController();\n const config = client.getConfig();\n\n (async () => {\n try {\n const res = await fetch(`${config.apiBase}/chats/${chatId}/messages/stream`, {\n method: 'POST',\n headers: client.getAuthHeaders(),\n body: JSON.stringify({ content }),\n signal: controller.signal,\n });\n\n if (!res.ok) {\n const body = await res.json().catch(() => ({ detail: res.statusText }));\n throw new Error(body.detail || 'Stream request failed');\n }\n\n const reader = res.body!.getReader();\n const decoder = new TextDecoder();\n let buffer = '';\n\n while (true) {\n const { done, value } = await reader.read();\n if (done) break;\n\n buffer += decoder.decode(value, { stream: true });\n const { chunks, remaining } = parseSSE(buffer);\n buffer = remaining;\n\n for (const chunk of chunks) {\n onChunk(chunk);\n if (chunk.event === 'done') {\n onDone?.();\n return;\n }\n }\n }\n\n // Process any remaining buffer\n if (buffer.trim()) {\n const { chunks } = parseSSE(buffer + '\\n\\n');\n for (const chunk of chunks) {\n onChunk(chunk);\n }\n }\n\n onDone?.();\n } catch (err) {\n if ((err as Error).name === 'AbortError') return;\n onError?.(err as Error);\n }\n })();\n\n return controller;\n}\n","import type { SinasClient } from './SinasClient';\nimport type { Collection, FileInfo, FileUploadRequest, FileUrlResult } from './types';\n\nexport async function listCollections(client: SinasClient): Promise<Collection[]> {\n const base = client.getProxyBase();\n const res = await client.fetch(`${base}/collections`);\n return res.json();\n}\n\nexport async function listFiles(\n client: SinasClient,\n namespace: string,\n collection: string\n): Promise<FileInfo[]> {\n const base = client.getProxyBase();\n const res = await client.fetch(`${base}/files/${namespace}/${collection}`);\n return res.json();\n}\n\nexport async function uploadFile(\n client: SinasClient,\n namespace: string,\n collection: string,\n data: FileUploadRequest,\n): Promise<FileInfo> {\n const apiBase = client.getConfig().apiBase;\n const res = await client.fetch(`${apiBase}/files/${namespace}/${collection}`, {\n method: 'POST',\n body: JSON.stringify(data),\n });\n return res.json();\n}\n\nexport async function generateFileUrl(\n client: SinasClient,\n namespace: string,\n collection: string,\n filename: string,\n expiresIn?: number,\n): Promise<FileUrlResult> {\n const apiBase = client.getConfig().apiBase;\n const params = new URLSearchParams();\n if (expiresIn) params.set('expires_in', String(expiresIn));\n const qs = params.toString() ? `?${params.toString()}` : '';\n const res = await client.fetch(\n `${apiBase}/files/${namespace}/${collection}/${encodeURIComponent(filename)}/url${qs}`,\n { method: 'POST' },\n );\n return res.json();\n}\n","import React from 'react';\nimport { executeQuery } from '../client/queries';\nimport { useClient } from './context';\nimport type { QueryResult } from '../client/types';\n\nexport interface UseQueryOptions {\n enabled?: boolean;\n refetchInterval?: number | null;\n}\n\nexport interface UseQueryResult {\n data: Record<string, unknown>[] | null;\n loading: boolean;\n error: string | null;\n rowCount: number | null;\n refetch: (overrideInput?: Record<string, unknown>) => Promise<QueryResult | undefined>;\n}\n\nexport function useQuery(\n ref: string,\n input: Record<string, unknown> = {},\n options: UseQueryOptions = {}\n): UseQueryResult {\n const client = useClient();\n const { enabled = true, refetchInterval = null } = options;\n\n const [data, setData] = React.useState<Record<string, unknown>[] | null>(null);\n const [loading, setLoading] = React.useState(false);\n const [error, setError] = React.useState<string | null>(null);\n const [rowCount, setRowCount] = React.useState<number | null>(null);\n\n const abortRef = React.useRef<AbortController | null>(null);\n const inputJson = JSON.stringify(input);\n\n const execute = React.useCallback(\n async (overrideInput?: Record<string, unknown>) => {\n abortRef.current?.abort();\n const controller = new AbortController();\n abortRef.current = controller;\n\n setLoading(true);\n setError(null);\n try {\n const result = await executeQuery(\n client,\n ref,\n overrideInput || JSON.parse(inputJson)\n );\n if (!controller.signal.aborted) {\n setData(result.data || null);\n setRowCount(result.rowCount ?? result.affectedRows ?? null);\n }\n return result;\n } catch (e) {\n if (!controller.signal.aborted) {\n setError((e as Error).message);\n }\n } finally {\n if (!controller.signal.aborted) {\n setLoading(false);\n }\n }\n },\n [client, ref, inputJson]\n );\n\n React.useEffect(() => {\n if (enabled) {\n execute();\n }\n return () => {\n abortRef.current?.abort();\n };\n }, [enabled, execute]);\n\n React.useEffect(() => {\n if (refetchInterval && enabled) {\n const id = setInterval(execute, refetchInterval);\n return () => clearInterval(id);\n }\n }, [refetchInterval, enabled, execute]);\n\n return { data, loading, error, rowCount, refetch: execute };\n}\n","import React from 'react';\nimport { SinasClient, type SinasClientOptions } from '../client/SinasClient';\n\nconst SinasContext = React.createContext<SinasClient | null>(null);\n\nexport interface SinasProviderProps {\n /** Pre-built client. If provided, options below are ignored. */\n client?: SinasClient;\n /** Standalone-mode options (baseUrl, token callbacks, etc.). */\n options?: SinasClientOptions;\n children: React.ReactNode;\n}\n\nexport function SinasProvider({ client, options, children }: SinasProviderProps) {\n const value = React.useMemo(\n () => client || new SinasClient(options),\n // We intentionally only re-create when `client` reference changes; `options`\n // is expected to be a stable object (callbacks reading from localStorage).\n // eslint-disable-next-line react-hooks/exhaustive-deps\n [client],\n );\n return React.createElement(SinasContext.Provider, { value }, children);\n}\n\nexport function useClient(): SinasClient {\n const client = React.useContext(SinasContext);\n if (client) return client;\n return defaultClient;\n}\n\nconst defaultClient = new SinasClient();\n","import React from 'react';\nimport { executeFunction } from '../client/functions';\nimport { useClient } from './context';\nimport type { FunctionResult } from '../client/types';\n\nexport interface UseExecuteResult {\n execute: (input?: Record<string, unknown>, timeout?: number) => Promise<FunctionResult | undefined>;\n result: unknown;\n loading: boolean;\n error: string | null;\n executionId: string | null;\n}\n\nexport function useExecute(ref: string): UseExecuteResult {\n const client = useClient();\n\n const [result, setResult] = React.useState<unknown>(null);\n const [loading, setLoading] = React.useState(false);\n const [error, setError] = React.useState<string | null>(null);\n const [executionId, setExecutionId] = React.useState<string | null>(null);\n\n const execute = React.useCallback(\n async (input: Record<string, unknown> = {}, timeout?: number) => {\n setLoading(true);\n setError(null);\n try {\n const data = await executeFunction(client, ref, input, timeout);\n setResult(data.result);\n setExecutionId(data.executionId);\n if (data.status === 'error') {\n setError(data.error || 'Function execution failed');\n } else if (data.status === 'timeout') {\n setError('Function execution timed out');\n }\n return data;\n } catch (e) {\n setError((e as Error).message);\n } finally {\n setLoading(false);\n }\n },\n [client, ref]\n );\n\n return { execute, result, loading, error, executionId };\n}\n","import React from 'react';\nimport { stateGet, stateSet, stateDelete, stateList } from '../client/states';\nimport { useClient } from './context';\nimport type { StateListResult } from '../client/types';\n\nexport interface UseStateStoreOptions {\n visibility?: 'private' | 'shared';\n}\n\nexport interface UseStateStoreResult {\n value: unknown;\n loading: boolean;\n error: string | null;\n save: (value: unknown, opts?: UseStateStoreOptions) => Promise<void>;\n remove: () => Promise<void>;\n refetch: () => Promise<void>;\n list: () => Promise<StateListResult | undefined>;\n}\n\nexport function useStateStore(ns: string, key?: string): UseStateStoreResult {\n const client = useClient();\n\n const [value, setValue] = React.useState<unknown>(null);\n const [loading, setLoading] = React.useState(true);\n const [error, setError] = React.useState<string | null>(null);\n\n const load = React.useCallback(async () => {\n if (!key) {\n setLoading(false);\n return;\n }\n setLoading(true);\n setError(null);\n try {\n const result = await stateGet(client, ns, key);\n if (result.found) {\n setValue(result.value);\n } else {\n setValue(null);\n }\n } catch (e) {\n setError((e as Error).message);\n } finally {\n setLoading(false);\n }\n }, [client, ns, key]);\n\n const save = React.useCallback(\n async (newValue: unknown, opts?: UseStateStoreOptions) => {\n if (!key) throw new Error('Cannot save without a key');\n setValue(newValue);\n setError(null);\n try {\n await stateSet(client, ns, key, newValue, opts?.visibility);\n } catch (e) {\n setError((e as Error).message);\n throw e;\n }\n },\n [client, ns, key]\n );\n\n const remove = React.useCallback(async () => {\n if (!key) throw new Error('Cannot delete without a key');\n setValue(null);\n setError(null);\n try {\n await stateDelete(client, ns, key);\n } catch (e) {\n setError((e as Error).message);\n throw e;\n }\n }, [client, ns, key]);\n\n const list = React.useCallback(async () => {\n setError(null);\n try {\n return await stateList(client, ns);\n } catch (e) {\n setError((e as Error).message);\n }\n }, [client, ns]);\n\n React.useEffect(() => {\n load();\n }, [load]);\n\n return { value, loading, error, save, remove, refetch: load, list };\n}\n","import React from 'react';\nimport { createChat, getChat, streamMessage, approveToolCall, streamFromChannel } from '../client/chat';\nimport { useClient } from './context';\nimport type { ChatMessageFull, ApprovalRequest, SSEChunk, MessageContent } from '../client/types';\n\nexport interface ToolResult {\n content: string;\n name: string;\n}\n\nexport interface ChatSessionMessage extends ChatMessageFull {\n /** True while streaming content is being appended */\n streaming?: boolean;\n /** Inline tool results keyed by tool_call_id (merged from tool_end events) */\n toolResults?: Record<string, ToolResult>;\n}\n\nexport interface ToolStatus {\n toolCallId: string;\n name: string;\n description: string;\n status: 'running' | 'complete';\n}\n\nexport interface UseChatResult {\n chatId: string | null;\n messages: ChatSessionMessage[];\n loading: boolean;\n streaming: boolean;\n error: string | null;\n pendingApprovals: ApprovalRequest[];\n toolStatus: ToolStatus[];\n send: (content: MessageContent) => void;\n approve: (toolCallId: string) => void;\n reject: (toolCallId: string) => void;\n stop: () => void;\n clearError: () => void;\n}\n\nexport interface UseChatOptions {\n chatId?: string;\n input?: Record<string, unknown>;\n}\n\nexport function useChat(\n agentRef: string,\n options?: UseChatOptions,\n): UseChatResult {\n const client = useClient();\n\n const [chatId, setChatId] = React.useState<string | null>(options?.chatId ?? null);\n const [messages, setMessages] = React.useState<ChatSessionMessage[]>([]);\n const [loading, setLoading] = React.useState(false);\n const [streaming, setStreaming] = React.useState(false);\n const [error, setError] = React.useState<string | null>(null);\n const [pendingApprovals, setPendingApprovals] = React.useState<ApprovalRequest[]>([]);\n const [toolStatus, setToolStatus] = React.useState<ToolStatus[]>([]);\n\n const abortRef = React.useRef<AbortController | null>(null);\n const chatIdRef = React.useRef<string | null>(chatId);\n chatIdRef.current = chatId;\n\n // Load existing chat on mount if chatId provided\n React.useEffect(() => {\n if (!options?.chatId) return;\n let cancelled = false;\n\n setLoading(true);\n getChat(client, options.chatId)\n .then((detail) => {\n if (cancelled) return;\n setChatId(detail.id);\n setMessages(detail.messages);\n if (detail.pendingApprovals?.length) {\n setPendingApprovals(detail.pendingApprovals);\n }\n })\n .catch((e) => {\n if (cancelled) return;\n setError((e as Error).message);\n })\n .finally(() => {\n if (!cancelled) setLoading(false);\n });\n\n return () => { cancelled = true; };\n }, [client, options?.chatId]);\n\n // Cleanup on unmount\n React.useEffect(() => {\n return () => {\n abortRef.current?.abort();\n };\n }, []);\n\n const handleStreamChunks = React.useCallback(\n (chunk: SSEChunk) => {\n if (chunk.event === 'message') {\n // Append text to the last assistant text message, or create a new one.\n const newContent = (() => {\n try {\n const parsed = JSON.parse(chunk.data);\n return parsed.content || '';\n } catch {\n return chunk.data;\n }\n })();\n if (!newContent) return;\n setMessages((prev) => {\n const last = prev[prev.length - 1];\n if (last && last.role === 'assistant' && !last.toolCalls && last.streaming) {\n // Append to existing text message\n const next = [...prev];\n next[next.length - 1] = { ...last, content: (last.content || '') + newContent };\n return next;\n }\n // Create a new text message\n return [...prev, {\n id: `tmp-text-${Date.now()}`,\n chatId: chatIdRef.current || '',\n role: 'assistant' as const,\n content: newContent,\n toolCalls: null,\n toolCallId: null,\n name: null,\n createdAt: new Date().toISOString(),\n streaming: true,\n }];\n });\n } else if (chunk.event === 'tool_start') {\n try {\n const parsed = JSON.parse(chunk.data);\n setToolStatus((prev) => [\n ...prev,\n { toolCallId: parsed.tool_call_id, name: parsed.name, description: parsed.description, status: 'running' },\n ]);\n setMessages((prev) => {\n if (prev.some((m) => m.toolCalls?.some((tc) => tc.id === parsed.tool_call_id))) {\n return prev;\n }\n // Stop streaming on previous text message (freeze it in place)\n const next = prev.map((m, i) =>\n i === prev.length - 1 && m.streaming && m.role === 'assistant' && !m.toolCalls\n ? { ...m, streaming: false }\n : m,\n );\n return [...next, {\n id: `tmp-tc-${parsed.tool_call_id}`,\n chatId: chatIdRef.current || '',\n role: 'assistant' as const,\n content: null,\n toolCalls: [{\n id: parsed.tool_call_id,\n type: 'function' as const,\n function: { name: parsed.name, arguments: parsed.arguments || '{}' },\n description: parsed.description,\n }],\n toolCallId: null,\n name: null,\n createdAt: new Date().toISOString(),\n streaming: true,\n }];\n });\n } catch {\n // ignore malformed tool_start events\n }\n } else if (chunk.event === 'tool_end') {\n try {\n const parsed = JSON.parse(chunk.data);\n setToolStatus((prev) =>\n prev.map((t) => t.toolCallId === parsed.tool_call_id ? { ...t, status: 'complete' } : t),\n );\n // Merge result into the existing tool call message (same bubble)\n if (parsed.result !== undefined) {\n const resultContent = typeof parsed.result === 'string' ? parsed.result : JSON.stringify(parsed.result);\n setMessages((prev) =>\n prev.map((m) => {\n if (m.toolCalls?.some((tc) => tc.id === parsed.tool_call_id)) {\n return {\n ...m,\n toolResults: {\n ...m.toolResults,\n [parsed.tool_call_id]: { content: resultContent, name: parsed.name },\n },\n };\n }\n return m;\n }),\n );\n }\n } catch {\n // ignore malformed tool_end events\n }\n } else if (chunk.event === 'approval_required') {\n try {\n const raw = JSON.parse(chunk.data);\n const parsed: ApprovalRequest = {\n type: raw.type,\n toolCallId: raw.tool_call_id,\n functionNamespace: raw.function_namespace,\n functionName: raw.function_name,\n arguments: raw.arguments,\n };\n setPendingApprovals((prev) => [...prev, parsed]);\n } catch {\n // ignore malformed approval events\n }\n } else if (chunk.event === 'error') {\n try {\n const parsed = JSON.parse(chunk.data);\n setError(parsed.error || 'Stream error');\n } catch {\n setError(chunk.data || 'Stream error');\n }\n }\n },\n [],\n );\n\n const refreshMessages = React.useCallback(\n async (id: string) => {\n try {\n const detail = await getChat(client, id);\n setMessages(detail.messages);\n if (detail.pendingApprovals?.length) {\n setPendingApprovals(detail.pendingApprovals);\n }\n } catch {\n // Refresh is best-effort — streaming content already visible\n }\n },\n [client],\n );\n\n const send = React.useCallback(\n (content: MessageContent) => {\n const doSend = async () => {\n let activeChatId = chatIdRef.current;\n\n // Auto-create chat on first send\n if (!activeChatId) {\n setLoading(true);\n setError(null);\n try {\n const result = await createChat(client, agentRef, options?.input);\n activeChatId = result.id;\n setChatId(result.id);\n chatIdRef.current = result.id;\n } catch (e) {\n setError((e as Error).message);\n setLoading(false);\n return;\n }\n setLoading(false);\n }\n\n abortRef.current?.abort();\n setStreaming(true);\n setError(null);\n setPendingApprovals([]);\n setToolStatus([]);\n\n // Add user message optimistically\n const displayContent = typeof content === 'string' ? content : JSON.stringify(content);\n const userMsg: ChatSessionMessage = {\n id: `tmp-user-${Date.now()}`,\n chatId: activeChatId,\n role: 'user',\n content: displayContent,\n toolCalls: null,\n toolCallId: null,\n name: null,\n createdAt: new Date().toISOString(),\n };\n setMessages((prev) => [...prev, userMsg]);\n\n const controller = streamMessage(\n client,\n activeChatId,\n content,\n handleStreamChunks,\n () => {\n setStreaming(false);\n setToolStatus([]);\n // Refresh to get authoritative server state\n refreshMessages(activeChatId!);\n },\n (err: Error) => {\n setError(err.message);\n setStreaming(false);\n setToolStatus([]);\n },\n );\n\n abortRef.current = controller;\n };\n\n doSend();\n },\n [client, agentRef, options?.input, handleStreamChunks, refreshMessages],\n );\n\n const handleApproval = React.useCallback(\n (toolCallId: string, approved: boolean) => {\n const currentChatId = chatIdRef.current;\n if (!currentChatId) return;\n\n setPendingApprovals((prev) => prev.filter((a) => a.toolCallId !== toolCallId));\n setStreaming(true);\n setError(null);\n\n // No placeholder needed — handleStreamChunks creates messages on demand\n\n (async () => {\n try {\n const result = await approveToolCall(client, currentChatId, toolCallId, approved);\n\n if (!approved) {\n setStreaming(false);\n refreshMessages(currentChatId);\n return;\n }\n\n // Connect to resume stream\n const controller = streamFromChannel(\n client,\n currentChatId,\n result.channelId,\n handleStreamChunks,\n () => {\n setStreaming(false);\n setToolStatus([]);\n refreshMessages(currentChatId);\n },\n (err: Error) => {\n setError(err.message);\n setStreaming(false);\n setToolStatus([]);\n },\n );\n\n abortRef.current = controller;\n } catch (e) {\n setError((e as Error).message);\n setStreaming(false);\n }\n })();\n },\n [client, handleStreamChunks, refreshMessages],\n );\n\n const approve = React.useCallback(\n (toolCallId: string) => handleApproval(toolCallId, true),\n [handleApproval],\n );\n\n const reject = React.useCallback(\n (toolCallId: string) => handleApproval(toolCallId, false),\n [handleApproval],\n );\n\n const stop = React.useCallback(() => {\n abortRef.current?.abort();\n abortRef.current = null;\n setStreaming(false);\n }, []);\n\n const clearError = React.useCallback(() => {\n setError(null);\n }, []);\n\n return {\n chatId,\n messages,\n loading,\n streaming,\n error,\n pendingApprovals,\n toolStatus,\n send,\n approve,\n reject,\n stop,\n clearError,\n };\n}\n","import { useClient } from './context';\nimport { useQuery } from './useQuery';\nimport { useExecute } from './useExecute';\nimport { useStateStore } from './useStateStore';\nimport { useChat } from './useChat';\nimport type { SinasConfig } from '../client/types';\nimport type { SinasClient } from '../client/SinasClient';\n\nexport interface UseSinasResult {\n config: SinasConfig;\n input: Record<string, unknown>;\n client: SinasClient;\n useQuery: typeof useQuery;\n useExecute: typeof useExecute;\n useStateStore: typeof useStateStore;\n useChat: typeof useChat;\n}\n\nexport function useSinas(): UseSinasResult {\n const client = useClient();\n\n return {\n config: client.getConfig(),\n input: client.getInput(),\n client,\n useQuery,\n useExecute,\n useStateStore,\n useChat,\n };\n}\n","import React from 'react';\nimport { useClient } from './context';\nimport { SinasAuthError } from '../client/errors';\nimport type {\n AuthUser,\n InfoResponse,\n LoginResponse,\n OTPVerifyResponse,\n} from '../client/types';\n\nexport type AuthStatus = 'loading' | 'authenticated' | 'unauthenticated';\n\nexport interface UseAuthResult {\n status: AuthStatus;\n user: AuthUser | null;\n info: InfoResponse | null;\n error: string | null;\n\n /**\n * Refresh the session by calling /auth/me with the current access token.\n * Call this on app boot and after token changes.\n */\n refresh: () => Promise<void>;\n\n /**\n * Start a login. In password-only mode this completes the login and\n * returns access/refresh tokens. In OTP / password+OTP mode the response\n * carries a `session_id` to feed into `verifyOTP`.\n */\n login: (email: string, password?: string) => Promise<LoginResponse>;\n\n /** Second step for OTP / password+OTP. Returns the final tokens. */\n verifyOTP: (sessionId: string, otpCode: string) => Promise<OTPVerifyResponse>;\n\n /** Revoke the refresh token and clear local auth state. */\n logout: (refreshToken?: string) => Promise<void>;\n}\n\nexport interface UseAuthOptions {\n /** Refresh on mount. Default true. */\n autoRefresh?: boolean;\n}\n\n/**\n * React hook for the standalone Sinas login flow. The hosting app is\n * responsible for storing the tokens it receives (typically in localStorage)\n * and wiring `getAccessToken` / `getRefreshToken` / `onTokenRefresh` on the\n * SinasProvider so this hook can read the current session.\n */\nexport function useAuth(options: UseAuthOptions = {}): UseAuthResult {\n const { autoRefresh = true } = options;\n const client = useClient();\n\n const [status, setStatus] = React.useState<AuthStatus>('loading');\n const [user, setUser] = React.useState<AuthUser | null>(null);\n const [info, setInfo] = React.useState<InfoResponse | null>(null);\n const [error, setError] = React.useState<string | null>(null);\n\n const refresh = React.useCallback(async () => {\n setError(null);\n try {\n // Fetch /info in parallel with /me (info is unauthenticated and cheap).\n const [infoResp, meResp] = await Promise.all([\n client.auth.getInfo().catch(() => null),\n client.getAccessToken() ? client.auth.getMe().catch(() => null) : Promise.resolve(null),\n ]);\n if (infoResp) setInfo(infoResp);\n if (meResp) {\n setUser(meResp);\n setStatus('authenticated');\n } else {\n setUser(null);\n setStatus('unauthenticated');\n }\n } catch (e) {\n setError(e instanceof Error ? e.message : String(e));\n setStatus('unauthenticated');\n }\n }, [client]);\n\n React.useEffect(() => {\n if (autoRefresh) void refresh();\n }, [autoRefresh, refresh]);\n\n const login = React.useCallback(\n async (email: string, password?: string) => {\n setError(null);\n try {\n return await client.auth.login({ email, password });\n } catch (e) {\n const msg = e instanceof Error ? e.message : String(e);\n setError(msg);\n throw e;\n }\n },\n [client],\n );\n\n const verifyOTP = React.useCallback(\n async (sessionId: string, otpCode: string) => {\n setError(null);\n try {\n return await client.auth.verifyOTP({ session_id: sessionId, otp_code: otpCode });\n } catch (e) {\n const msg = e instanceof Error ? e.message : String(e);\n setError(msg);\n throw e;\n }\n },\n [client],\n );\n\n const logout = React.useCallback(\n async (refreshToken?: string) => {\n if (refreshToken) {\n try {\n await client.auth.logout(refreshToken);\n } catch (e) {\n if (!(e instanceof SinasAuthError)) throw e;\n }\n }\n setUser(null);\n setStatus('unauthenticated');\n },\n [client],\n );\n\n return { status, user, info, error, refresh, login, verifyOTP, logout };\n}\n"],"mappings":"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","names":["parseRef","import_react","React","React","import_react","React","import_react","React","import_react","React","import_react","React","refresh","login","verifyOTP","logout"]}
|
|
1
|
+
{"version":3,"sources":["../src/index.ts","../src/client/errors.ts","../src/client/auth.ts","../src/client/SinasClient.ts","../src/client/queries.ts","../src/client/functions.ts","../src/client/states.ts","../src/client/chatEvents.ts","../src/client/chat.ts","../src/client/collections.ts","../src/hooks/useQuery.ts","../src/hooks/context.ts","../src/hooks/useExecute.ts","../src/hooks/useStateStore.ts","../src/hooks/useChat.ts","../src/hooks/chatState.ts","../src/hooks/useSinas.ts","../src/hooks/useAuth.ts"],"sourcesContent":["// Client\nexport { SinasClient, SinasClientAuth, type SinasClientOptions } from './client/SinasClient';\nexport { executeQuery } from './client/queries';\nexport {\n executeFunction,\n enqueueFunction,\n submitFunctionBatch,\n submitAgentBatch,\n getBatch,\n listBatchExecutions,\n cancelBatch,\n} from './client/functions';\nexport type {\n EnqueueFunctionOptions,\n EnqueueFunctionResult,\n SubmitFunctionBatchOptions,\n SubmitFunctionBatchResult,\n AgentBatchItem,\n SubmitAgentBatchOptions,\n SubmitAgentBatchResult,\n BatchStatus,\n BatchExecutionItem,\n} from './client/functions';\nexport { stateGet, stateSet, stateDelete, stateList } from './client/states';\nexport {\n createChat,\n sendMessage,\n streamMessage,\n getChat,\n approveToolCall,\n streamFromChannel,\n invokeAgent,\n listPendingInputs,\n answerPendingInput,\n} from './client/chat';\nexport {\n parsePendingInput,\n parsePendingInputs,\n pendingInputFromChunk,\n approvalResumeChannel,\n answerResumeChannel,\n} from './client/chatEvents';\nexport { listCollections, listFiles, uploadFile, generateFileUrl } from './client/collections';\nexport {\n getInfo,\n login,\n verifyOTP,\n refresh,\n logout,\n getMe,\n checkPermissions,\n} from './client/auth';\nexport {\n SinasError,\n SinasAuthError,\n SinasPermissionError,\n SinasNotFoundError,\n SinasTimeoutError,\n} from './client/errors';\n\n// Hooks\nexport { useQuery } from './hooks/useQuery';\nexport { useExecute } from './hooks/useExecute';\nexport { useStateStore } from './hooks/useStateStore';\nexport { useChat } from './hooks/useChat';\nexport { useSinas } from './hooks/useSinas';\nexport { useAuth } from './hooks/useAuth';\nexport { SinasProvider, useClient } from './hooks/context';\n\n// Types\nexport type {\n SinasConfig,\n QueryResult,\n FunctionResult,\n StateGetResult,\n StateListResult,\n ChatCreateResult,\n ChatMessage,\n ChatMessageFull,\n ToolCallInfo,\n ChatDetail,\n ApprovalRequest,\n ApprovalResult,\n ApprovalResume,\n ApproveToolCallOptions,\n PendingInput,\n TurnStatus,\n TurnUsage,\n TurnState,\n MessageSendResult,\n InvokeOptions,\n InvokeResult,\n AnswerPendingInputOptions,\n PendingInputAnswerAccepted,\n PendingInputAnswerResult,\n StreamOptions,\n StreamFromChannelOptions,\n StreamDone,\n InputRequiredEvent,\n RoundSuspendedEvent,\n ContentPart,\n TextContentPart,\n ImageContentPart,\n AudioContentPart,\n FileContentPart,\n ComponentContentPart,\n MessageContent,\n SSEChunk,\n Collection,\n FileInfo,\n FileUploadRequest,\n FileUrlResult,\n AuthMode,\n AuthUser,\n InfoResponse,\n LoginRequest,\n LoginResponse,\n OTPVerifyRequest,\n OTPVerifyResponse,\n RefreshResponse,\n PermissionCheckRequest,\n PermissionCheckResult,\n PermissionCheckResponse,\n} from './client/types';\nexport type { UseQueryOptions, UseQueryResult } from './hooks/useQuery';\nexport type { UseExecuteResult } from './hooks/useExecute';\nexport type { UseStateStoreResult, UseStateStoreOptions } from './hooks/useStateStore';\nexport type {\n ChatSessionMessage,\n ToolResult,\n ToolStatus,\n ChatThinking,\n ApproveOptions,\n FollowOptions,\n UseChatResult,\n UseChatOptions,\n} from './hooks/useChat';\nexport type { UseSinasResult } from './hooks/useSinas';\nexport type { UseAuthResult, UseAuthOptions, AuthStatus } from './hooks/useAuth';\nexport type { SinasProviderProps } from './hooks/context';\n","export class SinasError extends Error {\n public readonly status: number;\n public readonly detail: string;\n\n constructor(message: string, status: number = 0, detail?: string) {\n super(message);\n this.name = 'SinasError';\n this.status = status;\n this.detail = detail || message;\n }\n}\n\nexport class SinasAuthError extends SinasError {\n constructor(message: string = 'Authentication required') {\n super(message, 401);\n this.name = 'SinasAuthError';\n }\n}\n\nexport class SinasPermissionError extends SinasError {\n constructor(message: string = 'Permission denied') {\n super(message, 403);\n this.name = 'SinasPermissionError';\n }\n}\n\nexport class SinasNotFoundError extends SinasError {\n constructor(resource: string) {\n super(`${resource} not found`, 404);\n this.name = 'SinasNotFoundError';\n }\n}\n\nexport class SinasTimeoutError extends SinasError {\n constructor(message: string = 'Request timed out') {\n super(message, 408);\n this.name = 'SinasTimeoutError';\n }\n}\n","import {\n SinasError,\n SinasAuthError,\n SinasPermissionError,\n SinasNotFoundError,\n} from './errors';\nimport type {\n AuthUser,\n InfoResponse,\n LoginRequest,\n LoginResponse,\n OTPVerifyRequest,\n OTPVerifyResponse,\n PermissionCheckRequest,\n PermissionCheckResponse,\n RefreshResponse,\n} from './types';\n\nfunction trimBase(baseUrl: string): string {\n return baseUrl.replace(/\\/+$/, '');\n}\n\nasync function authFetch(\n baseUrl: string,\n path: string,\n init: RequestInit = {},\n accessToken?: string | null,\n): Promise<Response> {\n const headers = new Headers(init.headers);\n if (!headers.has('Content-Type') && init.body !== undefined) {\n headers.set('Content-Type', 'application/json');\n }\n if (accessToken) headers.set('Authorization', `Bearer ${accessToken}`);\n\n const res = await fetch(`${trimBase(baseUrl)}${path}`, { ...init, headers });\n if (res.ok || res.status === 204) return res;\n\n let detail: string = res.statusText;\n try {\n const body = await res.clone().json();\n detail = body.detail || body.message || detail;\n } catch {\n // body wasn't JSON\n }\n if (res.status === 401) throw new SinasAuthError(detail);\n if (res.status === 403) throw new SinasPermissionError(detail);\n if (res.status === 404) throw new SinasNotFoundError(detail);\n throw new SinasError(detail, res.status, detail);\n}\n\n/** Fetch unauthenticated instance info. Use before showing a login screen. */\nexport async function getInfo(baseUrl: string): Promise<InfoResponse> {\n const res = await authFetch(baseUrl, '/info');\n return (await res.json()) as InfoResponse;\n}\n\n/**\n * Start a login. Response shape depends on the workspace's auth_mode:\n * - \"password\": access_token + refresh_token are set → done.\n * - \"otp\" or \"password+otp\": session_id is set → call verifyOTP next.\n */\nexport async function login(\n baseUrl: string,\n request: LoginRequest,\n): Promise<LoginResponse> {\n const res = await authFetch(baseUrl, '/auth/login', {\n method: 'POST',\n body: JSON.stringify(request),\n });\n return (await res.json()) as LoginResponse;\n}\n\n/** Second step for \"otp\" / \"password+otp\" modes. Returns final tokens. */\nexport async function verifyOTP(\n baseUrl: string,\n request: OTPVerifyRequest,\n): Promise<OTPVerifyResponse> {\n const res = await authFetch(baseUrl, '/auth/verify-otp', {\n method: 'POST',\n body: JSON.stringify(request),\n });\n return (await res.json()) as OTPVerifyResponse;\n}\n\n/** Exchange a refresh token for a new access token. */\nexport async function refresh(\n baseUrl: string,\n refreshToken: string,\n): Promise<RefreshResponse> {\n const res = await authFetch(baseUrl, '/auth/refresh', {\n method: 'POST',\n body: JSON.stringify({ refresh_token: refreshToken }),\n });\n return (await res.json()) as RefreshResponse;\n}\n\n/** Revoke a refresh token. Best-effort; ignore 404. */\nexport async function logout(\n baseUrl: string,\n refreshToken: string,\n): Promise<void> {\n try {\n await authFetch(baseUrl, '/auth/logout', {\n method: 'POST',\n body: JSON.stringify({ refresh_token: refreshToken }),\n });\n } catch (e) {\n if (e instanceof SinasNotFoundError) return;\n throw e;\n }\n}\n\n/** Return the authenticated user (id, email, roles). */\nexport async function getMe(\n baseUrl: string,\n accessToken: string,\n): Promise<AuthUser> {\n const res = await authFetch(baseUrl, '/auth/me', { method: 'GET' }, accessToken);\n return (await res.json()) as AuthUser;\n}\n\n/** Check whether the authenticated user has the given permissions. */\nexport async function checkPermissions(\n baseUrl: string,\n accessToken: string,\n request: PermissionCheckRequest,\n): Promise<PermissionCheckResponse> {\n const res = await authFetch(\n baseUrl,\n '/auth/check-permissions',\n {\n method: 'POST',\n body: JSON.stringify({ logic: 'AND', ...request }),\n },\n accessToken,\n );\n return (await res.json()) as PermissionCheckResponse;\n}\n","import {\n SinasError,\n SinasAuthError,\n SinasPermissionError,\n SinasNotFoundError,\n} from './errors';\nimport * as authApi from './auth';\nimport type {\n SinasConfig,\n InfoResponse,\n LoginRequest,\n LoginResponse,\n OTPVerifyRequest,\n OTPVerifyResponse,\n PermissionCheckRequest,\n PermissionCheckResponse,\n RefreshResponse,\n AuthUser,\n} from './types';\n\ndeclare global {\n interface Window {\n __SINAS_CONFIG__?: SinasConfig;\n __SINAS_AUTH_TOKEN__?: string | null;\n }\n}\n\nexport interface SinasClientOptions {\n /** Embedded-component config. Falls back to window.__SINAS_CONFIG__. */\n config?: SinasConfig;\n /** Workspace base URL for standalone use. Overrides config.apiBase for non-proxy calls. */\n baseUrl?: string;\n /** Returns the current access token, or null. Falls back to window.__SINAS_AUTH_TOKEN__. */\n getAccessToken?: () => string | null;\n /** Returns the current refresh token. Required for auto-refresh on 401. */\n getRefreshToken?: () => string | null;\n /** Called with the new access token after a successful /auth/refresh. */\n onTokenRefresh?: (accessToken: string) => void;\n /** Called when a request remains unauthenticated after a refresh attempt. */\n onUnauthenticated?: () => void;\n}\n\nfunction hasWindow(): boolean {\n return typeof window !== 'undefined';\n}\n\nfunction trim(url: string): string {\n return url.replace(/\\/+$/, '');\n}\n\n/**\n * Auth namespace on SinasClient. Standalone counterparts live in client/auth.ts.\n */\nexport class SinasClientAuth {\n constructor(private readonly client: SinasClient) {}\n\n getInfo(): Promise<InfoResponse> {\n return authApi.getInfo(this.client.requireBaseUrl());\n }\n\n login(request: LoginRequest): Promise<LoginResponse> {\n return authApi.login(this.client.requireBaseUrl(), request);\n }\n\n verifyOTP(request: OTPVerifyRequest): Promise<OTPVerifyResponse> {\n return authApi.verifyOTP(this.client.requireBaseUrl(), request);\n }\n\n refresh(refreshToken: string): Promise<RefreshResponse> {\n return authApi.refresh(this.client.requireBaseUrl(), refreshToken);\n }\n\n logout(refreshToken: string): Promise<void> {\n return authApi.logout(this.client.requireBaseUrl(), refreshToken);\n }\n\n getMe(): Promise<AuthUser> {\n const token = this.client.getAccessToken();\n if (!token) throw new SinasAuthError('No access token available');\n return authApi.getMe(this.client.requireBaseUrl(), token);\n }\n\n checkPermissions(request: PermissionCheckRequest): Promise<PermissionCheckResponse> {\n const token = this.client.getAccessToken();\n if (!token) throw new SinasAuthError('No access token available');\n return authApi.checkPermissions(this.client.requireBaseUrl(), token, request);\n }\n}\n\nexport class SinasClient {\n readonly auth: SinasClientAuth;\n\n private readonly options: SinasClientOptions;\n private refreshInFlight: Promise<string | null> | null = null;\n\n constructor(options: SinasClientOptions = {}) {\n this.options = options;\n this.auth = new SinasClientAuth(this);\n }\n\n // ─── Config / base URL ───\n\n getConfig(): SinasConfig {\n const config =\n this.options.config || (hasWindow() ? window.__SINAS_CONFIG__ : undefined);\n if (!config) {\n return {\n apiBase: this.options.baseUrl ? `${trim(this.options.baseUrl)}/api/v1` : '',\n component: { namespace: '', name: '', version: '' },\n resources: {\n enabledAgents: [],\n enabledFunctions: [],\n enabledQueries: [],\n enabledComponents: [],\n enabledStores: [],\n },\n input: {},\n };\n }\n return config;\n }\n\n getInput(): Record<string, unknown> {\n return this.getConfig().input || {};\n }\n\n /** Workspace base URL (root of the Sinas instance). Throws if unset. */\n requireBaseUrl(): string {\n const url = this.getBaseUrl();\n if (!url) {\n throw new SinasError(\n 'No baseUrl configured. Construct with `new SinasClient({ baseUrl })` for standalone use.',\n 0,\n );\n }\n return url;\n }\n\n getBaseUrl(): string | null {\n if (this.options.baseUrl) return trim(this.options.baseUrl);\n // Embedded mode: derive from config.apiBase by stripping /api/v1\n const apiBase = this.getConfig().apiBase;\n if (!apiBase) return null;\n return trim(apiBase).replace(/\\/api\\/v1$/, '');\n }\n\n // ─── Tokens ───\n\n getAccessToken(): string | null {\n if (this.options.getAccessToken) return this.options.getAccessToken();\n if (hasWindow()) return window.__SINAS_AUTH_TOKEN__ ?? null;\n return null;\n }\n\n private getRefreshToken(): string | null {\n return this.options.getRefreshToken ? this.options.getRefreshToken() : null;\n }\n\n private async tryRefresh(): Promise<string | null> {\n const refreshToken = this.getRefreshToken();\n if (!refreshToken) return null;\n if (this.refreshInFlight) return this.refreshInFlight;\n const baseUrl = this.getBaseUrl();\n if (!baseUrl) return null;\n\n this.refreshInFlight = (async () => {\n try {\n const resp = await authApi.refresh(baseUrl, refreshToken);\n this.options.onTokenRefresh?.(resp.access_token);\n return resp.access_token;\n } catch {\n return null;\n } finally {\n this.refreshInFlight = null;\n }\n })();\n return this.refreshInFlight;\n }\n\n // ─── Headers / proxy ───\n\n getAuthHeaders(): Record<string, string> {\n const token = this.getAccessToken();\n const headers: Record<string, string> = { 'Content-Type': 'application/json' };\n if (token) headers['Authorization'] = `Bearer ${token}`;\n return headers;\n }\n\n getProxyBase(): string {\n const config = this.getConfig();\n const comp = config.component;\n return `${config.apiBase}/components/${comp.namespace}/${comp.name}/proxy`;\n }\n\n // ─── Fetch with refresh-on-401 ───\n\n async fetch(url: string, options: RequestInit = {}, _retried = false): Promise<Response> {\n const res = await fetch(url, {\n ...options,\n headers: {\n ...this.getAuthHeaders(),\n ...((options.headers as Record<string, string>) || {}),\n },\n });\n\n if (res.ok || res.status === 204) return res;\n\n if (res.status === 401 && !_retried) {\n const newToken = await this.tryRefresh();\n if (newToken) return this.fetch(url, options, true);\n this.options.onUnauthenticated?.();\n }\n\n const body = await res.json().catch(() => ({ detail: res.statusText }));\n const message = body.detail || body.message || res.statusText;\n\n if (res.status === 401) throw new SinasAuthError(message);\n if (res.status === 403) throw new SinasPermissionError(message);\n if (res.status === 404) throw new SinasNotFoundError(message);\n throw new SinasError(message, res.status);\n }\n}\n","import type { SinasClient } from './SinasClient';\nimport type { QueryResult } from './types';\n\nfunction parseRef(ref: string): [string, string] {\n const parts = ref.split('/');\n if (parts.length !== 2) {\n throw new Error(`Invalid query ref \"${ref}\": expected \"namespace/name\"`);\n }\n return [parts[0], parts[1]];\n}\n\nexport async function executeQuery(\n client: SinasClient,\n ref: string,\n input: Record<string, unknown> = {}\n): Promise<QueryResult> {\n const [ns, name] = parseRef(ref);\n const base = client.getProxyBase();\n const res = await client.fetch(`${base}/queries/${ns}/${name}/execute`, {\n method: 'POST',\n body: JSON.stringify({ input }),\n });\n const data = await res.json();\n return {\n success: data.success,\n operation: data.operation,\n data: data.data,\n rowCount: data.row_count,\n affectedRows: data.affected_rows,\n durationMs: data.duration_ms,\n };\n}\n","import type { SinasClient } from './SinasClient';\nimport type { FunctionResult } from './types';\n\nfunction parseRef(ref: string): [string, string] {\n const parts = ref.split('/');\n if (parts.length !== 2) {\n throw new Error(`Invalid function ref \"${ref}\": expected \"namespace/name\"`);\n }\n return [parts[0], parts[1]];\n}\n\nexport async function executeFunction(\n client: SinasClient,\n ref: string,\n input: Record<string, unknown> = {},\n timeout?: number\n): Promise<FunctionResult> {\n const [ns, name] = parseRef(ref);\n const base = client.getProxyBase();\n const body: Record<string, unknown> = { input };\n if (timeout !== undefined) {\n body.timeout = timeout;\n }\n const res = await client.fetch(`${base}/functions/${ns}/${name}/execute`, {\n method: 'POST',\n body: JSON.stringify(body),\n });\n const data = await res.json();\n return {\n status: data.status,\n executionId: data.execution_id,\n result: data.result,\n error: data.error,\n };\n}\n\nexport interface EnqueueFunctionOptions {\n /** App-supplied correlation id stored on the execution record. */\n triggerId?: string;\n /** Delay before the worker picks up the job, in seconds. */\n delaySeconds?: number;\n /**\n * HTTPS URL Sinas will POST to once the execution terminates.\n * Must match the instance's CALLBACK_URL_HOSTS allowlist.\n */\n callbackUrl?: string;\n}\n\nexport interface EnqueueFunctionResult {\n executionId: string;\n status: string;\n}\n\n/**\n * Fire-and-forget function enqueue. Returns immediately with the\n * execution_id. Poll `executions.get(id)` or rely on the callback URL\n * if one was provided.\n *\n * Standalone-mode only — uses the SinasClient's baseUrl (set in the\n * constructor). Embedded components should use `executeFunction` instead.\n */\nexport async function enqueueFunction(\n client: SinasClient,\n ref: string,\n input: Record<string, unknown> = {},\n options: EnqueueFunctionOptions = {},\n): Promise<EnqueueFunctionResult> {\n const [ns, name] = parseRef(ref);\n const baseUrl = client.requireBaseUrl();\n const body: Record<string, unknown> = { input };\n if (options.triggerId !== undefined) body.trigger_id = options.triggerId;\n if (options.delaySeconds !== undefined) body.delay_seconds = options.delaySeconds;\n if (options.callbackUrl !== undefined) body.callback_url = options.callbackUrl;\n\n const res = await client.fetch(`${baseUrl}/functions/${ns}/${name}/execute/async`, {\n method: 'POST',\n body: JSON.stringify(body),\n });\n const data = await res.json();\n return {\n executionId: data.execution_id,\n status: data.status,\n };\n}\n\nexport interface SubmitFunctionBatchOptions {\n triggerIdPrefix?: string;\n delaySeconds?: number;\n /** Fires once per execution. */\n callbackUrl?: string;\n /** Fires once when the entire batch terminates. */\n batchCallbackUrl?: string;\n}\n\nexport interface SubmitFunctionBatchResult {\n batchId: string;\n executionIds: string[];\n total: number;\n status: string;\n}\n\n/** Submit N function executions as a single batch. */\nexport async function submitFunctionBatch(\n client: SinasClient,\n ref: string,\n inputs: Record<string, unknown>[],\n options: SubmitFunctionBatchOptions = {},\n): Promise<SubmitFunctionBatchResult> {\n const [ns, name] = parseRef(ref);\n const baseUrl = client.requireBaseUrl();\n const body: Record<string, unknown> = { inputs };\n if (options.triggerIdPrefix !== undefined) body.trigger_id_prefix = options.triggerIdPrefix;\n if (options.delaySeconds !== undefined) body.delay_seconds = options.delaySeconds;\n if (options.callbackUrl !== undefined) body.callback_url = options.callbackUrl;\n if (options.batchCallbackUrl !== undefined) body.batch_callback_url = options.batchCallbackUrl;\n\n const res = await client.fetch(`${baseUrl}/functions/${ns}/${name}/execute/batch`, {\n method: 'POST',\n body: JSON.stringify(body),\n });\n const data = await res.json();\n return {\n batchId: data.batch_id,\n executionIds: data.execution_ids,\n total: data.total,\n status: data.status,\n };\n}\n\nexport interface AgentBatchItem {\n inputVariables?: Record<string, unknown>;\n message: string;\n}\n\nexport interface SubmitAgentBatchOptions {\n triggerIdPrefix?: string;\n callbackUrl?: string;\n batchCallbackUrl?: string;\n}\n\nexport interface SubmitAgentBatchResult {\n batchId: string;\n executionIds: string[];\n chatIds: string[];\n total: number;\n status: string;\n}\n\n/** Submit N agent invocations as a single batch. */\nexport async function submitAgentBatch(\n client: SinasClient,\n ref: string,\n inputs: AgentBatchItem[],\n options: SubmitAgentBatchOptions = {},\n): Promise<SubmitAgentBatchResult> {\n const [ns, name] = parseRef(ref);\n const baseUrl = client.requireBaseUrl();\n const body: Record<string, unknown> = {\n inputs: inputs.map((item) => ({\n input_variables: item.inputVariables || {},\n message: item.message,\n })),\n };\n if (options.triggerIdPrefix !== undefined) body.trigger_id_prefix = options.triggerIdPrefix;\n if (options.callbackUrl !== undefined) body.callback_url = options.callbackUrl;\n if (options.batchCallbackUrl !== undefined) body.batch_callback_url = options.batchCallbackUrl;\n\n const res = await client.fetch(`${baseUrl}/agents/${ns}/${name}/chats/batch`, {\n method: 'POST',\n body: JSON.stringify(body),\n });\n const data = await res.json();\n return {\n batchId: data.batch_id,\n executionIds: data.execution_ids,\n chatIds: data.chat_ids,\n total: data.total,\n status: data.status,\n };\n}\n\nexport interface BatchStatus {\n batchId: string;\n kind: string;\n target: { namespace: string; name: string };\n userId: string;\n total: number;\n completed: number;\n failed: number;\n cancelled: number;\n running: number;\n queued: number;\n status: string;\n startedAt: string | null;\n finishedAt: string | null;\n triggerIdPrefix: string | null;\n}\n\n/** Get aggregate progress for a batch. */\nexport async function getBatch(\n client: SinasClient,\n batchId: string,\n): Promise<BatchStatus> {\n const baseUrl = client.requireBaseUrl();\n const res = await client.fetch(`${baseUrl}/batches/${batchId}`);\n const data = await res.json();\n return {\n batchId: data.batch_id,\n kind: data.kind,\n target: data.target,\n userId: data.user_id,\n total: data.total,\n completed: data.completed,\n failed: data.failed,\n cancelled: data.cancelled,\n running: data.running,\n queued: data.queued,\n status: data.status,\n startedAt: data.started_at,\n finishedAt: data.finished_at,\n triggerIdPrefix: data.trigger_id_prefix,\n };\n}\n\nexport interface BatchExecutionItem {\n executionId: string;\n status: string;\n functionName: string;\n chatId: string | null;\n triggerId: string;\n startedAt: string | null;\n completedAt: string | null;\n durationMs: number | null;\n error: string | null;\n}\n\n/** List child executions of a batch, optionally filtered by status. */\nexport async function listBatchExecutions(\n client: SinasClient,\n batchId: string,\n options: { status?: string; limit?: number; offset?: number } = {},\n): Promise<BatchExecutionItem[]> {\n const baseUrl = client.requireBaseUrl();\n const params = new URLSearchParams();\n if (options.status) params.set('status', options.status);\n if (options.limit !== undefined) params.set('limit', String(options.limit));\n if (options.offset !== undefined) params.set('offset', String(options.offset));\n const q = params.toString();\n const res = await client.fetch(\n `${baseUrl}/batches/${batchId}/executions${q ? '?' + q : ''}`,\n );\n const data = await res.json();\n return (data.executions || []).map((row: Record<string, unknown>) => ({\n executionId: row.execution_id as string,\n status: row.status as string,\n functionName: row.function_name as string,\n chatId: (row.chat_id as string | null) ?? null,\n triggerId: row.trigger_id as string,\n startedAt: (row.started_at as string | null) ?? null,\n completedAt: (row.completed_at as string | null) ?? null,\n durationMs: (row.duration_ms as number | null) ?? null,\n error: (row.error as string | null) ?? null,\n }));\n}\n\n/** Cancel any queued/pending children of a batch. */\nexport async function cancelBatch(\n client: SinasClient,\n batchId: string,\n): Promise<{ batchId: string; status: string; cancelledChildren: number }> {\n const baseUrl = client.requireBaseUrl();\n const res = await client.fetch(`${baseUrl}/batches/${batchId}/cancel`, {\n method: 'POST',\n });\n const data = await res.json();\n return {\n batchId: data.batch_id,\n status: data.status,\n cancelledChildren: data.cancelled_children,\n };\n}\n","import type { SinasClient } from './SinasClient';\nimport type { StateGetResult, StateListResult } from './types';\n\nexport async function stateGet(\n client: SinasClient,\n ns: string,\n key: string\n): Promise<StateGetResult> {\n const base = client.getProxyBase();\n const res = await client.fetch(`${base}/states/${ns}`, {\n method: 'POST',\n body: JSON.stringify({ action: 'get', key }),\n });\n return res.json();\n}\n\nexport async function stateSet(\n client: SinasClient,\n ns: string,\n key: string,\n value: unknown,\n visibility: 'private' | 'shared' = 'private'\n): Promise<void> {\n const base = client.getProxyBase();\n await client.fetch(`${base}/states/${ns}`, {\n method: 'POST',\n body: JSON.stringify({ action: 'set', key, value, visibility }),\n });\n}\n\nexport async function stateDelete(\n client: SinasClient,\n ns: string,\n key: string\n): Promise<void> {\n const base = client.getProxyBase();\n await client.fetch(`${base}/states/${ns}`, {\n method: 'POST',\n body: JSON.stringify({ action: 'delete', key }),\n });\n}\n\nexport async function stateList(\n client: SinasClient,\n ns: string\n): Promise<StateListResult> {\n const base = client.getProxyBase();\n const res = await client.fetch(`${base}/states/${ns}`, {\n method: 'POST',\n body: JSON.stringify({ action: 'list' }),\n });\n return res.json();\n}\n","// Pure parsers for chat API payloads and stream events (no I/O), shared by\n// the client functions in chat.ts and the useChat hook.\nimport type {\n ApprovalRequest,\n ChatMessageFull,\n PendingInput,\n SSEChunk,\n StreamDone,\n TurnState,\n TurnStatus,\n TurnUsage,\n} from './types';\n\ntype Raw = Record<string, unknown>;\n\nconst isObject = (v: unknown): v is Raw => !!v && typeof v === 'object' && !Array.isArray(v);\nconst str = (v: unknown): string | null => (typeof v === 'string' ? v : null);\nconst num = (v: unknown): number => (typeof v === 'number' && Number.isFinite(v) ? v : 0);\n\nconst optionsOf = (v: unknown): string[] | null =>\n Array.isArray(v) && v.length > 0 && v.every((o) => typeof o === 'string') ? (v as string[]) : null;\n\n/**\n * One ask_user question from the API (`GET /chats/{id}/pending-input`, the\n * chat detail, a turn result, or an `input_required` stream event), or null\n * when the value isn't one.\n */\nexport function parsePendingInput(raw: unknown): PendingInput | null {\n if (!isObject(raw)) return null;\n if (typeof raw.tool_call_id !== 'string' || !raw.tool_call_id) return null;\n return {\n toolCallId: raw.tool_call_id,\n question: str(raw.question) ?? '',\n options: optionsOf(raw.options),\n expiresAt: str(raw.expires_at),\n createdAt: str(raw.created_at),\n };\n}\n\nexport function parsePendingInputs(raw: unknown): PendingInput[] {\n return Array.isArray(raw) ? raw.map(parsePendingInput).filter((p): p is PendingInput => p !== null) : [];\n}\n\n/**\n * The question an SSE chunk announces, or null. Streams send it as its own\n * `input_required` event; some earlier backends sent an inline turn's as a\n * `message` event whose data has `type: \"input_required\"`. Both are handled.\n */\nexport function pendingInputFromChunk(chunk: SSEChunk): PendingInput | null {\n if (chunk.event !== 'input_required' && chunk.event !== 'message') return null;\n let parsed: unknown;\n try {\n parsed = JSON.parse(chunk.data);\n } catch {\n return null;\n }\n if (chunk.event === 'message' && (!isObject(parsed) || parsed.type !== 'input_required')) return null;\n return parsePendingInput(parsed);\n}\n\n/** An approval as the API reports it (stream event or chat detail), or null when malformed. */\nexport function parseApproval(raw: unknown): ApprovalRequest | null {\n if (!isObject(raw) || typeof raw.tool_call_id !== 'string') return null;\n return {\n type: str(raw.type) ?? 'approval_required',\n toolCallId: raw.tool_call_id,\n functionNamespace: str(raw.function_namespace) ?? '',\n functionName: str(raw.function_name) ?? '',\n arguments: isObject(raw.arguments) ? raw.arguments : {},\n };\n}\n\nexport function parseUsage(raw: unknown): TurnUsage | null {\n if (!isObject(raw)) return null;\n return {\n calls: num(raw.calls),\n promptTokens: num(raw.prompt_tokens),\n completionTokens: num(raw.completion_tokens),\n totalTokens: num(raw.total_tokens),\n cacheReadTokens: num(raw.cache_read_tokens),\n cacheWriteTokens: num(raw.cache_write_tokens),\n costUsd: typeof raw.cost_usd === 'number' ? raw.cost_usd : null,\n unpricedCalls: num(raw.unpriced_calls),\n errors: num(raw.errors),\n };\n}\n\nconst TURN_STATUSES: readonly TurnStatus[] = ['completed', 'input_required', 'in_progress', 'injected'];\n\n/** The turn-state fields of a send / invoke / answer response; servers before 0.5 omit them. */\nexport function parseTurnState(raw: Raw): TurnState {\n const status = TURN_STATUSES.includes(raw.status as TurnStatus) ? (raw.status as TurnStatus) : 'completed';\n return {\n status,\n pendingInputs: parsePendingInputs(raw.pending_inputs),\n channelId: str(raw.channel_id),\n usage: parseUsage(raw.usage),\n };\n}\n\nexport function parseMessage(data: Raw): ChatMessageFull {\n const toolCalls = data.tool_calls as ChatMessageFull['toolCalls'] | undefined;\n return {\n id: data.id as string,\n chatId: data.chat_id as string,\n role: data.role as ChatMessageFull['role'],\n content: (data.content as string) ?? null,\n toolCalls: toolCalls ?? null,\n toolCallId: (data.tool_call_id as string) ?? null,\n name: (data.name as string) ?? null,\n createdAt: data.created_at as string,\n };\n}\n\n/** How a `done` event ended the stream. */\nexport function parseDone(data: string): StreamDone {\n try {\n const parsed = JSON.parse(data);\n if (isObject(parsed) && typeof parsed.status === 'string') return { status: parsed.status };\n } catch {\n // fall through\n }\n return { status: 'completed' };\n}\n\n/**\n * The channel to follow after an approval decision, or null when there is\n * nothing to stream yet. A round with several asked calls resumes once,\n * after its last decision; until then the response says `resume: \"waiting\"`.\n * On servers before 0.5 (no `resume` field) only an approval resumed.\n */\nexport function approvalResumeChannel(\n result: { resume?: string | null; channelId?: string | null },\n approved = true,\n): string | null {\n if (result.resume === 'waiting') return null;\n if (result.resume === undefined && !approved) return null;\n return result.channelId || null;\n}\n\n/**\n * The channel to follow after answering a question (202 response), or null.\n * The answer resumes the conversation only when it was the round's last\n * outstanding completion (`resumed`) or that resume is being retried\n * (`resumePending`).\n */\nexport function answerResumeChannel(result: {\n resumed?: boolean;\n resumePending?: boolean;\n channelId?: string | null;\n}): string | null {\n if (!result.resumed && !result.resumePending) return null;\n return result.channelId || null;\n}\n","import type { SinasClient } from './SinasClient';\nimport type {\n AnswerPendingInputOptions,\n ApprovalRequest,\n ApprovalResult,\n ApprovalResume,\n ApproveToolCallOptions,\n ChatCreateResult,\n ChatDetail,\n InvokeOptions,\n InvokeResult,\n MessageContent,\n MessageSendResult,\n PendingInput,\n PendingInputAnswerAccepted,\n PendingInputAnswerResult,\n SSEChunk,\n StreamDone,\n StreamFromChannelOptions,\n StreamOptions,\n} from './types';\nimport {\n parseApproval,\n parseDone,\n parseMessage,\n parsePendingInputs,\n parseTurnState,\n} from './chatEvents';\n\nfunction splitAgentRef(agentRef: string): [string, string] {\n const [ns, name] = agentRef.split('/');\n if (!ns || !name) {\n throw new Error(`Invalid agent ref \"${agentRef}\": expected \"namespace/name\"`);\n }\n return [ns, name];\n}\n\nexport async function createChat(\n client: SinasClient,\n agentRef: string,\n input?: Record<string, unknown>\n): Promise<ChatCreateResult> {\n const [ns, name] = splitAgentRef(agentRef);\n const config = client.getConfig();\n const res = await client.fetch(`${config.apiBase}/agents/${ns}/${name}/chats`, {\n method: 'POST',\n body: JSON.stringify({ input: input || {} }),\n });\n const data = await res.json();\n return {\n id: data.id,\n agentNamespace: data.agent_namespace,\n agentName: data.agent_name,\n title: data.title,\n };\n}\n\n/**\n * Send a message and wait for the turn (non-streaming). On Sinas 0.5+ the\n * result says how the turn ended (`status`): with `input_required`, answer\n * the questions in `pendingInputs` with `answerPendingInput`.\n */\nexport async function sendMessage(\n client: SinasClient,\n chatId: string,\n content: MessageContent\n): Promise<MessageSendResult> {\n const config = client.getConfig();\n const res = await client.fetch(`${config.apiBase}/chats/${chatId}/messages`, {\n method: 'POST',\n body: JSON.stringify({ content }),\n });\n const data = await res.json();\n return {\n id: data.id,\n chatId: data.chat_id,\n role: data.role,\n content: data.content,\n createdAt: data.created_at,\n ...parseTurnState(data),\n };\n}\n\n/**\n * Synchronous agent invoke: send a message, get the reply. Creates the chat\n * (or reuses the one for `sessionKey`). Check `status`: with\n * `input_required`, answer `pendingInputs` via `answerPendingInput`\n * (`{ wait: true }` returns the resumed turn's result the same way).\n */\nexport async function invokeAgent(\n client: SinasClient,\n agentRef: string,\n message: MessageContent,\n options: InvokeOptions = {},\n): Promise<InvokeResult> {\n const [ns, name] = splitAgentRef(agentRef);\n const config = client.getConfig();\n const body: Record<string, unknown> = { message };\n if (options.sessionKey !== undefined) body.session_key = options.sessionKey;\n if (options.reset !== undefined) body.reset = options.reset;\n if (options.input !== undefined) body.input = options.input;\n const res = await client.fetch(`${config.apiBase}/agents/${ns}/${name}/invoke`, {\n method: 'POST',\n body: JSON.stringify(body),\n });\n const data = await res.json();\n return {\n reply: typeof data.reply === 'string' ? data.reply : '',\n chatId: data.chat_id,\n sessionKey: data.session_key ?? null,\n ...parseTurnState(data),\n };\n}\n\nexport async function getChat(\n client: SinasClient,\n chatId: string,\n): Promise<ChatDetail> {\n const config = client.getConfig();\n const res = await client.fetch(`${config.apiBase}/chats/${chatId}`);\n const data = await res.json();\n const detail: ChatDetail = {\n id: data.id,\n agentNamespace: data.agent_namespace,\n agentName: data.agent_name,\n title: data.title,\n messages: (data.messages || []).map(parseMessage),\n pendingApprovals: (data.pending_approvals || [])\n .map(parseApproval)\n .filter((a: ApprovalRequest | null): a is ApprovalRequest => a !== null),\n };\n if (Array.isArray(data.pending_inputs)) {\n detail.pendingInputs = parsePendingInputs(data.pending_inputs);\n }\n return detail;\n}\n\n/**\n * Approve or reject a tool call that asked for approval. On Sinas 0.5+,\n * `resume` says whether the round resumes now (`queued`, follow `channelId`)\n * or waits for decisions on its other calls (`waiting`, nothing to stream);\n * `approvalResumeChannel(result, approved)` picks the channel to follow.\n */\nexport async function approveToolCall(\n client: SinasClient,\n chatId: string,\n toolCallId: string,\n approved: boolean,\n options: ApproveToolCallOptions = {},\n): Promise<ApprovalResult> {\n const config = client.getConfig();\n const body: Record<string, unknown> = { approved };\n if (approved && options.alwaysAllow) body.always_allow = true;\n const res = await client.fetch(\n `${config.apiBase}/chats/${chatId}/approve-tool/${encodeURIComponent(toolCallId)}`,\n { method: 'POST', body: JSON.stringify(body) },\n );\n const data = await res.json();\n const result: ApprovalResult = {\n status: data.status,\n toolCallId: data.tool_call_id,\n channelId: data.channel_id,\n };\n if (data.resume === 'waiting' || data.resume === 'queued') result.resume = data.resume as ApprovalResume;\n if (typeof data.message === 'string') result.message = data.message;\n return result;\n}\n\n/** The ask_user questions the chat is suspended on (Sinas 0.5+). */\nexport async function listPendingInputs(\n client: SinasClient,\n chatId: string,\n): Promise<PendingInput[]> {\n const config = client.getConfig();\n const res = await client.fetch(`${config.apiBase}/chats/${chatId}/pending-input`);\n return parsePendingInputs(await res.json());\n}\n\n/**\n * Answer an ask_user question; the answer becomes the call's tool result.\n * Without `wait`, resolves once the answer is recorded: follow\n * `answerResumeChannel(result)` (when not null) to stream the resumed turn.\n * With `{ wait: true }`, resolves with the resumed turn's result instead\n * (`input_required` again if the agent asks again).\n */\nexport function answerPendingInput(\n client: SinasClient,\n chatId: string,\n toolCallId: string,\n answer: string,\n options: AnswerPendingInputOptions & { wait: true },\n): Promise<PendingInputAnswerResult>;\nexport function answerPendingInput(\n client: SinasClient,\n chatId: string,\n toolCallId: string,\n answer: string,\n options?: AnswerPendingInputOptions & { wait?: false },\n): Promise<PendingInputAnswerAccepted>;\nexport function answerPendingInput(\n client: SinasClient,\n chatId: string,\n toolCallId: string,\n answer: string,\n options?: AnswerPendingInputOptions,\n): Promise<PendingInputAnswerAccepted | PendingInputAnswerResult>;\nexport async function answerPendingInput(\n client: SinasClient,\n chatId: string,\n toolCallId: string,\n answer: string,\n options: AnswerPendingInputOptions = {},\n): Promise<PendingInputAnswerAccepted | PendingInputAnswerResult> {\n const config = client.getConfig();\n const body: Record<string, unknown> = { answer };\n if (options.wait) body.wait = true;\n const res = await client.fetch(\n `${config.apiBase}/chats/${chatId}/pending-input/${encodeURIComponent(toolCallId)}`,\n { method: 'POST', body: JSON.stringify(body) },\n );\n const data = await res.json();\n if (options.wait) {\n return {\n toolCallId: data.tool_call_id,\n chatId: data.chat_id,\n reply: typeof data.reply === 'string' ? data.reply : '',\n message: data.message && typeof data.message === 'object' ? parseMessage(data.message) : null,\n ...parseTurnState(data),\n };\n }\n return {\n status: 'answered',\n toolCallId: data.tool_call_id,\n resumed: !!data.resumed,\n resumePending: !!data.resume_pending,\n channelId: data.channel_id ?? null,\n message: typeof data.message === 'string' ? data.message : '',\n };\n}\n\n/**\n * Follow a stream channel: the stream of a resumed round (after an approval\n * or an answer), an `in_progress` turn, or a reconnect.\n */\nexport function streamFromChannel(\n client: SinasClient,\n chatId: string,\n channelId: string,\n onChunk: (chunk: SSEChunk) => void,\n onDone?: (done: StreamDone) => void,\n onError?: (error: Error) => void,\n options: StreamFromChannelOptions = {},\n): AbortController {\n const config = client.getConfig();\n const params = new URLSearchParams({ last_id: options.lastId ?? '0' });\n if (options.includeThinking) params.set('include_thinking', 'true');\n return runSSE(\n `${config.apiBase}/chats/${chatId}/stream/${encodeURIComponent(channelId)}?${params}`,\n (signal) => ({ headers: client.getAuthHeaders(), signal }),\n 'Stream reconnect failed',\n onChunk,\n onDone,\n onError,\n );\n}\n\n/**\n * Open an SSE request and hand its events to `onChunk` until a `done`\n * event (or the end of the body), then call `onDone` once. Aborting the\n * returned controller ends it silently.\n */\nfunction runSSE(\n url: string,\n init: (signal: AbortSignal) => RequestInit,\n failure: string,\n onChunk: (chunk: SSEChunk) => void,\n onDone?: (done: StreamDone) => void,\n onError?: (error: Error) => void,\n): AbortController {\n const controller = new AbortController();\n\n (async () => {\n try {\n const res = await fetch(url, init(controller.signal));\n\n if (!res.ok) {\n const body = await res.json().catch(() => ({ detail: res.statusText }));\n throw new Error(body.detail || failure);\n }\n\n const reader = res.body!.getReader();\n const decoder = new TextDecoder();\n let buffer = '';\n\n while (true) {\n const { done, value } = await reader.read();\n if (done) break;\n\n buffer += decoder.decode(value, { stream: true });\n const { chunks, remaining } = parseSSE(buffer);\n buffer = remaining;\n\n for (const chunk of chunks) {\n onChunk(chunk);\n if (chunk.event === 'done') {\n onDone?.(parseDone(chunk.data));\n return;\n }\n }\n }\n\n // Process any remaining buffer\n if (buffer.trim()) {\n const { chunks } = parseSSE(buffer + '\\n\\n');\n for (const chunk of chunks) {\n onChunk(chunk);\n if (chunk.event === 'done') {\n onDone?.(parseDone(chunk.data));\n return;\n }\n }\n }\n\n onDone?.({ status: 'closed' });\n } catch (err) {\n if ((err as Error).name === 'AbortError') return;\n onError?.(err as Error);\n }\n })();\n\n return controller;\n}\n\n/**\n * Splits buffered SSE text into complete events (each ends with a blank\n * line); the incomplete tail is returned as `remaining` for the next read.\n */\nexport function parseSSE(buffer: string): { chunks: SSEChunk[]; remaining: string } {\n const chunks: SSEChunk[] = [];\n // Normalize \\r\\n to \\n (sse_starlette uses \\r\\n line endings). A \\r at\n // the very end stays in `remaining` until its \\n arrives.\n const normalized = buffer.replace(/\\r\\n/g, '\\n');\n let start = 0;\n let end: number;\n\n while ((end = normalized.indexOf('\\n\\n', start)) !== -1) {\n const block = normalized.slice(start, end);\n start = end + 2;\n let event = '';\n const data: string[] = [];\n for (const line of block.split('\\n')) {\n if (line.startsWith('event:')) event = line.slice(6).trim();\n else if (line.startsWith('data:')) data.push(line.slice(5).trim());\n }\n if (event || data.length) chunks.push({ event: event || 'message', data: data.join('\\n') });\n }\n\n return { chunks, remaining: normalized.slice(start) };\n}\n\n/** Send a message and stream the turn as SSE events. */\nexport function streamMessage(\n client: SinasClient,\n chatId: string,\n content: MessageContent,\n onChunk: (chunk: SSEChunk) => void,\n onDone?: (done: StreamDone) => void,\n onError?: (error: Error) => void,\n options: StreamOptions = {},\n): AbortController {\n const config = client.getConfig();\n const body: Record<string, unknown> = { content };\n if (options.includeThinking) body.include_thinking = true;\n return runSSE(\n `${config.apiBase}/chats/${chatId}/messages/stream`,\n (signal) => ({ method: 'POST', headers: client.getAuthHeaders(), body: JSON.stringify(body), signal }),\n 'Stream request failed',\n onChunk,\n onDone,\n onError,\n );\n}\n","import type { SinasClient } from './SinasClient';\nimport type { Collection, FileInfo, FileUploadRequest, FileUrlResult } from './types';\n\nexport async function listCollections(client: SinasClient): Promise<Collection[]> {\n const base = client.getProxyBase();\n const res = await client.fetch(`${base}/collections`);\n return res.json();\n}\n\nexport async function listFiles(\n client: SinasClient,\n namespace: string,\n collection: string\n): Promise<FileInfo[]> {\n const base = client.getProxyBase();\n const res = await client.fetch(`${base}/files/${namespace}/${collection}`);\n return res.json();\n}\n\nexport async function uploadFile(\n client: SinasClient,\n namespace: string,\n collection: string,\n data: FileUploadRequest,\n): Promise<FileInfo> {\n const apiBase = client.getConfig().apiBase;\n const res = await client.fetch(`${apiBase}/files/${namespace}/${collection}`, {\n method: 'POST',\n body: JSON.stringify(data),\n });\n return res.json();\n}\n\nexport async function generateFileUrl(\n client: SinasClient,\n namespace: string,\n collection: string,\n filename: string,\n expiresIn?: number,\n): Promise<FileUrlResult> {\n const apiBase = client.getConfig().apiBase;\n const params = new URLSearchParams();\n if (expiresIn) params.set('expires_in', String(expiresIn));\n const qs = params.toString() ? `?${params.toString()}` : '';\n const res = await client.fetch(\n `${apiBase}/files/${namespace}/${collection}/${encodeURIComponent(filename)}/url${qs}`,\n { method: 'POST' },\n );\n return res.json();\n}\n","import React from 'react';\nimport { executeQuery } from '../client/queries';\nimport { useClient } from './context';\nimport type { QueryResult } from '../client/types';\n\nexport interface UseQueryOptions {\n enabled?: boolean;\n refetchInterval?: number | null;\n}\n\nexport interface UseQueryResult {\n data: Record<string, unknown>[] | null;\n loading: boolean;\n error: string | null;\n rowCount: number | null;\n refetch: (overrideInput?: Record<string, unknown>) => Promise<QueryResult | undefined>;\n}\n\nexport function useQuery(\n ref: string,\n input: Record<string, unknown> = {},\n options: UseQueryOptions = {}\n): UseQueryResult {\n const client = useClient();\n const { enabled = true, refetchInterval = null } = options;\n\n const [data, setData] = React.useState<Record<string, unknown>[] | null>(null);\n const [loading, setLoading] = React.useState(false);\n const [error, setError] = React.useState<string | null>(null);\n const [rowCount, setRowCount] = React.useState<number | null>(null);\n\n const abortRef = React.useRef<AbortController | null>(null);\n const inputJson = JSON.stringify(input);\n\n const execute = React.useCallback(\n async (overrideInput?: Record<string, unknown>) => {\n abortRef.current?.abort();\n const controller = new AbortController();\n abortRef.current = controller;\n\n setLoading(true);\n setError(null);\n try {\n const result = await executeQuery(\n client,\n ref,\n overrideInput || JSON.parse(inputJson)\n );\n if (!controller.signal.aborted) {\n setData(result.data || null);\n setRowCount(result.rowCount ?? result.affectedRows ?? null);\n }\n return result;\n } catch (e) {\n if (!controller.signal.aborted) {\n setError((e as Error).message);\n }\n } finally {\n if (!controller.signal.aborted) {\n setLoading(false);\n }\n }\n },\n [client, ref, inputJson]\n );\n\n React.useEffect(() => {\n if (enabled) {\n execute();\n }\n return () => {\n abortRef.current?.abort();\n };\n }, [enabled, execute]);\n\n React.useEffect(() => {\n if (refetchInterval && enabled) {\n const id = setInterval(execute, refetchInterval);\n return () => clearInterval(id);\n }\n }, [refetchInterval, enabled, execute]);\n\n return { data, loading, error, rowCount, refetch: execute };\n}\n","import React from 'react';\nimport { SinasClient, type SinasClientOptions } from '../client/SinasClient';\n\nconst SinasContext = React.createContext<SinasClient | null>(null);\n\nexport interface SinasProviderProps {\n /** Pre-built client. If provided, options below are ignored. */\n client?: SinasClient;\n /** Standalone-mode options (baseUrl, token callbacks, etc.). */\n options?: SinasClientOptions;\n children: React.ReactNode;\n}\n\nexport function SinasProvider({ client, options, children }: SinasProviderProps) {\n const value = React.useMemo(\n () => client || new SinasClient(options),\n // We intentionally only re-create when `client` reference changes; `options`\n // is expected to be a stable object (callbacks reading from localStorage).\n // eslint-disable-next-line react-hooks/exhaustive-deps\n [client],\n );\n return React.createElement(SinasContext.Provider, { value }, children);\n}\n\nexport function useClient(): SinasClient {\n const client = React.useContext(SinasContext);\n if (client) return client;\n return defaultClient;\n}\n\nconst defaultClient = new SinasClient();\n","import React from 'react';\nimport { executeFunction } from '../client/functions';\nimport { useClient } from './context';\nimport type { FunctionResult } from '../client/types';\n\nexport interface UseExecuteResult {\n execute: (input?: Record<string, unknown>, timeout?: number) => Promise<FunctionResult | undefined>;\n result: unknown;\n loading: boolean;\n error: string | null;\n executionId: string | null;\n}\n\nexport function useExecute(ref: string): UseExecuteResult {\n const client = useClient();\n\n const [result, setResult] = React.useState<unknown>(null);\n const [loading, setLoading] = React.useState(false);\n const [error, setError] = React.useState<string | null>(null);\n const [executionId, setExecutionId] = React.useState<string | null>(null);\n\n const execute = React.useCallback(\n async (input: Record<string, unknown> = {}, timeout?: number) => {\n setLoading(true);\n setError(null);\n try {\n const data = await executeFunction(client, ref, input, timeout);\n setResult(data.result);\n setExecutionId(data.executionId);\n if (data.status === 'error') {\n setError(data.error || 'Function execution failed');\n } else if (data.status === 'timeout') {\n setError('Function execution timed out');\n }\n return data;\n } catch (e) {\n setError((e as Error).message);\n } finally {\n setLoading(false);\n }\n },\n [client, ref]\n );\n\n return { execute, result, loading, error, executionId };\n}\n","import React from 'react';\nimport { stateGet, stateSet, stateDelete, stateList } from '../client/states';\nimport { useClient } from './context';\nimport type { StateListResult } from '../client/types';\n\nexport interface UseStateStoreOptions {\n visibility?: 'private' | 'shared';\n}\n\nexport interface UseStateStoreResult {\n value: unknown;\n loading: boolean;\n error: string | null;\n save: (value: unknown, opts?: UseStateStoreOptions) => Promise<void>;\n remove: () => Promise<void>;\n refetch: () => Promise<void>;\n list: () => Promise<StateListResult | undefined>;\n}\n\nexport function useStateStore(ns: string, key?: string): UseStateStoreResult {\n const client = useClient();\n\n const [value, setValue] = React.useState<unknown>(null);\n const [loading, setLoading] = React.useState(true);\n const [error, setError] = React.useState<string | null>(null);\n\n const load = React.useCallback(async () => {\n if (!key) {\n setLoading(false);\n return;\n }\n setLoading(true);\n setError(null);\n try {\n const result = await stateGet(client, ns, key);\n if (result.found) {\n setValue(result.value);\n } else {\n setValue(null);\n }\n } catch (e) {\n setError((e as Error).message);\n } finally {\n setLoading(false);\n }\n }, [client, ns, key]);\n\n const save = React.useCallback(\n async (newValue: unknown, opts?: UseStateStoreOptions) => {\n if (!key) throw new Error('Cannot save without a key');\n setValue(newValue);\n setError(null);\n try {\n await stateSet(client, ns, key, newValue, opts?.visibility);\n } catch (e) {\n setError((e as Error).message);\n throw e;\n }\n },\n [client, ns, key]\n );\n\n const remove = React.useCallback(async () => {\n if (!key) throw new Error('Cannot delete without a key');\n setValue(null);\n setError(null);\n try {\n await stateDelete(client, ns, key);\n } catch (e) {\n setError((e as Error).message);\n throw e;\n }\n }, [client, ns, key]);\n\n const list = React.useCallback(async () => {\n setError(null);\n try {\n return await stateList(client, ns);\n } catch (e) {\n setError((e as Error).message);\n }\n }, [client, ns]);\n\n React.useEffect(() => {\n load();\n }, [load]);\n\n return { value, loading, error, save, remove, refetch: load, list };\n}\n","import React from 'react';\nimport {\n answerPendingInput,\n approveToolCall,\n createChat,\n getChat,\n streamFromChannel,\n streamMessage,\n} from '../client/chat';\nimport {\n answerResumeChannel,\n approvalResumeChannel,\n parseApproval,\n pendingInputFromChunk,\n} from '../client/chatEvents';\nimport { useClient } from './context';\nimport {\n NOT_THINKING,\n TRAILING_POLLS_MS,\n addApproval,\n applyTextDelta,\n applyThinking,\n applyToolEnd,\n applyToolStart,\n createLatestGate,\n mergePendingInputs,\n nextPendingPollMs,\n parseMessageChunk,\n stopThinking,\n thinkingView,\n type ThinkingRounds,\n} from './chatState';\nimport type {\n ChatMessageFull,\n ApprovalRequest,\n SSEChunk,\n MessageContent,\n PendingInput,\n StreamDone,\n} from '../client/types';\n\nexport interface ToolResult {\n content: string;\n name: string;\n}\n\nexport interface ChatSessionMessage extends ChatMessageFull {\n /** True while streaming content is being appended */\n streaming?: boolean;\n /** Inline tool results keyed by tool_call_id (merged from tool_end events) */\n toolResults?: Record<string, ToolResult>;\n}\n\nexport interface ToolStatus {\n toolCallId: string;\n name: string;\n description: string;\n status: 'running' | 'complete';\n}\n\n/**\n * The model's thinking during the current turn. Thinking isn't stored with\n * the messages, so it is only known while (and after) streaming the turn;\n * it resets when the next turn starts.\n */\nexport interface ChatThinking {\n /** The model is thinking right now (before its answer or next tool call). */\n active: boolean;\n /**\n * The thinking text so far this turn; only sent with `includeThinking`\n * (otherwise always ''). Thinking rounds are separated by a blank line.\n */\n text: string;\n}\n\nexport interface ApproveOptions {\n /** Approve this tool for the rest of the chat: it won't ask again (Sinas 0.5+). */\n alwaysAllow?: boolean;\n}\n\nexport interface FollowOptions {\n /** Last received stream entry id to resume after (default: from the start). */\n lastId?: string;\n}\n\nexport interface UseChatResult {\n chatId: string | null;\n messages: ChatSessionMessage[];\n loading: boolean;\n streaming: boolean;\n error: string | null;\n pendingApprovals: ApprovalRequest[];\n /**\n * The ask_user questions the conversation waits on (Sinas 0.5+): from\n * `input_required` stream events and from the chat as loaded. Answer with\n * `answer`.\n */\n pendingInputs: PendingInput[];\n /** The model's thinking in the current turn (see `includeThinking`). */\n thinking: ChatThinking;\n toolStatus: ToolStatus[];\n send: (content: MessageContent) => void;\n /**\n * Approve a tool call. When other calls of the same round still wait for a\n * decision, nothing streams until the last one is decided.\n */\n approve: (toolCallId: string, options?: ApproveOptions) => void;\n reject: (toolCallId: string) => void;\n /**\n * Answer an ask_user question. Resolves true once the answer is recorded\n * (the question is then removed from `pendingInputs`), false when it\n * failed (see `error`). When it was the round's last open question, the\n * resumed turn streams into `messages`.\n */\n answer: (toolCallId: string, answer: string) => Promise<boolean>;\n /**\n * Stream a channel into this session: a turn that goes on elsewhere (an\n * `in_progress` result, a reconnect to a running turn).\n */\n follow: (channelId: string, options?: FollowOptions) => void;\n stop: () => void;\n clearError: () => void;\n}\n\nexport interface UseChatOptions {\n chatId?: string;\n input?: Record<string, unknown>;\n /**\n * Stream the model's thinking text into `thinking.text` (Sinas 0.5+).\n * Without it, `thinking.active` still says when the model is thinking.\n */\n includeThinking?: boolean;\n /**\n * While questions wait with no stream open, re-read the chat periodically\n * and just after the earliest deadline, so an expired question (the round\n * then resumes server-side) or one answered elsewhere shows up without a\n * reload. Default true.\n */\n pollPendingInputs?: boolean;\n}\n\nexport function useChat(\n agentRef: string,\n options?: UseChatOptions,\n): UseChatResult {\n const client = useClient();\n const includeThinking = !!options?.includeThinking;\n const pollPendingInputs = options?.pollPendingInputs !== false;\n\n const [chatId, setChatId] = React.useState<string | null>(options?.chatId ?? null);\n const [messages, setMessages] = React.useState<ChatSessionMessage[]>([]);\n const [loading, setLoading] = React.useState(false);\n const [streaming, setStreaming] = React.useState(false);\n const [error, setError] = React.useState<string | null>(null);\n const [pendingApprovals, setPendingApprovals] = React.useState<ApprovalRequest[]>([]);\n const [pendingInputs, setPendingInputs] = React.useState<PendingInput[]>([]);\n const [thinking, setThinking] = React.useState<ThinkingRounds>(NOT_THINKING);\n const thinkingShown = React.useMemo(() => thinkingView(thinking), [thinking]);\n const [toolStatus, setToolStatus] = React.useState<ToolStatus[]>([]);\n // Index into TRAILING_POLLS_MS while re-reading a chat whose question went\n // away server-side; its length means \"not trailing\".\n const [trailingPoll, setTrailingPoll] = React.useState(TRAILING_POLLS_MS.length);\n // Bumped after each poll so the next one is scheduled even when the poll's\n // refresh was superseded (and so changed nothing).\n const [pollTick, setPollTick] = React.useState(0);\n\n const abortRef = React.useRef<AbortController | null>(null);\n const chatIdRef = React.useRef<string | null>(chatId);\n chatIdRef.current = chatId;\n // Only the newest refresh (or turn) may write the server's state.\n const [gate] = React.useState(createLatestGate);\n\n /**\n * Re-read the server's state: messages, approvals, questions. Resolves to\n * the questions shown, or null when the read failed or a newer refresh or\n * turn superseded it (its result is then dropped).\n */\n const refresh = React.useCallback(\n async (id: string): Promise<PendingInput[] | null> => {\n const ticket = gate.next();\n try {\n const detail = await getChat(client, id);\n if (!gate.isCurrent(ticket)) return null;\n setMessages(detail.messages);\n setPendingApprovals(detail.pendingApprovals ?? []);\n const inputs = detail.pendingInputs ?? [];\n setPendingInputs(inputs);\n return inputs;\n } catch {\n // Best-effort: what is already shown stays when the read fails.\n return null;\n }\n },\n [client, gate],\n );\n\n // Load existing chat on mount if chatId provided\n React.useEffect(() => {\n if (!options?.chatId) return;\n let cancelled = false;\n const ticket = gate.next();\n\n setLoading(true);\n getChat(client, options.chatId)\n .then((detail) => {\n if (cancelled || !gate.isCurrent(ticket)) return;\n setChatId(detail.id);\n setMessages(detail.messages);\n setPendingApprovals(detail.pendingApprovals ?? []);\n setPendingInputs(detail.pendingInputs ?? []);\n })\n .catch((e) => {\n if (cancelled) return;\n setError((e as Error).message);\n })\n .finally(() => {\n if (!cancelled) setLoading(false);\n });\n\n return () => { cancelled = true; };\n }, [client, gate, options?.chatId]);\n\n // Cleanup on unmount\n React.useEffect(() => {\n return () => {\n abortRef.current?.abort();\n };\n }, []);\n\n // While questions wait with no stream open, nothing announces that one\n // expired (the round then resumes server-side) or was answered elsewhere:\n // re-read the chat periodically and just after the earliest deadline,\n // then a few more times once a question went away, to show the reply.\n React.useEffect(() => {\n if (!pollPendingInputs || streaming || !chatId) return;\n let delay: number | null = null;\n if (pendingInputs.length > 0) delay = nextPendingPollMs(pendingInputs, Date.now());\n else if (trailingPoll < TRAILING_POLLS_MS.length) delay = TRAILING_POLLS_MS[trailingPoll];\n if (delay === null) return;\n const waiting = pendingInputs.map((p) => p.toolCallId);\n const timer = setTimeout(async () => {\n const now = await refresh(chatId);\n if (waiting.length === 0) setTrailingPoll((i) => i + 1);\n else if (now && waiting.some((id) => !now.some((p) => p.toolCallId === id))) setTrailingPoll(0);\n setPollTick((t) => t + 1);\n }, delay);\n return () => clearTimeout(timer);\n }, [pollPendingInputs, chatId, streaming, pendingInputs, trailingPoll, pollTick, refresh]);\n\n const handleStreamChunk = React.useCallback(\n (chunk: SSEChunk) => {\n // A question: its own event, or (some earlier backends, inline turn)\n // a typed message event.\n const asked = pendingInputFromChunk(chunk);\n if (asked) {\n setThinking(stopThinking);\n setPendingInputs((prev) => mergePendingInputs(prev, [asked]));\n return;\n }\n const chatIdNow = chatIdRef.current || '';\n if (chunk.event === 'message') {\n const { text, thinking: thought } = parseMessageChunk(chunk.data);\n if (thought !== undefined) setThinking((prev) => applyThinking(prev, thought));\n if (text) {\n setThinking(stopThinking);\n setMessages((prev) => applyTextDelta(prev, text, chatIdNow));\n }\n } else if (chunk.event === 'tool_start') {\n setThinking(stopThinking);\n try {\n const parsed = JSON.parse(chunk.data);\n setToolStatus((prev) => [\n ...prev,\n { toolCallId: parsed.tool_call_id, name: parsed.name, description: parsed.description, status: 'running' },\n ]);\n setMessages((prev) => applyToolStart(prev, parsed, chatIdNow));\n } catch {\n // ignore malformed tool_start events\n }\n } else if (chunk.event === 'tool_end') {\n try {\n const parsed = JSON.parse(chunk.data);\n setToolStatus((prev) =>\n prev.map((t) => (t.toolCallId === parsed.tool_call_id ? { ...t, status: 'complete' } : t)),\n );\n setMessages((prev) => applyToolEnd(prev, parsed));\n } catch {\n // ignore malformed tool_end events\n }\n } else if (chunk.event === 'approval_required') {\n setThinking(stopThinking);\n try {\n const approval = parseApproval(JSON.parse(chunk.data));\n if (approval) setPendingApprovals((prev) => addApproval(prev, approval));\n } catch {\n // ignore malformed approval events\n }\n } else if (chunk.event === 'error') {\n setThinking(stopThinking);\n try {\n const parsed = JSON.parse(chunk.data);\n setError(parsed.error || 'Stream error');\n } catch {\n setError(chunk.data || 'Stream error');\n }\n }\n },\n [],\n );\n\n const streamCallbacks = React.useCallback(\n (id: string) =>\n [\n (_done: StreamDone) => {\n setStreaming(false);\n setToolStatus([]);\n setThinking(stopThinking);\n // Re-read the authoritative server state (and, after a suspended\n // turn, the questions it waits on).\n refresh(id);\n },\n (err: Error) => {\n setError(err.message);\n setStreaming(false);\n setToolStatus([]);\n setThinking(stopThinking);\n },\n ] as const,\n [refresh],\n );\n\n // Stream a channel (a resumed round after an approval or an answer).\n const followChannel = React.useCallback(\n (id: string, channelId: string, lastId?: string) => {\n abortRef.current?.abort();\n gate.next(); // a refresh still in flight is older than this stream\n setStreaming(true);\n setError(null);\n setThinking(NOT_THINKING);\n const [onDone, onError] = streamCallbacks(id);\n abortRef.current = streamFromChannel(client, id, channelId, handleStreamChunk, onDone, onError, {\n includeThinking,\n lastId,\n });\n },\n [client, gate, includeThinking, handleStreamChunk, streamCallbacks],\n );\n\n const send = React.useCallback(\n (content: MessageContent) => {\n const doSend = async () => {\n let activeChatId = chatIdRef.current;\n\n // Auto-create chat on first send\n if (!activeChatId) {\n setLoading(true);\n setError(null);\n try {\n const result = await createChat(client, agentRef, options?.input);\n activeChatId = result.id;\n setChatId(result.id);\n chatIdRef.current = result.id;\n } catch (e) {\n setError((e as Error).message);\n setLoading(false);\n return;\n }\n setLoading(false);\n }\n\n abortRef.current?.abort();\n gate.next(); // a refresh still in flight is older than this turn\n setStreaming(true);\n setError(null);\n setPendingApprovals([]);\n setToolStatus([]);\n setThinking(NOT_THINKING);\n\n // Add user message optimistically\n const displayContent = typeof content === 'string' ? content : JSON.stringify(content);\n const userMsg: ChatSessionMessage = {\n id: `tmp-user-${Date.now()}`,\n chatId: activeChatId,\n role: 'user',\n content: displayContent,\n toolCalls: null,\n toolCallId: null,\n name: null,\n createdAt: new Date().toISOString(),\n };\n setMessages((prev) => [...prev, userMsg]);\n\n const [onDone, onError] = streamCallbacks(activeChatId);\n abortRef.current = streamMessage(client, activeChatId, content, handleStreamChunk, onDone, onError, {\n includeThinking,\n });\n };\n\n doSend();\n },\n [client, agentRef, options?.input, gate, includeThinking, handleStreamChunk, streamCallbacks],\n );\n\n const decide = React.useCallback(\n (toolCallId: string, approved: boolean, alwaysAllow: boolean) => {\n const id = chatIdRef.current;\n if (!id) return;\n gate.next(); // a refresh in flight must not bring the card back\n setPendingApprovals((prev) => prev.filter((a) => a.toolCallId !== toolCallId));\n setError(null);\n\n (async () => {\n try {\n const result = await approveToolCall(client, id, toolCallId, approved, { alwaysAllow });\n // Until the round's last decision there is nothing to stream: the\n // remaining approvals stay pending.\n const channelId = approvalResumeChannel(result, approved);\n if (channelId) followChannel(id, channelId);\n else if (result.resume === undefined) refresh(id); // pre-0.5 rejection\n } catch (e) {\n setError((e as Error).message);\n // Show what is actually still pending (expired, already decided…)\n refresh(id);\n }\n })();\n },\n [client, gate, followChannel, refresh],\n );\n\n const approve = React.useCallback(\n (toolCallId: string, opts?: ApproveOptions) => decide(toolCallId, true, !!opts?.alwaysAllow),\n [decide],\n );\n\n const reject = React.useCallback(\n (toolCallId: string) => decide(toolCallId, false, false),\n [decide],\n );\n\n const answer = React.useCallback(\n async (toolCallId: string, text: string): Promise<boolean> => {\n const id = chatIdRef.current;\n if (!id) return false;\n setError(null);\n try {\n const result = await answerPendingInput(client, id, toolCallId, text);\n gate.next(); // a refresh in flight must not bring the question back\n setPendingInputs((prev) => prev.filter((p) => p.toolCallId !== toolCallId));\n // The last outstanding completion resumes the round on a fresh\n // channel; otherwise the round keeps waiting on the others.\n const channelId = answerResumeChannel(result);\n if (channelId) followChannel(id, channelId);\n return true;\n } catch (e) {\n setError((e as Error).message);\n refresh(id);\n return false;\n }\n },\n [client, gate, followChannel, refresh],\n );\n\n const follow = React.useCallback(\n (channelId: string, opts?: FollowOptions) => {\n const id = chatIdRef.current;\n if (!id) return;\n followChannel(id, channelId, opts?.lastId);\n },\n [followChannel],\n );\n\n const stop = React.useCallback(() => {\n abortRef.current?.abort();\n abortRef.current = null;\n setStreaming(false);\n setThinking(stopThinking);\n }, []);\n\n const clearError = React.useCallback(() => {\n setError(null);\n }, []);\n\n return {\n chatId,\n messages,\n loading,\n streaming,\n error,\n pendingApprovals,\n pendingInputs,\n thinking: thinkingShown,\n toolStatus,\n send,\n approve,\n reject,\n answer,\n follow,\n stop,\n clearError,\n };\n}\n","// useChat's state transitions as pure functions, so they can be tested\n// without React (tests/chat-state.test.mjs). The hook only wires them to\n// state.\nimport type { ApprovalRequest, PendingInput } from '../client/types';\nimport type { ChatSessionMessage, ChatThinking } from './useChat';\n\n/** What a `message` stream event carries: answer text and/or thinking. */\nexport interface MessageChunk {\n /** Answer text ('' when the event carries none, e.g. a typed event such as tool_rejected). */\n text: string;\n /** Thinking text: '' for \"the model started thinking\", undefined when not a thinking event. */\n thinking?: string;\n}\n\nexport function parseMessageChunk(data: string): MessageChunk {\n let parsed: unknown;\n try {\n parsed = JSON.parse(data);\n } catch {\n return { text: data };\n }\n if (!parsed || typeof parsed !== 'object') return { text: '' };\n const p = parsed as Record<string, unknown>;\n const out: MessageChunk = { text: typeof p.content === 'string' ? p.content : '' };\n if (typeof p.thinking === 'string') out.thinking = p.thinking;\n return out;\n}\n\n/** Appends streamed text to the assistant message being streamed, or starts one. */\nexport function applyTextDelta(\n messages: ChatSessionMessage[],\n text: string,\n chatId: string,\n now: Date = new Date(),\n): ChatSessionMessage[] {\n if (!text) return messages;\n const last = messages[messages.length - 1];\n if (last && last.role === 'assistant' && !last.toolCalls && last.streaming) {\n const next = [...messages];\n next[next.length - 1] = { ...last, content: (last.content || '') + text };\n return next;\n }\n return [\n ...messages,\n {\n id: `tmp-text-${now.getTime()}`,\n chatId,\n role: 'assistant',\n content: text,\n toolCalls: null,\n toolCallId: null,\n name: null,\n createdAt: now.toISOString(),\n streaming: true,\n },\n ];\n}\n\nexport interface ToolStartEvent {\n tool_call_id: string;\n name: string;\n arguments?: string;\n description?: string;\n}\n\n/** Shows a started tool call as its own bubble (once), freezing the text before it. */\nexport function applyToolStart(\n messages: ChatSessionMessage[],\n event: ToolStartEvent,\n chatId: string,\n now: Date = new Date(),\n): ChatSessionMessage[] {\n if (messages.some((m) => m.toolCalls?.some((tc) => tc.id === event.tool_call_id))) return messages;\n const frozen = messages.map((m, i) =>\n i === messages.length - 1 && m.streaming && m.role === 'assistant' && !m.toolCalls ? { ...m, streaming: false } : m,\n );\n return [\n ...frozen,\n {\n id: `tmp-tc-${event.tool_call_id}`,\n chatId,\n role: 'assistant',\n content: null,\n toolCalls: [\n {\n id: event.tool_call_id,\n type: 'function',\n function: { name: event.name, arguments: event.arguments || '{}' },\n description: event.description,\n },\n ],\n toolCallId: null,\n name: null,\n createdAt: now.toISOString(),\n streaming: true,\n },\n ];\n}\n\n/** Merges a finished tool call's result into its bubble. */\nexport function applyToolEnd(\n messages: ChatSessionMessage[],\n event: { tool_call_id: string; name: string; result?: unknown },\n): ChatSessionMessage[] {\n if (event.result === undefined) return messages;\n const content = typeof event.result === 'string' ? event.result : JSON.stringify(event.result);\n return messages.map((m) =>\n m.toolCalls?.some((tc) => tc.id === event.tool_call_id)\n ? { ...m, toolResults: { ...m.toolResults, [event.tool_call_id]: { content, name: event.name } } }\n : m,\n );\n}\n\n/** Adds an approval card unless that call already has one. */\nexport function addApproval(current: ApprovalRequest[], approval: ApprovalRequest): ApprovalRequest[] {\n return current.some((a) => a.toolCallId === approval.toolCallId) ? current : [...current, approval];\n}\n\n/** Adds questions not already listed (by tool call id), keeping order. */\nexport function mergePendingInputs(current: PendingInput[], incoming: PendingInput[]): PendingInput[] {\n const seen = new Set(current.map((p) => p.toolCallId));\n const added = incoming.filter((p) => !seen.has(p.toolCallId) && seen.add(p.toolCallId));\n return added.length ? [...current, ...added] : current;\n}\n\n/** The hook's thinking state: one entry per thinking round of the turn. */\nexport interface ThinkingRounds {\n active: boolean;\n rounds: string[];\n}\n\nexport const NOT_THINKING: ThinkingRounds = { active: false, rounds: [] };\n\n/**\n * A thinking chunk: the model is thinking. The first chunk after the answer\n * or a tool call started (often an empty \"started thinking\") opens a new\n * round.\n */\nexport function applyThinking(state: ThinkingRounds, thinking: string): ThinkingRounds {\n if (!state.active) return { active: true, rounds: [...state.rounds, thinking] };\n if (!thinking) return state;\n const rounds = [...state.rounds];\n rounds[rounds.length - 1] += thinking;\n return { active: true, rounds };\n}\n\n/** The answer, a tool call or the end of the stream: thinking has stopped. */\nexport function stopThinking(state: ThinkingRounds): ThinkingRounds {\n return state.active ? { ...state, active: false } : state;\n}\n\n/** What the hook returns: the rounds' text, separated by a blank line. */\nexport function thinkingView(state: ThinkingRounds): ChatThinking {\n return { active: state.active, text: state.rounds.filter((r) => r).join('\\n\\n') };\n}\n\n/**\n * Orders asynchronous refreshes: each one takes a ticket, and only the\n * newest ticket may write its result. A slow refresh from an earlier turn\n * then can't overwrite what a later turn (or a later refresh) showed.\n * Starting a turn also takes a ticket, voiding refreshes still in flight.\n */\nexport function createLatestGate() {\n let latest = 0;\n return {\n next: (): number => ++latest,\n isCurrent: (ticket: number): boolean => ticket === latest,\n };\n}\n\n/** Never wait longer than this between checks while a question is open. */\nexport const PENDING_POLL_MAX_MS = 30_000;\nconst PENDING_POLL_MIN_MS = 1_000;\n/** Checked this long after a deadline (the server's expiry sweep runs about once a minute). */\nconst EXPIRY_GRACE_MS = 5_000;\n/** Once a deadline has passed, how often to check until the sweep has run. */\nconst OVERDUE_POLL_MS = 10_000;\n\n/**\n * How long to wait before re-reading a chat that waits on ask_user\n * questions with no stream open. An unanswered question expires and the\n * round resumes server-side without the client being told; re-reading\n * every PENDING_POLL_MAX_MS, and just after the earliest deadline, shows\n * that (and an answer given elsewhere) without a reload.\n */\nexport function nextPendingPollMs(inputs: PendingInput[], nowMs: number): number {\n let wait = PENDING_POLL_MAX_MS;\n for (const input of inputs) {\n const deadline = input.expiresAt ? Date.parse(input.expiresAt) : NaN;\n if (Number.isNaN(deadline)) continue;\n const untilDue = deadline + EXPIRY_GRACE_MS - nowMs;\n wait = Math.min(wait, untilDue > 0 ? untilDue : OVERDUE_POLL_MS);\n }\n return Math.max(PENDING_POLL_MIN_MS, wait);\n}\n\n/**\n * After a question disappears without an answer from this hook (it expired,\n * or was answered elsewhere), the round resumes server-side: re-read the\n * chat at these delays to show the reply.\n */\nexport const TRAILING_POLLS_MS = [5_000, 15_000, 30_000];\n","import { useClient } from './context';\nimport { useQuery } from './useQuery';\nimport { useExecute } from './useExecute';\nimport { useStateStore } from './useStateStore';\nimport { useChat } from './useChat';\nimport type { SinasConfig } from '../client/types';\nimport type { SinasClient } from '../client/SinasClient';\n\nexport interface UseSinasResult {\n config: SinasConfig;\n input: Record<string, unknown>;\n client: SinasClient;\n useQuery: typeof useQuery;\n useExecute: typeof useExecute;\n useStateStore: typeof useStateStore;\n useChat: typeof useChat;\n}\n\nexport function useSinas(): UseSinasResult {\n const client = useClient();\n\n return {\n config: client.getConfig(),\n input: client.getInput(),\n client,\n useQuery,\n useExecute,\n useStateStore,\n useChat,\n };\n}\n","import React from 'react';\nimport { useClient } from './context';\nimport { SinasAuthError } from '../client/errors';\nimport type {\n AuthUser,\n InfoResponse,\n LoginResponse,\n OTPVerifyResponse,\n} from '../client/types';\n\nexport type AuthStatus = 'loading' | 'authenticated' | 'unauthenticated';\n\nexport interface UseAuthResult {\n status: AuthStatus;\n user: AuthUser | null;\n info: InfoResponse | null;\n error: string | null;\n\n /**\n * Refresh the session by calling /auth/me with the current access token.\n * Call this on app boot and after token changes.\n */\n refresh: () => Promise<void>;\n\n /**\n * Start a login. In password-only mode this completes the login and\n * returns access/refresh tokens. In OTP / password+OTP mode the response\n * carries a `session_id` to feed into `verifyOTP`.\n */\n login: (email: string, password?: string) => Promise<LoginResponse>;\n\n /** Second step for OTP / password+OTP. Returns the final tokens. */\n verifyOTP: (sessionId: string, otpCode: string) => Promise<OTPVerifyResponse>;\n\n /** Revoke the refresh token and clear local auth state. */\n logout: (refreshToken?: string) => Promise<void>;\n}\n\nexport interface UseAuthOptions {\n /** Refresh on mount. Default true. */\n autoRefresh?: boolean;\n}\n\n/**\n * React hook for the standalone Sinas login flow. The hosting app is\n * responsible for storing the tokens it receives (typically in localStorage)\n * and wiring `getAccessToken` / `getRefreshToken` / `onTokenRefresh` on the\n * SinasProvider so this hook can read the current session.\n */\nexport function useAuth(options: UseAuthOptions = {}): UseAuthResult {\n const { autoRefresh = true } = options;\n const client = useClient();\n\n const [status, setStatus] = React.useState<AuthStatus>('loading');\n const [user, setUser] = React.useState<AuthUser | null>(null);\n const [info, setInfo] = React.useState<InfoResponse | null>(null);\n const [error, setError] = React.useState<string | null>(null);\n\n const refresh = React.useCallback(async () => {\n setError(null);\n try {\n // Fetch /info in parallel with /me (info is unauthenticated and cheap).\n const [infoResp, meResp] = await Promise.all([\n client.auth.getInfo().catch(() => null),\n client.getAccessToken() ? client.auth.getMe().catch(() => null) : Promise.resolve(null),\n ]);\n if (infoResp) setInfo(infoResp);\n if (meResp) {\n setUser(meResp);\n setStatus('authenticated');\n } else {\n setUser(null);\n setStatus('unauthenticated');\n }\n } catch (e) {\n setError(e instanceof Error ? e.message : String(e));\n setStatus('unauthenticated');\n }\n }, [client]);\n\n React.useEffect(() => {\n if (autoRefresh) void refresh();\n }, [autoRefresh, refresh]);\n\n const login = React.useCallback(\n async (email: string, password?: string) => {\n setError(null);\n try {\n return await client.auth.login({ email, password });\n } catch (e) {\n const msg = e instanceof Error ? e.message : String(e);\n setError(msg);\n throw e;\n }\n },\n [client],\n );\n\n const verifyOTP = React.useCallback(\n async (sessionId: string, otpCode: string) => {\n setError(null);\n try {\n return await client.auth.verifyOTP({ session_id: sessionId, otp_code: otpCode });\n } catch (e) {\n const msg = e instanceof Error ? e.message : String(e);\n setError(msg);\n throw e;\n }\n },\n [client],\n );\n\n const logout = React.useCallback(\n async (refreshToken?: string) => {\n if (refreshToken) {\n try {\n await client.auth.logout(refreshToken);\n } catch (e) {\n if (!(e instanceof SinasAuthError)) throw e;\n }\n }\n setUser(null);\n setStatus('unauthenticated');\n },\n [client],\n );\n\n return { status, user, info, error, refresh, login, verifyOTP, logout };\n}\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;;;ACAO,IAAM,aAAN,cAAyB,MAAM;AAAA,EAIpC,YAAY,SAAiB,SAAiB,GAAG,QAAiB;AAChE,UAAM,OAAO;AACb,SAAK,OAAO;AACZ,SAAK,SAAS;AACd,SAAK,SAAS,UAAU;AAAA,EAC1B;AACF;AAEO,IAAM,iBAAN,cAA6B,WAAW;AAAA,EAC7C,YAAY,UAAkB,2BAA2B;AACvD,UAAM,SAAS,GAAG;AAClB,SAAK,OAAO;AAAA,EACd;AACF;AAEO,IAAM,uBAAN,cAAmC,WAAW;AAAA,EACnD,YAAY,UAAkB,qBAAqB;AACjD,UAAM,SAAS,GAAG;AAClB,SAAK,OAAO;AAAA,EACd;AACF;AAEO,IAAM,qBAAN,cAAiC,WAAW;AAAA,EACjD,YAAY,UAAkB;AAC5B,UAAM,GAAG,QAAQ,cAAc,GAAG;AAClC,SAAK,OAAO;AAAA,EACd;AACF;AAEO,IAAM,oBAAN,cAAgC,WAAW;AAAA,EAChD,YAAY,UAAkB,qBAAqB;AACjD,UAAM,SAAS,GAAG;AAClB,SAAK,OAAO;AAAA,EACd;AACF;;;ACpBA,SAAS,SAAS,SAAyB;AACzC,SAAO,QAAQ,QAAQ,QAAQ,EAAE;AACnC;AAEA,eAAe,UACb,SACA,MACA,OAAoB,CAAC,GACrB,aACmB;AACnB,QAAM,UAAU,IAAI,QAAQ,KAAK,OAAO;AACxC,MAAI,CAAC,QAAQ,IAAI,cAAc,KAAK,KAAK,SAAS,QAAW;AAC3D,YAAQ,IAAI,gBAAgB,kBAAkB;AAAA,EAChD;AACA,MAAI,YAAa,SAAQ,IAAI,iBAAiB,UAAU,WAAW,EAAE;AAErE,QAAM,MAAM,MAAM,MAAM,GAAG,SAAS,OAAO,CAAC,GAAG,IAAI,IAAI,EAAE,GAAG,MAAM,QAAQ,CAAC;AAC3E,MAAI,IAAI,MAAM,IAAI,WAAW,IAAK,QAAO;AAEzC,MAAI,SAAiB,IAAI;AACzB,MAAI;AACF,UAAM,OAAO,MAAM,IAAI,MAAM,EAAE,KAAK;AACpC,aAAS,KAAK,UAAU,KAAK,WAAW;AAAA,EAC1C,QAAQ;AAAA,EAER;AACA,MAAI,IAAI,WAAW,IAAK,OAAM,IAAI,eAAe,MAAM;AACvD,MAAI,IAAI,WAAW,IAAK,OAAM,IAAI,qBAAqB,MAAM;AAC7D,MAAI,IAAI,WAAW,IAAK,OAAM,IAAI,mBAAmB,MAAM;AAC3D,QAAM,IAAI,WAAW,QAAQ,IAAI,QAAQ,MAAM;AACjD;AAGA,eAAsB,QAAQ,SAAwC;AACpE,QAAM,MAAM,MAAM,UAAU,SAAS,OAAO;AAC5C,SAAQ,MAAM,IAAI,KAAK;AACzB;AAOA,eAAsB,MACpB,SACA,SACwB;AACxB,QAAM,MAAM,MAAM,UAAU,SAAS,eAAe;AAAA,IAClD,QAAQ;AAAA,IACR,MAAM,KAAK,UAAU,OAAO;AAAA,EAC9B,CAAC;AACD,SAAQ,MAAM,IAAI,KAAK;AACzB;AAGA,eAAsB,UACpB,SACA,SAC4B;AAC5B,QAAM,MAAM,MAAM,UAAU,SAAS,oBAAoB;AAAA,IACvD,QAAQ;AAAA,IACR,MAAM,KAAK,UAAU,OAAO;AAAA,EAC9B,CAAC;AACD,SAAQ,MAAM,IAAI,KAAK;AACzB;AAGA,eAAsB,QACpB,SACA,cAC0B;AAC1B,QAAM,MAAM,MAAM,UAAU,SAAS,iBAAiB;AAAA,IACpD,QAAQ;AAAA,IACR,MAAM,KAAK,UAAU,EAAE,eAAe,aAAa,CAAC;AAAA,EACtD,CAAC;AACD,SAAQ,MAAM,IAAI,KAAK;AACzB;AAGA,eAAsB,OACpB,SACA,cACe;AACf,MAAI;AACF,UAAM,UAAU,SAAS,gBAAgB;AAAA,MACvC,QAAQ;AAAA,MACR,MAAM,KAAK,UAAU,EAAE,eAAe,aAAa,CAAC;AAAA,IACtD,CAAC;AAAA,EACH,SAAS,GAAG;AACV,QAAI,aAAa,mBAAoB;AACrC,UAAM;AAAA,EACR;AACF;AAGA,eAAsB,MACpB,SACA,aACmB;AACnB,QAAM,MAAM,MAAM,UAAU,SAAS,YAAY,EAAE,QAAQ,MAAM,GAAG,WAAW;AAC/E,SAAQ,MAAM,IAAI,KAAK;AACzB;AAGA,eAAsB,iBACpB,SACA,aACA,SACkC;AAClC,QAAM,MAAM,MAAM;AAAA,IAChB;AAAA,IACA;AAAA,IACA;AAAA,MACE,QAAQ;AAAA,MACR,MAAM,KAAK,UAAU,EAAE,OAAO,OAAO,GAAG,QAAQ,CAAC;AAAA,IACnD;AAAA,IACA;AAAA,EACF;AACA,SAAQ,MAAM,IAAI,KAAK;AACzB;;;AC/FA,SAAS,YAAqB;AAC5B,SAAO,OAAO,WAAW;AAC3B;AAEA,SAAS,KAAK,KAAqB;AACjC,SAAO,IAAI,QAAQ,QAAQ,EAAE;AAC/B;AAKO,IAAM,kBAAN,MAAsB;AAAA,EAC3B,YAA6B,QAAqB;AAArB;AAAA,EAAsB;AAAA,EAEnD,UAAiC;AAC/B,WAAe,QAAQ,KAAK,OAAO,eAAe,CAAC;AAAA,EACrD;AAAA,EAEA,MAAM,SAA+C;AACnD,WAAe,MAAM,KAAK,OAAO,eAAe,GAAG,OAAO;AAAA,EAC5D;AAAA,EAEA,UAAU,SAAuD;AAC/D,WAAe,UAAU,KAAK,OAAO,eAAe,GAAG,OAAO;AAAA,EAChE;AAAA,EAEA,QAAQ,cAAgD;AACtD,WAAe,QAAQ,KAAK,OAAO,eAAe,GAAG,YAAY;AAAA,EACnE;AAAA,EAEA,OAAO,cAAqC;AAC1C,WAAe,OAAO,KAAK,OAAO,eAAe,GAAG,YAAY;AAAA,EAClE;AAAA,EAEA,QAA2B;AACzB,UAAM,QAAQ,KAAK,OAAO,eAAe;AACzC,QAAI,CAAC,MAAO,OAAM,IAAI,eAAe,2BAA2B;AAChE,WAAe,MAAM,KAAK,OAAO,eAAe,GAAG,KAAK;AAAA,EAC1D;AAAA,EAEA,iBAAiB,SAAmE;AAClF,UAAM,QAAQ,KAAK,OAAO,eAAe;AACzC,QAAI,CAAC,MAAO,OAAM,IAAI,eAAe,2BAA2B;AAChE,WAAe,iBAAiB,KAAK,OAAO,eAAe,GAAG,OAAO,OAAO;AAAA,EAC9E;AACF;AAEO,IAAM,cAAN,MAAkB;AAAA,EAMvB,YAAY,UAA8B,CAAC,GAAG;AAF9C,SAAQ,kBAAiD;AAGvD,SAAK,UAAU;AACf,SAAK,OAAO,IAAI,gBAAgB,IAAI;AAAA,EACtC;AAAA;AAAA,EAIA,YAAyB;AACvB,UAAM,SACJ,KAAK,QAAQ,WAAW,UAAU,IAAI,OAAO,mBAAmB;AAClE,QAAI,CAAC,QAAQ;AACX,aAAO;AAAA,QACL,SAAS,KAAK,QAAQ,UAAU,GAAG,KAAK,KAAK,QAAQ,OAAO,CAAC,YAAY;AAAA,QACzE,WAAW,EAAE,WAAW,IAAI,MAAM,IAAI,SAAS,GAAG;AAAA,QAClD,WAAW;AAAA,UACT,eAAe,CAAC;AAAA,UAChB,kBAAkB,CAAC;AAAA,UACnB,gBAAgB,CAAC;AAAA,UACjB,mBAAmB,CAAC;AAAA,UACpB,eAAe,CAAC;AAAA,QAClB;AAAA,QACA,OAAO,CAAC;AAAA,MACV;AAAA,IACF;AACA,WAAO;AAAA,EACT;AAAA,EAEA,WAAoC;AAClC,WAAO,KAAK,UAAU,EAAE,SAAS,CAAC;AAAA,EACpC;AAAA;AAAA,EAGA,iBAAyB;AACvB,UAAM,MAAM,KAAK,WAAW;AAC5B,QAAI,CAAC,KAAK;AACR,YAAM,IAAI;AAAA,QACR;AAAA,QACA;AAAA,MACF;AAAA,IACF;AACA,WAAO;AAAA,EACT;AAAA,EAEA,aAA4B;AAC1B,QAAI,KAAK,QAAQ,QAAS,QAAO,KAAK,KAAK,QAAQ,OAAO;AAE1D,UAAM,UAAU,KAAK,UAAU,EAAE;AACjC,QAAI,CAAC,QAAS,QAAO;AACrB,WAAO,KAAK,OAAO,EAAE,QAAQ,cAAc,EAAE;AAAA,EAC/C;AAAA;AAAA,EAIA,iBAAgC;AAC9B,QAAI,KAAK,QAAQ,eAAgB,QAAO,KAAK,QAAQ,eAAe;AACpE,QAAI,UAAU,EAAG,QAAO,OAAO,wBAAwB;AACvD,WAAO;AAAA,EACT;AAAA,EAEQ,kBAAiC;AACvC,WAAO,KAAK,QAAQ,kBAAkB,KAAK,QAAQ,gBAAgB,IAAI;AAAA,EACzE;AAAA,EAEA,MAAc,aAAqC;AACjD,UAAM,eAAe,KAAK,gBAAgB;AAC1C,QAAI,CAAC,aAAc,QAAO;AAC1B,QAAI,KAAK,gBAAiB,QAAO,KAAK;AACtC,UAAM,UAAU,KAAK,WAAW;AAChC,QAAI,CAAC,QAAS,QAAO;AAErB,SAAK,mBAAmB,YAAY;AAClC,UAAI;AACF,cAAM,OAAO,MAAc,QAAQ,SAAS,YAAY;AACxD,aAAK,QAAQ,iBAAiB,KAAK,YAAY;AAC/C,eAAO,KAAK;AAAA,MACd,QAAQ;AACN,eAAO;AAAA,MACT,UAAE;AACA,aAAK,kBAAkB;AAAA,MACzB;AAAA,IACF,GAAG;AACH,WAAO,KAAK;AAAA,EACd;AAAA;AAAA,EAIA,iBAAyC;AACvC,UAAM,QAAQ,KAAK,eAAe;AAClC,UAAM,UAAkC,EAAE,gBAAgB,mBAAmB;AAC7E,QAAI,MAAO,SAAQ,eAAe,IAAI,UAAU,KAAK;AACrD,WAAO;AAAA,EACT;AAAA,EAEA,eAAuB;AACrB,UAAM,SAAS,KAAK,UAAU;AAC9B,UAAM,OAAO,OAAO;AACpB,WAAO,GAAG,OAAO,OAAO,eAAe,KAAK,SAAS,IAAI,KAAK,IAAI;AAAA,EACpE;AAAA;AAAA,EAIA,MAAM,MAAM,KAAa,UAAuB,CAAC,GAAG,WAAW,OAA0B;AACvF,UAAM,MAAM,MAAM,MAAM,KAAK;AAAA,MAC3B,GAAG;AAAA,MACH,SAAS;AAAA,QACP,GAAG,KAAK,eAAe;AAAA,QACvB,GAAK,QAAQ,WAAsC,CAAC;AAAA,MACtD;AAAA,IACF,CAAC;AAED,QAAI,IAAI,MAAM,IAAI,WAAW,IAAK,QAAO;AAEzC,QAAI,IAAI,WAAW,OAAO,CAAC,UAAU;AACnC,YAAM,WAAW,MAAM,KAAK,WAAW;AACvC,UAAI,SAAU,QAAO,KAAK,MAAM,KAAK,SAAS,IAAI;AAClD,WAAK,QAAQ,oBAAoB;AAAA,IACnC;AAEA,UAAM,OAAO,MAAM,IAAI,KAAK,EAAE,MAAM,OAAO,EAAE,QAAQ,IAAI,WAAW,EAAE;AACtE,UAAM,UAAU,KAAK,UAAU,KAAK,WAAW,IAAI;AAEnD,QAAI,IAAI,WAAW,IAAK,OAAM,IAAI,eAAe,OAAO;AACxD,QAAI,IAAI,WAAW,IAAK,OAAM,IAAI,qBAAqB,OAAO;AAC9D,QAAI,IAAI,WAAW,IAAK,OAAM,IAAI,mBAAmB,OAAO;AAC5D,UAAM,IAAI,WAAW,SAAS,IAAI,MAAM;AAAA,EAC1C;AACF;;;AC1NA,SAAS,SAAS,KAA+B;AAC/C,QAAM,QAAQ,IAAI,MAAM,GAAG;AAC3B,MAAI,MAAM,WAAW,GAAG;AACtB,UAAM,IAAI,MAAM,sBAAsB,GAAG,8BAA8B;AAAA,EACzE;AACA,SAAO,CAAC,MAAM,CAAC,GAAG,MAAM,CAAC,CAAC;AAC5B;AAEA,eAAsB,aACpB,QACA,KACA,QAAiC,CAAC,GACZ;AACtB,QAAM,CAAC,IAAI,IAAI,IAAI,SAAS,GAAG;AAC/B,QAAM,OAAO,OAAO,aAAa;AACjC,QAAM,MAAM,MAAM,OAAO,MAAM,GAAG,IAAI,YAAY,EAAE,IAAI,IAAI,YAAY;AAAA,IACtE,QAAQ;AAAA,IACR,MAAM,KAAK,UAAU,EAAE,MAAM,CAAC;AAAA,EAChC,CAAC;AACD,QAAM,OAAO,MAAM,IAAI,KAAK;AAC5B,SAAO;AAAA,IACL,SAAS,KAAK;AAAA,IACd,WAAW,KAAK;AAAA,IAChB,MAAM,KAAK;AAAA,IACX,UAAU,KAAK;AAAA,IACf,cAAc,KAAK;AAAA,IACnB,YAAY,KAAK;AAAA,EACnB;AACF;;;AC5BA,SAASA,UAAS,KAA+B;AAC/C,QAAM,QAAQ,IAAI,MAAM,GAAG;AAC3B,MAAI,MAAM,WAAW,GAAG;AACtB,UAAM,IAAI,MAAM,yBAAyB,GAAG,8BAA8B;AAAA,EAC5E;AACA,SAAO,CAAC,MAAM,CAAC,GAAG,MAAM,CAAC,CAAC;AAC5B;AAEA,eAAsB,gBACpB,QACA,KACA,QAAiC,CAAC,GAClC,SACyB;AACzB,QAAM,CAAC,IAAI,IAAI,IAAIA,UAAS,GAAG;AAC/B,QAAM,OAAO,OAAO,aAAa;AACjC,QAAM,OAAgC,EAAE,MAAM;AAC9C,MAAI,YAAY,QAAW;AACzB,SAAK,UAAU;AAAA,EACjB;AACA,QAAM,MAAM,MAAM,OAAO,MAAM,GAAG,IAAI,cAAc,EAAE,IAAI,IAAI,YAAY;AAAA,IACxE,QAAQ;AAAA,IACR,MAAM,KAAK,UAAU,IAAI;AAAA,EAC3B,CAAC;AACD,QAAM,OAAO,MAAM,IAAI,KAAK;AAC5B,SAAO;AAAA,IACL,QAAQ,KAAK;AAAA,IACb,aAAa,KAAK;AAAA,IAClB,QAAQ,KAAK;AAAA,IACb,OAAO,KAAK;AAAA,EACd;AACF;AA2BA,eAAsB,gBACpB,QACA,KACA,QAAiC,CAAC,GAClC,UAAkC,CAAC,GACH;AAChC,QAAM,CAAC,IAAI,IAAI,IAAIA,UAAS,GAAG;AAC/B,QAAM,UAAU,OAAO,eAAe;AACtC,QAAM,OAAgC,EAAE,MAAM;AAC9C,MAAI,QAAQ,cAAc,OAAW,MAAK,aAAa,QAAQ;AAC/D,MAAI,QAAQ,iBAAiB,OAAW,MAAK,gBAAgB,QAAQ;AACrE,MAAI,QAAQ,gBAAgB,OAAW,MAAK,eAAe,QAAQ;AAEnE,QAAM,MAAM,MAAM,OAAO,MAAM,GAAG,OAAO,cAAc,EAAE,IAAI,IAAI,kBAAkB;AAAA,IACjF,QAAQ;AAAA,IACR,MAAM,KAAK,UAAU,IAAI;AAAA,EAC3B,CAAC;AACD,QAAM,OAAO,MAAM,IAAI,KAAK;AAC5B,SAAO;AAAA,IACL,aAAa,KAAK;AAAA,IAClB,QAAQ,KAAK;AAAA,EACf;AACF;AAmBA,eAAsB,oBACpB,QACA,KACA,QACA,UAAsC,CAAC,GACH;AACpC,QAAM,CAAC,IAAI,IAAI,IAAIA,UAAS,GAAG;AAC/B,QAAM,UAAU,OAAO,eAAe;AACtC,QAAM,OAAgC,EAAE,OAAO;AAC/C,MAAI,QAAQ,oBAAoB,OAAW,MAAK,oBAAoB,QAAQ;AAC5E,MAAI,QAAQ,iBAAiB,OAAW,MAAK,gBAAgB,QAAQ;AACrE,MAAI,QAAQ,gBAAgB,OAAW,MAAK,eAAe,QAAQ;AACnE,MAAI,QAAQ,qBAAqB,OAAW,MAAK,qBAAqB,QAAQ;AAE9E,QAAM,MAAM,MAAM,OAAO,MAAM,GAAG,OAAO,cAAc,EAAE,IAAI,IAAI,kBAAkB;AAAA,IACjF,QAAQ;AAAA,IACR,MAAM,KAAK,UAAU,IAAI;AAAA,EAC3B,CAAC;AACD,QAAM,OAAO,MAAM,IAAI,KAAK;AAC5B,SAAO;AAAA,IACL,SAAS,KAAK;AAAA,IACd,cAAc,KAAK;AAAA,IACnB,OAAO,KAAK;AAAA,IACZ,QAAQ,KAAK;AAAA,EACf;AACF;AAsBA,eAAsB,iBACpB,QACA,KACA,QACA,UAAmC,CAAC,GACH;AACjC,QAAM,CAAC,IAAI,IAAI,IAAIA,UAAS,GAAG;AAC/B,QAAM,UAAU,OAAO,eAAe;AACtC,QAAM,OAAgC;AAAA,IACpC,QAAQ,OAAO,IAAI,CAAC,UAAU;AAAA,MAC5B,iBAAiB,KAAK,kBAAkB,CAAC;AAAA,MACzC,SAAS,KAAK;AAAA,IAChB,EAAE;AAAA,EACJ;AACA,MAAI,QAAQ,oBAAoB,OAAW,MAAK,oBAAoB,QAAQ;AAC5E,MAAI,QAAQ,gBAAgB,OAAW,MAAK,eAAe,QAAQ;AACnE,MAAI,QAAQ,qBAAqB,OAAW,MAAK,qBAAqB,QAAQ;AAE9E,QAAM,MAAM,MAAM,OAAO,MAAM,GAAG,OAAO,WAAW,EAAE,IAAI,IAAI,gBAAgB;AAAA,IAC5E,QAAQ;AAAA,IACR,MAAM,KAAK,UAAU,IAAI;AAAA,EAC3B,CAAC;AACD,QAAM,OAAO,MAAM,IAAI,KAAK;AAC5B,SAAO;AAAA,IACL,SAAS,KAAK;AAAA,IACd,cAAc,KAAK;AAAA,IACnB,SAAS,KAAK;AAAA,IACd,OAAO,KAAK;AAAA,IACZ,QAAQ,KAAK;AAAA,EACf;AACF;AAoBA,eAAsB,SACpB,QACA,SACsB;AACtB,QAAM,UAAU,OAAO,eAAe;AACtC,QAAM,MAAM,MAAM,OAAO,MAAM,GAAG,OAAO,YAAY,OAAO,EAAE;AAC9D,QAAM,OAAO,MAAM,IAAI,KAAK;AAC5B,SAAO;AAAA,IACL,SAAS,KAAK;AAAA,IACd,MAAM,KAAK;AAAA,IACX,QAAQ,KAAK;AAAA,IACb,QAAQ,KAAK;AAAA,IACb,OAAO,KAAK;AAAA,IACZ,WAAW,KAAK;AAAA,IAChB,QAAQ,KAAK;AAAA,IACb,WAAW,KAAK;AAAA,IAChB,SAAS,KAAK;AAAA,IACd,QAAQ,KAAK;AAAA,IACb,QAAQ,KAAK;AAAA,IACb,WAAW,KAAK;AAAA,IAChB,YAAY,KAAK;AAAA,IACjB,iBAAiB,KAAK;AAAA,EACxB;AACF;AAeA,eAAsB,oBACpB,QACA,SACA,UAAgE,CAAC,GAClC;AAC/B,QAAM,UAAU,OAAO,eAAe;AACtC,QAAM,SAAS,IAAI,gBAAgB;AACnC,MAAI,QAAQ,OAAQ,QAAO,IAAI,UAAU,QAAQ,MAAM;AACvD,MAAI,QAAQ,UAAU,OAAW,QAAO,IAAI,SAAS,OAAO,QAAQ,KAAK,CAAC;AAC1E,MAAI,QAAQ,WAAW,OAAW,QAAO,IAAI,UAAU,OAAO,QAAQ,MAAM,CAAC;AAC7E,QAAM,IAAI,OAAO,SAAS;AAC1B,QAAM,MAAM,MAAM,OAAO;AAAA,IACvB,GAAG,OAAO,YAAY,OAAO,cAAc,IAAI,MAAM,IAAI,EAAE;AAAA,EAC7D;AACA,QAAM,OAAO,MAAM,IAAI,KAAK;AAC5B,UAAQ,KAAK,cAAc,CAAC,GAAG,IAAI,CAAC,SAAkC;AAAA,IACpE,aAAa,IAAI;AAAA,IACjB,QAAQ,IAAI;AAAA,IACZ,cAAc,IAAI;AAAA,IAClB,QAAS,IAAI,WAA6B;AAAA,IAC1C,WAAW,IAAI;AAAA,IACf,WAAY,IAAI,cAAgC;AAAA,IAChD,aAAc,IAAI,gBAAkC;AAAA,IACpD,YAAa,IAAI,eAAiC;AAAA,IAClD,OAAQ,IAAI,SAA2B;AAAA,EACzC,EAAE;AACJ;AAGA,eAAsB,YACpB,QACA,SACyE;AACzE,QAAM,UAAU,OAAO,eAAe;AACtC,QAAM,MAAM,MAAM,OAAO,MAAM,GAAG,OAAO,YAAY,OAAO,WAAW;AAAA,IACrE,QAAQ;AAAA,EACV,CAAC;AACD,QAAM,OAAO,MAAM,IAAI,KAAK;AAC5B,SAAO;AAAA,IACL,SAAS,KAAK;AAAA,IACd,QAAQ,KAAK;AAAA,IACb,mBAAmB,KAAK;AAAA,EAC1B;AACF;;;ACrRA,eAAsB,SACpB,QACA,IACA,KACyB;AACzB,QAAM,OAAO,OAAO,aAAa;AACjC,QAAM,MAAM,MAAM,OAAO,MAAM,GAAG,IAAI,WAAW,EAAE,IAAI;AAAA,IACrD,QAAQ;AAAA,IACR,MAAM,KAAK,UAAU,EAAE,QAAQ,OAAO,IAAI,CAAC;AAAA,EAC7C,CAAC;AACD,SAAO,IAAI,KAAK;AAClB;AAEA,eAAsB,SACpB,QACA,IACA,KACA,OACA,aAAmC,WACpB;AACf,QAAM,OAAO,OAAO,aAAa;AACjC,QAAM,OAAO,MAAM,GAAG,IAAI,WAAW,EAAE,IAAI;AAAA,IACzC,QAAQ;AAAA,IACR,MAAM,KAAK,UAAU,EAAE,QAAQ,OAAO,KAAK,OAAO,WAAW,CAAC;AAAA,EAChE,CAAC;AACH;AAEA,eAAsB,YACpB,QACA,IACA,KACe;AACf,QAAM,OAAO,OAAO,aAAa;AACjC,QAAM,OAAO,MAAM,GAAG,IAAI,WAAW,EAAE,IAAI;AAAA,IACzC,QAAQ;AAAA,IACR,MAAM,KAAK,UAAU,EAAE,QAAQ,UAAU,IAAI,CAAC;AAAA,EAChD,CAAC;AACH;AAEA,eAAsB,UACpB,QACA,IAC0B;AAC1B,QAAM,OAAO,OAAO,aAAa;AACjC,QAAM,MAAM,MAAM,OAAO,MAAM,GAAG,IAAI,WAAW,EAAE,IAAI;AAAA,IACrD,QAAQ;AAAA,IACR,MAAM,KAAK,UAAU,EAAE,QAAQ,OAAO,CAAC;AAAA,EACzC,CAAC;AACD,SAAO,IAAI,KAAK;AAClB;;;ACrCA,IAAM,WAAW,CAAC,MAAyB,CAAC,CAAC,KAAK,OAAO,MAAM,YAAY,CAAC,MAAM,QAAQ,CAAC;AAC3F,IAAM,MAAM,CAAC,MAA+B,OAAO,MAAM,WAAW,IAAI;AACxE,IAAM,MAAM,CAAC,MAAwB,OAAO,MAAM,YAAY,OAAO,SAAS,CAAC,IAAI,IAAI;AAEvF,IAAM,YAAY,CAAC,MACjB,MAAM,QAAQ,CAAC,KAAK,EAAE,SAAS,KAAK,EAAE,MAAM,CAAC,MAAM,OAAO,MAAM,QAAQ,IAAK,IAAiB;AAOzF,SAAS,kBAAkB,KAAmC;AACnE,MAAI,CAAC,SAAS,GAAG,EAAG,QAAO;AAC3B,MAAI,OAAO,IAAI,iBAAiB,YAAY,CAAC,IAAI,aAAc,QAAO;AACtE,SAAO;AAAA,IACL,YAAY,IAAI;AAAA,IAChB,UAAU,IAAI,IAAI,QAAQ,KAAK;AAAA,IAC/B,SAAS,UAAU,IAAI,OAAO;AAAA,IAC9B,WAAW,IAAI,IAAI,UAAU;AAAA,IAC7B,WAAW,IAAI,IAAI,UAAU;AAAA,EAC/B;AACF;AAEO,SAAS,mBAAmB,KAA8B;AAC/D,SAAO,MAAM,QAAQ,GAAG,IAAI,IAAI,IAAI,iBAAiB,EAAE,OAAO,CAAC,MAAyB,MAAM,IAAI,IAAI,CAAC;AACzG;AAOO,SAAS,sBAAsB,OAAsC;AAC1E,MAAI,MAAM,UAAU,oBAAoB,MAAM,UAAU,UAAW,QAAO;AAC1E,MAAI;AACJ,MAAI;AACF,aAAS,KAAK,MAAM,MAAM,IAAI;AAAA,EAChC,QAAQ;AACN,WAAO;AAAA,EACT;AACA,MAAI,MAAM,UAAU,cAAc,CAAC,SAAS,MAAM,KAAK,OAAO,SAAS,kBAAmB,QAAO;AACjG,SAAO,kBAAkB,MAAM;AACjC;AAGO,SAAS,cAAc,KAAsC;AAClE,MAAI,CAAC,SAAS,GAAG,KAAK,OAAO,IAAI,iBAAiB,SAAU,QAAO;AACnE,SAAO;AAAA,IACL,MAAM,IAAI,IAAI,IAAI,KAAK;AAAA,IACvB,YAAY,IAAI;AAAA,IAChB,mBAAmB,IAAI,IAAI,kBAAkB,KAAK;AAAA,IAClD,cAAc,IAAI,IAAI,aAAa,KAAK;AAAA,IACxC,WAAW,SAAS,IAAI,SAAS,IAAI,IAAI,YAAY,CAAC;AAAA,EACxD;AACF;AAEO,SAAS,WAAW,KAAgC;AACzD,MAAI,CAAC,SAAS,GAAG,EAAG,QAAO;AAC3B,SAAO;AAAA,IACL,OAAO,IAAI,IAAI,KAAK;AAAA,IACpB,cAAc,IAAI,IAAI,aAAa;AAAA,IACnC,kBAAkB,IAAI,IAAI,iBAAiB;AAAA,IAC3C,aAAa,IAAI,IAAI,YAAY;AAAA,IACjC,iBAAiB,IAAI,IAAI,iBAAiB;AAAA,IAC1C,kBAAkB,IAAI,IAAI,kBAAkB;AAAA,IAC5C,SAAS,OAAO,IAAI,aAAa,WAAW,IAAI,WAAW;AAAA,IAC3D,eAAe,IAAI,IAAI,cAAc;AAAA,IACrC,QAAQ,IAAI,IAAI,MAAM;AAAA,EACxB;AACF;AAEA,IAAM,gBAAuC,CAAC,aAAa,kBAAkB,eAAe,UAAU;AAG/F,SAAS,eAAe,KAAqB;AAClD,QAAM,SAAS,cAAc,SAAS,IAAI,MAAoB,IAAK,IAAI,SAAwB;AAC/F,SAAO;AAAA,IACL;AAAA,IACA,eAAe,mBAAmB,IAAI,cAAc;AAAA,IACpD,WAAW,IAAI,IAAI,UAAU;AAAA,IAC7B,OAAO,WAAW,IAAI,KAAK;AAAA,EAC7B;AACF;AAEO,SAAS,aAAa,MAA4B;AACvD,QAAM,YAAY,KAAK;AACvB,SAAO;AAAA,IACL,IAAI,KAAK;AAAA,IACT,QAAQ,KAAK;AAAA,IACb,MAAM,KAAK;AAAA,IACX,SAAU,KAAK,WAAsB;AAAA,IACrC,WAAW,aAAa;AAAA,IACxB,YAAa,KAAK,gBAA2B;AAAA,IAC7C,MAAO,KAAK,QAAmB;AAAA,IAC/B,WAAW,KAAK;AAAA,EAClB;AACF;AAGO,SAAS,UAAU,MAA0B;AAClD,MAAI;AACF,UAAM,SAAS,KAAK,MAAM,IAAI;AAC9B,QAAI,SAAS,MAAM,KAAK,OAAO,OAAO,WAAW,SAAU,QAAO,EAAE,QAAQ,OAAO,OAAO;AAAA,EAC5F,QAAQ;AAAA,EAER;AACA,SAAO,EAAE,QAAQ,YAAY;AAC/B;AAQO,SAAS,sBACd,QACA,WAAW,MACI;AACf,MAAI,OAAO,WAAW,UAAW,QAAO;AACxC,MAAI,OAAO,WAAW,UAAa,CAAC,SAAU,QAAO;AACrD,SAAO,OAAO,aAAa;AAC7B;AAQO,SAAS,oBAAoB,QAIlB;AAChB,MAAI,CAAC,OAAO,WAAW,CAAC,OAAO,cAAe,QAAO;AACrD,SAAO,OAAO,aAAa;AAC7B;;;AC5HA,SAAS,cAAc,UAAoC;AACzD,QAAM,CAAC,IAAI,IAAI,IAAI,SAAS,MAAM,GAAG;AACrC,MAAI,CAAC,MAAM,CAAC,MAAM;AAChB,UAAM,IAAI,MAAM,sBAAsB,QAAQ,8BAA8B;AAAA,EAC9E;AACA,SAAO,CAAC,IAAI,IAAI;AAClB;AAEA,eAAsB,WACpB,QACA,UACA,OAC2B;AAC3B,QAAM,CAAC,IAAI,IAAI,IAAI,cAAc,QAAQ;AACzC,QAAM,SAAS,OAAO,UAAU;AAChC,QAAM,MAAM,MAAM,OAAO,MAAM,GAAG,OAAO,OAAO,WAAW,EAAE,IAAI,IAAI,UAAU;AAAA,IAC7E,QAAQ;AAAA,IACR,MAAM,KAAK,UAAU,EAAE,OAAO,SAAS,CAAC,EAAE,CAAC;AAAA,EAC7C,CAAC;AACD,QAAM,OAAO,MAAM,IAAI,KAAK;AAC5B,SAAO;AAAA,IACL,IAAI,KAAK;AAAA,IACT,gBAAgB,KAAK;AAAA,IACrB,WAAW,KAAK;AAAA,IAChB,OAAO,KAAK;AAAA,EACd;AACF;AAOA,eAAsB,YACpB,QACA,QACA,SAC4B;AAC5B,QAAM,SAAS,OAAO,UAAU;AAChC,QAAM,MAAM,MAAM,OAAO,MAAM,GAAG,OAAO,OAAO,UAAU,MAAM,aAAa;AAAA,IAC3E,QAAQ;AAAA,IACR,MAAM,KAAK,UAAU,EAAE,QAAQ,CAAC;AAAA,EAClC,CAAC;AACD,QAAM,OAAO,MAAM,IAAI,KAAK;AAC5B,SAAO;AAAA,IACL,IAAI,KAAK;AAAA,IACT,QAAQ,KAAK;AAAA,IACb,MAAM,KAAK;AAAA,IACX,SAAS,KAAK;AAAA,IACd,WAAW,KAAK;AAAA,IAChB,GAAG,eAAe,IAAI;AAAA,EACxB;AACF;AAQA,eAAsB,YACpB,QACA,UACA,SACA,UAAyB,CAAC,GACH;AACvB,QAAM,CAAC,IAAI,IAAI,IAAI,cAAc,QAAQ;AACzC,QAAM,SAAS,OAAO,UAAU;AAChC,QAAM,OAAgC,EAAE,QAAQ;AAChD,MAAI,QAAQ,eAAe,OAAW,MAAK,cAAc,QAAQ;AACjE,MAAI,QAAQ,UAAU,OAAW,MAAK,QAAQ,QAAQ;AACtD,MAAI,QAAQ,UAAU,OAAW,MAAK,QAAQ,QAAQ;AACtD,QAAM,MAAM,MAAM,OAAO,MAAM,GAAG,OAAO,OAAO,WAAW,EAAE,IAAI,IAAI,WAAW;AAAA,IAC9E,QAAQ;AAAA,IACR,MAAM,KAAK,UAAU,IAAI;AAAA,EAC3B,CAAC;AACD,QAAM,OAAO,MAAM,IAAI,KAAK;AAC5B,SAAO;AAAA,IACL,OAAO,OAAO,KAAK,UAAU,WAAW,KAAK,QAAQ;AAAA,IACrD,QAAQ,KAAK;AAAA,IACb,YAAY,KAAK,eAAe;AAAA,IAChC,GAAG,eAAe,IAAI;AAAA,EACxB;AACF;AAEA,eAAsB,QACpB,QACA,QACqB;AACrB,QAAM,SAAS,OAAO,UAAU;AAChC,QAAM,MAAM,MAAM,OAAO,MAAM,GAAG,OAAO,OAAO,UAAU,MAAM,EAAE;AAClE,QAAM,OAAO,MAAM,IAAI,KAAK;AAC5B,QAAM,SAAqB;AAAA,IACzB,IAAI,KAAK;AAAA,IACT,gBAAgB,KAAK;AAAA,IACrB,WAAW,KAAK;AAAA,IAChB,OAAO,KAAK;AAAA,IACZ,WAAW,KAAK,YAAY,CAAC,GAAG,IAAI,YAAY;AAAA,IAChD,mBAAmB,KAAK,qBAAqB,CAAC,GAC3C,IAAI,aAAa,EACjB,OAAO,CAAC,MAAoD,MAAM,IAAI;AAAA,EAC3E;AACA,MAAI,MAAM,QAAQ,KAAK,cAAc,GAAG;AACtC,WAAO,gBAAgB,mBAAmB,KAAK,cAAc;AAAA,EAC/D;AACA,SAAO;AACT;AAQA,eAAsB,gBACpB,QACA,QACA,YACA,UACA,UAAkC,CAAC,GACV;AACzB,QAAM,SAAS,OAAO,UAAU;AAChC,QAAM,OAAgC,EAAE,SAAS;AACjD,MAAI,YAAY,QAAQ,YAAa,MAAK,eAAe;AACzD,QAAM,MAAM,MAAM,OAAO;AAAA,IACvB,GAAG,OAAO,OAAO,UAAU,MAAM,iBAAiB,mBAAmB,UAAU,CAAC;AAAA,IAChF,EAAE,QAAQ,QAAQ,MAAM,KAAK,UAAU,IAAI,EAAE;AAAA,EAC/C;AACA,QAAM,OAAO,MAAM,IAAI,KAAK;AAC5B,QAAM,SAAyB;AAAA,IAC7B,QAAQ,KAAK;AAAA,IACb,YAAY,KAAK;AAAA,IACjB,WAAW,KAAK;AAAA,EAClB;AACA,MAAI,KAAK,WAAW,aAAa,KAAK,WAAW,SAAU,QAAO,SAAS,KAAK;AAChF,MAAI,OAAO,KAAK,YAAY,SAAU,QAAO,UAAU,KAAK;AAC5D,SAAO;AACT;AAGA,eAAsB,kBACpB,QACA,QACyB;AACzB,QAAM,SAAS,OAAO,UAAU;AAChC,QAAM,MAAM,MAAM,OAAO,MAAM,GAAG,OAAO,OAAO,UAAU,MAAM,gBAAgB;AAChF,SAAO,mBAAmB,MAAM,IAAI,KAAK,CAAC;AAC5C;AA8BA,eAAsB,mBACpB,QACA,QACA,YACA,QACA,UAAqC,CAAC,GAC0B;AAChE,QAAM,SAAS,OAAO,UAAU;AAChC,QAAM,OAAgC,EAAE,OAAO;AAC/C,MAAI,QAAQ,KAAM,MAAK,OAAO;AAC9B,QAAM,MAAM,MAAM,OAAO;AAAA,IACvB,GAAG,OAAO,OAAO,UAAU,MAAM,kBAAkB,mBAAmB,UAAU,CAAC;AAAA,IACjF,EAAE,QAAQ,QAAQ,MAAM,KAAK,UAAU,IAAI,EAAE;AAAA,EAC/C;AACA,QAAM,OAAO,MAAM,IAAI,KAAK;AAC5B,MAAI,QAAQ,MAAM;AAChB,WAAO;AAAA,MACL,YAAY,KAAK;AAAA,MACjB,QAAQ,KAAK;AAAA,MACb,OAAO,OAAO,KAAK,UAAU,WAAW,KAAK,QAAQ;AAAA,MACrD,SAAS,KAAK,WAAW,OAAO,KAAK,YAAY,WAAW,aAAa,KAAK,OAAO,IAAI;AAAA,MACzF,GAAG,eAAe,IAAI;AAAA,IACxB;AAAA,EACF;AACA,SAAO;AAAA,IACL,QAAQ;AAAA,IACR,YAAY,KAAK;AAAA,IACjB,SAAS,CAAC,CAAC,KAAK;AAAA,IAChB,eAAe,CAAC,CAAC,KAAK;AAAA,IACtB,WAAW,KAAK,cAAc;AAAA,IAC9B,SAAS,OAAO,KAAK,YAAY,WAAW,KAAK,UAAU;AAAA,EAC7D;AACF;AAMO,SAAS,kBACd,QACA,QACA,WACA,SACA,QACA,SACA,UAAoC,CAAC,GACpB;AACjB,QAAM,SAAS,OAAO,UAAU;AAChC,QAAM,SAAS,IAAI,gBAAgB,EAAE,SAAS,QAAQ,UAAU,IAAI,CAAC;AACrE,MAAI,QAAQ,gBAAiB,QAAO,IAAI,oBAAoB,MAAM;AAClE,SAAO;AAAA,IACL,GAAG,OAAO,OAAO,UAAU,MAAM,WAAW,mBAAmB,SAAS,CAAC,IAAI,MAAM;AAAA,IACnF,CAAC,YAAY,EAAE,SAAS,OAAO,eAAe,GAAG,OAAO;AAAA,IACxD;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,EACF;AACF;AAOA,SAAS,OACP,KACA,MACA,SACA,SACA,QACA,SACiB;AACjB,QAAM,aAAa,IAAI,gBAAgB;AAEvC,GAAC,YAAY;AACX,QAAI;AACF,YAAM,MAAM,MAAM,MAAM,KAAK,KAAK,WAAW,MAAM,CAAC;AAEpD,UAAI,CAAC,IAAI,IAAI;AACX,cAAM,OAAO,MAAM,IAAI,KAAK,EAAE,MAAM,OAAO,EAAE,QAAQ,IAAI,WAAW,EAAE;AACtE,cAAM,IAAI,MAAM,KAAK,UAAU,OAAO;AAAA,MACxC;AAEA,YAAM,SAAS,IAAI,KAAM,UAAU;AACnC,YAAM,UAAU,IAAI,YAAY;AAChC,UAAI,SAAS;AAEb,aAAO,MAAM;AACX,cAAM,EAAE,MAAM,MAAM,IAAI,MAAM,OAAO,KAAK;AAC1C,YAAI,KAAM;AAEV,kBAAU,QAAQ,OAAO,OAAO,EAAE,QAAQ,KAAK,CAAC;AAChD,cAAM,EAAE,QAAQ,UAAU,IAAI,SAAS,MAAM;AAC7C,iBAAS;AAET,mBAAW,SAAS,QAAQ;AAC1B,kBAAQ,KAAK;AACb,cAAI,MAAM,UAAU,QAAQ;AAC1B,qBAAS,UAAU,MAAM,IAAI,CAAC;AAC9B;AAAA,UACF;AAAA,QACF;AAAA,MACF;AAGA,UAAI,OAAO,KAAK,GAAG;AACjB,cAAM,EAAE,OAAO,IAAI,SAAS,SAAS,MAAM;AAC3C,mBAAW,SAAS,QAAQ;AAC1B,kBAAQ,KAAK;AACb,cAAI,MAAM,UAAU,QAAQ;AAC1B,qBAAS,UAAU,MAAM,IAAI,CAAC;AAC9B;AAAA,UACF;AAAA,QACF;AAAA,MACF;AAEA,eAAS,EAAE,QAAQ,SAAS,CAAC;AAAA,IAC/B,SAAS,KAAK;AACZ,UAAK,IAAc,SAAS,aAAc;AAC1C,gBAAU,GAAY;AAAA,IACxB;AAAA,EACF,GAAG;AAEH,SAAO;AACT;AAMO,SAAS,SAAS,QAA2D;AAClF,QAAM,SAAqB,CAAC;AAG5B,QAAM,aAAa,OAAO,QAAQ,SAAS,IAAI;AAC/C,MAAI,QAAQ;AACZ,MAAI;AAEJ,UAAQ,MAAM,WAAW,QAAQ,QAAQ,KAAK,OAAO,IAAI;AACvD,UAAM,QAAQ,WAAW,MAAM,OAAO,GAAG;AACzC,YAAQ,MAAM;AACd,QAAI,QAAQ;AACZ,UAAM,OAAiB,CAAC;AACxB,eAAW,QAAQ,MAAM,MAAM,IAAI,GAAG;AACpC,UAAI,KAAK,WAAW,QAAQ,EAAG,SAAQ,KAAK,MAAM,CAAC,EAAE,KAAK;AAAA,eACjD,KAAK,WAAW,OAAO,EAAG,MAAK,KAAK,KAAK,MAAM,CAAC,EAAE,KAAK,CAAC;AAAA,IACnE;AACA,QAAI,SAAS,KAAK,OAAQ,QAAO,KAAK,EAAE,OAAO,SAAS,WAAW,MAAM,KAAK,KAAK,IAAI,EAAE,CAAC;AAAA,EAC5F;AAEA,SAAO,EAAE,QAAQ,WAAW,WAAW,MAAM,KAAK,EAAE;AACtD;AAGO,SAAS,cACd,QACA,QACA,SACA,SACA,QACA,SACA,UAAyB,CAAC,GACT;AACjB,QAAM,SAAS,OAAO,UAAU;AAChC,QAAM,OAAgC,EAAE,QAAQ;AAChD,MAAI,QAAQ,gBAAiB,MAAK,mBAAmB;AACrD,SAAO;AAAA,IACL,GAAG,OAAO,OAAO,UAAU,MAAM;AAAA,IACjC,CAAC,YAAY,EAAE,QAAQ,QAAQ,SAAS,OAAO,eAAe,GAAG,MAAM,KAAK,UAAU,IAAI,GAAG,OAAO;AAAA,IACpG;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,EACF;AACF;;;AC1XA,eAAsB,gBAAgB,QAA4C;AAChF,QAAM,OAAO,OAAO,aAAa;AACjC,QAAM,MAAM,MAAM,OAAO,MAAM,GAAG,IAAI,cAAc;AACpD,SAAO,IAAI,KAAK;AAClB;AAEA,eAAsB,UACpB,QACA,WACA,YACqB;AACrB,QAAM,OAAO,OAAO,aAAa;AACjC,QAAM,MAAM,MAAM,OAAO,MAAM,GAAG,IAAI,UAAU,SAAS,IAAI,UAAU,EAAE;AACzE,SAAO,IAAI,KAAK;AAClB;AAEA,eAAsB,WACpB,QACA,WACA,YACA,MACmB;AACnB,QAAM,UAAU,OAAO,UAAU,EAAE;AACnC,QAAM,MAAM,MAAM,OAAO,MAAM,GAAG,OAAO,UAAU,SAAS,IAAI,UAAU,IAAI;AAAA,IAC5E,QAAQ;AAAA,IACR,MAAM,KAAK,UAAU,IAAI;AAAA,EAC3B,CAAC;AACD,SAAO,IAAI,KAAK;AAClB;AAEA,eAAsB,gBACpB,QACA,WACA,YACA,UACA,WACwB;AACxB,QAAM,UAAU,OAAO,UAAU,EAAE;AACnC,QAAM,SAAS,IAAI,gBAAgB;AACnC,MAAI,UAAW,QAAO,IAAI,cAAc,OAAO,SAAS,CAAC;AACzD,QAAM,KAAK,OAAO,SAAS,IAAI,IAAI,OAAO,SAAS,CAAC,KAAK;AACzD,QAAM,MAAM,MAAM,OAAO;AAAA,IACvB,GAAG,OAAO,UAAU,SAAS,IAAI,UAAU,IAAI,mBAAmB,QAAQ,CAAC,OAAO,EAAE;AAAA,IACpF,EAAE,QAAQ,OAAO;AAAA,EACnB;AACA,SAAO,IAAI,KAAK;AAClB;;;ACjDA,IAAAC,gBAAkB;;;ACAlB,mBAAkB;AAGlB,IAAM,eAAe,aAAAC,QAAM,cAAkC,IAAI;AAU1D,SAAS,cAAc,EAAE,QAAQ,SAAS,SAAS,GAAuB;AAC/E,QAAM,QAAQ,aAAAA,QAAM;AAAA,IAClB,MAAM,UAAU,IAAI,YAAY,OAAO;AAAA;AAAA;AAAA;AAAA,IAIvC,CAAC,MAAM;AAAA,EACT;AACA,SAAO,aAAAA,QAAM,cAAc,aAAa,UAAU,EAAE,MAAM,GAAG,QAAQ;AACvE;AAEO,SAAS,YAAyB;AACvC,QAAM,SAAS,aAAAA,QAAM,WAAW,YAAY;AAC5C,MAAI,OAAQ,QAAO;AACnB,SAAO;AACT;AAEA,IAAM,gBAAgB,IAAI,YAAY;;;ADZ/B,SAAS,SACd,KACA,QAAiC,CAAC,GAClC,UAA2B,CAAC,GACZ;AAChB,QAAM,SAAS,UAAU;AACzB,QAAM,EAAE,UAAU,MAAM,kBAAkB,KAAK,IAAI;AAEnD,QAAM,CAAC,MAAM,OAAO,IAAI,cAAAC,QAAM,SAA2C,IAAI;AAC7E,QAAM,CAAC,SAAS,UAAU,IAAI,cAAAA,QAAM,SAAS,KAAK;AAClD,QAAM,CAAC,OAAO,QAAQ,IAAI,cAAAA,QAAM,SAAwB,IAAI;AAC5D,QAAM,CAAC,UAAU,WAAW,IAAI,cAAAA,QAAM,SAAwB,IAAI;AAElE,QAAM,WAAW,cAAAA,QAAM,OAA+B,IAAI;AAC1D,QAAM,YAAY,KAAK,UAAU,KAAK;AAEtC,QAAM,UAAU,cAAAA,QAAM;AAAA,IACpB,OAAO,kBAA4C;AACjD,eAAS,SAAS,MAAM;AACxB,YAAM,aAAa,IAAI,gBAAgB;AACvC,eAAS,UAAU;AAEnB,iBAAW,IAAI;AACf,eAAS,IAAI;AACb,UAAI;AACF,cAAM,SAAS,MAAM;AAAA,UACnB;AAAA,UACA;AAAA,UACA,iBAAiB,KAAK,MAAM,SAAS;AAAA,QACvC;AACA,YAAI,CAAC,WAAW,OAAO,SAAS;AAC9B,kBAAQ,OAAO,QAAQ,IAAI;AAC3B,sBAAY,OAAO,YAAY,OAAO,gBAAgB,IAAI;AAAA,QAC5D;AACA,eAAO;AAAA,MACT,SAAS,GAAG;AACV,YAAI,CAAC,WAAW,OAAO,SAAS;AAC9B,mBAAU,EAAY,OAAO;AAAA,QAC/B;AAAA,MACF,UAAE;AACA,YAAI,CAAC,WAAW,OAAO,SAAS;AAC9B,qBAAW,KAAK;AAAA,QAClB;AAAA,MACF;AAAA,IACF;AAAA,IACA,CAAC,QAAQ,KAAK,SAAS;AAAA,EACzB;AAEA,gBAAAA,QAAM,UAAU,MAAM;AACpB,QAAI,SAAS;AACX,cAAQ;AAAA,IACV;AACA,WAAO,MAAM;AACX,eAAS,SAAS,MAAM;AAAA,IAC1B;AAAA,EACF,GAAG,CAAC,SAAS,OAAO,CAAC;AAErB,gBAAAA,QAAM,UAAU,MAAM;AACpB,QAAI,mBAAmB,SAAS;AAC9B,YAAM,KAAK,YAAY,SAAS,eAAe;AAC/C,aAAO,MAAM,cAAc,EAAE;AAAA,IAC/B;AAAA,EACF,GAAG,CAAC,iBAAiB,SAAS,OAAO,CAAC;AAEtC,SAAO,EAAE,MAAM,SAAS,OAAO,UAAU,SAAS,QAAQ;AAC5D;;;AEnFA,IAAAC,gBAAkB;AAaX,SAAS,WAAW,KAA+B;AACxD,QAAM,SAAS,UAAU;AAEzB,QAAM,CAAC,QAAQ,SAAS,IAAI,cAAAC,QAAM,SAAkB,IAAI;AACxD,QAAM,CAAC,SAAS,UAAU,IAAI,cAAAA,QAAM,SAAS,KAAK;AAClD,QAAM,CAAC,OAAO,QAAQ,IAAI,cAAAA,QAAM,SAAwB,IAAI;AAC5D,QAAM,CAAC,aAAa,cAAc,IAAI,cAAAA,QAAM,SAAwB,IAAI;AAExE,QAAM,UAAU,cAAAA,QAAM;AAAA,IACpB,OAAO,QAAiC,CAAC,GAAG,YAAqB;AAC/D,iBAAW,IAAI;AACf,eAAS,IAAI;AACb,UAAI;AACF,cAAM,OAAO,MAAM,gBAAgB,QAAQ,KAAK,OAAO,OAAO;AAC9D,kBAAU,KAAK,MAAM;AACrB,uBAAe,KAAK,WAAW;AAC/B,YAAI,KAAK,WAAW,SAAS;AAC3B,mBAAS,KAAK,SAAS,2BAA2B;AAAA,QACpD,WAAW,KAAK,WAAW,WAAW;AACpC,mBAAS,8BAA8B;AAAA,QACzC;AACA,eAAO;AAAA,MACT,SAAS,GAAG;AACV,iBAAU,EAAY,OAAO;AAAA,MAC/B,UAAE;AACA,mBAAW,KAAK;AAAA,MAClB;AAAA,IACF;AAAA,IACA,CAAC,QAAQ,GAAG;AAAA,EACd;AAEA,SAAO,EAAE,SAAS,QAAQ,SAAS,OAAO,YAAY;AACxD;;;AC7CA,IAAAC,gBAAkB;AAmBX,SAAS,cAAc,IAAY,KAAmC;AAC3E,QAAM,SAAS,UAAU;AAEzB,QAAM,CAAC,OAAO,QAAQ,IAAI,cAAAC,QAAM,SAAkB,IAAI;AACtD,QAAM,CAAC,SAAS,UAAU,IAAI,cAAAA,QAAM,SAAS,IAAI;AACjD,QAAM,CAAC,OAAO,QAAQ,IAAI,cAAAA,QAAM,SAAwB,IAAI;AAE5D,QAAM,OAAO,cAAAA,QAAM,YAAY,YAAY;AACzC,QAAI,CAAC,KAAK;AACR,iBAAW,KAAK;AAChB;AAAA,IACF;AACA,eAAW,IAAI;AACf,aAAS,IAAI;AACb,QAAI;AACF,YAAM,SAAS,MAAM,SAAS,QAAQ,IAAI,GAAG;AAC7C,UAAI,OAAO,OAAO;AAChB,iBAAS,OAAO,KAAK;AAAA,MACvB,OAAO;AACL,iBAAS,IAAI;AAAA,MACf;AAAA,IACF,SAAS,GAAG;AACV,eAAU,EAAY,OAAO;AAAA,IAC/B,UAAE;AACA,iBAAW,KAAK;AAAA,IAClB;AAAA,EACF,GAAG,CAAC,QAAQ,IAAI,GAAG,CAAC;AAEpB,QAAM,OAAO,cAAAA,QAAM;AAAA,IACjB,OAAO,UAAmB,SAAgC;AACxD,UAAI,CAAC,IAAK,OAAM,IAAI,MAAM,2BAA2B;AACrD,eAAS,QAAQ;AACjB,eAAS,IAAI;AACb,UAAI;AACF,cAAM,SAAS,QAAQ,IAAI,KAAK,UAAU,MAAM,UAAU;AAAA,MAC5D,SAAS,GAAG;AACV,iBAAU,EAAY,OAAO;AAC7B,cAAM;AAAA,MACR;AAAA,IACF;AAAA,IACA,CAAC,QAAQ,IAAI,GAAG;AAAA,EAClB;AAEA,QAAM,SAAS,cAAAA,QAAM,YAAY,YAAY;AAC3C,QAAI,CAAC,IAAK,OAAM,IAAI,MAAM,6BAA6B;AACvD,aAAS,IAAI;AACb,aAAS,IAAI;AACb,QAAI;AACF,YAAM,YAAY,QAAQ,IAAI,GAAG;AAAA,IACnC,SAAS,GAAG;AACV,eAAU,EAAY,OAAO;AAC7B,YAAM;AAAA,IACR;AAAA,EACF,GAAG,CAAC,QAAQ,IAAI,GAAG,CAAC;AAEpB,QAAM,OAAO,cAAAA,QAAM,YAAY,YAAY;AACzC,aAAS,IAAI;AACb,QAAI;AACF,aAAO,MAAM,UAAU,QAAQ,EAAE;AAAA,IACnC,SAAS,GAAG;AACV,eAAU,EAAY,OAAO;AAAA,IAC/B;AAAA,EACF,GAAG,CAAC,QAAQ,EAAE,CAAC;AAEf,gBAAAA,QAAM,UAAU,MAAM;AACpB,SAAK;AAAA,EACP,GAAG,CAAC,IAAI,CAAC;AAET,SAAO,EAAE,OAAO,SAAS,OAAO,MAAM,QAAQ,SAAS,MAAM,KAAK;AACpE;;;ACxFA,IAAAC,gBAAkB;;;ACcX,SAAS,kBAAkB,MAA4B;AAC5D,MAAI;AACJ,MAAI;AACF,aAAS,KAAK,MAAM,IAAI;AAAA,EAC1B,QAAQ;AACN,WAAO,EAAE,MAAM,KAAK;AAAA,EACtB;AACA,MAAI,CAAC,UAAU,OAAO,WAAW,SAAU,QAAO,EAAE,MAAM,GAAG;AAC7D,QAAM,IAAI;AACV,QAAM,MAAoB,EAAE,MAAM,OAAO,EAAE,YAAY,WAAW,EAAE,UAAU,GAAG;AACjF,MAAI,OAAO,EAAE,aAAa,SAAU,KAAI,WAAW,EAAE;AACrD,SAAO;AACT;AAGO,SAAS,eACd,UACA,MACA,QACA,MAAY,oBAAI,KAAK,GACC;AACtB,MAAI,CAAC,KAAM,QAAO;AAClB,QAAM,OAAO,SAAS,SAAS,SAAS,CAAC;AACzC,MAAI,QAAQ,KAAK,SAAS,eAAe,CAAC,KAAK,aAAa,KAAK,WAAW;AAC1E,UAAM,OAAO,CAAC,GAAG,QAAQ;AACzB,SAAK,KAAK,SAAS,CAAC,IAAI,EAAE,GAAG,MAAM,UAAU,KAAK,WAAW,MAAM,KAAK;AACxE,WAAO;AAAA,EACT;AACA,SAAO;AAAA,IACL,GAAG;AAAA,IACH;AAAA,MACE,IAAI,YAAY,IAAI,QAAQ,CAAC;AAAA,MAC7B;AAAA,MACA,MAAM;AAAA,MACN,SAAS;AAAA,MACT,WAAW;AAAA,MACX,YAAY;AAAA,MACZ,MAAM;AAAA,MACN,WAAW,IAAI,YAAY;AAAA,MAC3B,WAAW;AAAA,IACb;AAAA,EACF;AACF;AAUO,SAAS,eACd,UACA,OACA,QACA,MAAY,oBAAI,KAAK,GACC;AACtB,MAAI,SAAS,KAAK,CAAC,MAAM,EAAE,WAAW,KAAK,CAAC,OAAO,GAAG,OAAO,MAAM,YAAY,CAAC,EAAG,QAAO;AAC1F,QAAM,SAAS,SAAS;AAAA,IAAI,CAAC,GAAG,MAC9B,MAAM,SAAS,SAAS,KAAK,EAAE,aAAa,EAAE,SAAS,eAAe,CAAC,EAAE,YAAY,EAAE,GAAG,GAAG,WAAW,MAAM,IAAI;AAAA,EACpH;AACA,SAAO;AAAA,IACL,GAAG;AAAA,IACH;AAAA,MACE,IAAI,UAAU,MAAM,YAAY;AAAA,MAChC;AAAA,MACA,MAAM;AAAA,MACN,SAAS;AAAA,MACT,WAAW;AAAA,QACT;AAAA,UACE,IAAI,MAAM;AAAA,UACV,MAAM;AAAA,UACN,UAAU,EAAE,MAAM,MAAM,MAAM,WAAW,MAAM,aAAa,KAAK;AAAA,UACjE,aAAa,MAAM;AAAA,QACrB;AAAA,MACF;AAAA,MACA,YAAY;AAAA,MACZ,MAAM;AAAA,MACN,WAAW,IAAI,YAAY;AAAA,MAC3B,WAAW;AAAA,IACb;AAAA,EACF;AACF;AAGO,SAAS,aACd,UACA,OACsB;AACtB,MAAI,MAAM,WAAW,OAAW,QAAO;AACvC,QAAM,UAAU,OAAO,MAAM,WAAW,WAAW,MAAM,SAAS,KAAK,UAAU,MAAM,MAAM;AAC7F,SAAO,SAAS;AAAA,IAAI,CAAC,MACnB,EAAE,WAAW,KAAK,CAAC,OAAO,GAAG,OAAO,MAAM,YAAY,IAClD,EAAE,GAAG,GAAG,aAAa,EAAE,GAAG,EAAE,aAAa,CAAC,MAAM,YAAY,GAAG,EAAE,SAAS,MAAM,MAAM,KAAK,EAAE,EAAE,IAC/F;AAAA,EACN;AACF;AAGO,SAAS,YAAY,SAA4B,UAA8C;AACpG,SAAO,QAAQ,KAAK,CAAC,MAAM,EAAE,eAAe,SAAS,UAAU,IAAI,UAAU,CAAC,GAAG,SAAS,QAAQ;AACpG;AAGO,SAAS,mBAAmB,SAAyB,UAA0C;AACpG,QAAM,OAAO,IAAI,IAAI,QAAQ,IAAI,CAAC,MAAM,EAAE,UAAU,CAAC;AACrD,QAAM,QAAQ,SAAS,OAAO,CAAC,MAAM,CAAC,KAAK,IAAI,EAAE,UAAU,KAAK,KAAK,IAAI,EAAE,UAAU,CAAC;AACtF,SAAO,MAAM,SAAS,CAAC,GAAG,SAAS,GAAG,KAAK,IAAI;AACjD;AAQO,IAAM,eAA+B,EAAE,QAAQ,OAAO,QAAQ,CAAC,EAAE;AAOjE,SAAS,cAAc,OAAuB,UAAkC;AACrF,MAAI,CAAC,MAAM,OAAQ,QAAO,EAAE,QAAQ,MAAM,QAAQ,CAAC,GAAG,MAAM,QAAQ,QAAQ,EAAE;AAC9E,MAAI,CAAC,SAAU,QAAO;AACtB,QAAM,SAAS,CAAC,GAAG,MAAM,MAAM;AAC/B,SAAO,OAAO,SAAS,CAAC,KAAK;AAC7B,SAAO,EAAE,QAAQ,MAAM,OAAO;AAChC;AAGO,SAAS,aAAa,OAAuC;AAClE,SAAO,MAAM,SAAS,EAAE,GAAG,OAAO,QAAQ,MAAM,IAAI;AACtD;AAGO,SAAS,aAAa,OAAqC;AAChE,SAAO,EAAE,QAAQ,MAAM,QAAQ,MAAM,MAAM,OAAO,OAAO,CAAC,MAAM,CAAC,EAAE,KAAK,MAAM,EAAE;AAClF;AAQO,SAAS,mBAAmB;AACjC,MAAI,SAAS;AACb,SAAO;AAAA,IACL,MAAM,MAAc,EAAE;AAAA,IACtB,WAAW,CAAC,WAA4B,WAAW;AAAA,EACrD;AACF;AAGO,IAAM,sBAAsB;AACnC,IAAM,sBAAsB;AAE5B,IAAM,kBAAkB;AAExB,IAAM,kBAAkB;AASjB,SAAS,kBAAkB,QAAwB,OAAuB;AAC/E,MAAI,OAAO;AACX,aAAW,SAAS,QAAQ;AAC1B,UAAM,WAAW,MAAM,YAAY,KAAK,MAAM,MAAM,SAAS,IAAI;AACjE,QAAI,OAAO,MAAM,QAAQ,EAAG;AAC5B,UAAM,WAAW,WAAW,kBAAkB;AAC9C,WAAO,KAAK,IAAI,MAAM,WAAW,IAAI,WAAW,eAAe;AAAA,EACjE;AACA,SAAO,KAAK,IAAI,qBAAqB,IAAI;AAC3C;AAOO,IAAM,oBAAoB,CAAC,KAAO,MAAQ,GAAM;;;AD5DhD,SAAS,QACd,UACA,SACe;AACf,QAAM,SAAS,UAAU;AACzB,QAAM,kBAAkB,CAAC,CAAC,SAAS;AACnC,QAAM,oBAAoB,SAAS,sBAAsB;AAEzD,QAAM,CAAC,QAAQ,SAAS,IAAI,cAAAC,QAAM,SAAwB,SAAS,UAAU,IAAI;AACjF,QAAM,CAAC,UAAU,WAAW,IAAI,cAAAA,QAAM,SAA+B,CAAC,CAAC;AACvE,QAAM,CAAC,SAAS,UAAU,IAAI,cAAAA,QAAM,SAAS,KAAK;AAClD,QAAM,CAAC,WAAW,YAAY,IAAI,cAAAA,QAAM,SAAS,KAAK;AACtD,QAAM,CAAC,OAAO,QAAQ,IAAI,cAAAA,QAAM,SAAwB,IAAI;AAC5D,QAAM,CAAC,kBAAkB,mBAAmB,IAAI,cAAAA,QAAM,SAA4B,CAAC,CAAC;AACpF,QAAM,CAAC,eAAe,gBAAgB,IAAI,cAAAA,QAAM,SAAyB,CAAC,CAAC;AAC3E,QAAM,CAAC,UAAU,WAAW,IAAI,cAAAA,QAAM,SAAyB,YAAY;AAC3E,QAAM,gBAAgB,cAAAA,QAAM,QAAQ,MAAM,aAAa,QAAQ,GAAG,CAAC,QAAQ,CAAC;AAC5E,QAAM,CAAC,YAAY,aAAa,IAAI,cAAAA,QAAM,SAAuB,CAAC,CAAC;AAGnE,QAAM,CAAC,cAAc,eAAe,IAAI,cAAAA,QAAM,SAAS,kBAAkB,MAAM;AAG/E,QAAM,CAAC,UAAU,WAAW,IAAI,cAAAA,QAAM,SAAS,CAAC;AAEhD,QAAM,WAAW,cAAAA,QAAM,OAA+B,IAAI;AAC1D,QAAM,YAAY,cAAAA,QAAM,OAAsB,MAAM;AACpD,YAAU,UAAU;AAEpB,QAAM,CAAC,IAAI,IAAI,cAAAA,QAAM,SAAS,gBAAgB;AAO9C,QAAMC,WAAU,cAAAD,QAAM;AAAA,IACpB,OAAO,OAA+C;AACpD,YAAM,SAAS,KAAK,KAAK;AACzB,UAAI;AACF,cAAM,SAAS,MAAM,QAAQ,QAAQ,EAAE;AACvC,YAAI,CAAC,KAAK,UAAU,MAAM,EAAG,QAAO;AACpC,oBAAY,OAAO,QAAQ;AAC3B,4BAAoB,OAAO,oBAAoB,CAAC,CAAC;AACjD,cAAM,SAAS,OAAO,iBAAiB,CAAC;AACxC,yBAAiB,MAAM;AACvB,eAAO;AAAA,MACT,QAAQ;AAEN,eAAO;AAAA,MACT;AAAA,IACF;AAAA,IACA,CAAC,QAAQ,IAAI;AAAA,EACf;AAGA,gBAAAA,QAAM,UAAU,MAAM;AACpB,QAAI,CAAC,SAAS,OAAQ;AACtB,QAAI,YAAY;AAChB,UAAM,SAAS,KAAK,KAAK;AAEzB,eAAW,IAAI;AACf,YAAQ,QAAQ,QAAQ,MAAM,EAC3B,KAAK,CAAC,WAAW;AAChB,UAAI,aAAa,CAAC,KAAK,UAAU,MAAM,EAAG;AAC1C,gBAAU,OAAO,EAAE;AACnB,kBAAY,OAAO,QAAQ;AAC3B,0BAAoB,OAAO,oBAAoB,CAAC,CAAC;AACjD,uBAAiB,OAAO,iBAAiB,CAAC,CAAC;AAAA,IAC7C,CAAC,EACA,MAAM,CAAC,MAAM;AACZ,UAAI,UAAW;AACf,eAAU,EAAY,OAAO;AAAA,IAC/B,CAAC,EACA,QAAQ,MAAM;AACb,UAAI,CAAC,UAAW,YAAW,KAAK;AAAA,IAClC,CAAC;AAEH,WAAO,MAAM;AAAE,kBAAY;AAAA,IAAM;AAAA,EACnC,GAAG,CAAC,QAAQ,MAAM,SAAS,MAAM,CAAC;AAGlC,gBAAAA,QAAM,UAAU,MAAM;AACpB,WAAO,MAAM;AACX,eAAS,SAAS,MAAM;AAAA,IAC1B;AAAA,EACF,GAAG,CAAC,CAAC;AAML,gBAAAA,QAAM,UAAU,MAAM;AACpB,QAAI,CAAC,qBAAqB,aAAa,CAAC,OAAQ;AAChD,QAAI,QAAuB;AAC3B,QAAI,cAAc,SAAS,EAAG,SAAQ,kBAAkB,eAAe,KAAK,IAAI,CAAC;AAAA,aACxE,eAAe,kBAAkB,OAAQ,SAAQ,kBAAkB,YAAY;AACxF,QAAI,UAAU,KAAM;AACpB,UAAM,UAAU,cAAc,IAAI,CAAC,MAAM,EAAE,UAAU;AACrD,UAAM,QAAQ,WAAW,YAAY;AACnC,YAAM,MAAM,MAAMC,SAAQ,MAAM;AAChC,UAAI,QAAQ,WAAW,EAAG,iBAAgB,CAAC,MAAM,IAAI,CAAC;AAAA,eAC7C,OAAO,QAAQ,KAAK,CAAC,OAAO,CAAC,IAAI,KAAK,CAAC,MAAM,EAAE,eAAe,EAAE,CAAC,EAAG,iBAAgB,CAAC;AAC9F,kBAAY,CAAC,MAAM,IAAI,CAAC;AAAA,IAC1B,GAAG,KAAK;AACR,WAAO,MAAM,aAAa,KAAK;AAAA,EACjC,GAAG,CAAC,mBAAmB,QAAQ,WAAW,eAAe,cAAc,UAAUA,QAAO,CAAC;AAEzF,QAAM,oBAAoB,cAAAD,QAAM;AAAA,IAC9B,CAAC,UAAoB;AAGnB,YAAM,QAAQ,sBAAsB,KAAK;AACzC,UAAI,OAAO;AACT,oBAAY,YAAY;AACxB,yBAAiB,CAAC,SAAS,mBAAmB,MAAM,CAAC,KAAK,CAAC,CAAC;AAC5D;AAAA,MACF;AACA,YAAM,YAAY,UAAU,WAAW;AACvC,UAAI,MAAM,UAAU,WAAW;AAC7B,cAAM,EAAE,MAAM,UAAU,QAAQ,IAAI,kBAAkB,MAAM,IAAI;AAChE,YAAI,YAAY,OAAW,aAAY,CAAC,SAAS,cAAc,MAAM,OAAO,CAAC;AAC7E,YAAI,MAAM;AACR,sBAAY,YAAY;AACxB,sBAAY,CAAC,SAAS,eAAe,MAAM,MAAM,SAAS,CAAC;AAAA,QAC7D;AAAA,MACF,WAAW,MAAM,UAAU,cAAc;AACvC,oBAAY,YAAY;AACxB,YAAI;AACF,gBAAM,SAAS,KAAK,MAAM,MAAM,IAAI;AACpC,wBAAc,CAAC,SAAS;AAAA,YACtB,GAAG;AAAA,YACH,EAAE,YAAY,OAAO,cAAc,MAAM,OAAO,MAAM,aAAa,OAAO,aAAa,QAAQ,UAAU;AAAA,UAC3G,CAAC;AACD,sBAAY,CAAC,SAAS,eAAe,MAAM,QAAQ,SAAS,CAAC;AAAA,QAC/D,QAAQ;AAAA,QAER;AAAA,MACF,WAAW,MAAM,UAAU,YAAY;AACrC,YAAI;AACF,gBAAM,SAAS,KAAK,MAAM,MAAM,IAAI;AACpC;AAAA,YAAc,CAAC,SACb,KAAK,IAAI,CAAC,MAAO,EAAE,eAAe,OAAO,eAAe,EAAE,GAAG,GAAG,QAAQ,WAAW,IAAI,CAAE;AAAA,UAC3F;AACA,sBAAY,CAAC,SAAS,aAAa,MAAM,MAAM,CAAC;AAAA,QAClD,QAAQ;AAAA,QAER;AAAA,MACF,WAAW,MAAM,UAAU,qBAAqB;AAC9C,oBAAY,YAAY;AACxB,YAAI;AACF,gBAAM,WAAW,cAAc,KAAK,MAAM,MAAM,IAAI,CAAC;AACrD,cAAI,SAAU,qBAAoB,CAAC,SAAS,YAAY,MAAM,QAAQ,CAAC;AAAA,QACzE,QAAQ;AAAA,QAER;AAAA,MACF,WAAW,MAAM,UAAU,SAAS;AAClC,oBAAY,YAAY;AACxB,YAAI;AACF,gBAAM,SAAS,KAAK,MAAM,MAAM,IAAI;AACpC,mBAAS,OAAO,SAAS,cAAc;AAAA,QACzC,QAAQ;AACN,mBAAS,MAAM,QAAQ,cAAc;AAAA,QACvC;AAAA,MACF;AAAA,IACF;AAAA,IACA,CAAC;AAAA,EACH;AAEA,QAAM,kBAAkB,cAAAA,QAAM;AAAA,IAC5B,CAAC,OACC;AAAA,MACE,CAAC,UAAsB;AACrB,qBAAa,KAAK;AAClB,sBAAc,CAAC,CAAC;AAChB,oBAAY,YAAY;AAGxB,QAAAC,SAAQ,EAAE;AAAA,MACZ;AAAA,MACA,CAAC,QAAe;AACd,iBAAS,IAAI,OAAO;AACpB,qBAAa,KAAK;AAClB,sBAAc,CAAC,CAAC;AAChB,oBAAY,YAAY;AAAA,MAC1B;AAAA,IACF;AAAA,IACF,CAACA,QAAO;AAAA,EACV;AAGA,QAAM,gBAAgB,cAAAD,QAAM;AAAA,IAC1B,CAAC,IAAY,WAAmB,WAAoB;AAClD,eAAS,SAAS,MAAM;AACxB,WAAK,KAAK;AACV,mBAAa,IAAI;AACjB,eAAS,IAAI;AACb,kBAAY,YAAY;AACxB,YAAM,CAAC,QAAQ,OAAO,IAAI,gBAAgB,EAAE;AAC5C,eAAS,UAAU,kBAAkB,QAAQ,IAAI,WAAW,mBAAmB,QAAQ,SAAS;AAAA,QAC9F;AAAA,QACA;AAAA,MACF,CAAC;AAAA,IACH;AAAA,IACA,CAAC,QAAQ,MAAM,iBAAiB,mBAAmB,eAAe;AAAA,EACpE;AAEA,QAAM,OAAO,cAAAA,QAAM;AAAA,IACjB,CAAC,YAA4B;AAC3B,YAAM,SAAS,YAAY;AACzB,YAAI,eAAe,UAAU;AAG7B,YAAI,CAAC,cAAc;AACjB,qBAAW,IAAI;AACf,mBAAS,IAAI;AACb,cAAI;AACF,kBAAM,SAAS,MAAM,WAAW,QAAQ,UAAU,SAAS,KAAK;AAChE,2BAAe,OAAO;AACtB,sBAAU,OAAO,EAAE;AACnB,sBAAU,UAAU,OAAO;AAAA,UAC7B,SAAS,GAAG;AACV,qBAAU,EAAY,OAAO;AAC7B,uBAAW,KAAK;AAChB;AAAA,UACF;AACA,qBAAW,KAAK;AAAA,QAClB;AAEA,iBAAS,SAAS,MAAM;AACxB,aAAK,KAAK;AACV,qBAAa,IAAI;AACjB,iBAAS,IAAI;AACb,4BAAoB,CAAC,CAAC;AACtB,sBAAc,CAAC,CAAC;AAChB,oBAAY,YAAY;AAGxB,cAAM,iBAAiB,OAAO,YAAY,WAAW,UAAU,KAAK,UAAU,OAAO;AACrF,cAAM,UAA8B;AAAA,UAClC,IAAI,YAAY,KAAK,IAAI,CAAC;AAAA,UAC1B,QAAQ;AAAA,UACR,MAAM;AAAA,UACN,SAAS;AAAA,UACT,WAAW;AAAA,UACX,YAAY;AAAA,UACZ,MAAM;AAAA,UACN,YAAW,oBAAI,KAAK,GAAE,YAAY;AAAA,QACpC;AACA,oBAAY,CAAC,SAAS,CAAC,GAAG,MAAM,OAAO,CAAC;AAExC,cAAM,CAAC,QAAQ,OAAO,IAAI,gBAAgB,YAAY;AACtD,iBAAS,UAAU,cAAc,QAAQ,cAAc,SAAS,mBAAmB,QAAQ,SAAS;AAAA,UAClG;AAAA,QACF,CAAC;AAAA,MACH;AAEA,aAAO;AAAA,IACT;AAAA,IACA,CAAC,QAAQ,UAAU,SAAS,OAAO,MAAM,iBAAiB,mBAAmB,eAAe;AAAA,EAC9F;AAEA,QAAM,SAAS,cAAAA,QAAM;AAAA,IACnB,CAAC,YAAoB,UAAmB,gBAAyB;AAC/D,YAAM,KAAK,UAAU;AACrB,UAAI,CAAC,GAAI;AACT,WAAK,KAAK;AACV,0BAAoB,CAAC,SAAS,KAAK,OAAO,CAAC,MAAM,EAAE,eAAe,UAAU,CAAC;AAC7E,eAAS,IAAI;AAEb,OAAC,YAAY;AACX,YAAI;AACF,gBAAM,SAAS,MAAM,gBAAgB,QAAQ,IAAI,YAAY,UAAU,EAAE,YAAY,CAAC;AAGtF,gBAAM,YAAY,sBAAsB,QAAQ,QAAQ;AACxD,cAAI,UAAW,eAAc,IAAI,SAAS;AAAA,mBACjC,OAAO,WAAW,OAAW,CAAAC,SAAQ,EAAE;AAAA,QAClD,SAAS,GAAG;AACV,mBAAU,EAAY,OAAO;AAE7B,UAAAA,SAAQ,EAAE;AAAA,QACZ;AAAA,MACF,GAAG;AAAA,IACL;AAAA,IACA,CAAC,QAAQ,MAAM,eAAeA,QAAO;AAAA,EACvC;AAEA,QAAM,UAAU,cAAAD,QAAM;AAAA,IACpB,CAAC,YAAoB,SAA0B,OAAO,YAAY,MAAM,CAAC,CAAC,MAAM,WAAW;AAAA,IAC3F,CAAC,MAAM;AAAA,EACT;AAEA,QAAM,SAAS,cAAAA,QAAM;AAAA,IACnB,CAAC,eAAuB,OAAO,YAAY,OAAO,KAAK;AAAA,IACvD,CAAC,MAAM;AAAA,EACT;AAEA,QAAM,SAAS,cAAAA,QAAM;AAAA,IACnB,OAAO,YAAoB,SAAmC;AAC5D,YAAM,KAAK,UAAU;AACrB,UAAI,CAAC,GAAI,QAAO;AAChB,eAAS,IAAI;AACb,UAAI;AACF,cAAM,SAAS,MAAM,mBAAmB,QAAQ,IAAI,YAAY,IAAI;AACpE,aAAK,KAAK;AACV,yBAAiB,CAAC,SAAS,KAAK,OAAO,CAAC,MAAM,EAAE,eAAe,UAAU,CAAC;AAG1E,cAAM,YAAY,oBAAoB,MAAM;AAC5C,YAAI,UAAW,eAAc,IAAI,SAAS;AAC1C,eAAO;AAAA,MACT,SAAS,GAAG;AACV,iBAAU,EAAY,OAAO;AAC7B,QAAAC,SAAQ,EAAE;AACV,eAAO;AAAA,MACT;AAAA,IACF;AAAA,IACA,CAAC,QAAQ,MAAM,eAAeA,QAAO;AAAA,EACvC;AAEA,QAAM,SAAS,cAAAD,QAAM;AAAA,IACnB,CAAC,WAAmB,SAAyB;AAC3C,YAAM,KAAK,UAAU;AACrB,UAAI,CAAC,GAAI;AACT,oBAAc,IAAI,WAAW,MAAM,MAAM;AAAA,IAC3C;AAAA,IACA,CAAC,aAAa;AAAA,EAChB;AAEA,QAAM,OAAO,cAAAA,QAAM,YAAY,MAAM;AACnC,aAAS,SAAS,MAAM;AACxB,aAAS,UAAU;AACnB,iBAAa,KAAK;AAClB,gBAAY,YAAY;AAAA,EAC1B,GAAG,CAAC,CAAC;AAEL,QAAM,aAAa,cAAAA,QAAM,YAAY,MAAM;AACzC,aAAS,IAAI;AAAA,EACf,GAAG,CAAC,CAAC;AAEL,SAAO;AAAA,IACL;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA,UAAU;AAAA,IACV;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,EACF;AACF;;;AEleO,SAAS,WAA2B;AACzC,QAAM,SAAS,UAAU;AAEzB,SAAO;AAAA,IACL,QAAQ,OAAO,UAAU;AAAA,IACzB,OAAO,OAAO,SAAS;AAAA,IACvB;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,EACF;AACF;;;AC9BA,IAAAE,gBAAkB;AAiDX,SAAS,QAAQ,UAA0B,CAAC,GAAkB;AACnE,QAAM,EAAE,cAAc,KAAK,IAAI;AAC/B,QAAM,SAAS,UAAU;AAEzB,QAAM,CAAC,QAAQ,SAAS,IAAI,cAAAC,QAAM,SAAqB,SAAS;AAChE,QAAM,CAAC,MAAM,OAAO,IAAI,cAAAA,QAAM,SAA0B,IAAI;AAC5D,QAAM,CAAC,MAAM,OAAO,IAAI,cAAAA,QAAM,SAA8B,IAAI;AAChE,QAAM,CAAC,OAAO,QAAQ,IAAI,cAAAA,QAAM,SAAwB,IAAI;AAE5D,QAAMC,WAAU,cAAAD,QAAM,YAAY,YAAY;AAC5C,aAAS,IAAI;AACb,QAAI;AAEF,YAAM,CAAC,UAAU,MAAM,IAAI,MAAM,QAAQ,IAAI;AAAA,QAC3C,OAAO,KAAK,QAAQ,EAAE,MAAM,MAAM,IAAI;AAAA,QACtC,OAAO,eAAe,IAAI,OAAO,KAAK,MAAM,EAAE,MAAM,MAAM,IAAI,IAAI,QAAQ,QAAQ,IAAI;AAAA,MACxF,CAAC;AACD,UAAI,SAAU,SAAQ,QAAQ;AAC9B,UAAI,QAAQ;AACV,gBAAQ,MAAM;AACd,kBAAU,eAAe;AAAA,MAC3B,OAAO;AACL,gBAAQ,IAAI;AACZ,kBAAU,iBAAiB;AAAA,MAC7B;AAAA,IACF,SAAS,GAAG;AACV,eAAS,aAAa,QAAQ,EAAE,UAAU,OAAO,CAAC,CAAC;AACnD,gBAAU,iBAAiB;AAAA,IAC7B;AAAA,EACF,GAAG,CAAC,MAAM,CAAC;AAEX,gBAAAA,QAAM,UAAU,MAAM;AACpB,QAAI,YAAa,MAAKC,SAAQ;AAAA,EAChC,GAAG,CAAC,aAAaA,QAAO,CAAC;AAEzB,QAAMC,SAAQ,cAAAF,QAAM;AAAA,IAClB,OAAO,OAAe,aAAsB;AAC1C,eAAS,IAAI;AACb,UAAI;AACF,eAAO,MAAM,OAAO,KAAK,MAAM,EAAE,OAAO,SAAS,CAAC;AAAA,MACpD,SAAS,GAAG;AACV,cAAM,MAAM,aAAa,QAAQ,EAAE,UAAU,OAAO,CAAC;AACrD,iBAAS,GAAG;AACZ,cAAM;AAAA,MACR;AAAA,IACF;AAAA,IACA,CAAC,MAAM;AAAA,EACT;AAEA,QAAMG,aAAY,cAAAH,QAAM;AAAA,IACtB,OAAO,WAAmB,YAAoB;AAC5C,eAAS,IAAI;AACb,UAAI;AACF,eAAO,MAAM,OAAO,KAAK,UAAU,EAAE,YAAY,WAAW,UAAU,QAAQ,CAAC;AAAA,MACjF,SAAS,GAAG;AACV,cAAM,MAAM,aAAa,QAAQ,EAAE,UAAU,OAAO,CAAC;AACrD,iBAAS,GAAG;AACZ,cAAM;AAAA,MACR;AAAA,IACF;AAAA,IACA,CAAC,MAAM;AAAA,EACT;AAEA,QAAMI,UAAS,cAAAJ,QAAM;AAAA,IACnB,OAAO,iBAA0B;AAC/B,UAAI,cAAc;AAChB,YAAI;AACF,gBAAM,OAAO,KAAK,OAAO,YAAY;AAAA,QACvC,SAAS,GAAG;AACV,cAAI,EAAE,aAAa,gBAAiB,OAAM;AAAA,QAC5C;AAAA,MACF;AACA,cAAQ,IAAI;AACZ,gBAAU,iBAAiB;AAAA,IAC7B;AAAA,IACA,CAAC,MAAM;AAAA,EACT;AAEA,SAAO,EAAE,QAAQ,MAAM,MAAM,OAAO,SAAAC,UAAS,OAAAC,QAAO,WAAAC,YAAW,QAAAC,QAAO;AACxE;","names":["parseRef","import_react","React","React","import_react","React","import_react","React","import_react","React","refresh","import_react","React","refresh","login","verifyOTP","logout"]}
|
package/dist/index.d.cts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import { QueryResult, FunctionResult, StateListResult, ChatMessageFull, ApprovalRequest, MessageContent, SinasConfig, SinasClient, AuthUser, InfoResponse, LoginResponse, OTPVerifyResponse, SinasClientOptions } from './client.cjs';
|
|
2
|
-
export { ApprovalResult, AudioContentPart, AuthMode, ChatCreateResult, ChatDetail, ChatMessage, Collection, ComponentContentPart, ContentPart, FileContentPart, FileInfo, FileUploadRequest, FileUrlResult, ImageContentPart, LoginRequest, OTPVerifyRequest, PermissionCheckRequest, PermissionCheckResponse, PermissionCheckResult, RefreshResponse, SSEChunk, SinasAuthError, SinasClientAuth, SinasError, SinasNotFoundError, SinasPermissionError, SinasTimeoutError, StateGetResult, TextContentPart, ToolCallInfo, approveToolCall, checkPermissions, createChat, executeFunction, executeQuery, generateFileUrl, getChat, getInfo, getMe, listCollections, listFiles, login, logout, refresh, sendMessage, stateDelete, stateGet, stateList, stateSet, streamFromChannel, streamMessage, uploadFile, verifyOTP } from './client.cjs';
|
|
1
|
+
import { QueryResult, FunctionResult, StateListResult, ChatMessageFull, ApprovalRequest, PendingInput, MessageContent, SinasConfig, SinasClient, AuthUser, InfoResponse, LoginResponse, OTPVerifyResponse, SinasClientOptions } from './client.cjs';
|
|
2
|
+
export { AgentBatchItem, AnswerPendingInputOptions, ApprovalResult, ApprovalResume, ApproveToolCallOptions, AudioContentPart, AuthMode, BatchExecutionItem, BatchStatus, ChatCreateResult, ChatDetail, ChatMessage, Collection, ComponentContentPart, ContentPart, EnqueueFunctionOptions, EnqueueFunctionResult, FileContentPart, FileInfo, FileUploadRequest, FileUrlResult, ImageContentPart, InputRequiredEvent, InvokeOptions, InvokeResult, LoginRequest, MessageSendResult, OTPVerifyRequest, PendingInputAnswerAccepted, PendingInputAnswerResult, PermissionCheckRequest, PermissionCheckResponse, PermissionCheckResult, RefreshResponse, RoundSuspendedEvent, SSEChunk, SinasAuthError, SinasClientAuth, SinasError, SinasNotFoundError, SinasPermissionError, SinasTimeoutError, StateGetResult, StreamDone, StreamFromChannelOptions, StreamOptions, SubmitAgentBatchOptions, SubmitAgentBatchResult, SubmitFunctionBatchOptions, SubmitFunctionBatchResult, TextContentPart, ToolCallInfo, TurnState, TurnStatus, TurnUsage, answerPendingInput, answerResumeChannel, approvalResumeChannel, approveToolCall, cancelBatch, checkPermissions, createChat, enqueueFunction, executeFunction, executeQuery, generateFileUrl, getBatch, getChat, getInfo, getMe, invokeAgent, listBatchExecutions, listCollections, listFiles, listPendingInputs, login, logout, parsePendingInput, parsePendingInputs, pendingInputFromChunk, refresh, sendMessage, stateDelete, stateGet, stateList, stateSet, streamFromChannel, streamMessage, submitAgentBatch, submitFunctionBatch, uploadFile, verifyOTP } from './client.cjs';
|
|
3
3
|
import React from 'react';
|
|
4
4
|
|
|
5
5
|
interface UseQueryOptions {
|
|
@@ -54,6 +54,28 @@ interface ToolStatus {
|
|
|
54
54
|
description: string;
|
|
55
55
|
status: 'running' | 'complete';
|
|
56
56
|
}
|
|
57
|
+
/**
|
|
58
|
+
* The model's thinking during the current turn. Thinking isn't stored with
|
|
59
|
+
* the messages, so it is only known while (and after) streaming the turn;
|
|
60
|
+
* it resets when the next turn starts.
|
|
61
|
+
*/
|
|
62
|
+
interface ChatThinking {
|
|
63
|
+
/** The model is thinking right now (before its answer or next tool call). */
|
|
64
|
+
active: boolean;
|
|
65
|
+
/**
|
|
66
|
+
* The thinking text so far this turn; only sent with `includeThinking`
|
|
67
|
+
* (otherwise always ''). Thinking rounds are separated by a blank line.
|
|
68
|
+
*/
|
|
69
|
+
text: string;
|
|
70
|
+
}
|
|
71
|
+
interface ApproveOptions {
|
|
72
|
+
/** Approve this tool for the rest of the chat: it won't ask again (Sinas 0.5+). */
|
|
73
|
+
alwaysAllow?: boolean;
|
|
74
|
+
}
|
|
75
|
+
interface FollowOptions {
|
|
76
|
+
/** Last received stream entry id to resume after (default: from the start). */
|
|
77
|
+
lastId?: string;
|
|
78
|
+
}
|
|
57
79
|
interface UseChatResult {
|
|
58
80
|
chatId: string | null;
|
|
59
81
|
messages: ChatSessionMessage[];
|
|
@@ -61,16 +83,52 @@ interface UseChatResult {
|
|
|
61
83
|
streaming: boolean;
|
|
62
84
|
error: string | null;
|
|
63
85
|
pendingApprovals: ApprovalRequest[];
|
|
86
|
+
/**
|
|
87
|
+
* The ask_user questions the conversation waits on (Sinas 0.5+): from
|
|
88
|
+
* `input_required` stream events and from the chat as loaded. Answer with
|
|
89
|
+
* `answer`.
|
|
90
|
+
*/
|
|
91
|
+
pendingInputs: PendingInput[];
|
|
92
|
+
/** The model's thinking in the current turn (see `includeThinking`). */
|
|
93
|
+
thinking: ChatThinking;
|
|
64
94
|
toolStatus: ToolStatus[];
|
|
65
95
|
send: (content: MessageContent) => void;
|
|
66
|
-
|
|
96
|
+
/**
|
|
97
|
+
* Approve a tool call. When other calls of the same round still wait for a
|
|
98
|
+
* decision, nothing streams until the last one is decided.
|
|
99
|
+
*/
|
|
100
|
+
approve: (toolCallId: string, options?: ApproveOptions) => void;
|
|
67
101
|
reject: (toolCallId: string) => void;
|
|
102
|
+
/**
|
|
103
|
+
* Answer an ask_user question. Resolves true once the answer is recorded
|
|
104
|
+
* (the question is then removed from `pendingInputs`), false when it
|
|
105
|
+
* failed (see `error`). When it was the round's last open question, the
|
|
106
|
+
* resumed turn streams into `messages`.
|
|
107
|
+
*/
|
|
108
|
+
answer: (toolCallId: string, answer: string) => Promise<boolean>;
|
|
109
|
+
/**
|
|
110
|
+
* Stream a channel into this session: a turn that goes on elsewhere (an
|
|
111
|
+
* `in_progress` result, a reconnect to a running turn).
|
|
112
|
+
*/
|
|
113
|
+
follow: (channelId: string, options?: FollowOptions) => void;
|
|
68
114
|
stop: () => void;
|
|
69
115
|
clearError: () => void;
|
|
70
116
|
}
|
|
71
117
|
interface UseChatOptions {
|
|
72
118
|
chatId?: string;
|
|
73
119
|
input?: Record<string, unknown>;
|
|
120
|
+
/**
|
|
121
|
+
* Stream the model's thinking text into `thinking.text` (Sinas 0.5+).
|
|
122
|
+
* Without it, `thinking.active` still says when the model is thinking.
|
|
123
|
+
*/
|
|
124
|
+
includeThinking?: boolean;
|
|
125
|
+
/**
|
|
126
|
+
* While questions wait with no stream open, re-read the chat periodically
|
|
127
|
+
* and just after the earliest deadline, so an expired question (the round
|
|
128
|
+
* then resumes server-side) or one answered elsewhere shows up without a
|
|
129
|
+
* reload. Default true.
|
|
130
|
+
*/
|
|
131
|
+
pollPendingInputs?: boolean;
|
|
74
132
|
}
|
|
75
133
|
declare function useChat(agentRef: string, options?: UseChatOptions): UseChatResult;
|
|
76
134
|
|
|
@@ -129,4 +187,4 @@ interface SinasProviderProps {
|
|
|
129
187
|
declare function SinasProvider({ client, options, children }: SinasProviderProps): React.FunctionComponentElement<React.ProviderProps<SinasClient | null>>;
|
|
130
188
|
declare function useClient(): SinasClient;
|
|
131
189
|
|
|
132
|
-
export { ApprovalRequest, type AuthStatus, AuthUser, ChatMessageFull, type ChatSessionMessage, FunctionResult, InfoResponse, LoginResponse, MessageContent, OTPVerifyResponse, QueryResult, SinasClient, SinasClientOptions, SinasConfig, SinasProvider, type SinasProviderProps, StateListResult, type ToolResult, type ToolStatus, type UseAuthOptions, type UseAuthResult, type UseChatOptions, type UseChatResult, type UseExecuteResult, type UseQueryOptions, type UseQueryResult, type UseSinasResult, type UseStateStoreOptions, type UseStateStoreResult, useAuth, useChat, useClient, useExecute, useQuery, useSinas, useStateStore };
|
|
190
|
+
export { ApprovalRequest, type ApproveOptions, type AuthStatus, AuthUser, ChatMessageFull, type ChatSessionMessage, type ChatThinking, type FollowOptions, FunctionResult, InfoResponse, LoginResponse, MessageContent, OTPVerifyResponse, PendingInput, QueryResult, SinasClient, SinasClientOptions, SinasConfig, SinasProvider, type SinasProviderProps, StateListResult, type ToolResult, type ToolStatus, type UseAuthOptions, type UseAuthResult, type UseChatOptions, type UseChatResult, type UseExecuteResult, type UseQueryOptions, type UseQueryResult, type UseSinasResult, type UseStateStoreOptions, type UseStateStoreResult, useAuth, useChat, useClient, useExecute, useQuery, useSinas, useStateStore };
|