import { Template, TemplateBase } from '@declaw/sdk';
import type { BuildInfo, TemplateBuildStatus, CopyItem, TemplateBuildOpts, GetBuildStatusOpts } from '@declaw/sdk';
Templates let you pre-build sandbox images with specific packages, files, and environment variables. Once built, reference a template by alias in Sandbox.create({ template: 'my-alias' }).
TemplateBase
TemplateBase is a fluent class for defining template contents. Chain methods to build the definition, then pass it to Template.build().
import { TemplateBase } from '@declaw/sdk';
const template = new TemplateBase()
.fromBaseImage('ubuntu:22.04')
.aptInstall('python3', 'python3-pip', 'nodejs', 'npm')
.runCmd(['pip3', 'install', 'pandas', 'numpy'])
.copy('./local_setup.sh', '/usr/local/bin/setup.sh', 0o755)
.setEnvs({ PYTHONPATH: '/home/user', NODE_ENV: 'production' })
.setStartCmd('sleep infinity');
.fromBaseImage(image?)
Set the base Docker image.
image
string
default:"'ubuntu:22.04'"
Docker image tag.
Returns this
.aptInstall(...packages)
Install apt packages.
template.aptInstall('git', 'curl', 'jq');
One or more package names to install via apt-get install.
Returns this
.runCmd(cmds)
Add a build-time command (equivalent to a Dockerfile RUN).
template.runCmd(['pip3', 'install', 'torch', '--index-url', 'https://download.pytorch.org/whl/cpu']);
Command as an array of strings (executable + arguments).
Returns this
.copy(src, dst, mode?)
Copy a local file into the image at build time.
template.copy('./requirements.txt', '/app/requirements.txt');
template.copy('./startup.sh', '/usr/local/bin/startup.sh', 0o755);
Destination path inside the image.
Unix file permission bits (e.g. 0o755 for executable).
Returns this
.setEnvs(envs)
Set environment variables baked into the image.
template.setEnvs({ APP_ENV: 'production', PORT: '8080' });
envs
Record<string, string>
required
Key-value pairs to set as environment variables.
Returns this
.setStartCmd(cmd)
Set a command to run when the sandbox boots.
template.setStartCmd('python3 /app/server.py');
Shell command to execute on sandbox start.
Returns this
.toJSON()
Serialize the template to a JSON-friendly object for the API.
Returns Record<string, any>
Template
Template is a static class for submitting and querying template builds. All methods are async.
Template.build()
Submit a template build and wait for completion.
import { Template, TemplateBase } from '@declaw/sdk';
const template = new TemplateBase()
.aptInstall('python3-pip')
.runCmd(['pip3', 'install', 'pandas']);
const info: BuildInfo = await Template.build(template, 'data-analysis', {
cpuCount: 2,
memoryMb: 2048,
onBuildLogs: (log) => console.log(log),
apiKey: 'your-api-key',
domain: '104.198.24.180:8080',
});
console.log('Template ID:', info.templateId);
The template definition to build.
Human-readable name used as template in Sandbox.create().
TemplateBuildOpts
Number of CPUs for the build worker.
Memory in MB for the build worker.
Callback invoked for each log line during the build.
Per-request HTTP timeout in milliseconds.
Returns Promise<BuildInfo>
Template.buildInBackground()
Submit a template build and return immediately without waiting.
const info = await Template.buildInBackground(template, 'my-template', {
apiKey: 'your-api-key',
domain: '104.198.24.180:8080',
});
console.log('Build started:', info.buildId);
Parameters are the same as Template.build() except onBuildLogs is excluded.
Returns Promise<BuildInfo>
Template.getBuildStatus()
Poll the status of a background build.
const status = await Template.getBuildStatus('build-id', {
apiKey: 'your-api-key',
domain: '104.198.24.180:8080',
});
console.log(status.status); // "pending" | "running" | "succeeded" | "failed"
console.log(status.logs.at(-1)); // latest log line
Build ID from a previous build() or buildInBackground() call. Must be
alphanumeric with hyphens/underscores.
Optional: apiKey, domain, requestTimeout.
Returns Promise<TemplateBuildStatus>
Data models
BuildInfo
interface BuildInfo {
buildId: string;
status: string;
templateId?: string; // Set once build succeeds
}
TemplateBuildStatus
interface TemplateBuildStatus {
buildId: string;
status: string; // "pending" | "running" | "succeeded" | "failed"
logs: string[]; // Accumulated build log lines
}
CopyItem
interface CopyItem {
src: string;
dst: string;
mode?: number;
}
GetBuildStatusOpts
interface GetBuildStatusOpts {
apiKey?: string;
domain?: string;
requestTimeout?: number;
}
Polling a background build
import { Template, TemplateBase } from '@declaw/sdk';
const template = new TemplateBase()
.aptInstall('nodejs', 'npm')
.runCmd(['npm', 'install', '-g', 'typescript']);
const info = await Template.buildInBackground(template, 'node-ts', {
apiKey: 'your-api-key',
domain: '104.198.24.180:8080',
});
let status = await Template.getBuildStatus(info.buildId, {
apiKey: 'your-api-key',
domain: '104.198.24.180:8080',
});
while (status.status === 'pending' || status.status === 'running') {
await new Promise((r) => setTimeout(r, 3000));
status = await Template.getBuildStatus(info.buildId, {
apiKey: 'your-api-key',
domain: '104.198.24.180:8080',
});
console.log(`Build ${status.status}: ${status.logs.at(-1) ?? ''}`);
}
if (status.status !== 'succeeded') {
throw new Error('Template build failed');
}
Using a template
import { Sandbox } from '@declaw/sdk';
const sbx = await Sandbox.create({
template: 'data-analysis', // alias set during build
apiKey: 'your-api-key',
domain: '104.198.24.180:8080',
});
// pandas is already installed
const result = await sbx.commands.run(
'python3 -c "import pandas; print(pandas.__version__)"',
);
console.log(result.stdout);
await sbx.kill();