@agentuity/server 0.0.105 → 0.0.106
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/api/api.d.ts +11 -6
- package/dist/api/api.d.ts.map +1 -1
- package/dist/api/api.js +21 -13
- package/dist/api/api.js.map +1 -1
- package/dist/api/index.d.ts +1 -0
- package/dist/api/index.d.ts.map +1 -1
- package/dist/api/index.js +1 -0
- package/dist/api/index.js.map +1 -1
- package/dist/api/project/deploy.d.ts +0 -6
- package/dist/api/project/deploy.d.ts.map +1 -1
- package/dist/api/project/deploy.js +0 -2
- package/dist/api/project/deploy.js.map +1 -1
- package/dist/api/project/get.d.ts +2 -1
- package/dist/api/project/get.d.ts.map +1 -1
- package/dist/api/project/get.js +10 -2
- package/dist/api/project/get.js.map +1 -1
- package/dist/api/region/create.d.ts +2 -0
- package/dist/api/region/create.d.ts.map +1 -1
- package/dist/api/region/create.js +1 -0
- package/dist/api/region/create.js.map +1 -1
- package/dist/api/region/delete.d.ts +12 -2
- package/dist/api/region/delete.d.ts.map +1 -1
- package/dist/api/region/delete.js +6 -1
- package/dist/api/region/delete.js.map +1 -1
- package/dist/api/region/resources.d.ts +4 -0
- package/dist/api/region/resources.d.ts.map +1 -1
- package/dist/api/region/resources.js +2 -0
- package/dist/api/region/resources.js.map +1 -1
- package/dist/api/sandbox/client.d.ts +125 -0
- package/dist/api/sandbox/client.d.ts.map +1 -0
- package/dist/api/sandbox/client.js +202 -0
- package/dist/api/sandbox/client.js.map +1 -0
- package/dist/api/sandbox/create.d.ts +24 -0
- package/dist/api/sandbox/create.d.ts.map +1 -0
- package/dist/api/sandbox/create.js +133 -0
- package/dist/api/sandbox/create.js.map +1 -0
- package/dist/api/sandbox/destroy.d.ts +14 -0
- package/dist/api/sandbox/destroy.d.ts.map +1 -0
- package/dist/api/sandbox/destroy.js +25 -0
- package/dist/api/sandbox/destroy.js.map +1 -0
- package/dist/api/sandbox/execute.d.ts +18 -0
- package/dist/api/sandbox/execute.d.ts.map +1 -0
- package/dist/api/sandbox/execute.js +77 -0
- package/dist/api/sandbox/execute.js.map +1 -0
- package/dist/api/sandbox/execution.d.ts +46 -0
- package/dist/api/sandbox/execution.d.ts.map +1 -0
- package/dist/api/sandbox/execution.js +101 -0
- package/dist/api/sandbox/execution.js.map +1 -0
- package/dist/api/sandbox/files.d.ts +41 -0
- package/dist/api/sandbox/files.d.ts.map +1 -0
- package/dist/api/sandbox/files.js +91 -0
- package/dist/api/sandbox/files.js.map +1 -0
- package/dist/api/sandbox/get.d.ts +16 -0
- package/dist/api/sandbox/get.d.ts.map +1 -0
- package/dist/api/sandbox/get.js +57 -0
- package/dist/api/sandbox/get.js.map +1 -0
- package/dist/api/sandbox/index.d.ts +22 -0
- package/dist/api/sandbox/index.d.ts.map +1 -0
- package/dist/api/sandbox/index.js +12 -0
- package/dist/api/sandbox/index.js.map +1 -0
- package/dist/api/sandbox/list.d.ts +15 -0
- package/dist/api/sandbox/list.d.ts.map +1 -0
- package/dist/api/sandbox/list.js +75 -0
- package/dist/api/sandbox/list.js.map +1 -0
- package/dist/api/sandbox/run.d.ts +28 -0
- package/dist/api/sandbox/run.d.ts.map +1 -0
- package/dist/api/sandbox/run.js +269 -0
- package/dist/api/sandbox/run.js.map +1 -0
- package/dist/api/sandbox/snapshot.d.ts +89 -0
- package/dist/api/sandbox/snapshot.d.ts.map +1 -0
- package/dist/api/sandbox/snapshot.js +140 -0
- package/dist/api/sandbox/snapshot.js.map +1 -0
- package/dist/api/sandbox/util.d.ts +37 -0
- package/dist/api/sandbox/util.d.ts.map +1 -0
- package/dist/api/sandbox/util.js +45 -0
- package/dist/api/sandbox/util.js.map +1 -0
- package/dist/config.d.ts +1 -0
- package/dist/config.d.ts.map +1 -1
- package/dist/config.js +1 -0
- package/dist/config.js.map +1 -1
- package/dist/runtime-bootstrap.d.ts.map +1 -1
- package/dist/runtime-bootstrap.js +3 -0
- package/dist/runtime-bootstrap.js.map +1 -1
- package/package.json +4 -4
- package/src/api/api.ts +33 -13
- package/src/api/index.ts +1 -0
- package/src/api/project/deploy.ts +0 -2
- package/src/api/project/get.ts +10 -2
- package/src/api/region/create.ts +1 -0
- package/src/api/region/delete.ts +9 -2
- package/src/api/region/resources.ts +2 -0
- package/src/api/sandbox/client.ts +349 -0
- package/src/api/sandbox/create.ts +166 -0
- package/src/api/sandbox/destroy.ts +41 -0
- package/src/api/sandbox/execute.ts +102 -0
- package/src/api/sandbox/execution.ts +154 -0
- package/src/api/sandbox/files.ts +138 -0
- package/src/api/sandbox/get.ts +74 -0
- package/src/api/sandbox/index.ts +35 -0
- package/src/api/sandbox/list.ts +94 -0
- package/src/api/sandbox/run.ts +360 -0
- package/src/api/sandbox/snapshot.ts +247 -0
- package/src/api/sandbox/util.ts +55 -0
- package/src/config.ts +2 -0
- package/src/runtime-bootstrap.ts +3 -0
|
@@ -0,0 +1,166 @@
|
|
|
1
|
+
import { z } from 'zod';
|
|
2
|
+
import { APIClient, APIResponseSchema } from '../api';
|
|
3
|
+
import { SandboxResponseError, API_VERSION } from './util';
|
|
4
|
+
import type { SandboxCreateOptions, SandboxStatus } from '@agentuity/core';
|
|
5
|
+
|
|
6
|
+
const SandboxCreateRequestSchema = z
|
|
7
|
+
.object({
|
|
8
|
+
resources: z
|
|
9
|
+
.object({
|
|
10
|
+
memory: z.string().optional().describe('Memory limit (e.g., "512Mi", "1Gi")'),
|
|
11
|
+
cpu: z.string().optional().describe('CPU limit (e.g., "0.5", "1")'),
|
|
12
|
+
disk: z.string().optional().describe('Disk size limit (e.g., "1Gi", "10Gi")'),
|
|
13
|
+
})
|
|
14
|
+
.optional()
|
|
15
|
+
.describe('Resource constraints for the sandbox'),
|
|
16
|
+
env: z
|
|
17
|
+
.record(z.string(), z.string())
|
|
18
|
+
.optional()
|
|
19
|
+
.describe('Environment variables to set in the sandbox'),
|
|
20
|
+
network: z
|
|
21
|
+
.object({
|
|
22
|
+
enabled: z.boolean().optional().describe('Whether network access is enabled'),
|
|
23
|
+
})
|
|
24
|
+
.optional()
|
|
25
|
+
.describe('Network configuration for the sandbox'),
|
|
26
|
+
stream: z
|
|
27
|
+
.object({
|
|
28
|
+
stdout: z.string().optional().describe('Stream ID for stdout output'),
|
|
29
|
+
stderr: z.string().optional().describe('Stream ID for stderr output'),
|
|
30
|
+
stdin: z.string().optional().describe('Stream ID for stdin input'),
|
|
31
|
+
timestamps: z.boolean().optional().describe('Whether to include timestamps in output'),
|
|
32
|
+
})
|
|
33
|
+
.optional()
|
|
34
|
+
.describe('Stream configuration for I/O redirection'),
|
|
35
|
+
timeout: z
|
|
36
|
+
.object({
|
|
37
|
+
idle: z.string().optional().describe('Idle timeout duration (e.g., "5m", "1h")'),
|
|
38
|
+
execution: z.string().optional().describe('Maximum execution time (e.g., "30m", "2h")'),
|
|
39
|
+
})
|
|
40
|
+
.optional()
|
|
41
|
+
.describe('Timeout settings for the sandbox'),
|
|
42
|
+
command: z
|
|
43
|
+
.object({
|
|
44
|
+
exec: z.array(z.string()).describe('Command and arguments to execute'),
|
|
45
|
+
files: z
|
|
46
|
+
.array(
|
|
47
|
+
z.object({
|
|
48
|
+
path: z
|
|
49
|
+
.string()
|
|
50
|
+
.describe('Path to the file relative to the sandbox workspace'),
|
|
51
|
+
content: z.string().describe('Base64-encoded file content'),
|
|
52
|
+
})
|
|
53
|
+
)
|
|
54
|
+
.optional()
|
|
55
|
+
.describe('Files to write before execution'),
|
|
56
|
+
mode: z
|
|
57
|
+
.enum(['oneshot', 'interactive'])
|
|
58
|
+
.optional()
|
|
59
|
+
.describe('Execution mode: oneshot runs once, interactive keeps running'),
|
|
60
|
+
})
|
|
61
|
+
.optional()
|
|
62
|
+
.describe('Initial command to run in the sandbox'),
|
|
63
|
+
snapshot: z.string().optional().describe('Snapshot ID to restore the sandbox from'),
|
|
64
|
+
dependencies: z
|
|
65
|
+
.array(z.string())
|
|
66
|
+
.optional()
|
|
67
|
+
.describe('Apt packages to install when creating the sandbox'),
|
|
68
|
+
})
|
|
69
|
+
.describe('Request body for creating a new sandbox');
|
|
70
|
+
|
|
71
|
+
const SandboxCreateDataSchema = z
|
|
72
|
+
.object({
|
|
73
|
+
sandboxId: z.string().describe('Unique identifier for the created sandbox'),
|
|
74
|
+
status: z
|
|
75
|
+
.enum(['creating', 'idle', 'running', 'terminated', 'failed'])
|
|
76
|
+
.describe('Current status of the sandbox'),
|
|
77
|
+
stdoutStreamId: z.string().optional().describe('Stream ID for reading stdout'),
|
|
78
|
+
stdoutStreamUrl: z.string().optional().describe('URL for streaming stdout output'),
|
|
79
|
+
stderrStreamId: z.string().optional().describe('Stream ID for reading stderr'),
|
|
80
|
+
stderrStreamUrl: z.string().optional().describe('URL for streaming stderr output'),
|
|
81
|
+
})
|
|
82
|
+
.describe('Response data from sandbox creation');
|
|
83
|
+
|
|
84
|
+
const SandboxCreateResponseSchema = APIResponseSchema(SandboxCreateDataSchema);
|
|
85
|
+
|
|
86
|
+
export interface SandboxCreateResponse {
|
|
87
|
+
sandboxId: string;
|
|
88
|
+
status: SandboxStatus;
|
|
89
|
+
stdoutStreamId?: string;
|
|
90
|
+
stdoutStreamUrl?: string;
|
|
91
|
+
stderrStreamId?: string;
|
|
92
|
+
stderrStreamUrl?: string;
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
export interface SandboxCreateParams {
|
|
96
|
+
options?: SandboxCreateOptions;
|
|
97
|
+
orgId?: string;
|
|
98
|
+
}
|
|
99
|
+
|
|
100
|
+
/**
|
|
101
|
+
* Creates a new sandbox instance.
|
|
102
|
+
*
|
|
103
|
+
* @param client - The API client to use for the request
|
|
104
|
+
* @param params - Parameters for creating the sandbox
|
|
105
|
+
* @returns The created sandbox response including sandbox ID and stream URLs
|
|
106
|
+
* @throws {SandboxResponseError} If the sandbox creation fails
|
|
107
|
+
*/
|
|
108
|
+
export async function sandboxCreate(
|
|
109
|
+
client: APIClient,
|
|
110
|
+
params: SandboxCreateParams = {}
|
|
111
|
+
): Promise<SandboxCreateResponse> {
|
|
112
|
+
const { options = {}, orgId } = params;
|
|
113
|
+
const body: z.infer<typeof SandboxCreateRequestSchema> = {};
|
|
114
|
+
|
|
115
|
+
if (options.resources) {
|
|
116
|
+
body.resources = options.resources;
|
|
117
|
+
}
|
|
118
|
+
if (options.env) {
|
|
119
|
+
body.env = options.env;
|
|
120
|
+
}
|
|
121
|
+
if (options.network) {
|
|
122
|
+
body.network = options.network;
|
|
123
|
+
}
|
|
124
|
+
if (options.stream) {
|
|
125
|
+
body.stream = options.stream;
|
|
126
|
+
}
|
|
127
|
+
if (options.timeout) {
|
|
128
|
+
body.timeout = options.timeout;
|
|
129
|
+
}
|
|
130
|
+
if (options.command) {
|
|
131
|
+
body.command = {
|
|
132
|
+
exec: options.command.exec,
|
|
133
|
+
mode: options.command.mode,
|
|
134
|
+
files: options.command.files?.map((f) => ({
|
|
135
|
+
path: f.path,
|
|
136
|
+
content: f.content.toString('base64'),
|
|
137
|
+
})),
|
|
138
|
+
};
|
|
139
|
+
}
|
|
140
|
+
if (options.snapshot) {
|
|
141
|
+
body.snapshot = options.snapshot;
|
|
142
|
+
}
|
|
143
|
+
if (options.dependencies && options.dependencies.length > 0) {
|
|
144
|
+
body.dependencies = options.dependencies;
|
|
145
|
+
}
|
|
146
|
+
|
|
147
|
+
const queryParams = new URLSearchParams();
|
|
148
|
+
if (orgId) {
|
|
149
|
+
queryParams.set('orgId', orgId);
|
|
150
|
+
}
|
|
151
|
+
const queryString = queryParams.toString();
|
|
152
|
+
const url = `/sandbox/${API_VERSION}${queryString ? `?${queryString}` : ''}`;
|
|
153
|
+
|
|
154
|
+
const resp = await client.post<z.infer<typeof SandboxCreateResponseSchema>>(
|
|
155
|
+
url,
|
|
156
|
+
body,
|
|
157
|
+
SandboxCreateResponseSchema,
|
|
158
|
+
SandboxCreateRequestSchema
|
|
159
|
+
);
|
|
160
|
+
|
|
161
|
+
if (resp.success) {
|
|
162
|
+
return resp.data;
|
|
163
|
+
}
|
|
164
|
+
|
|
165
|
+
throw new SandboxResponseError({ message: resp.message });
|
|
166
|
+
}
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
import { z } from 'zod';
|
|
2
|
+
import { APIClient, APIResponseSchemaNoData } from '../api';
|
|
3
|
+
import { SandboxResponseError, API_VERSION } from './util';
|
|
4
|
+
|
|
5
|
+
const DestroyResponseSchema = APIResponseSchemaNoData();
|
|
6
|
+
|
|
7
|
+
export interface SandboxDestroyParams {
|
|
8
|
+
sandboxId: string;
|
|
9
|
+
orgId?: string;
|
|
10
|
+
}
|
|
11
|
+
|
|
12
|
+
/**
|
|
13
|
+
* Destroys a sandbox and releases all associated resources.
|
|
14
|
+
*
|
|
15
|
+
* @param client - The API client to use for the request
|
|
16
|
+
* @param params - Parameters including the sandbox ID to destroy
|
|
17
|
+
* @throws {SandboxResponseError} If the sandbox is not found or destruction fails
|
|
18
|
+
*/
|
|
19
|
+
export async function sandboxDestroy(
|
|
20
|
+
client: APIClient,
|
|
21
|
+
params: SandboxDestroyParams
|
|
22
|
+
): Promise<void> {
|
|
23
|
+
const { sandboxId, orgId } = params;
|
|
24
|
+
const queryParams = new URLSearchParams();
|
|
25
|
+
if (orgId) {
|
|
26
|
+
queryParams.set('orgId', orgId);
|
|
27
|
+
}
|
|
28
|
+
const queryString = queryParams.toString();
|
|
29
|
+
const url = `/sandbox/${API_VERSION}/${sandboxId}${queryString ? `?${queryString}` : ''}`;
|
|
30
|
+
|
|
31
|
+
const resp = await client.delete<z.infer<typeof DestroyResponseSchema>>(
|
|
32
|
+
url,
|
|
33
|
+
DestroyResponseSchema
|
|
34
|
+
);
|
|
35
|
+
|
|
36
|
+
if (resp.success) {
|
|
37
|
+
return;
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
throw new SandboxResponseError({ message: resp.message, sandboxId });
|
|
41
|
+
}
|
|
@@ -0,0 +1,102 @@
|
|
|
1
|
+
import { z } from 'zod';
|
|
2
|
+
import { APIClient, APIResponseSchema } from '../api';
|
|
3
|
+
import { SandboxResponseError, API_VERSION } from './util';
|
|
4
|
+
import { FileToWriteSchema } from './files';
|
|
5
|
+
import type { ExecuteOptions, Execution, ExecutionStatus } from '@agentuity/core';
|
|
6
|
+
|
|
7
|
+
const ExecuteRequestSchema = z
|
|
8
|
+
.object({
|
|
9
|
+
command: z.array(z.string()).describe('Command and arguments to execute'),
|
|
10
|
+
files: z.array(FileToWriteSchema).optional().describe('Files to write before execution'),
|
|
11
|
+
timeout: z.string().optional().describe('Execution timeout (e.g., "30s", "5m")'),
|
|
12
|
+
stream: z
|
|
13
|
+
.object({
|
|
14
|
+
stdout: z.string().optional().describe('Stream ID for stdout output'),
|
|
15
|
+
stderr: z.string().optional().describe('Stream ID for stderr output'),
|
|
16
|
+
timestamps: z.boolean().optional().describe('Whether to include timestamps in output'),
|
|
17
|
+
})
|
|
18
|
+
.optional()
|
|
19
|
+
.describe('Stream configuration for output redirection'),
|
|
20
|
+
})
|
|
21
|
+
.describe('Request body for executing a command in a sandbox');
|
|
22
|
+
|
|
23
|
+
const ExecuteDataSchema = z
|
|
24
|
+
.object({
|
|
25
|
+
executionId: z.string().describe('Unique identifier for the execution'),
|
|
26
|
+
status: z
|
|
27
|
+
.enum(['queued', 'running', 'completed', 'failed', 'timeout', 'cancelled'])
|
|
28
|
+
.describe('Current status of the execution'),
|
|
29
|
+
exitCode: z.number().optional().describe('Exit code of the executed command'),
|
|
30
|
+
durationMs: z.number().optional().describe('Execution duration in milliseconds'),
|
|
31
|
+
stdoutStreamUrl: z.string().optional().describe('URL for streaming stdout output'),
|
|
32
|
+
stderrStreamUrl: z.string().optional().describe('URL for streaming stderr output'),
|
|
33
|
+
})
|
|
34
|
+
.describe('Response data from command execution');
|
|
35
|
+
|
|
36
|
+
const ExecuteResponseSchema = APIResponseSchema(ExecuteDataSchema);
|
|
37
|
+
|
|
38
|
+
export interface SandboxExecuteParams {
|
|
39
|
+
sandboxId: string;
|
|
40
|
+
options: ExecuteOptions;
|
|
41
|
+
orgId?: string;
|
|
42
|
+
signal?: AbortSignal;
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
/**
|
|
46
|
+
* Executes a command in an existing sandbox.
|
|
47
|
+
*
|
|
48
|
+
* @param client - The API client to use for the request
|
|
49
|
+
* @param params - Parameters including sandbox ID and execution options
|
|
50
|
+
* @returns The execution result including status and stream URLs
|
|
51
|
+
* @throws {SandboxResponseError} If the execution request fails
|
|
52
|
+
*/
|
|
53
|
+
export async function sandboxExecute(
|
|
54
|
+
client: APIClient,
|
|
55
|
+
params: SandboxExecuteParams
|
|
56
|
+
): Promise<Execution> {
|
|
57
|
+
const { sandboxId, options, orgId, signal } = params;
|
|
58
|
+
const body: z.infer<typeof ExecuteRequestSchema> = {
|
|
59
|
+
command: options.command,
|
|
60
|
+
};
|
|
61
|
+
|
|
62
|
+
if (options.files) {
|
|
63
|
+
body.files = options.files.map((f) => ({
|
|
64
|
+
path: f.path,
|
|
65
|
+
content: f.content.toString('base64'),
|
|
66
|
+
}));
|
|
67
|
+
}
|
|
68
|
+
if (options.timeout) {
|
|
69
|
+
body.timeout = options.timeout;
|
|
70
|
+
}
|
|
71
|
+
if (options.stream) {
|
|
72
|
+
body.stream = options.stream;
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
const queryParams = new URLSearchParams();
|
|
76
|
+
if (orgId) {
|
|
77
|
+
queryParams.set('orgId', orgId);
|
|
78
|
+
}
|
|
79
|
+
const queryString = queryParams.toString();
|
|
80
|
+
const url = `/sandbox/${API_VERSION}/${sandboxId}/execute${queryString ? `?${queryString}` : ''}`;
|
|
81
|
+
|
|
82
|
+
const resp = await client.post<z.infer<typeof ExecuteResponseSchema>>(
|
|
83
|
+
url,
|
|
84
|
+
body,
|
|
85
|
+
ExecuteResponseSchema,
|
|
86
|
+
ExecuteRequestSchema,
|
|
87
|
+
signal ?? options.signal
|
|
88
|
+
);
|
|
89
|
+
|
|
90
|
+
if (resp.success) {
|
|
91
|
+
return {
|
|
92
|
+
executionId: resp.data.executionId,
|
|
93
|
+
status: resp.data.status as ExecutionStatus,
|
|
94
|
+
exitCode: resp.data.exitCode,
|
|
95
|
+
durationMs: resp.data.durationMs,
|
|
96
|
+
stdoutStreamUrl: resp.data.stdoutStreamUrl,
|
|
97
|
+
stderrStreamUrl: resp.data.stderrStreamUrl,
|
|
98
|
+
};
|
|
99
|
+
}
|
|
100
|
+
|
|
101
|
+
throw new SandboxResponseError({ message: resp.message, sandboxId });
|
|
102
|
+
}
|
|
@@ -0,0 +1,154 @@
|
|
|
1
|
+
import { z } from 'zod';
|
|
2
|
+
import { APIClient, APIResponseSchema } from '../api';
|
|
3
|
+
import { SandboxResponseError, API_VERSION } from './util';
|
|
4
|
+
import type { ExecutionStatus } from '@agentuity/core';
|
|
5
|
+
|
|
6
|
+
const ExecutionInfoSchema = z
|
|
7
|
+
.object({
|
|
8
|
+
executionId: z.string().describe('Unique identifier for the execution'),
|
|
9
|
+
sandboxId: z.string().describe('ID of the sandbox where the execution ran'),
|
|
10
|
+
status: z
|
|
11
|
+
.enum(['queued', 'running', 'completed', 'failed', 'timeout', 'cancelled'])
|
|
12
|
+
.describe('Current status of the execution'),
|
|
13
|
+
command: z.array(z.string()).optional().describe('Command that was executed'),
|
|
14
|
+
exitCode: z.number().optional().describe('Exit code of the executed command'),
|
|
15
|
+
durationMs: z.number().optional().describe('Execution duration in milliseconds'),
|
|
16
|
+
startedAt: z.string().optional().describe('ISO timestamp when execution started'),
|
|
17
|
+
completedAt: z.string().optional().describe('ISO timestamp when execution completed'),
|
|
18
|
+
error: z.string().optional().describe('Error message if execution failed'),
|
|
19
|
+
stdoutStreamUrl: z.string().optional().describe('URL to stream stdout output'),
|
|
20
|
+
stderrStreamUrl: z.string().optional().describe('URL to stream stderr output'),
|
|
21
|
+
})
|
|
22
|
+
.describe('Detailed information about a command execution');
|
|
23
|
+
|
|
24
|
+
const ExecutionGetResponseSchema = APIResponseSchema(ExecutionInfoSchema);
|
|
25
|
+
|
|
26
|
+
const ExecutionListDataSchema = z
|
|
27
|
+
.object({
|
|
28
|
+
executions: z.array(ExecutionInfoSchema).describe('List of executions'),
|
|
29
|
+
})
|
|
30
|
+
.describe('List of executions for a sandbox');
|
|
31
|
+
|
|
32
|
+
const ExecutionListResponseSchema = APIResponseSchema(ExecutionListDataSchema);
|
|
33
|
+
|
|
34
|
+
export interface ExecutionInfo {
|
|
35
|
+
executionId: string;
|
|
36
|
+
sandboxId: string;
|
|
37
|
+
status: ExecutionStatus;
|
|
38
|
+
command?: string[];
|
|
39
|
+
exitCode?: number;
|
|
40
|
+
durationMs?: number;
|
|
41
|
+
startedAt?: string;
|
|
42
|
+
completedAt?: string;
|
|
43
|
+
error?: string;
|
|
44
|
+
stdoutStreamUrl?: string;
|
|
45
|
+
stderrStreamUrl?: string;
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
export interface ExecutionGetParams {
|
|
49
|
+
executionId: string;
|
|
50
|
+
orgId?: string;
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
/**
|
|
54
|
+
* Retrieves detailed information about a specific execution.
|
|
55
|
+
*
|
|
56
|
+
* @param client - The API client to use for the request
|
|
57
|
+
* @param params - Parameters including the execution ID
|
|
58
|
+
* @returns Detailed execution information including status, timing, and errors
|
|
59
|
+
* @throws {SandboxResponseError} If the execution is not found or request fails
|
|
60
|
+
*/
|
|
61
|
+
export async function executionGet(
|
|
62
|
+
client: APIClient,
|
|
63
|
+
params: ExecutionGetParams
|
|
64
|
+
): Promise<ExecutionInfo> {
|
|
65
|
+
const { executionId, orgId } = params;
|
|
66
|
+
const queryParams = new URLSearchParams();
|
|
67
|
+
if (orgId) {
|
|
68
|
+
queryParams.set('orgId', orgId);
|
|
69
|
+
}
|
|
70
|
+
const queryString = queryParams.toString();
|
|
71
|
+
const url = `/sandbox/${API_VERSION}/execution/${executionId}${queryString ? `?${queryString}` : ''}`;
|
|
72
|
+
|
|
73
|
+
const resp = await client.get<z.infer<typeof ExecutionGetResponseSchema>>(
|
|
74
|
+
url,
|
|
75
|
+
ExecutionGetResponseSchema
|
|
76
|
+
);
|
|
77
|
+
|
|
78
|
+
if (resp.success) {
|
|
79
|
+
return {
|
|
80
|
+
executionId: resp.data.executionId,
|
|
81
|
+
sandboxId: resp.data.sandboxId,
|
|
82
|
+
status: resp.data.status as ExecutionStatus,
|
|
83
|
+
command: resp.data.command,
|
|
84
|
+
exitCode: resp.data.exitCode,
|
|
85
|
+
durationMs: resp.data.durationMs,
|
|
86
|
+
startedAt: resp.data.startedAt,
|
|
87
|
+
completedAt: resp.data.completedAt,
|
|
88
|
+
error: resp.data.error,
|
|
89
|
+
stdoutStreamUrl: resp.data.stdoutStreamUrl,
|
|
90
|
+
stderrStreamUrl: resp.data.stderrStreamUrl,
|
|
91
|
+
};
|
|
92
|
+
}
|
|
93
|
+
|
|
94
|
+
throw new SandboxResponseError({ message: resp.message, executionId });
|
|
95
|
+
}
|
|
96
|
+
|
|
97
|
+
export interface ExecutionListParams {
|
|
98
|
+
sandboxId: string;
|
|
99
|
+
orgId?: string;
|
|
100
|
+
limit?: number;
|
|
101
|
+
}
|
|
102
|
+
|
|
103
|
+
export interface ExecutionListResponse {
|
|
104
|
+
executions: ExecutionInfo[];
|
|
105
|
+
}
|
|
106
|
+
|
|
107
|
+
/**
|
|
108
|
+
* Lists all executions for a specific sandbox.
|
|
109
|
+
*
|
|
110
|
+
* @param client - The API client to use for the request
|
|
111
|
+
* @param params - Parameters including the sandbox ID and optional limit
|
|
112
|
+
* @returns List of execution information for the sandbox
|
|
113
|
+
* @throws {SandboxResponseError} If the sandbox is not found or request fails
|
|
114
|
+
*/
|
|
115
|
+
export async function executionList(
|
|
116
|
+
client: APIClient,
|
|
117
|
+
params: ExecutionListParams
|
|
118
|
+
): Promise<ExecutionListResponse> {
|
|
119
|
+
const { sandboxId, orgId, limit } = params;
|
|
120
|
+
const queryParams = new URLSearchParams();
|
|
121
|
+
if (orgId) {
|
|
122
|
+
queryParams.set('orgId', orgId);
|
|
123
|
+
}
|
|
124
|
+
if (limit !== undefined) {
|
|
125
|
+
queryParams.set('limit', String(limit));
|
|
126
|
+
}
|
|
127
|
+
const queryString = queryParams.toString();
|
|
128
|
+
const url = `/sandbox/${API_VERSION}/sandboxes/${sandboxId}/executions${queryString ? `?${queryString}` : ''}`;
|
|
129
|
+
|
|
130
|
+
const resp = await client.get<z.infer<typeof ExecutionListResponseSchema>>(
|
|
131
|
+
url,
|
|
132
|
+
ExecutionListResponseSchema
|
|
133
|
+
);
|
|
134
|
+
|
|
135
|
+
if (resp.success) {
|
|
136
|
+
return {
|
|
137
|
+
executions: resp.data.executions.map((exec) => ({
|
|
138
|
+
executionId: exec.executionId,
|
|
139
|
+
sandboxId: exec.sandboxId,
|
|
140
|
+
status: exec.status as ExecutionStatus,
|
|
141
|
+
command: exec.command,
|
|
142
|
+
exitCode: exec.exitCode,
|
|
143
|
+
durationMs: exec.durationMs,
|
|
144
|
+
startedAt: exec.startedAt,
|
|
145
|
+
completedAt: exec.completedAt,
|
|
146
|
+
error: exec.error,
|
|
147
|
+
stdoutStreamUrl: exec.stdoutStreamUrl,
|
|
148
|
+
stderrStreamUrl: exec.stderrStreamUrl,
|
|
149
|
+
})),
|
|
150
|
+
};
|
|
151
|
+
}
|
|
152
|
+
|
|
153
|
+
throw new SandboxResponseError({ message: resp.message, sandboxId });
|
|
154
|
+
}
|
|
@@ -0,0 +1,138 @@
|
|
|
1
|
+
import { z } from 'zod';
|
|
2
|
+
import { APIClient } from '../api';
|
|
3
|
+
import { SandboxResponseError, API_VERSION } from './util';
|
|
4
|
+
import type { FileToWrite } from '@agentuity/core';
|
|
5
|
+
|
|
6
|
+
export const FileToWriteSchema = z.object({
|
|
7
|
+
path: z.string().describe('Path to the file relative to the sandbox workspace'),
|
|
8
|
+
content: z.string().describe('Base64-encoded file content'),
|
|
9
|
+
});
|
|
10
|
+
|
|
11
|
+
const WriteFilesRequestSchema = z
|
|
12
|
+
.object({
|
|
13
|
+
files: z.array(FileToWriteSchema).describe('Array of files to write'),
|
|
14
|
+
})
|
|
15
|
+
.describe('Request body for writing files to a sandbox');
|
|
16
|
+
|
|
17
|
+
const WriteFilesDataSchema = z
|
|
18
|
+
.object({
|
|
19
|
+
filesWritten: z.number().describe('Number of files successfully written'),
|
|
20
|
+
})
|
|
21
|
+
.describe('Response data from writing files');
|
|
22
|
+
|
|
23
|
+
const WriteFilesResponseSchema = z.discriminatedUnion('success', [
|
|
24
|
+
z.object({
|
|
25
|
+
success: z.literal<false>(false),
|
|
26
|
+
message: z.string().describe('the error message'),
|
|
27
|
+
}),
|
|
28
|
+
z.object({
|
|
29
|
+
success: z.literal<true>(true),
|
|
30
|
+
data: WriteFilesDataSchema.optional(),
|
|
31
|
+
filesWritten: z.number().optional(),
|
|
32
|
+
}),
|
|
33
|
+
]);
|
|
34
|
+
|
|
35
|
+
export interface WriteFilesParams {
|
|
36
|
+
sandboxId: string;
|
|
37
|
+
files: FileToWrite[];
|
|
38
|
+
orgId?: string;
|
|
39
|
+
signal?: AbortSignal;
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
export interface WriteFilesResult {
|
|
43
|
+
filesWritten: number;
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
/**
|
|
47
|
+
* Writes files to a sandbox workspace.
|
|
48
|
+
*
|
|
49
|
+
* @param client - The API client to use for the request
|
|
50
|
+
* @param params - Parameters including sandbox ID and files to write
|
|
51
|
+
* @returns The result including number of files written
|
|
52
|
+
* @throws {SandboxResponseError} If the write request fails
|
|
53
|
+
*/
|
|
54
|
+
export async function sandboxWriteFiles(
|
|
55
|
+
client: APIClient,
|
|
56
|
+
params: WriteFilesParams
|
|
57
|
+
): Promise<WriteFilesResult> {
|
|
58
|
+
const { sandboxId, files, orgId, signal } = params;
|
|
59
|
+
|
|
60
|
+
const body: z.infer<typeof WriteFilesRequestSchema> = {
|
|
61
|
+
files: files.map((f) => ({
|
|
62
|
+
path: f.path,
|
|
63
|
+
content: f.content.toString('base64'),
|
|
64
|
+
})),
|
|
65
|
+
};
|
|
66
|
+
|
|
67
|
+
const queryParams = new URLSearchParams();
|
|
68
|
+
if (orgId) {
|
|
69
|
+
queryParams.set('orgId', orgId);
|
|
70
|
+
}
|
|
71
|
+
const queryString = queryParams.toString();
|
|
72
|
+
const url = `/fs/${API_VERSION}/${sandboxId}${queryString ? `?${queryString}` : ''}`;
|
|
73
|
+
|
|
74
|
+
const resp = await client.post<z.infer<typeof WriteFilesResponseSchema>>(
|
|
75
|
+
url,
|
|
76
|
+
body,
|
|
77
|
+
WriteFilesResponseSchema,
|
|
78
|
+
WriteFilesRequestSchema,
|
|
79
|
+
signal
|
|
80
|
+
);
|
|
81
|
+
|
|
82
|
+
if (resp.success) {
|
|
83
|
+
return {
|
|
84
|
+
filesWritten: resp.data?.filesWritten ?? resp.filesWritten ?? 0,
|
|
85
|
+
};
|
|
86
|
+
}
|
|
87
|
+
|
|
88
|
+
throw new SandboxResponseError({ message: resp.message, sandboxId });
|
|
89
|
+
}
|
|
90
|
+
|
|
91
|
+
export interface ReadFileParams {
|
|
92
|
+
sandboxId: string;
|
|
93
|
+
path: string;
|
|
94
|
+
orgId?: string;
|
|
95
|
+
signal?: AbortSignal;
|
|
96
|
+
}
|
|
97
|
+
|
|
98
|
+
/**
|
|
99
|
+
* Reads a file from a sandbox workspace.
|
|
100
|
+
*
|
|
101
|
+
* @param client - The API client to use for the request
|
|
102
|
+
* @param params - Parameters including sandbox ID and file path
|
|
103
|
+
* @returns A ReadableStream of the file contents
|
|
104
|
+
* @throws {SandboxResponseError} If the read request fails
|
|
105
|
+
*/
|
|
106
|
+
export async function sandboxReadFile(
|
|
107
|
+
client: APIClient,
|
|
108
|
+
params: ReadFileParams
|
|
109
|
+
): Promise<ReadableStream<Uint8Array>> {
|
|
110
|
+
const { sandboxId, path, orgId, signal } = params;
|
|
111
|
+
|
|
112
|
+
const queryParams = new URLSearchParams();
|
|
113
|
+
queryParams.set('path', path);
|
|
114
|
+
if (orgId) {
|
|
115
|
+
queryParams.set('orgId', orgId);
|
|
116
|
+
}
|
|
117
|
+
const queryString = queryParams.toString();
|
|
118
|
+
const url = `/fs/${API_VERSION}/${sandboxId}?${queryString}`;
|
|
119
|
+
|
|
120
|
+
const response = await client.rawGet(url, signal);
|
|
121
|
+
|
|
122
|
+
if (!response.ok) {
|
|
123
|
+
const text = await response.text().catch(() => 'Unknown error');
|
|
124
|
+
throw new SandboxResponseError({
|
|
125
|
+
message: `Failed to read file: ${response.status} ${text}`,
|
|
126
|
+
sandboxId,
|
|
127
|
+
});
|
|
128
|
+
}
|
|
129
|
+
|
|
130
|
+
if (!response.body) {
|
|
131
|
+
throw new SandboxResponseError({
|
|
132
|
+
message: 'No response body',
|
|
133
|
+
sandboxId,
|
|
134
|
+
});
|
|
135
|
+
}
|
|
136
|
+
|
|
137
|
+
return response.body;
|
|
138
|
+
}
|
|
@@ -0,0 +1,74 @@
|
|
|
1
|
+
import { z } from 'zod';
|
|
2
|
+
import { APIClient, APIResponseSchema } from '../api';
|
|
3
|
+
import { SandboxResponseError, API_VERSION } from './util';
|
|
4
|
+
import type { SandboxInfo, SandboxStatus } from '@agentuity/core';
|
|
5
|
+
|
|
6
|
+
const SandboxInfoDataSchema = z
|
|
7
|
+
.object({
|
|
8
|
+
sandboxId: z.string().describe('Unique identifier for the sandbox'),
|
|
9
|
+
status: z
|
|
10
|
+
.enum(['creating', 'idle', 'running', 'terminated', 'failed'])
|
|
11
|
+
.describe('Current status of the sandbox'),
|
|
12
|
+
createdAt: z.string().describe('ISO timestamp when the sandbox was created'),
|
|
13
|
+
region: z.string().optional().describe('Region where the sandbox is running'),
|
|
14
|
+
snapshotId: z.string().optional().describe('Snapshot ID this sandbox was created from'),
|
|
15
|
+
snapshotTag: z.string().optional().describe('Snapshot tag this sandbox was created from'),
|
|
16
|
+
executions: z.number().describe('Total number of executions in this sandbox'),
|
|
17
|
+
stdoutStreamUrl: z.string().optional().describe('URL for streaming stdout output'),
|
|
18
|
+
stderrStreamUrl: z.string().optional().describe('URL for streaming stderr output'),
|
|
19
|
+
dependencies: z
|
|
20
|
+
.array(z.string())
|
|
21
|
+
.optional()
|
|
22
|
+
.describe('Apt packages installed in the sandbox'),
|
|
23
|
+
})
|
|
24
|
+
.describe('Detailed information about a sandbox');
|
|
25
|
+
|
|
26
|
+
const SandboxGetResponseSchema = APIResponseSchema(SandboxInfoDataSchema);
|
|
27
|
+
|
|
28
|
+
export interface SandboxGetParams {
|
|
29
|
+
sandboxId: string;
|
|
30
|
+
orgId?: string;
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
/**
|
|
34
|
+
* Retrieves information about a specific sandbox.
|
|
35
|
+
*
|
|
36
|
+
* @param client - The API client to use for the request
|
|
37
|
+
* @param params - Parameters including the sandbox ID
|
|
38
|
+
* @returns Sandbox information including status, creation time, and execution count
|
|
39
|
+
* @throws {SandboxResponseError} If the sandbox is not found or request fails
|
|
40
|
+
*/
|
|
41
|
+
export async function sandboxGet(
|
|
42
|
+
client: APIClient,
|
|
43
|
+
params: SandboxGetParams
|
|
44
|
+
): Promise<SandboxInfo> {
|
|
45
|
+
const { sandboxId, orgId } = params;
|
|
46
|
+
const queryParams = new URLSearchParams();
|
|
47
|
+
if (orgId) {
|
|
48
|
+
queryParams.set('orgId', orgId);
|
|
49
|
+
}
|
|
50
|
+
const queryString = queryParams.toString();
|
|
51
|
+
const url = `/sandbox/${API_VERSION}/${sandboxId}${queryString ? `?${queryString}` : ''}`;
|
|
52
|
+
|
|
53
|
+
const resp = await client.get<z.infer<typeof SandboxGetResponseSchema>>(
|
|
54
|
+
url,
|
|
55
|
+
SandboxGetResponseSchema
|
|
56
|
+
);
|
|
57
|
+
|
|
58
|
+
if (resp.success) {
|
|
59
|
+
return {
|
|
60
|
+
sandboxId: resp.data.sandboxId,
|
|
61
|
+
status: resp.data.status as SandboxStatus,
|
|
62
|
+
createdAt: resp.data.createdAt,
|
|
63
|
+
region: resp.data.region,
|
|
64
|
+
snapshotId: resp.data.snapshotId,
|
|
65
|
+
snapshotTag: resp.data.snapshotTag,
|
|
66
|
+
executions: resp.data.executions,
|
|
67
|
+
stdoutStreamUrl: resp.data.stdoutStreamUrl,
|
|
68
|
+
stderrStreamUrl: resp.data.stderrStreamUrl,
|
|
69
|
+
dependencies: resp.data.dependencies,
|
|
70
|
+
};
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
throw new SandboxResponseError({ message: resp.message, sandboxId });
|
|
74
|
+
}
|