Skip to main content

Python bindings for nono capability-based sandboxing

Project description

nono-py

Python bindings for nono, a capability-based sandboxing library.

nono provides OS-enforced sandboxing using Landlock (Linux) and Seatbelt (macOS). Once a sandbox is applied, unauthorized operations are structurally impossible.

Installation

pip install nono-py

From source

Requires Rust toolchain and maturin:

pip install maturin
maturin develop

Usage

from nono_py import CapabilitySet, AccessMode, apply, is_supported

# Check platform support
if not is_supported():
    print("Sandboxing not supported on this platform")
    exit(1)

# Build capability set
caps = CapabilitySet()
caps.allow_path("/tmp", AccessMode.READ_WRITE)
caps.allow_path("/home/user/project", AccessMode.READ)
caps.allow_file("/etc/hosts", AccessMode.READ)
caps.block_network()

# Apply sandbox (irreversible!)
apply(caps)

# Now the process can only access granted paths
# Network access is blocked
# This applies to all child processes too

API Reference

Sandboxing

CapabilitySet + apply()

Sandbox the current process (irreversible):

caps = CapabilitySet()
caps.allow_path("/tmp", AccessMode.READ_WRITE)
caps.block_network()
apply(caps)  # Process is now sandboxed

sandboxed_exec

Run a command in a sandboxed child process. The parent stays unsandboxed and can call this repeatedly with different capabilities:

caps = CapabilitySet()
caps.allow_path("/workspace", AccessMode.READ_WRITE)
caps.block_network()
result = sandboxed_exec(caps, ["python", "agent.py"], cwd="/workspace", timeout_secs=30.0)
print(result.stdout, result.exit_code)

Network Proxy

Domain-filtered network access for sandboxed children. The proxy intercepts outbound HTTP requests and enforces a host allowlist. For API calls, it performs credential injection: the sandboxed process sends a dummy token, and the proxy transparently swaps in the real API key (loaded from the OS keyring) before forwarding upstream. The sandboxed process never sees the real secret.

from nono_py import ProxyConfig, RouteConfig, start_proxy

config = ProxyConfig(
    allowed_hosts=["api.openai.com", "*.anthropic.com"],
    routes=[
        RouteConfig(prefix="/openai", upstream="https://api.openai.com", credential_key="openai-key"),
    ],
)
proxy = start_proxy(config)

# Inject proxy env vars into sandboxed child
env = list(proxy.env_vars().items()) + list(proxy.credential_env_vars().items())
result = sandboxed_exec(caps, ["python", "agent.py"], env=env)

# Audit trail
events = proxy.drain_audit_events()
proxy.shutdown()

Filesystem Snapshots

Content-addressable snapshots with Merkle-committed state and rollback:

from nono_py import SnapshotManager, ExclusionConfig

mgr = SnapshotManager(
    session_dir="~/.nono/rollbacks/session-001",
    tracked_paths=["/workspace"],
    exclusion=ExclusionConfig(exclude_patterns=["node_modules", "__pycache__"]),
)
mgr.create_baseline()

# ... agent runs and modifies files ...

manifest, changes = mgr.create_incremental()
for change in changes:
    print(f"{change.change_type}: {change.path}")

# Roll back
mgr.restore_to(snapshot_number=0)

Other Classes

  • QueryContext - Check permissions without applying the sandbox
  • SandboxState - Serialize/restore capability sets as JSON
  • SupportInfo - Platform support details
  • Policy - Load and resolve policy.json documents
  • SessionMetadata - Session audit trail with Merkle roots and network events

Functions

  • apply(caps) - Apply sandbox (irreversible)
  • sandboxed_exec(caps, command, ...) - Run command in sandboxed child
  • start_proxy(config) - Start network filtering proxy
  • is_supported() / support_info() - Platform support
  • load_policy(json) / load_embedded_policy() - Policy loading

Platform Support

Platform Backend Requirements
Linux Landlock Kernel 5.13+ with Landlock enabled
macOS Seatbelt macOS 10.5+
Windows - Not supported

Development

# Install dev dependencies
pip install maturin pytest mypy

# Build and install for development
make dev

# Run tests
make test

# Run linters
make lint

# Format code
make fmt

License

Apache-2.0

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

nono_py-0.7.0.tar.gz (136.5 kB view details)

Uploaded Source

Built Distributions

If you're not sure about the file name format, learn more about wheel file names.

nono_py-0.7.0-cp313-cp313-manylinux_2_17_x86_64.manylinux2014_x86_64.whl (4.3 MB view details)

Uploaded CPython 3.13manylinux: glibc 2.17+ x86-64

nono_py-0.7.0-cp313-cp313-manylinux_2_17_aarch64.manylinux2014_aarch64.whl (4.1 MB view details)

Uploaded CPython 3.13manylinux: glibc 2.17+ ARM64

nono_py-0.7.0-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl (4.3 MB view details)

Uploaded CPython 3.12manylinux: glibc 2.17+ x86-64

nono_py-0.7.0-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl (4.1 MB view details)

Uploaded CPython 3.12manylinux: glibc 2.17+ ARM64

