broods 0.6.0 → 0.6.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -17,14 +17,16 @@ bun add -g broods
17
17
  broods dev
18
18
  ```
19
19
 
20
- `ai` is an optional peer dependency. The CLI and the SDK both run without it —
21
- it is only needed to resolve the AI SDK types the SDK re-exports, so add it when
22
- you consume those types from TypeScript:
20
+ `ai` is a peer dependency. npm and bun install it for you; add it explicitly on
21
+ package managers that do not auto-install peers:
23
22
 
24
23
  ```bash
25
24
  npm install ai
26
25
  ```
27
26
 
27
+ The published types import from `ai` directly, so without it `defineAgent`'s
28
+ model options resolve to error types and a valid agent config fails to compile.
29
+
28
30
  ## Invoke an Agent
29
31
 
30
32
  ```ts
package/dist/account.d.ts CHANGED
@@ -664,10 +664,17 @@ interface ChannelRecordConfig {
664
664
  actorIds: string[];
665
665
  }>;
666
666
  }
667
+ /** The environment a tool belongs to. Tools with the same name in two environments are two tools. */
668
+ interface ToolScope {
669
+ project: string;
670
+ environment: string;
671
+ }
667
672
  /** Public uploaded-tool record returned by the tools routes. */
668
673
  interface AccountTool {
669
674
  accountId: string;
670
675
  toolId: string;
676
+ projectId: string;
677
+ environmentId: string;
671
678
  name: string;
672
679
  description: string;
673
680
  inputSchema: unknown;
@@ -852,8 +859,9 @@ declare class BroodsAccountClient {
852
859
  snapshotSandbox(sandboxId: string, reservationKey: string, name: string): Promise<SandboxSnapshotResult>;
853
860
  /** Mint a short-lived sealed ticket for an interactive PTY session on a persistent sandbox (`sandbox`/`lambda` providers). Throws on 404/403/409. */
854
861
  openSandboxTerminal(sandboxId: string, reservationKey: string): Promise<SandboxTerminalTicket>;
855
- listTools(): Promise<AccountTool[]>;
856
- createTool(input: CreateToolInput): Promise<AccountTool>;
862
+ /** Tools live in one environment, so the collection routes need a scope. Both fields are required. */
863
+ listTools(scope: ToolScope): Promise<AccountTool[]>;
864
+ createTool(scope: ToolScope, input: CreateToolInput): Promise<AccountTool>;
857
865
  getTool(toolId: string): Promise<AccountTool | null>;
858
866
  /** PATCH an uploaded tool. Omitting `bundle` keeps the stored bundle and runtime. Returns null when the tool is gone. */
859
867
  updateTool(toolId: string, patch: UpdateToolInput): Promise<AccountTool | null>;
@@ -907,4 +915,4 @@ declare class BroodsAccountClient {
907
915
  }
908
916
 
909
917
  export { BroodsAccountApiError, BroodsAccountClient, envPlaceholder };
910
- export type { AccountAgent, AccountChannel, AccountEnvVar, AccountPolicy, AccountSandbox, AccountTool, AccountWorkspace, BroodsAccount, BroodsAccountClientOptions, ChannelRecordConfig, CreateAgentResult, CreateToolInput, DeleteAccountResult, RotateSecretResult, SandboxLifecycleResult, SandboxSnapshotResult, SandboxTerminalTicket, SkillUploadInput, UpdateAgentInput, UpdateToolInput, WorkspaceFileEntry };
918
+ export type { AccountAgent, AccountChannel, AccountEnvVar, AccountPolicy, AccountSandbox, AccountTool, AccountWorkspace, BroodsAccount, BroodsAccountClientOptions, ChannelRecordConfig, CreateAgentResult, CreateToolInput, DeleteAccountResult, RotateSecretResult, SandboxLifecycleResult, SandboxSnapshotResult, SandboxTerminalTicket, SkillUploadInput, ToolScope, UpdateAgentInput, UpdateToolInput, WorkspaceFileEntry };
package/dist/account.js CHANGED
@@ -1 +1 @@
1
- import{a,b,c}from"./chunk-5pazmghy.js";import"./chunk-51a2zca3.js";export{b as BroodsAccountApiError,c as BroodsAccountClient,a as envPlaceholder};
1
+ import{a,b,c}from"./chunk-vmm9rm5v.js";import"./chunk-51a2zca3.js";export{b as BroodsAccountApiError,c as BroodsAccountClient,a as envPlaceholder};
@@ -0,0 +1,2 @@
1
+ var c=/^[A-Z][A-Z0-9_]*$/;function u(e){if(!c.test(e)||e.length>64)throw Error("envPlaceholder name must match /^[A-Z][A-Z0-9_]*$/ and be at most 64 characters.");return`\${${e}}`}class o extends Error{status;body;constructor(e,t,n,s){super(`${e} ${t} failed with ${n}: ${s}`);this.name="BroodsAccountApiError",this.status=n,this.body=s}}function i(e){return typeof process<"u"?process?.env?.[e]:void 0}function a(e){return`?${new URLSearchParams({project:e.project,environment:e.environment}).toString()}`}class l{baseUrl;accountSecret;fetchImpl;constructor(e={}){let t=e.baseUrl??i("BROODS_BASE_URL")??"https://gateway.broods.app",n=e.accountSecret??i("BROODS_ACCOUNT_SECRET");if(!n)throw Error("BroodsAccountClient requires an accountSecret (or BROODS_ACCOUNT_SECRET).");let s=t.length;while(s>0&&t.charCodeAt(s-1)===47)s-=1;this.baseUrl=t.slice(0,s),this.accountSecret=n,this.fetchImpl=e.fetch??fetch}async getAccount(){let e=await this.request("GET","/v1/account");if(!e)throw new o("GET","/v1/account",404,"Account not found");return e.account}async updateAccount(e){return(await this.request("PATCH","/v1/account",e))?.account??null}async rotateSecret(){let e=await this.request("POST","/v1/account/rotate-secret");if(!e)throw new o("POST","/v1/account/rotate-secret",404,"Account not found");return e}async deleteAccount(){return await this.request("DELETE","/v1/account")??{deleted:!1}}webhookUrl(e,t){let n=[e,t].map(encodeURIComponent);return`${this.baseUrl}/webhooks/${n.join("/")}`}async listAgents(){return(await this.request("GET","/v1/agents"))?.agents??[]}async createAgent(e){let t=await this.request("POST","/v1/agents",e);if(!t)throw new o("POST","/v1/agents",404,"Not found");return t}async getAgent(e){return await this.request("GET",`/v1/agents/${encodeURIComponent(e)}`)}async updateAgent(e,t){return await this.request("PATCH",`/v1/agents/${encodeURIComponent(e)}`,t)}async deleteAgent(e){return(await this.request("DELETE",`/v1/agents/${encodeURIComponent(e)}`))?.deleted??!1}async listEnvVars(){return(await this.request("GET","/v1/env"))?.env??[]}async setEnvVar(e,t){await this.request("PUT",`/v1/env/${encodeURIComponent(e)}`,{value:t})}async deleteEnvVar(e){return(await this.request("DELETE",`/v1/env/${encodeURIComponent(e)}`))?.deleted??!1}async listCrons(){return(await this.request("GET","/v1/crons"))?.crons??[]}async createCron(e){let t=await this.request("POST","/v1/crons",e);if(!t)throw new o("POST","/v1/crons",404,"Not found");return t}async getCron(e){return await this.request("GET",`/v1/crons/${encodeURIComponent(e)}`)}async updateCron(e,t){return await this.request("PATCH",`/v1/crons/${encodeURIComponent(e)}`,t)}async deleteCron(e){return(await this.request("DELETE",`/v1/crons/${encodeURIComponent(e)}`))?.deleted??!1}async listCronRuns(e,t={}){let n=t.limit!==void 0?`?limit=${t.limit}`:"";return(await this.request("GET",`/v1/crons/${encodeURIComponent(e)}/runs${n}`))?.runs??[]}async listWorkspaces(){return(await this.request("GET","/v1/workspaces"))?.workspaces??[]}async createWorkspace(e){let t=await this.request("POST","/v1/workspaces",e);if(!t)throw new o("POST","/v1/workspaces",404,"Not found");return t}async getWorkspace(e){return await this.request("GET",`/v1/workspaces/${encodeURIComponent(e)}`)}async updateWorkspace(e,t){return await this.request("PATCH",`/v1/workspaces/${encodeURIComponent(e)}`,t)}async deleteWorkspace(e){return(await this.request("DELETE",`/v1/workspaces/${encodeURIComponent(e)}`))?.deleted??!1}async listWorkspaceFiles(e){return(await this.request("GET",`/v1/workspaces/${encodeURIComponent(e)}/files`))?.files??[]}async getWorkspaceFileUrl(e,t){let n=`?path=${encodeURIComponent(t)}`;return(await this.request("GET",`/v1/workspaces/${encodeURIComponent(e)}/files${n}`))?.url??null}async uploadWorkspaceFile(e,t){let n=`/v1/workspaces/${encodeURIComponent(e)}/files`,s=await this.request("POST",n,t);if(!s)throw new o("POST",n,404,"Workspace not found");return s.file}async renameWorkspaceFile(e,t,n){return(await this.request("PATCH",`/v1/workspaces/${encodeURIComponent(e)}/files`,{path:t,newPath:n}))?.renamed??!1}async deleteWorkspaceFile(e,t){return(await this.request("DELETE",`/v1/workspaces/${encodeURIComponent(e)}/files`,{path:t}))?.deleted??!1}async listSandboxes(){return(await this.request("GET","/v1/sandboxes"))?.sandboxes??[]}async createSandbox(e){let t=await this.request("POST","/v1/sandboxes",e);if(!t)throw new o("POST","/v1/sandboxes",404,"Not found");return t}async getSandbox(e){return await this.request("GET",`/v1/sandboxes/${encodeURIComponent(e)}`)}async updateSandbox(e,t){return await this.request("PATCH",`/v1/sandboxes/${encodeURIComponent(e)}`,t)}async deleteSandbox(e){return(await this.request("DELETE",`/v1/sandboxes/${encodeURIComponent(e)}`))?.deleted??!1}async suspendSandbox(e,t){return await this.sandboxAction(e,"suspend",{reservationKey:t})}async resumeSandbox(e,t){return await this.sandboxAction(e,"resume",{reservationKey:t})}async terminateSandbox(e,t){return await this.sandboxAction(e,"terminate",{reservationKey:t})}async snapshotSandbox(e,t,n){return await this.sandboxAction(e,"snapshot",{reservationKey:t,name:n})}async openSandboxTerminal(e,t){return await this.sandboxAction(e,"terminal",{reservationKey:t})}async listTools(e){return(await this.request("GET",`/v1/tools${a(e)}`))?.tools??[]}async createTool(e,t){let n=`/v1/tools${a(e)}`,s=await this.request("POST",n,t);if(!s)throw new o("POST",n,404,"Not found");return s}async getTool(e){return await this.request("GET",`/v1/tools/${encodeURIComponent(e)}`)}async updateTool(e,t){return await this.request("PATCH",`/v1/tools/${encodeURIComponent(e)}`,t)}async deleteTool(e){return(await this.request("DELETE",`/v1/tools/${encodeURIComponent(e)}`))?.deleted??!1}async listPolicies(){return(await this.request("GET","/v1/policies"))?.policies??[]}async createPolicy(e){let t=await this.request("POST","/v1/policies",e);if(!t)throw new o("POST","/v1/policies",404,"Not found");return t}async getPolicy(e){return await this.request("GET",`/v1/policies/${encodeURIComponent(e)}`)}async updatePolicy(e,t){return await this.request("PATCH",`/v1/policies/${encodeURIComponent(e)}`,t)}async deletePolicy(e){return(await this.request("DELETE",`/v1/policies/${encodeURIComponent(e)}`))?.deleted??!1}async listChannels(){return(await this.request("GET","/v1/channels"))?.channels??[]}async createChannel(e){let t=await this.request("POST","/v1/channels",e);if(!t)throw new o("POST","/v1/channels",404,"Not found");return t}async getChannel(e){return await this.request("GET",`/v1/channels/${encodeURIComponent(e)}`)}async updateChannel(e,t){return await this.request("PATCH",`/v1/channels/${encodeURIComponent(e)}`,t)}async deleteChannel(e){return(await this.request("DELETE",`/v1/channels/${encodeURIComponent(e)}`))?.deleted??!1}async listSkills(){return(await this.request("GET","/v1/skills"))?.skills??[]}async createSkill(e){let t=await this.request("POST","/v1/skills",e);if(!t)throw new o("POST","/v1/skills",404,"Not found");return t}async getSkill(e){return await this.request("GET",`/v1/skills/${encodeURIComponent(e)}`)}async uploadSkill(e,t){let n=`/v1/skills/${encodeURIComponent(e)}`,s=await this.request("PUT",n,t);if(!s)throw new o("PUT",n,404,"Skill not found");return s}async deleteSkill(e){return(await this.request("DELETE",`/v1/skills/${encodeURIComponent(e)}`))?.deleted??!1}async sandboxAction(e,t,n){let s=`/v1/sandboxes/${encodeURIComponent(e)}/${t}`,r=await this.request("POST",s,n);if(!r)throw new o("POST",s,404,"Sandbox not found");return r}async request(e,t,n){let s=await this.fetchImpl(`${this.baseUrl}${t}`,{method:e,headers:{Authorization:`Bearer ${this.accountSecret}`,...n!==void 0?{"Content-Type":"application/json"}:{}},...n!==void 0?{body:JSON.stringify(n)}:{}});if(s.status===404)return null;if(!s.ok)throw new o(e,t,s.status,await s.text());return await s.json()}}
2
+ export{u as a,o as b,l as c};