Override Cowork VM Backend Selection with Environment Variable in Claude Desktop

Set COWORK_VM_BACKEND to kvm, bwrap, or host to force Claude Desktop's isolation backend, bypassing auto-detection.

The aaddrick/claude-desktop-debian project implements a Linux "Cowork" isolation layer that automatically selects the best available virtualization backend. Operators can override this auto-detection by setting the COWORK_VM_BACKEND environment variable, forcing the application to use a specific isolation strategy regardless of system capabilities.

How the Backend Override Works

Backend Options Overview

Claude Desktop supports three distinct isolation backends selectable via environment variable:

Backend Isolation Level Environment Value
KVM Full QEMU/KVM virtual machine kvm
Bubblewrap Namespace sandbox (default) bwrap
Host-direct No isolation, runs directly on host host

When COWORK_VM_BACKEND is present in the environment, both the daemon and launcher skip the normal probing sequence and instantiate the specified backend class immediately.

Detection Logic in the Daemon

In scripts/cowork-vm-service.js, the daemon reads the override at line 47 and routes to the appropriate backend class:

const BACKEND_OVERRIDE = process.env.COWORK_VM_BACKEND || null;

function detectBackend(emitEvent) {
    const override = BACKEND_OVERRIDE;
    if (override) {
        log(`Backend override: ${override}`);
        switch (override.toLowerCase()) {
        case 'kvm':   return new KvmBackend(emitEvent);
        case 'bwrap': return new BwrapBackend(emitEvent);
        case 'host':  return new HostBackend(emitEvent);
        default:
            logError(`Unknown backend override "${override}", falling back to auto-detect`);
        }
    }
    /* … auto-detect path … */
}

If the supplied value does not match kvm, bwrap, or host, the system logs an error and proceeds to auto-detection rather than failing.

Launcher Verification

The launcher script scripts/launcher-common.sh (lines 12300-12340) mirrors this logic to report the active backend during diagnostic runs:

if [[ -n ${COWORK_VM_BACKEND-} ]]; then
    case ${COWORK_VM_BACKEND,,} in
        kvm)   cowork_backend='KVM (full VM isolation, via override)' ;;
        bwrap) cowork_backend='bubblewrap (namespace sandbox, via override)' ;;
        host)  cowork_backend='host-direct (no isolation, via override)' ;;
    esac
else
    # …auto-detect fallback logic…

fi
_info "Cowork isolation: $cowork_backend"

Practical Usage Examples

Force KVM Virtualization

To run Claude Desktop with full VM isolation regardless of default settings:

export COWORK_VM_BACKEND=kvm
./claude-desktop.AppImage

Use Bubblewrap Sandboxing

Explicitly select the namespace sandbox when KVM is available but undesirable:

export COWORK_VM_BACKEND=bwrap
./claude-desktop.AppImage

Run Without Isolation

Enable host-direct mode for debugging scenarios where isolation interferes with development:

export COWORK_VM_BACKEND=host
./claude-desktop.AppImage

Verify Active Backend

Check which backend is actually loaded using the diagnostic flag:

./claude-desktop.AppImage --doctor

Look for the line indicating the override status:


Cowork isolation: KVM (full VM isolation, via override)

Implementation Details

The following files in the aaddrick/claude-desktop-debian repository implement the backend selection logic:

File Purpose
scripts/cowork-vm-service.js Daemon backend detection and instantiation
scripts/launcher-common.sh Launcher diagnostic reporting and backend identification
docs/cowork-linux-handover.md High-level architecture documentation
docs/learnings/cowork-vm-daemon.md Detailed daemon implementation notes

Summary

  • Set COWORK_VM_BACKEND to kvm, bwrap, or host to override automatic backend selection in Claude Desktop.
  • The daemon in scripts/cowork-vm-service.js checks this variable at startup and instantiates the matching backend class directly.
  • The launcher in scripts/launcher-common.sh reports the override status during --doctor diagnostic runs.
  • Invalid values trigger a logged error and fallback to auto-detection rather than preventing startup.

Frequently Asked Questions

What happens if I set COWORK_VM_BACKEND to an invalid value?

If you specify a value other than kvm, bwrap, or host, the daemon logs an error message and proceeds with normal auto-detection. The application will not crash; it simply ignores the invalid override and selects the best available backend based on system capabilities.

Can I mix COWORK_VM_BACKEND with other environment variables?

Yes. The backend override operates independently of other configuration variables. For example, you can combine COWORK_VM_BACKEND=kvm with resource limit variables or display settings. The backend selection logic only examines the COWORK_VM_BACKEND value when deciding which isolation class to instantiate.

Why does the --doctor flag show "via override" next to the backend name?

The launcher script appends "(via override)" to the backend description whenever COWORK_VM_BACKEND is present in the environment. This indicator confirms that the current isolation mode results from your explicit environment setting rather than the default auto-detection logic that probes for available virtualization tools.

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 →