nono_py-0.7.0-cp312-cp312-macosx_11_0_arm64.whl (2.8 MB view details)

Uploaded CPython 3.12macOS 11.0+ ARM64

nono_py-0.7.0-cp312-cp312-macosx_10_12_x86_64.whl (3.0 MB view details)

Uploaded CPython 3.12macOS 10.12+ x86-64

nono_py-0.7.0-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl (4.3 MB view details)

Uploaded CPython 3.11manylinux: glibc 2.17+ x86-64

nono_py-0.7.0-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl (4.1 MB view details)

Uploaded CPython 3.11manylinux: glibc 2.17+ ARM64

nono_py-0.7.0-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl (4.3 MB view details)

Uploaded CPython 3.10manylinux: glibc 2.17+ x86-64

nono_py-0.7.0-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl (4.1 MB view details)

Uploaded CPython 3.10manylinux: glibc 2.17+ ARM64

nono_py-0.7.0-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl (4.3 MB view details)

Uploaded CPython 3.9manylinux: glibc 2.17+ x86-64

nono_py-0.7.0-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl (4.1 MB view details)

Uploaded CPython 3.9manylinux: glibc 2.17+ ARM64

File details

Details for the file nono_py-0.7.0.tar.gz.

File metadata

  • Download URL: nono_py-0.7.0.tar.gz
  • Upload date:
  • Size: 136.5 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.7

File hashes

Hashes for nono_py-0.7.0.tar.gz
Algorithm Hash digest
SHA256 30576a5f1d89f630e754950d2daa62b325ec65b93346ec4337f4bc2055811c9d
MD5 74cb06572d1012056e0c4ae737e83fb4
BLAKE2b-256 d72d45694928d239ef307de27140f13c60954ab1ca9282dc9b7889a709b167cf

See more details on using hashes here.

Provenance

The following attestation bundles were made for nono_py-0.7.0.tar.gz:

Publisher: publish.yml on always-further/nono-py

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file nono_py-0.7.0-cp313-cp313-manylinux_2_17_x86_64.manylinux2014_x86_64.whl.

File metadata

File hashes

Hashes for nono_py-0.7.0-cp313-cp313-manylinux_2_17_x86_64.manylinux2014_x86_64.whl
Algorithm Hash digest
SHA256 3bae618ac228b4c71d8a9951a9c72003de9c170c91bbc49d382e5b9d2eb40e9e
MD5 ef11f8a0561bc1daeeb23da51e884e12
BLAKE2b-256 d08768761b1fab59d4f8db3c5440642d4373b174f58420674d89edda16561a1a

See more details on using hashes here.

Provenance

The following attestation bundles were made for nono_py-0.7.0-cp313-cp313-manylinux_2_17_x86_64.manylinux2014_x86_64.whl:

Publisher: publish.yml on always-further/nono-py

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file nono_py-0.7.0-cp313-cp313-manylinux_2_17_aarch64.manylinux2014_aarch64.whl.

File metadata

File hashes

Hashes for nono_py-0.7.0-cp313-cp313-manylinux_2_17_aarch64.manylinux2014_aarch64.whl
Algorithm Hash digest
SHA256 3aea8ae61c14b38ca93f06de9dabc34928142a0f84a61caa30ffd5ebaaaf30d8
MD5 4f4e389696e6c4ad2faa8514e7977c5d
BLAKE2b-256 2f04f01bbdc2690345b28c6cb2ebfa68fe65b89e3bcc95879d3e931d3c2df600

See more details on using hashes here.

Provenance

The following attestation bundles were made for nono_py-0.7.0-cp313-cp313-manylinux_2_17_aarch64.manylinux2014_aarch64.whl:

Publisher: publish.yml on always-further/nono-py

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file nono_py-0.7.0-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl.

File metadata

File hashes

Hashes for nono_py-0.7.0-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl
Algorithm Hash digest
SHA256 7fdb56b322469216122b125042a5e6bf86465ddfe34bde0b74abc7105a8e0c7c
MD5 ae5c2ead6178ece83f78ee9fbb8e56c7
BLAKE2b-256 1d53a3d8b00008f3c1c33d821c8e0d6eb6caeed3d378f0bfbb43249b3b5dd277

See more details on using hashes here.

Provenance

The following attestation bundles were made for nono_py-0.7.0-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl:

Publisher: publish.yml on always-further/nono-py

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file nono_py-0.7.0-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl.

File metadata

File hashes

Hashes for nono_py-0.7.0-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl
Algorithm Hash digest
SHA256 73d66c2b8d80e19bc9e786d4ce66b8e274f11f97c2730c07443cd1b43c7f53fc
MD5 0c6bcfd97bb02b907ec503aa176d5cc2
BLAKE2b-256 7ebb51ef7e4ff18c3b40a7f8e4efa21f62aa433530af08df84ee04735dfd9b76

See more details on using hashes here.

Provenance

The following attestation bundles were made for nono_py-0.7.0-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl:

Publisher: publish.yml on always-further/nono-py

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file nono_py-0.7.0-cp312-cp312-macosx_11_0_arm64.whl.

File metadata

