@standardagents/builder 0.37.0 → 0.37.2
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/built-in-routes.js +1168 -905
- package/dist/built-in-routes.js.map +1 -1
- package/dist/client/{ApiKeysView-CTfDKe47.js → ApiKeysView-BhuT3pIF.js} +1 -1
- package/dist/client/{CenteredContentView-BrVntknT.js → CenteredContentView-CfgX3Ao3.js} +1 -1
- package/dist/client/{CompositionView-BT-1sFij.js → CompositionView-B9FfWMHd.js} +1 -1
- package/dist/client/{ConfirmDialog.vue_vue_type_script_setup_true_lang-yyjbXnqu.js → ConfirmDialog.vue_vue_type_script_setup_true_lang-BqwwsXWJ.js} +1 -1
- package/dist/client/{CopyButton.vue_vue_type_script_setup_true_lang-BWgZbcol.js → CopyButton.vue_vue_type_script_setup_true_lang-Cqm3Vt3E.js} +1 -1
- package/dist/client/{DataTable.vue_vue_type_script_setup_true_lang-DP_WTiEu.js → DataTable.vue_vue_type_script_setup_true_lang-CA5qgsty.js} +1 -1
- package/dist/client/{JsonViewer-DY4s92Td.js → JsonViewer-ByQKCShF.js} +1 -1
- package/dist/client/{LoginView-DHYLpkb0.js → LoginView-J4qtHbQK.js} +1 -1
- package/dist/client/{MarketplaceView-Bcil0ES3.js → MarketplaceView-CshdWDqp.js} +1 -1
- package/dist/client/{Modal.vue_vue_type_script_setup_true_lang-BJgJZ56X.js → Modal.vue_vue_type_script_setup_true_lang-DKdB9A8Z.js} +1 -1
- package/dist/client/{ModelModal.vue_vue_type_script_setup_true_lang-BXTP0K4Z.js → ModelModal.vue_vue_type_script_setup_true_lang-BAxaBZsx.js} +1 -1
- package/dist/client/{ModelsView-_RY4gQ79.js → ModelsView-B_n306yk.js} +1 -1
- package/dist/client/{PromptEditView-D8kyGi30.js → PromptEditView-C85qRgsE.js} +1 -1
- package/dist/client/{PromptModal-DSPIuleV.js → PromptModal-PNpoJfqD.js} +1 -1
- package/dist/client/{PromptsView-DPvBDPJf.js → PromptsView-BKnfThIF.js} +1 -1
- package/dist/client/{ProvidersView-PaPnME7I.js → ProvidersView-Df41VhHD.js} +1 -1
- package/dist/client/ThreadInspectorPane.vue_vue_type_script_setup_true_lang-CtIBWHUR.js +22 -0
- package/dist/client/{ThreadsView-BW4SYvFN.js → ThreadsView-sjo5Rrcm.js} +1 -1
- package/dist/client/{ToolsView-xsIVTHh0.js → ToolsView-C0MH9x3N.js} +1 -1
- package/dist/client/{UsersView-CSXdBGA-.js → UsersView--TQiJYP7.js} +1 -1
- package/dist/client/{VariablesView-Bl5S2ZDn.js → VariablesView-BO3UljZu.js} +1 -1
- package/dist/client/assets/{ThreadInspectorPane-CnbmdCdH.css → ThreadInspectorPane-D9ZMzSTn.css} +1 -1
- package/dist/client/{index-Df4DTwgs.js → index-BgZnQr8X.js} +2 -2
- package/dist/client/index.html +1 -1
- package/dist/{index-yV9JL4r3.d.ts → index-DceFbLG9.d.ts} +45 -1
- package/dist/index.d.ts +2 -2
- package/dist/index.js +958 -815
- package/dist/index.js.map +1 -1
- package/dist/packing.js +213 -161
- package/dist/packing.js.map +1 -1
- package/dist/plugin.js +535 -505
- package/dist/plugin.js.map +1 -1
- package/dist/runtime.d.ts +110 -38
- package/dist/runtime.js +174 -21
- package/dist/runtime.js.map +1 -1
- package/dist/test.d.ts +1 -1
- package/package.json +5 -5
- package/dist/client/ThreadInspectorPane.vue_vue_type_script_setup_true_lang-BAUlrnb6.js +0 -23
package/dist/runtime.d.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import { e as ThreadEnv,
|
|
2
|
-
export { f as BuilderThreadEndpointHandler, C as CLIENT_STREAM_CHUNK_BYTES,
|
|
1
|
+
import { i as AuthContext, e as ThreadEnv, v as Agent, x as ThreadMetadata, y as ToolResult, M as Message, n as ClientToolRequest, o as ClientToolResponse, p as ClientStreamRequest, q as ClientStreamResponse, G as FileRecord, F as FlowState, K as FileStats, J as GrepResult, H as AttachmentRef, Q as MessageContent, E as Env, w as ThreadInstance } from './index-DceFbLG9.js';
|
|
2
|
+
export { A as AuthUser, f as BuilderThreadEndpointHandler, C as CLIENT_STREAM_CHUNK_BYTES, t as ClientDuplex, u as ClientForwarding, B as Controller, a as ControllerContext, z as FlowResult, O as ImageContentPart, I as ImageMetadata, L as LLMResponse, P as MultimodalContent, R as RequestContext, S as StorageBackend, D as TelemetryEvent, N as TextContentPart, b as ThreadEndpointContext, T as ToolCall, g as authenticate, j as callClient, k as callClientStream, c as createThreadEndpointHandler, m as decodeStreamChunk, d as defineController, l as encodeStreamChunk, h as requireAdmin, r as requireAuth, s as supportsClientForwarding } from './index-DceFbLG9.js';
|
|
3
3
|
import { CodeExecutionOptions, CodeExecutionResult, SubagentRegistryEntry, InjectMessageInput, QueueMessageInput, CredentialGrant, SkillMetadata, SkillFileInput, ModelDefinition as ModelDefinition$1, ToolArgs, PromptTextPart, PromptEnvPart, VariableDefinition, SubpromptConfig as SubpromptConfig$1, PromptToolConfig as PromptToolConfig$1, SubagentToolConfig as SubagentToolConfig$1, ReasoningConfig, SideConfig as SideConfig$1, LLMProviderInterface, ContentPart, TextPart, ImagePart, FilePart, ThreadState, NamespaceContext, DefinitionLoader } from '@standardagents/spec';
|
|
4
4
|
export { AgentType, DefinitionLoader, GlobalNamespaceContext, HookSignatures, ImageContent, ModelCapabilities, ModelProvider, NamespaceContext, PackageSignature, PackedExports, PackedMeta, PackedMetadata, PackedNamespaceContext, PromptInput, PromptTextPart, ProviderAssistantMessage, ProviderError, ProviderErrorCode, ProviderFactory, ProviderFactoryConfig, ProviderFinishReason, ProviderGeneratedImage, ProviderMessage, ProviderMessageContent, ModelCapabilities as ProviderModelCapabilities, ProviderReasoningDetail, ProviderRequest, ProviderResponse, ProviderStreamChunk, ProviderSystemMessage, ProviderTool, ProviderToolCallPart, ProviderToolMessage, ProviderToolResultContent, ProviderUsage, ProviderUserMessage, ReasoningConfig, StructuredPrompt, TextContent, Tool, ToolArgs, ToolArgsNode, ToolArgsRawShape, ToolContent, belongsToPackage, defineAgent, defineHook, defineModel, definePrompt, defineTool, isPacked, isVisibleInNamespace, mapReasoningLevel } from '@standardagents/spec';
|
|
5
5
|
import { DurableObject, WorkerEntrypoint } from 'cloudflare:workers';
|
|
@@ -94,46 +94,39 @@ declare global {
|
|
|
94
94
|
}
|
|
95
95
|
|
|
96
96
|
/**
|
|
97
|
-
*
|
|
97
|
+
* Permissions utility for role-based access control
|
|
98
98
|
*
|
|
99
|
-
*
|
|
100
|
-
* -
|
|
101
|
-
* -
|
|
102
|
-
*
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
username: string;
|
|
107
|
-
/** 'admin' | 'user' | 'api' (API-only: normal API access, no UI, no logs). */
|
|
108
|
-
role: string;
|
|
109
|
-
/**
|
|
110
|
-
* Explicit permission grants (e.g. 'logs'). `null`/absent = legacy row with
|
|
111
|
-
* no explicit set — see {@link hasPermission} for the fallback rules.
|
|
112
|
-
*/
|
|
113
|
-
permissions?: string[] | null;
|
|
114
|
-
platform_user_id?: string | null;
|
|
115
|
-
email?: string | null;
|
|
116
|
-
display_name?: string | null;
|
|
117
|
-
avatar_url?: string | null;
|
|
118
|
-
}
|
|
119
|
-
interface AuthContext {
|
|
120
|
-
user: AuthUser;
|
|
121
|
-
authType: 'super_admin' | 'session' | 'api_key';
|
|
122
|
-
}
|
|
123
|
-
/**
|
|
124
|
-
* Authenticate a request using various token types
|
|
99
|
+
* Current behavior:
|
|
100
|
+
* - Admin role can do everything (early return true)
|
|
101
|
+
* - Other roles only get baseline access (own threads)
|
|
102
|
+
*
|
|
103
|
+
* The `can()` function checks arbitrary permission strings.
|
|
104
|
+
* Currently, non-admin users have no explicit permissions,
|
|
105
|
+
* meaning they rely on ownership checks for access.
|
|
125
106
|
*/
|
|
126
|
-
|
|
107
|
+
|
|
127
108
|
/**
|
|
128
|
-
*
|
|
129
|
-
*
|
|
109
|
+
* Check if a user can access a specific thread
|
|
110
|
+
*
|
|
111
|
+
* @param auth - The authenticated user context
|
|
112
|
+
* @param thread - The thread to check access for (must have user_id)
|
|
113
|
+
* @returns true if the user can access the thread
|
|
130
114
|
*/
|
|
131
|
-
declare function
|
|
115
|
+
declare function canAccessThread(auth: AuthContext, thread: {
|
|
116
|
+
user_id: string | null;
|
|
117
|
+
}): boolean;
|
|
118
|
+
|
|
119
|
+
/** Central API exposure policy shared by the generated Worker router and tests. */
|
|
120
|
+
declare function isHostedInstance(env: Record<string, unknown> | undefined): boolean;
|
|
132
121
|
/**
|
|
133
|
-
*
|
|
134
|
-
*
|
|
122
|
+
* Local-only conveniences are enabled by the request destination, not merely
|
|
123
|
+
* by the absence of a deployment flag. This makes an incorrectly configured
|
|
124
|
+
* internet-facing Worker fail closed while preserving localhost and OrbStack.
|
|
135
125
|
*/
|
|
136
|
-
declare function
|
|
126
|
+
declare function isTrustedLocalDevelopmentRequest(request: Request, env: Record<string, unknown> | undefined): boolean;
|
|
127
|
+
declare function isPublicApiRoute(routePath: string, request: Request, env: Record<string, unknown> | undefined): boolean;
|
|
128
|
+
/** Instance-global authoring and package-management surfaces are admin-only. */
|
|
129
|
+
declare function isAdminOnlyApiRoute(routePath: string, method?: string): boolean;
|
|
137
130
|
|
|
138
131
|
type AlarmQueueStatus = "pending" | "processing" | "completed" | "failed" | "agent_canceled" | "user_canceled";
|
|
139
132
|
type EffectCancelSource = "agent" | "user";
|
|
@@ -1938,6 +1931,12 @@ interface ThreadRegistryEntry {
|
|
|
1938
1931
|
*/
|
|
1939
1932
|
last_message_at?: number | null;
|
|
1940
1933
|
}
|
|
1934
|
+
/**
|
|
1935
|
+
* Safe registry projection carried by system events. Thread env and arbitrary
|
|
1936
|
+
* properties are intentionally excluded: the stream is an invalidation/list
|
|
1937
|
+
* surface, not a second transport for thread configuration or secrets.
|
|
1938
|
+
*/
|
|
1939
|
+
type ThreadEventPayload = Pick<ThreadRegistryEntry, 'id' | 'agent_name' | 'origin_agent_name' | 'user_id' | 'tags' | 'parent' | 'terminated' | 'created_at' | 'last_activity_at' | 'executing' | 'last_message_preview' | 'last_message_at'>;
|
|
1941
1940
|
interface PendingSubagentAttachmentRef {
|
|
1942
1941
|
path: string;
|
|
1943
1942
|
name?: string;
|
|
@@ -2045,6 +2044,77 @@ interface Provider$1 {
|
|
|
2045
2044
|
sdk: string;
|
|
2046
2045
|
api_key: string;
|
|
2047
2046
|
}
|
|
2047
|
+
/**
|
|
2048
|
+
* Lightweight agent metadata included with real-time thread events.
|
|
2049
|
+
*/
|
|
2050
|
+
interface ThreadEventAgent {
|
|
2051
|
+
name: string;
|
|
2052
|
+
title: string;
|
|
2053
|
+
type: string;
|
|
2054
|
+
description?: string;
|
|
2055
|
+
icon?: string;
|
|
2056
|
+
}
|
|
2057
|
+
/**
|
|
2058
|
+
* DurableAgentBuilder - The root Durable Object for AgentBuilder.
|
|
2059
|
+
*
|
|
2060
|
+
* This is a singleton DO that stores:
|
|
2061
|
+
* - Thread registry (maps thread IDs to agent names)
|
|
2062
|
+
* - User authentication data
|
|
2063
|
+
* - Provider credentials (API keys for LLM providers)
|
|
2064
|
+
* - Edit lock state for coordinated edits
|
|
2065
|
+
*
|
|
2066
|
+
* ## Usage
|
|
2067
|
+
*
|
|
2068
|
+
* Users must extend this class to provide virtual module access:
|
|
2069
|
+
*
|
|
2070
|
+
* ```typescript
|
|
2071
|
+
* import { DurableAgentBuilder } from '@standardagents/builder/runtime';
|
|
2072
|
+
* import { models } from 'virtual:@standardagents-models';
|
|
2073
|
+
* import { prompts } from 'virtual:@standardagents-prompts';
|
|
2074
|
+
* import { agents } from 'virtual:@standardagents-agents';
|
|
2075
|
+
*
|
|
2076
|
+
* export class AgentBuilder extends DurableAgentBuilder {
|
|
2077
|
+
* models() { return models; }
|
|
2078
|
+
* prompts() { return prompts; }
|
|
2079
|
+
* agents() { return agents; }
|
|
2080
|
+
* }
|
|
2081
|
+
* ```
|
|
2082
|
+
*/
|
|
2083
|
+
/**
|
|
2084
|
+
* Event types that can be emitted via WebSocket
|
|
2085
|
+
*/
|
|
2086
|
+
type AgentBuilderEvent = {
|
|
2087
|
+
type: 'thread_created';
|
|
2088
|
+
thread: ThreadEventPayload & {
|
|
2089
|
+
agent?: ThreadEventAgent;
|
|
2090
|
+
};
|
|
2091
|
+
} | {
|
|
2092
|
+
type: 'thread_updated';
|
|
2093
|
+
thread: ThreadEventPayload & {
|
|
2094
|
+
agent?: ThreadEventAgent;
|
|
2095
|
+
};
|
|
2096
|
+
} | {
|
|
2097
|
+
type: 'thread_deleted';
|
|
2098
|
+
threadId: string;
|
|
2099
|
+
}
|
|
2100
|
+
/**
|
|
2101
|
+
* Lightweight activity signal. Kept separate from `thread_updated` because it
|
|
2102
|
+
* fires on every execution start/stop: re-broadcasting the whole registry
|
|
2103
|
+
* entry would decrypt thread env on each transition for data that never
|
|
2104
|
+
* changed.
|
|
2105
|
+
*/
|
|
2106
|
+
| {
|
|
2107
|
+
type: 'thread_activity';
|
|
2108
|
+
threadId: string;
|
|
2109
|
+
/** Present only when this event actually wrote the field: a message-only
|
|
2110
|
+
* recency stamp omits last_activity_at, and `executing` rides only on a
|
|
2111
|
+
* real transition — clients must leave their current value alone for
|
|
2112
|
+
* absent fields. */
|
|
2113
|
+
last_activity_at?: number;
|
|
2114
|
+
executing?: boolean;
|
|
2115
|
+
last_message_preview?: string | null;
|
|
2116
|
+
last_message_at?: number | null;
|
|
2117
|
+
};
|
|
2048
2118
|
/** Sort orders supported by `listThreads`. */
|
|
2049
2119
|
type ThreadListSort = 'activity' | 'created' | 'oldest';
|
|
2050
2120
|
declare class DurableAgentBuilder<Env extends AgentBuilderEnv = AgentBuilderEnv> extends DurableObject<Env> {
|
|
@@ -2568,9 +2638,11 @@ declare class DurableAgentBuilder<Env extends AgentBuilderEnv = AgentBuilderEnv>
|
|
|
2568
2638
|
*/
|
|
2569
2639
|
broadcastThreadUpdated(threadId: string): Promise<void>;
|
|
2570
2640
|
/**
|
|
2571
|
-
* Broadcast an event to
|
|
2641
|
+
* Broadcast an event only to its owner or an explicitly all-scoped admin.
|
|
2572
2642
|
*/
|
|
2573
2643
|
private broadcastEvent;
|
|
2644
|
+
/** Resolve a thread owner without decrypting its env or loading the row. */
|
|
2645
|
+
private getThreadOwnerId;
|
|
2574
2646
|
/**
|
|
2575
2647
|
* WebSocket Hibernation API handler for incoming messages
|
|
2576
2648
|
* Called when a message is received on a hibernated WebSocket
|
|
@@ -4191,4 +4263,4 @@ declare function createNamespaceContext(agentDef: {
|
|
|
4191
4263
|
*/
|
|
4192
4264
|
declare function isQualifiedName(name: string): boolean;
|
|
4193
4265
|
|
|
4194
|
-
export { Agent, type AgentBuilderEnv, type AgentDefinition, AttachmentRef,
|
|
4266
|
+
export { Agent, type AgentBuilderEnv, type AgentBuilderEvent, type AgentDefinition, AttachmentRef, AuthContext, type BroadcastOptions, ClientStreamRequest, ClientStreamResponse, ClientToolRequest, ClientToolResponse, CodeExecutionBridge, DurableAgentBuilder, DurableThread, DurableUserHub, Env, FileRecord, FileStats, FlowState, FlowStateSdk, type FlowStateWithSdk, GrepResult, type HubClientInfo, type ImageContextConfig, type InjectMessageOptions$1 as InjectMessageOptions, type Provider as LLMProviderInterface, Message, MessageContent, type ModelDefinition, NamespaceResolutionError, NamespacedRegistry, type PromptContent, type PromptDefinition, type PromptIncludePart, type PromptPart, type PromptToolConfig, type Provider$1 as Provider, type ProviderContentPart, type ProviderFilePart, type ProviderImagePart, ProviderRegistry, type ProviderTextPart, type SessionToolBinding, type SessionToolConfig, type SideConfig, type SubagentToolConfig, type SubpromptConfig, ThreadEnv, type ThreadEventPayload, ThreadInstance, ThreadMetadata, type ThreadRegistryEntry, ThreadWatchdog, type ThreadWatchdogState, type ToolConfig, ToolResult, type UpdateThreadParams, type User, type WatchdogCheckin, type WatchdogProbeResult, buildImageDescription, canAccessThread, cat, createNamespaceContext, emitThreadEvent, enhanceFlowState, exists, find, forceTurn, generateImageDescription, getFileStats, getMessages, getMessagesToSummarize, getShortName, getThumbnail, getUnsummarizedImageAttachments, getVisibleAgentNames, getVisibleModelNames, getVisiblePromptNames, getVisibleToolNames, grep, hasImageAttachments, head, injectMessage, isAdminOnlyApiRoute, isHostedInstance, isPublicApiRoute, isQualifiedName, isTrustedLocalDevelopmentRequest, linkFile, mkdir, move, optimizeImageContext, parseQualifiedName, qualifyName, queueTool, readFile, readdir, reloadHistory, rename, replaceImagesWithDescriptions, resolveAgent, resolveHook, resolveModel, resolvePrompt, resolveTool, rmdir, stat, tail, unlink, updateThread, writeFile, writeImage };
|
package/dist/runtime.js
CHANGED
|
@@ -13710,7 +13710,7 @@ var init_ThreadStateImpl = __esm({
|
|
|
13710
13710
|
const toolCallId = this._flowState?.currentToolCall?.id;
|
|
13711
13711
|
const canPark = !!(toolCallId && this._executionState && typeof instance.dispatchClientTool === "function");
|
|
13712
13712
|
const side = this._flowState?.currentSide === "b" ? "b" : "a";
|
|
13713
|
-
const mustParkForApproval =
|
|
13713
|
+
const mustParkForApproval = await this.forwardedCallNeedsApproval(request);
|
|
13714
13714
|
if (mustParkForApproval && canPark && toolCallId && typeof instance.hasBridge === "function" && await instance.hasBridge()) {
|
|
13715
13715
|
await instance.dispatchClientTool(request, toolCallId, side);
|
|
13716
13716
|
const getDelivered = instance.getDeliveredClientToolResult;
|
|
@@ -14854,6 +14854,84 @@ async function requireAdmin(request, env) {
|
|
|
14854
14854
|
return result;
|
|
14855
14855
|
}
|
|
14856
14856
|
|
|
14857
|
+
// src/utils/permissions.ts
|
|
14858
|
+
function canAccessThread(auth, thread) {
|
|
14859
|
+
if (auth.user.role === "admin") {
|
|
14860
|
+
return true;
|
|
14861
|
+
}
|
|
14862
|
+
if (thread.user_id === null) {
|
|
14863
|
+
return false;
|
|
14864
|
+
}
|
|
14865
|
+
return thread.user_id === auth.user.id;
|
|
14866
|
+
}
|
|
14867
|
+
|
|
14868
|
+
// src/routing/access-policy.ts
|
|
14869
|
+
var PUBLIC_ROUTES = /* @__PURE__ */ new Set([
|
|
14870
|
+
"/api/auth/bootstrap",
|
|
14871
|
+
"/api/auth/login",
|
|
14872
|
+
"/api/auth/config",
|
|
14873
|
+
"/api/auth/brolly-control",
|
|
14874
|
+
"/api/auth/platform-cleanup",
|
|
14875
|
+
"/api/auth/platform-replica",
|
|
14876
|
+
"/api/auth/sa/start",
|
|
14877
|
+
"/api/auth/sa/callback",
|
|
14878
|
+
"/api/config",
|
|
14879
|
+
"/api/auth/oauth/github",
|
|
14880
|
+
"/api/auth/oauth/google",
|
|
14881
|
+
"/api/auth/oauth/github/callback",
|
|
14882
|
+
"/api/auth/oauth/google/callback",
|
|
14883
|
+
"/api/hooks"
|
|
14884
|
+
]);
|
|
14885
|
+
function isProviderIconRoute(routePath) {
|
|
14886
|
+
return /^\/api\/providers\/[^/]+\/icon$/.test(routePath);
|
|
14887
|
+
}
|
|
14888
|
+
function isHostedInstance(env) {
|
|
14889
|
+
const value = env?.STANDARD_AGENTS_HOSTED;
|
|
14890
|
+
if (typeof value === "string") {
|
|
14891
|
+
const normalized = value.trim().toLowerCase();
|
|
14892
|
+
return normalized !== "" && normalized !== "0" && normalized !== "false";
|
|
14893
|
+
}
|
|
14894
|
+
return Boolean(value);
|
|
14895
|
+
}
|
|
14896
|
+
function isTrustedLocalDevelopmentRequest(request, env) {
|
|
14897
|
+
if (isHostedInstance(env)) return false;
|
|
14898
|
+
let hostname;
|
|
14899
|
+
try {
|
|
14900
|
+
hostname = new URL(request.url).hostname.toLowerCase();
|
|
14901
|
+
} catch {
|
|
14902
|
+
return false;
|
|
14903
|
+
}
|
|
14904
|
+
return hostname === "localhost" || hostname === "127.0.0.1" || hostname === "::1" || hostname.endsWith(".localhost") || hostname.endsWith(".orb.local");
|
|
14905
|
+
}
|
|
14906
|
+
function isPublicApiRoute(routePath, request, env) {
|
|
14907
|
+
if (PUBLIC_ROUTES.has(routePath)) return true;
|
|
14908
|
+
if (routePath === "/api/auth/device/start" || routePath.startsWith("/api/auth/device/")) {
|
|
14909
|
+
return true;
|
|
14910
|
+
}
|
|
14911
|
+
if (isProviderIconRoute(routePath)) {
|
|
14912
|
+
return true;
|
|
14913
|
+
}
|
|
14914
|
+
if (!isTrustedLocalDevelopmentRequest(request, env)) return false;
|
|
14915
|
+
return routePath === "/api/threads" || routePath.startsWith("/api/threads/") || routePath === "/api/platform" || routePath.startsWith("/api/platform/") || routePath === "/api/platform-session" || routePath.startsWith("/api/platform-session/") || routePath === "/api/platform-auth" || routePath.startsWith("/api/platform-auth/");
|
|
14916
|
+
}
|
|
14917
|
+
function isAdminOnlyApiRoute(routePath, method = "GET") {
|
|
14918
|
+
if (routePath === "/api/skills" || routePath.startsWith("/api/skills/")) return true;
|
|
14919
|
+
if (routePath === "/api/pack" || routePath.startsWith("/api/pack/")) return true;
|
|
14920
|
+
if (routePath === "/api/unpack" || routePath.startsWith("/api/unpack/")) return true;
|
|
14921
|
+
if (routePath === "/api/prompts" || routePath.startsWith("/api/prompts/")) return true;
|
|
14922
|
+
if (routePath === "/api/tools" || routePath.startsWith("/api/tools/")) return true;
|
|
14923
|
+
if (routePath === "/api/models" || routePath.startsWith("/api/models/")) return true;
|
|
14924
|
+
if (routePath === "/api/providers") return true;
|
|
14925
|
+
if (routePath.startsWith("/api/providers/")) {
|
|
14926
|
+
return !isProviderIconRoute(routePath);
|
|
14927
|
+
}
|
|
14928
|
+
if (routePath.startsWith("/api/agents/")) {
|
|
14929
|
+
return !/^\/api\/agents\/[^/]+\/tenvs$/.test(routePath);
|
|
14930
|
+
}
|
|
14931
|
+
if (routePath === "/api/agents" && method.toUpperCase() !== "GET") return true;
|
|
14932
|
+
return false;
|
|
14933
|
+
}
|
|
14934
|
+
|
|
14857
14935
|
// src/runtime.ts
|
|
14858
14936
|
init_client_forwarding();
|
|
14859
14937
|
|
|
@@ -16534,6 +16612,18 @@ function messageTimestampSeconds(message) {
|
|
|
16534
16612
|
return Math.floor(micros / (1e3 * TIMESTAMP_MULTIPLIER));
|
|
16535
16613
|
}
|
|
16536
16614
|
|
|
16615
|
+
// src/events/access.ts
|
|
16616
|
+
var EVENT_STREAM_USER_ID_HEADER = "X-Standard-Agents-Event-User-Id";
|
|
16617
|
+
var EVENT_STREAM_SCOPE_HEADER = "X-Standard-Agents-Event-Scope";
|
|
16618
|
+
function isEventSocketAttachment(value) {
|
|
16619
|
+
if (!value || typeof value !== "object") return false;
|
|
16620
|
+
const attachment = value;
|
|
16621
|
+
return attachment.channel === "events" && (attachment.scope === "user" || attachment.scope === "all") && typeof attachment.userId === "string" && attachment.userId.length > 0;
|
|
16622
|
+
}
|
|
16623
|
+
function eventSocketCanReceive(attachment, ownerUserId) {
|
|
16624
|
+
return attachment.scope === "all" || ownerUserId !== null && attachment.userId === ownerUserId;
|
|
16625
|
+
}
|
|
16626
|
+
|
|
16537
16627
|
// src/durable-objects/agentbuilder-migrations/0001_initial.ts
|
|
16538
16628
|
var migration36 = {
|
|
16539
16629
|
version: 1,
|
|
@@ -17562,8 +17652,13 @@ var DurableAgentBuilder = class extends DurableObject {
|
|
|
17562
17652
|
const sockets = ctx.getWebSockets();
|
|
17563
17653
|
for (const ws of sockets) {
|
|
17564
17654
|
const attachment = ws.deserializeAttachment();
|
|
17565
|
-
if (attachment
|
|
17655
|
+
if (isEventSocketAttachment(attachment)) {
|
|
17566
17656
|
this.eventSockets.add(ws);
|
|
17657
|
+
} else if (attachment?.channel === "events") {
|
|
17658
|
+
try {
|
|
17659
|
+
ws.close(1012, "Reconnect to establish an authenticated event scope");
|
|
17660
|
+
} catch {
|
|
17661
|
+
}
|
|
17567
17662
|
}
|
|
17568
17663
|
}
|
|
17569
17664
|
}
|
|
@@ -18192,7 +18287,10 @@ ${result ?? error ?? "No result content."}${attachmentSummary}`;
|
|
|
18192
18287
|
executing: false
|
|
18193
18288
|
};
|
|
18194
18289
|
const eventThread = await this.toThreadEventPayload(thread);
|
|
18195
|
-
this.broadcastEvent(
|
|
18290
|
+
this.broadcastEvent(
|
|
18291
|
+
{ type: "thread_created", thread: eventThread },
|
|
18292
|
+
thread.user_id
|
|
18293
|
+
);
|
|
18196
18294
|
await this.runAfterThreadCreatedHook(thread);
|
|
18197
18295
|
return thread;
|
|
18198
18296
|
}
|
|
@@ -18495,14 +18593,20 @@ ${result ?? error ?? "No result content."}${attachmentSummary}`;
|
|
|
18495
18593
|
stampedMessageAt = stampAt;
|
|
18496
18594
|
}
|
|
18497
18595
|
}
|
|
18498
|
-
this.
|
|
18499
|
-
|
|
18500
|
-
|
|
18501
|
-
|
|
18502
|
-
|
|
18503
|
-
|
|
18504
|
-
|
|
18505
|
-
|
|
18596
|
+
const ownerUserId = await this.getThreadOwnerId(threadId);
|
|
18597
|
+
if (ownerUserId !== void 0) {
|
|
18598
|
+
this.broadcastEvent(
|
|
18599
|
+
{
|
|
18600
|
+
type: "thread_activity",
|
|
18601
|
+
threadId,
|
|
18602
|
+
...activityAt !== void 0 ? { last_activity_at: activityAt } : {},
|
|
18603
|
+
...executing !== void 0 ? { executing } : {},
|
|
18604
|
+
...preview != null ? { last_message_preview: preview } : {},
|
|
18605
|
+
...stampedMessageAt !== void 0 ? { last_message_at: stampedMessageAt } : {}
|
|
18606
|
+
},
|
|
18607
|
+
ownerUserId
|
|
18608
|
+
);
|
|
18609
|
+
}
|
|
18506
18610
|
}
|
|
18507
18611
|
/**
|
|
18508
18612
|
* Fill in previews for threads that predate preview tracking. Callers read
|
|
@@ -18529,8 +18633,14 @@ ${result ?? error ?? "No result content."}${attachmentSummary}`;
|
|
|
18529
18633
|
*/
|
|
18530
18634
|
async deleteThread(id) {
|
|
18531
18635
|
await this.ensureMigrated();
|
|
18636
|
+
const ownerUserId = await this.getThreadOwnerId(id);
|
|
18532
18637
|
await this.ctx.storage.sql.exec(`DELETE FROM threads WHERE id = ?`, id);
|
|
18533
|
-
|
|
18638
|
+
if (ownerUserId !== void 0) {
|
|
18639
|
+
this.broadcastEvent(
|
|
18640
|
+
{ type: "thread_deleted", threadId: id },
|
|
18641
|
+
ownerUserId
|
|
18642
|
+
);
|
|
18643
|
+
}
|
|
18534
18644
|
return true;
|
|
18535
18645
|
}
|
|
18536
18646
|
/**
|
|
@@ -18592,7 +18702,10 @@ ${result ?? error ?? "No result content."}${attachmentSummary}`;
|
|
|
18592
18702
|
const updated = await this.getThread(id);
|
|
18593
18703
|
if (updated) {
|
|
18594
18704
|
const eventThread = await this.toThreadEventPayload(updated);
|
|
18595
|
-
this.broadcastEvent(
|
|
18705
|
+
this.broadcastEvent(
|
|
18706
|
+
{ type: "thread_updated", thread: eventThread },
|
|
18707
|
+
updated.user_id
|
|
18708
|
+
);
|
|
18596
18709
|
}
|
|
18597
18710
|
} catch {
|
|
18598
18711
|
}
|
|
@@ -18672,7 +18785,10 @@ ${result ?? error ?? "No result content."}${attachmentSummary}`;
|
|
|
18672
18785
|
const updated = await this.getThread(id);
|
|
18673
18786
|
if (updated) {
|
|
18674
18787
|
const eventThread = await this.toThreadEventPayload(updated);
|
|
18675
|
-
this.broadcastEvent(
|
|
18788
|
+
this.broadcastEvent(
|
|
18789
|
+
{ type: "thread_updated", thread: eventThread },
|
|
18790
|
+
updated.user_id
|
|
18791
|
+
);
|
|
18676
18792
|
}
|
|
18677
18793
|
return updated;
|
|
18678
18794
|
}
|
|
@@ -19377,7 +19493,18 @@ ${result ?? error ?? "No result content."}${attachmentSummary}`;
|
|
|
19377
19493
|
}
|
|
19378
19494
|
async toThreadEventPayload(thread) {
|
|
19379
19495
|
const eventThread = {
|
|
19380
|
-
|
|
19496
|
+
id: thread.id,
|
|
19497
|
+
agent_name: thread.agent_name,
|
|
19498
|
+
origin_agent_name: thread.origin_agent_name,
|
|
19499
|
+
user_id: thread.user_id,
|
|
19500
|
+
tags: thread.tags,
|
|
19501
|
+
parent: thread.parent,
|
|
19502
|
+
terminated: thread.terminated,
|
|
19503
|
+
created_at: thread.created_at,
|
|
19504
|
+
last_activity_at: thread.last_activity_at,
|
|
19505
|
+
executing: thread.executing,
|
|
19506
|
+
last_message_preview: thread.last_message_preview,
|
|
19507
|
+
last_message_at: thread.last_message_at
|
|
19381
19508
|
};
|
|
19382
19509
|
try {
|
|
19383
19510
|
const agentDef = await this.loadAgent(thread.agent_name);
|
|
@@ -20244,10 +20371,21 @@ ${result ?? error ?? "No result content."}${attachmentSummary}`;
|
|
|
20244
20371
|
* Uses Hibernation API to reduce costs during inactivity
|
|
20245
20372
|
*/
|
|
20246
20373
|
async handleEventsWebSocketUpgrade(request) {
|
|
20374
|
+
const attachment = {
|
|
20375
|
+
channel: "events",
|
|
20376
|
+
scope: request.headers.get(EVENT_STREAM_SCOPE_HEADER) === "all" ? "all" : "user",
|
|
20377
|
+
userId: request.headers.get(EVENT_STREAM_USER_ID_HEADER) ?? ""
|
|
20378
|
+
};
|
|
20379
|
+
if (!isEventSocketAttachment(attachment)) {
|
|
20380
|
+
return Response.json(
|
|
20381
|
+
{ error: "Missing authenticated event subscription" },
|
|
20382
|
+
{ status: 401 }
|
|
20383
|
+
);
|
|
20384
|
+
}
|
|
20247
20385
|
const pair = new WebSocketPair();
|
|
20248
20386
|
const [client, server] = Object.values(pair);
|
|
20249
20387
|
this.ctx.acceptWebSocket(server);
|
|
20250
|
-
server.serializeAttachment(
|
|
20388
|
+
server.serializeAttachment(attachment);
|
|
20251
20389
|
this.eventSockets.add(server);
|
|
20252
20390
|
return new Response(null, {
|
|
20253
20391
|
status: 101,
|
|
@@ -20268,17 +20406,23 @@ ${result ?? error ?? "No result content."}${attachmentSummary}`;
|
|
|
20268
20406
|
const thread = await this.getThread(threadId);
|
|
20269
20407
|
if (!thread) return;
|
|
20270
20408
|
const eventThread = await this.toThreadEventPayload(thread);
|
|
20271
|
-
this.broadcastEvent(
|
|
20409
|
+
this.broadcastEvent(
|
|
20410
|
+
{ type: "thread_updated", thread: eventThread },
|
|
20411
|
+
thread.user_id
|
|
20412
|
+
);
|
|
20272
20413
|
}
|
|
20273
20414
|
/**
|
|
20274
|
-
* Broadcast an event to
|
|
20415
|
+
* Broadcast an event only to its owner or an explicitly all-scoped admin.
|
|
20275
20416
|
*/
|
|
20276
|
-
broadcastEvent(event) {
|
|
20417
|
+
broadcastEvent(event, ownerUserId) {
|
|
20277
20418
|
const payload = JSON.stringify(event);
|
|
20278
20419
|
for (const ws of Array.from(this.eventSockets)) {
|
|
20279
20420
|
try {
|
|
20280
20421
|
if (ws.readyState === WebSocket.OPEN) {
|
|
20281
|
-
ws.
|
|
20422
|
+
const attachment = ws.deserializeAttachment();
|
|
20423
|
+
if (isEventSocketAttachment(attachment) && eventSocketCanReceive(attachment, ownerUserId)) {
|
|
20424
|
+
ws.send(payload);
|
|
20425
|
+
}
|
|
20282
20426
|
} else {
|
|
20283
20427
|
this.eventSockets.delete(ws);
|
|
20284
20428
|
}
|
|
@@ -20287,6 +20431,15 @@ ${result ?? error ?? "No result content."}${attachmentSummary}`;
|
|
|
20287
20431
|
}
|
|
20288
20432
|
}
|
|
20289
20433
|
}
|
|
20434
|
+
/** Resolve a thread owner without decrypting its env or loading the row. */
|
|
20435
|
+
async getThreadOwnerId(threadId) {
|
|
20436
|
+
const cursor = await this.ctx.storage.sql.exec(
|
|
20437
|
+
`SELECT user_id FROM threads WHERE id = ? LIMIT 1`,
|
|
20438
|
+
threadId
|
|
20439
|
+
);
|
|
20440
|
+
const rows = cursor.toArray();
|
|
20441
|
+
return rows[0]?.user_id;
|
|
20442
|
+
}
|
|
20290
20443
|
/**
|
|
20291
20444
|
* WebSocket Hibernation API handler for incoming messages
|
|
20292
20445
|
* Called when a message is received on a hibernated WebSocket
|
|
@@ -28541,6 +28694,6 @@ init_context();
|
|
|
28541
28694
|
init_ProviderRegistry();
|
|
28542
28695
|
init_types2();
|
|
28543
28696
|
|
|
28544
|
-
export { CLIENT_STREAM_CHUNK_BYTES, CodeExecutionBridge, DurableAgentBuilder, DurableThread, DurableUserHub, FlowStateSdk, NamespaceResolutionError, ProviderRegistry, ThreadWatchdog, authenticate, buildImageDescription, callClient, callClientStream, cat, createNamespaceContext, createThreadEndpointHandler, decodeStreamChunk, defineController2 as defineController, emitThreadEvent, encodeStreamChunk, enhanceFlowState, exists, find, forceTurn, generateImageDescription, getFileStats, getMessages, getMessagesToSummarize, getShortName, getThumbnail, getUnsummarizedImageAttachments, getVisibleAgentNames, getVisibleModelNames, getVisiblePromptNames, getVisibleToolNames, grep, hasImageAttachments, head, injectMessage, isQualifiedName, linkFile, mkdir, move, optimizeImageContext, parseQualifiedName, qualifyName, queueTool, readFile, readdir, reloadHistory, rename, replaceImagesWithDescriptions, requireAdmin, requireAuth, resolveAgent, resolveHook, resolveModel, resolvePrompt, resolveTool, rmdir, stat, supportsClientForwarding, tail, unlink, updateThread, writeFile, writeImage };
|
|
28697
|
+
export { CLIENT_STREAM_CHUNK_BYTES, CodeExecutionBridge, DurableAgentBuilder, DurableThread, DurableUserHub, FlowStateSdk, NamespaceResolutionError, ProviderRegistry, ThreadWatchdog, authenticate, buildImageDescription, callClient, callClientStream, canAccessThread, cat, createNamespaceContext, createThreadEndpointHandler, decodeStreamChunk, defineController2 as defineController, emitThreadEvent, encodeStreamChunk, enhanceFlowState, exists, find, forceTurn, generateImageDescription, getFileStats, getMessages, getMessagesToSummarize, getShortName, getThumbnail, getUnsummarizedImageAttachments, getVisibleAgentNames, getVisibleModelNames, getVisiblePromptNames, getVisibleToolNames, grep, hasImageAttachments, head, injectMessage, isAdminOnlyApiRoute, isHostedInstance, isPublicApiRoute, isQualifiedName, isTrustedLocalDevelopmentRequest, linkFile, mkdir, move, optimizeImageContext, parseQualifiedName, qualifyName, queueTool, readFile, readdir, reloadHistory, rename, replaceImagesWithDescriptions, requireAdmin, requireAuth, resolveAgent, resolveHook, resolveModel, resolvePrompt, resolveTool, rmdir, stat, supportsClientForwarding, tail, unlink, updateThread, writeFile, writeImage };
|
|
28545
28698
|
//# sourceMappingURL=runtime.js.map
|
|
28546
28699
|
//# sourceMappingURL=runtime.js.map
|