Skip to content

Blog

Give your AI agent your files — safely

Three ways deputyOS lets your local AI assistant access your files, each gated through a single audit-friendly policy file.

5 min read deputyOS team

Letting an AI agent access your files is, on most operating systems, an all-or-nothing deal. Either it can see everything under your home directory or it can see nothing. That’s not great for either side: too much for the user, too little for the agent.

deputyOS introduced a drive-mount policy system specifically to fix this. Every mount is explicit, scoped, reviewable, and revocable. This is what it does and how to use it.

The three surfaces

1. VM host-FS passthrough

If deputyOS is running as a VM on your laptop (via the desktop launcher → WSL2 / UTM / qemu/KVM), you can share a host folder into the appliance.

  • Windows (WSL2): the launcher detects /mnt/c / /mnt/wslg and offers per-folder selection.
  • macOS (UTM): virtiofs share — pick a host folder; it appears at /mnt/deputyos/<id>/.
  • Linux (qemu/KVM): same virtiofs path.

Use case: you want your locally-running Hermes to read your Obsidian vault. Pick the vault folder. Done.

2. Removable drives on bare metal

Plug a USB stick or external SSD into a Pi 5 / NUC / mini-PC. With the policy default (removable.enabled = false), nothing happens. Flip the policy:

sudo jq '.removable.enabled = true | .removable.auto_mount = true' /etc/deputyos/mounts-policy.json \
  | sudo tee /etc/deputyos/mounts-policy.json

Now the udev rule auto-mounts new USB block devices under /mnt/deputyos/<label-or-uuid>/. The helper enforces:

  • nosuid,nodev,noexec mount options for unknown filesystems.
  • ro by default (you can flip to rw per-device in the policy).
  • LUKS-encrypted volumes are refused until you cryptsetup luksOpen them manually. The agent never holds disk keys.

Use case: you want your agent to read receipts and scans from a USB stick. Plug it in; mounted in milliseconds; agent sees it. Unplug; gone.

3. SMB / NFS network shares

For NAS users (TrueNAS, Synology, Unraid, Asustor). From the wizard’s “Network shares (advanced)” tile or via:

deputyctl mounts add \
  --id photos \
  --host-path "//nas.lan/photos" \
  --guest-path /mnt/deputyos/photos \
  --mode ro

The wizard collects credentials (host, share, username, password / NFS export options) and writes them to /etc/deputyos/secrets.env (mode 0600). The policy file references them by env-var name only — the policy is safe to commit to backups.

Use case: your TrueNAS holds a photo library. Mount it read-only. Khoj indexes it locally; queries work even when the NAS is offline (the embeddings are local).

The policy file

/etc/deputyos/mounts-policy.json is the single source of truth:

{
  "$schema": "https://www.deputyos.com/schemas/mounts-policy-v1.json",
  "version": 1,
  "host_fs": [
    { "id": "documents", "host_path": "/home/me/Documents",
      "guest_path": "/mnt/deputyos/documents", "mode": "rw" }
  ],
  "removable": {
    "enabled": false,
    "auto_mount": false,
    "default_mode": "ro",
    "mount_options_unknown_fs": "nosuid,nodev,noexec"
  },
  "network": [
    { "id": "photos", "kind": "cifs",
      "source": "//nas.lan/photos",
      "guest_path": "/mnt/deputyos/photos",
      "mode": "ro",
      "credentials_env": "NAS_PHOTOS" }
  ]
}

It’s atomic-rename written by deputyctl mounts add/remove. Race-free; backup-friendly.

How AppArmor enforces the boundary

Every agent profile (OpenClaw / Hermes / Khoj) has an AppArmor profile loaded in enforce mode at boot. The relevant rule:

/mnt/deputyos/** rwk,
/etc/deputyos/secrets.env r,
/etc/deputyos/mounts-policy.json r,

/mnt/deputyos/** is the only mount-able tree the agent can touch. Even if the agent code had a bug that tried to write /etc/shadow, AppArmor’s enforce mode would deny it. The kernel doesn’t care what the agent intended; it knows what the policy says.

This is the core property: the agent process literally cannot reach files outside the mount-policy-declared paths. Not “shouldn’t” — can’t.

Reviewing what’s mounted

Three surfaces, same data:

CLI

deputyctl mounts list
# kind           id               guest-path                      mode source
# host-fs        documents        /mnt/deputyos/documents          rw   /home/me/Documents
# network/cifs   photos           /mnt/deputyos/photos             ro   //nas.lan/photos

Wizard

/mounts page lists the same with a form to add and a button to remove.

PWA “Mounts” card

/app/mounts/ on the always-on PWA. Same list, one-click revoke per row.

Revoking a mount

deputyctl mounts remove documents — atomic policy update. The deputyos-mounts.service materialiser unmounts on next sync. The agent’s view at /mnt/deputyos/documents is removed; existing file handles are invalidated.

The PWA’s revoke button does the same atomically.

What this prevents

A scenario we obsess over: someone gives their AI agent access to a folder. Three months later, the agent has skill X that turns out to have a path-traversal bug. Without policy, that bug touches the entire filesystem. With policy, the worst case is bounded by /mnt/deputyos/** — concretely, the folders you chose to mount.

The blast radius is whatever you explicitly chose, not whatever the agent process happens to have permission for.

What this doesn’t prevent

Honesty matters:

  • The agent can still read what you mount. If you mount your password manager’s database folder, the agent can read your password database. Don’t do this.
  • The agent can still send what it reads to its model provider. When the agent generates a response, the model prompt includes context that came from mounted files. If your model provider is OpenAI, your file content reaches OpenAI. The air-gapped tier eliminates this; cloud tiers do not.
  • Skills can write to mounted rw paths. That’s the point. If a skill misbehaves, it can corrupt files there. The mitigation is ro mode for sensitive content; rw only for places the agent legitimately needs to write.

These are user-judgement decisions, not policy-system decisions.

Common patterns

Read-only Documents folder

deputyctl mounts add --id docs \
  --host-path ~/Documents \
  --guest-path /mnt/deputyos/docs \
  --mode ro

Good for letting the agent reference your notes without being able to modify them.

deputyctl mounts add --id current-project \
  --host-path ~/code/agentvfs \
  --guest-path /mnt/deputyos/current-project \
  --mode rw

Risky if your agent runs untrusted skills. Pair with frequent backups.

Read-only photo library via SMB

Via the wizard’s “Network shares” tile, configured against your NAS. Khoj indexes locally; queries work offline.

USB stick for one-off file ingestion

Enable removable in the policy; plug in; agent reads; unplug. Auto-revoked when device disappears.

What’s not in the system yet

  • Per-skill mount permissions. Today all skills inside a profile inherit the profile’s AppArmor scope. Per-skill ACLs are on the roadmap.
  • Per-mount audit log. The agent’s reads/writes aren’t logged at the policy level. You can hook post-message to capture file references.
  • Encrypted mounts at rest from the agent’s view. If you mount an encrypted FUSE filesystem, the agent sees decrypted content. (That’s what FUSE is for; just noting it.)

Trying it

The drive-mount system is in v0.3.0. Once your deputyOS device is up, deputyctl mounts add ... is the entry point. The how-to doc has the recipes for each surface; the PWA’s Mounts card is the always-on revoke surface.

If you’ve been holding off on giving your AI assistant your files because the existing tools are too coarse-grained — this is the system to try.

Related posts

Search

Search index isn't built yet. Run npm run build to generate it (Pagefind writes to dist/pagefind/).