JuliusBrussee/caveman · error · Error
caveman build: config must use strict lock and required sand
Error message
caveman build: config must use strict lock and required sandbox
What it means
Thrown by `loadBuildInputs` for every CLI command that loads build config. It imports `caveman.config.ts` (or the passed path), reads the `default` or named `config` export, and hard-requires `config.lock === "strict"` and `config.sandbox === "required"`. Anything else — wrong export shape, missing config, or lenient settings — fails the build immediately: the framework only produces locks for strict-lock, required-sandbox builds.
Source
Thrown at packages/agent/src/cli.ts:1005
"package.json",
"package-lock.json",
"npm-shrinkwrap.json",
"pnpm-lock.yaml",
"yarn.lock",
] as const;
async function loadBuildInputs(
root: string,
configPath: string,
beforeSourceHash?: (
inputs: Omit<LoadedBuildInputs, "sourceSha256">,
) => Promise<void>,
): Promise<LoadedBuildInputs> {
const configAbsolute = resolve(root, configPath);
const imported = await importFresh(configAbsolute) as { default?: BuildConfig; config?: BuildConfig };
const config = imported.default ?? imported.config;
if (!config || config.lock !== "strict" || config.sandbox !== "required") {
throw new Error("caveman build: config must use strict lock and required sandbox");
}
const entryAbsolute = resolve(root, config.entry);
const agent = await loadAgent(entryAbsolute);
const evalFiles: string[] = [];
for await (const path of glob(config.evals, { cwd: root })) evalFiles.push(resolve(root, path));
evalFiles.sort();
const evals: EvalDefinition[] = [];
for (const path of evalFiles) {
const module = await importFresh(path) as Record<string, unknown>;
for (const value of Object.values(module)) {
if (isEval(value)) evals.push(value);
}
}
await beforeSourceHash?.({ config, agent, evals });
const sourceFiles = new Set<string>([configAbsolute, entryAbsolute, ...evalFiles]);
for (const pattern of SOURCE_PATTERNS) {
for await (const path of glob(pattern, { cwd: root })) sourceFiles.add(resolve(root, path));
}View on GitHub (pinned to 27d5a3981a)
Solutions
- Set both literals in the config export: `lock: "strict"`, `sandbox: "required"`.
- Confirm the export is `export default` or `export const config`.
- If you intentionally need host sandbox (coding agents), use the code.ts session surface instead of the locked build CLI — `compile` refuses host mode anywhere in the graph.
- Check you passed the right config path as args[0]; the default is `caveman.config.ts` at the project root.
Example fix
// before
default export defineConfig({ lock: "strict", sandbox: "host" });
// after
export default defineConfig({ lock: "strict", sandbox: "required" }); Defensive patterns
Strategy: validation
Validate before calling
type BuildConfigShape = { lock?: unknown; sandbox?: unknown };
function configIsValid(config: BuildConfigShape | undefined): boolean {
return !!config && config.lock === "strict" && config.sandbox === "required";
}
// assert configIsValid((await import(configPath)).default) before invoking the CLI Type guard
function isStrictBuildConfig(v: unknown): v is { lock: "strict"; sandbox: "required" } {
return typeof v === "object" && v !== null &&
(v as { lock?: unknown }).lock === "strict" &&
(v as { sandbox?: unknown }).sandbox === "required";
} Try / catch
try {
await build(args);
} catch (error) {
if (error instanceof Error && error.message.includes("strict lock and required sandbox")) {
// fix caveman.config.ts export and retry
} else throw error;
} Prevention
- Use the framework's defineConfig helper so literal types catch typos at compile time.
- Never use host sandbox with the locked build path; use the coding-session surface instead.
- Export config as `default` or named `config` only.
When it happens
Trigger: A `caveman.config.ts` exporting `{ lock: "loose" }` or `{ sandbox: "host" }` or omitting either field; exporting the config under a name that is neither `default` nor `config`; pointing `--config` at a file whose export is a plain object without the two required literal values.
Common situations: Copy-pasting a config template from an older version that defaulted these fields; switching sandbox to `host` for a coding agent and then trying the locked build path (host mode is lock-ineligible by design); typo in the export name (`export const buildConfig = ...` is not read).
Related errors
- caveman build: dataResidency is not enforced yet; refusing t
- caveman build: requiredFixturePassRate must be in (0,1]
- caveman build: qualityRetention must be in (0,1]
- cave_sandbox_conformance_failed
- cave_build_lock_missing: approve required evals, then run np
AI-assisted analysis of JuliusBrussee/caveman@27d5a3981a (2026-08-15).
Data as JSON: /api/errors/52afed0fe8d9aa61.
Report an issue: GitHub.