How Apache Maka's Sandbox Boundary Enforces Tool Execution Controls

Apache Maka enforces tool execution controls through a four-stage sandbox boundary system that selects backends, validates declared permissions, requests user-approved expansions, and blocks unauthorized access at runtime.

The sandbox boundary in Apache Maka is the core security mechanism that isolates every tool execution. Derived from a permission profile, this boundary is consulted before any tool runs and can reject, modify, or expand the authority granted to that tool. This article examines how the apache/maka source code implements deterministic, auditable tool execution controls.

The Four-Stage Enforcement Flow

Apache Maka's sandbox enforcement consists of tightly coupled components that operate in sequence:

Stage Component Key Function
1 SandboxManager Selects backend and decides if sandboxing is required
2 ExecutionBoundary Represents current authority attached to each session
3 Pre-flight validation Checks declared expansions against current boundary
4 request_sandbox_boundary tool Requests and applies user-approved boundary expansions

Stage 1: Sandbox Selection with SandboxManager

The enforcement process begins in packages/runtime/src/sandbox/sandbox-manager.ts. The SandboxManager.selectInitial method (lines 42-56) determines whether a sandbox is needed and which platform-specific backend to use.

Three sandbox preferences control this decision:

  • forbid — Runs the command outside any sandbox
  • require — Mandates sandbox creation regardless of profile
  • auto — Creates a sandbox when profileRequiresSandbox returns true (filesystem or network is restricted)
import { SandboxManager } from '@maka/runtime/src/sandbox/sandbox-manager.js';
import { createWorkspaceWritePermissionProfile } from '@maka/core/permission-profile.js';

const manager = new SandboxManager([
  // backends registered: linux, windows, macos-seatbelt
]);

const profile = createWorkspaceWritePermissionProfile(); // needs filesystem write
const selection = manager.selectInitial({
  profile,
  preference: 'auto',
});

if (!selection.ok) {
  console.error('Cannot sandbox on this platform:', selection.message);
} else {
  console.log('Sandbox type selected:', selection.sandboxType);
}

When sandboxing is required, the selected backend produces a SandboxTransformRequest that embeds the current ExecutionBoundary into child process launch parameters.

Stage 2: ExecutionBoundary Authority Representation

The ExecutionBoundary type in packages/core/src/sandbox-boundary.ts represents three possible authority states:

  • Managed — A profile with explicit allow/deny lists
  • Bypass — A token granting unrestricted access
  • External — An immutable boundary inherited from outside

This boundary object travels with every session and is passed to each tool runtime, ensuring consistent enforcement across the execution lifecycle.

Stage 3: Pre-flight Boundary Validation

Before a tool executes, Maka validates any sandbox boundary expansion declared by that tool. This pre-flight check occurs in packages/runtime/src/sandbox/sandbox-boundary-declaration.ts.

Tools declare expanded needs using the SandboxBoundaryExpansion type:

import { sandboxBoundaryExpansionSchema } from '@maka/runtime/src/sandbox/sandbox-boundary-declaration.js';

const myBoundary = {
  filesystem: {
    entries: [
      { path: '/tmp/data', access: 'write', scope: 'subtree' },
      { path: '/tmp/data/readme.txt', access: 'read', scope: 'exact' },
    ],
  },
  network: { enabled: true },
};

const schema = sandboxBoundaryExpansionSchema;
if (!schema.safeParse(myBoundary).success) throw new Error('Invalid boundary');

The preflightDeclaredSandboxBoundary function (lines 43-89) handles three outcomes via assessSandboxBoundaryExpansion (lines 34-46):

  • Explicit deny — Requested path conflicts with a deny entry → outcome conflict
  • Already contained — Current profile already grants requested rights → outcome noop
  • Apply required — New profile produced by applySandboxBoundaryExpansion (lines 84-88), forcing a boundary request

If validation fails, Maka throws SandboxCommandError with reason sandbox_boundary_required.