File hashes

Hashes for nono_py-0.7.0-cp312-cp312-macosx_11_0_arm64.whl
Algorithm Hash digest
SHA256 db25fff057dbba9aabc764d94a206c0707525a43da7335354aaa63cd89add7ca
MD5 e6008f608b9329a6234007f9ed84695f
BLAKE2b-256 deaf55de4904cfd477075c24893e00f2a4dcea6942c397a993a822831578b47a

See more details on using hashes here.

Provenance

The following attestation bundles were made for nono_py-0.7.0-cp312-cp312-macosx_11_0_arm64.whl:

Publisher: publish.yml on always-further/nono-py

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file nono_py-0.7.0-cp312-cp312-macosx_10_12_x86_64.whl.

File metadata

File hashes

Hashes for nono_py-0.7.0-cp312-cp312-macosx_10_12_x86_64.whl
Algorithm Hash digest
SHA256 974310a564dbe56bd31f95b4465bb0fe0f1463a03566d7e21beda32a52b46e13
MD5 d1f892eebd9dfed7275823b42859f5cd
BLAKE2b-256 6428cd3083578a3ebcf6bb838bb2ccb7ce192ea7013c74b2baa5a5aa25b2fed4

See more details on using hashes here.

Provenance

The following attestation bundles were made for nono_py-0.7.0-cp312-cp312-macosx_10_12_x86_64.whl:

Publisher: publish.yml on always-further/nono-py

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file nono_py-0.7.0-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl.

File metadata

File hashes

Hashes for nono_py-0.7.0-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl
Algorithm Hash digest
SHA256 61fb7aa0f85bf3d5045f4350c7ff9619acdf3840d10005e732e78ebbb1ada163
MD5 e238c6de9ba7ba521d0d719d8b36884d
BLAKE2b-256 9ba79d3fe0336e4da7380c9940710baca829b204d7b795c99c706e04f9edb570

See more details on using hashes here.

Provenance

The following attestation bundles were made for nono_py-0.7.0-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl:

Publisher: publish.yml on always-further/nono-py

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file nono_py-0.7.0-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl.

File metadata

File hashes

Hashes for nono_py-0.7.0-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl
Algorithm Hash digest
SHA256 7bcbe0f363aef3681f2e0063062898dea292cca41b5ff38335da484cd25f9c41
MD5 302a87308cdb2bfe7564b17669432b42
BLAKE2b-256 8d00f35c07b966c05ffb7510dcfc7192179f469529036dcc9d88e30e5def49ad

See more details on using hashes here.

Provenance

The following attestation bundles were made for nono_py-0.7.0-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl:

Publisher: publish.yml on always-further/nono-py

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file nono_py-0.7.0-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl.

File metadata

File hashes

Hashes for nono_py-0.7.0-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl
Algorithm Hash digest
SHA256 f81cf4d3e0435b909f21ba232e69e82d37f033b03e52453670b2368aef8d369a
MD5 6f3524640bff416be17735d5db658bb5
BLAKE2b-256 f27600842079b4ed26ffd4f5243d77e7f44382fb80550eedf7671d2fcb713a2d

See more details on using hashes here.

Provenance

The following attestation bundles were made for nono_py-0.7.0-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl:

Publisher: publish.yml on always-further/nono-py

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file nono_py-0.7.0-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl.

File metadata

File hashes

Hashes for nono_py-0.7.0-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl
Algorithm Hash digest
SHA256 74ad52b3f1eff95ca14853914248bc1e120f04ca318c5f35e869cb431aeba787
MD5 04537da7d1f2f2a5d991e69ca5842d56
BLAKE2b-256 c42b38bb0e2ebed101a71e4a90a835837fd4b90dfd2b6a1b4b0b00d460e57617

See more details on using hashes here.

Provenance

The following attestation bundles were made for nono_py-0.7.0-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl:

Publisher: publish.yml on always-further/nono-py

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file nono_py-0.7.0-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl.

File metadata

File hashes

Hashes for nono_py-0.7.0-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl
Algorithm Hash digest
SHA256 083abc3fea92f5b2a194cd9e752e4ab3ca2c65a8039947f1c4430eb82653e3e5
MD5 30f1b8c12b09940ec25e5e4369a927df
BLAKE2b-256 4831cab5f157a258c447de120fb4716579f1de09c5c9e931c3e30a9297242686

See more details on using hashes here.

Provenance

The following attestation bundles were made for nono_py-0.7.0-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl:

Publisher: publish.yml on always-further/nono-py

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file nono_py-0.7.0-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl.

File metadata

File hashes

Hashes for nono_py-0.7.0-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl
Algorithm Hash digest
SHA256 1582ecad29cd5d9edd008e6a1e32f184b2cc696f5cf042a4de6935dc4cf67f96
MD5 57e29cea26c1010114331d8865424315
BLAKE2b-256 de67b6ac9ab2d3e12b64173ae13a680932620950591988f6590dda1727458d2a

See more details on using hashes here.

Provenance

The following attestation bundles were made for nono_py-0.7.0-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl:

Publisher: publish.yml on always-further/nono-py

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page