Stage 4: Runtime Boundary Requests and Enforcement

When pre-flight demands wider authority, tools invoke the request_sandbox_boundary tool implemented in packages/runtime/src/sandbox/sandbox-boundary-tool.ts (lines 57-78):

import { buildRequestSandboxBoundaryTool } from '@maka/runtime/src/sandbox/sandbox-boundary-tool.js';

const requestTool = buildRequestSandboxBoundaryTool();

async function run(context) {
  const settlement = await requestTool.impl(
    { 
      expansion: requiredExpansion, 
      justification: 'Need to edit temporary files' 
    },
    context,
  );
  console.log('Boundary approved:', settlement.boundary);
}

The host (desktop, TUI, or CI) decides whether to approve the minimal possible expansion. Key behaviors:

  • Approved expansions merge into the session profile via applySandboxBoundaryExpansion
  • Host denial returns SANDBOX_BOUNDARY_DENIED_FOR_TURN (lines 45-47), preventing retry loops
  • All filesystem and network access is verified against the effective profile via sandboxBoundaryExpansionAllowsPath (lines 70-81)

Fine-Grained Permission Controls

The sandbox boundary validates multiple dimensions of authority:

Dimension Options Enforcement Location
Path Exact match or subtree scope sandbox-boundary-path.ts
Access mode read, write, or both assessSandboxBoundaryExpansion
Network Enabled/disabled boolean SandboxBoundaryExpansion type
Explicit deny Override grant entries Profile merge logic

Path normalization occurs in sandbox-boundary-path.ts, ensuring canonical paths prevent escape attempts through symlinks or relative traversal.

Platform-Specific Backend Enforcement

The selected backend enforces boundaries at the OS level:

Each backend translates the ExecutionBoundary into platform-native constraints, ensuring consistent security semantics across operating systems.

Summary

Apache Maka's sandbox boundary enforces tool execution controls through:

  • Static selection — SandboxManager decides whether and how to sandbox based on profile and user preference
  • Dynamic expansion — Tools request additional authority through request_sandbox_boundary, requiring explicit host approval
  • Pre-flight validation — preflightDeclaredSandboxBoundary rejects or escalates declared expansions before execution
  • Runtime verification — Every access is checked against the effective boundary via sandboxBoundaryExpansionAllowsPath

This layered architecture ensures that even malicious or compromised tools cannot escape their granted authority without user-visible escalation.

Frequently Asked Questions

What happens when a tool requests access outside its sandbox boundary?

Maka throws SandboxCommandError with reason sandbox_boundary_required. The tool may then invoke request_sandbox_boundary to seek user approval for a minimal expansion. If denied, the tool receives SANDBOX_BOUNDARY_DENIED_FOR_TURN and cannot retry during the current turn.

How does Maka prevent sandbox escape through path traversal?

The normalizeSandboxBoundaryPath function in sandbox-boundary-path.ts canonicalizes all paths before validation. This resolves symlinks and eliminates relative path components, ensuring assessSandboxBoundaryExpansion compares absolute, normalized paths against the profile's allow and deny lists.

Can users completely disable sandboxing in Apache Maka?

Yes. Setting the sandbox preference to forbid in SandboxManager.selectInitial runs commands outside any sandbox. This bypass is recorded in the session's ExecutionBoundary as a bypass token, maintaining auditability while removing enforcement.

Where is the core boundary logic defined versus runtime enforcement?

Core data structures and validation live in packages/core/src/sandbox-boundary.ts (platform-agnostic). Runtime enforcement—including backend selection, pre-flight checks, and the request tool—resides in packages/runtime/src/sandbox/ (platform-specific backends in sibling files).

Have a question about this repo?

These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:

Share the following with your agent to get started:
curl -s "https://instagit.com/install.md"

Works with
Claude Codex Cursor VS Code OpenClaw Any MCP Client

Maintain an open-source project? Get it listed too →