proc-jail 0.2.0__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (42) hide show
  1. proc_jail-0.2.0/.github/workflows/ci.yml +145 -0
  2. proc_jail-0.2.0/.github/workflows/release.yml +164 -0
  3. proc_jail-0.2.0/.gitignore +16 -0
  4. proc_jail-0.2.0/CHANGELOG.md +57 -0
  5. proc_jail-0.2.0/Cargo.lock +364 -0
  6. proc_jail-0.2.0/Cargo.toml +30 -0
  7. proc_jail-0.2.0/LICENSE-APACHE +190 -0
  8. proc_jail-0.2.0/LICENSE-MIT +21 -0
  9. proc_jail-0.2.0/PKG-INFO +304 -0
  10. proc_jail-0.2.0/README.md +275 -0
  11. proc_jail-0.2.0/SECURITY.md +135 -0
  12. proc_jail-0.2.0/docs/design-decisions.md +85 -0
  13. proc_jail-0.2.0/docs/risky-binaries.md +131 -0
  14. proc_jail-0.2.0/docs/windows.md +86 -0
  15. proc_jail-0.2.0/proc_jail/__init__.py +27 -0
  16. proc_jail-0.2.0/proc_jail/__init__.pyi +282 -0
  17. proc_jail-0.2.0/proc_jail/py.typed +0 -0
  18. proc_jail-0.2.0/proc_jail_spec_v3.md +1078 -0
  19. proc_jail-0.2.0/pyproject.toml +40 -0
  20. proc_jail-0.2.0/python/Cargo.toml +18 -0
  21. proc_jail-0.2.0/python/README.md +198 -0
  22. proc_jail-0.2.0/python/src/lib.rs +645 -0
  23. proc_jail-0.2.0/python/tests/test_proc_jail.py +414 -0
  24. proc_jail-0.2.0/scripts/check_versions.py +54 -0
  25. proc_jail-0.2.0/src/arg_parser.rs +197 -0
  26. proc_jail-0.2.0/src/arg_rules.rs +305 -0
  27. proc_jail-0.2.0/src/canonical.rs +101 -0
  28. proc_jail-0.2.0/src/cwd_policy.rs +213 -0
  29. proc_jail-0.2.0/src/double_dash.rs +164 -0
  30. proc_jail-0.2.0/src/env_policy.rs +246 -0
  31. proc_jail-0.2.0/src/error.rs +145 -0
  32. proc_jail-0.2.0/src/file_check.rs +140 -0
  33. proc_jail-0.2.0/src/lib.rs +91 -0
  34. proc_jail-0.2.0/src/limits.rs +57 -0
  35. proc_jail-0.2.0/src/output.rs +38 -0
  36. proc_jail-0.2.0/src/policy.rs +357 -0
  37. proc_jail-0.2.0/src/prepared.rs +433 -0
  38. proc_jail-0.2.0/src/request.rs +75 -0
  39. proc_jail-0.2.0/src/risky.rs +209 -0
  40. proc_jail-0.2.0/tests/adversarial.rs +800 -0
  41. proc_jail-0.2.0/tests/integration.rs +299 -0
  42. proc_jail-0.2.0/tests/launch.rs +335 -0
@@ -0,0 +1,145 @@
1
+ name: CI
2
+
3
+ on:
4
+ push:
5
+ branches: [main]
6
+ pull_request:
7
+ branches: [main]
8
+
9
+ permissions:
10
+ contents: read
11
+
12
+ env:
13
+ CARGO_TERM_COLOR: always
14
+
15
+ jobs:
16
+ versions:
17
+ name: Package versions
18
+ runs-on: ubuntu-latest
19
+ steps:
20
+ - uses: actions/checkout@v4
21
+ - uses: actions/setup-python@v5
22
+ with:
23
+ python-version: "3.11"
24
+ - run: python scripts/check_versions.py
25
+
26
+ audit:
27
+ name: Dependency audit
28
+ runs-on: ubuntu-latest
29
+ steps:
30
+ - uses: actions/checkout@v4
31
+ - uses: dtolnay/rust-toolchain@stable
32
+ - name: Generate Cargo.lock
33
+ run: cargo generate-lockfile
34
+ env:
35
+ CARGO_RESOLVER_INCOMPATIBLE_RUST_VERSIONS: fallback
36
+ - uses: rustsec/audit-check@v2
37
+ with:
38
+ token: ${{ secrets.GITHUB_TOKEN }}
39
+
40
+ test:
41
+ name: Test (${{ matrix.os }}, Rust ${{ matrix.rust }})
42
+ runs-on: ${{ matrix.os }}
43
+ strategy:
44
+ fail-fast: false
45
+ matrix:
46
+ os: [ubuntu-latest, macos-latest]
47
+ rust: [stable, "1.75"] # stable + MSRV
48
+ steps:
49
+ - uses: actions/checkout@v4
50
+ # Stable cargo resolves the lockfile; MSRV-aware fallback keeps
51
+ # dependencies compatible with rust-version on the MSRV job.
52
+ - uses: dtolnay/rust-toolchain@stable
53
+ - uses: dtolnay/rust-toolchain@master
54
+ with:
55
+ toolchain: ${{ matrix.rust }}
56
+ - uses: Swatinem/rust-cache@v2
57
+ - name: Generate Cargo.lock
58
+ run: cargo +stable generate-lockfile
59
+ env:
60
+ CARGO_RESOLVER_INCOMPATIBLE_RUST_VERSIONS: fallback
61
+ - run: cargo +${{ matrix.rust }} test --features tracing
62
+
63
+ clippy:
64
+ name: Clippy
65
+ runs-on: ubuntu-latest
66
+ steps:
67
+ - uses: actions/checkout@v4
68
+ - uses: dtolnay/rust-toolchain@stable
69
+ with:
70
+ components: clippy
71
+ - uses: Swatinem/rust-cache@v2
72
+ - run: cargo clippy --features tracing -- -D warnings
73
+
74
+ fmt:
75
+ name: Format
76
+ runs-on: ubuntu-latest
77
+ steps:
78
+ - uses: actions/checkout@v4
79
+ - uses: dtolnay/rust-toolchain@stable
80
+ with:
81
+ components: rustfmt
82
+ - run: cargo fmt --check
83
+
84
+ docs:
85
+ name: Documentation
86
+ runs-on: ubuntu-latest
87
+ steps:
88
+ - uses: actions/checkout@v4
89
+ - uses: dtolnay/rust-toolchain@stable
90
+ - uses: Swatinem/rust-cache@v2
91
+ - run: cargo doc --no-deps
92
+ env:
93
+ RUSTDOCFLAGS: -D warnings
94
+
95
+ python:
96
+ name: Python Bindings
97
+ runs-on: ubuntu-latest
98
+ steps:
99
+ - uses: actions/checkout@v4
100
+ - uses: dtolnay/rust-toolchain@stable
101
+ - uses: actions/setup-python@v5
102
+ with:
103
+ python-version: "3.11"
104
+ - name: Install maturin
105
+ run: pip install maturin
106
+ - name: Build Python wheel
107
+ working-directory: python
108
+ run: maturin build
109
+ - name: Test imports
110
+ run: |
111
+ WHEEL=$(find target/wheels -maxdepth 1 -name '*.whl' -print -quit)
112
+ pip install "$WHEEL"
113
+ python -c "
114
+ from proc_jail import (
115
+ ProcPolicyBuilder, ProcRequest, ArgRules,
116
+ InjectDoubleDash, RiskyBinPolicy, RiskCategory,
117
+ PreparedCommand, Output, ProcPolicy
118
+ )
119
+ print('All imports OK')
120
+ "
121
+
122
+ python-tests:
123
+ name: Python Tests (${{ matrix.os }}, ${{ matrix.python }})
124
+ runs-on: ${{ matrix.os }}
125
+ strategy:
126
+ fail-fast: false
127
+ matrix:
128
+ os: [ubuntu-latest, macos-latest]
129
+ python: ["3.8", "3.15"]
130
+ steps:
131
+ - uses: actions/checkout@v4
132
+ - uses: dtolnay/rust-toolchain@stable
133
+ - uses: actions/setup-python@v5
134
+ with:
135
+ python-version: ${{ matrix.python }}
136
+ - name: Install dependencies
137
+ run: pip install "maturin>=1,<2" pytest
138
+ - name: Build and install
139
+ run: |
140
+ cd python && maturin build
141
+ WHEEL=$(find ../target/wheels -maxdepth 1 -name '*.whl' -print -quit)
142
+ pip install "$WHEEL"
143
+ - name: Run Python tests
144
+ working-directory: python
145
+ run: pytest tests/ -v --tb=short
@@ -0,0 +1,164 @@
1
+ name: Release
2
+
3
+ on:
4
+ push:
5
+ tags:
6
+ - "v*"
7
+
8
+ permissions:
9
+ contents: read
10
+
11
+ env:
12
+ CARGO_TERM_COLOR: always
13
+
14
+ jobs:
15
+ preflight:
16
+ name: Release preflight
17
+ runs-on: ubuntu-latest
18
+ steps:
19
+ - uses: actions/checkout@v4
20
+ - uses: actions/setup-python@v5
21
+ with:
22
+ python-version: "3.15"
23
+ - uses: dtolnay/rust-toolchain@stable
24
+ - name: Verify tag and package versions
25
+ run: python scripts/check_versions.py --tag "$GITHUB_REF_NAME"
26
+ - name: Test workspace
27
+ run: cargo test --all --all-features
28
+ - name: Verify crates.io package
29
+ run: cargo publish --dry-run
30
+
31
+ build-rust:
32
+ name: Build crates.io package
33
+ needs: preflight
34
+ runs-on: ubuntu-latest
35
+ steps:
36
+ - uses: actions/checkout@v4
37
+ - uses: dtolnay/rust-toolchain@stable
38
+ - run: cargo package
39
+ - uses: actions/upload-artifact@v4
40
+ with:
41
+ name: rust-package
42
+ path: target/package/*.crate
43
+ if-no-files-found: error
44
+
45
+ build-python:
46
+ name: Build Python wheel (${{ matrix.target }})
47
+ needs: preflight
48
+ runs-on: ${{ matrix.os }}
49
+ strategy:
50
+ fail-fast: false
51
+ matrix:
52
+ include:
53
+ - os: ubuntu-24.04
54
+ target: x86_64
55
+ manylinux: auto
56
+ - os: ubuntu-24.04-arm
57
+ target: aarch64
58
+ manylinux: auto
59
+ - os: macos-15-intel
60
+ target: x86_64
61
+ manylinux: off
62
+ - os: macos-15
63
+ target: aarch64
64
+ manylinux: off
65
+ steps:
66
+ - uses: actions/checkout@v4
67
+ - uses: actions/setup-python@v5
68
+ with:
69
+ python-version: "3.15"
70
+ - uses: dtolnay/rust-toolchain@stable
71
+ - name: Build wheel
72
+ uses: PyO3/maturin-action@v1
73
+ with:
74
+ working-directory: python
75
+ target: ${{ matrix.target }}
76
+ args: --release --out dist
77
+ manylinux: ${{ matrix.manylinux }}
78
+ - name: Smoke-test wheel
79
+ run: |
80
+ python -m pip install --force-reinstall python/dist/*.whl
81
+ python -c "import proc_jail, sys; assert proc_jail.__version__ == sys.argv[1]" "${GITHUB_REF_NAME#v}"
82
+ - uses: actions/upload-artifact@v4
83
+ with:
84
+ name: python-wheel-${{ matrix.target }}-${{ matrix.os }}
85
+ path: python/dist/*.whl
86
+ if-no-files-found: error
87
+
88
+ build-sdist:
89
+ name: Build Python source distribution
90
+ needs: preflight
91
+ runs-on: ubuntu-latest
92
+ steps:
93
+ - uses: actions/checkout@v4
94
+ - uses: actions/setup-python@v5
95
+ with:
96
+ python-version: "3.15"
97
+ - uses: dtolnay/rust-toolchain@stable
98
+ - run: python -m pip install "maturin>=1,<2" twine
99
+ - run: maturin sdist --manifest-path python/Cargo.toml --out python/dist
100
+ - run: twine check python/dist/*
101
+ - uses: actions/upload-artifact@v4
102
+ with:
103
+ name: python-sdist
104
+ path: python/dist/*.tar.gz
105
+ if-no-files-found: error
106
+
107
+ validate-python:
108
+ name: Validate Python artifacts
109
+ needs: [build-python, build-sdist]
110
+ runs-on: ubuntu-latest
111
+ steps:
112
+ - uses: actions/setup-python@v5
113
+ with:
114
+ python-version: "3.15"
115
+ - uses: actions/download-artifact@v4
116
+ with:
117
+ pattern: python-*
118
+ path: dist
119
+ merge-multiple: true
120
+ - run: python -m pip install twine
121
+ - run: twine check dist/*
122
+
123
+ publish-rust:
124
+ name: Publish to crates.io
125
+ needs: [build-rust, validate-python]
126
+ runs-on: ubuntu-latest
127
+ steps:
128
+ - uses: actions/checkout@v4
129
+ - uses: dtolnay/rust-toolchain@stable
130
+ - run: cargo publish --token ${{ secrets.CARGO_REGISTRY_TOKEN }}
131
+
132
+ publish-python:
133
+ name: Publish to PyPI
134
+ needs: [build-rust, validate-python]
135
+ runs-on: ubuntu-latest
136
+ steps:
137
+ - uses: actions/download-artifact@v4
138
+ with:
139
+ pattern: python-*
140
+ path: dist
141
+ merge-multiple: true
142
+ - uses: pypa/gh-action-pypi-publish@release/v1
143
+ with:
144
+ password: ${{ secrets.PYPI_API_TOKEN }}
145
+
146
+ github-release:
147
+ name: Create GitHub release
148
+ needs: [publish-rust, publish-python]
149
+ runs-on: ubuntu-latest
150
+ permissions:
151
+ contents: write
152
+ steps:
153
+ - uses: actions/checkout@v4
154
+ - uses: actions/download-artifact@v4
155
+ with:
156
+ path: dist
157
+ merge-multiple: true
158
+ - name: Generate checksums
159
+ working-directory: dist
160
+ run: sha256sum -- * > SHA256SUMS
161
+ - name: Create release
162
+ env:
163
+ GH_TOKEN: ${{ github.token }}
164
+ run: gh release create "$GITHUB_REF_NAME" dist/* --verify-tag --generate-notes
@@ -0,0 +1,16 @@
1
+ # Rust
2
+ /target
3
+ Cargo.lock
4
+
5
+ # Python
6
+ python/.venv/
7
+ python/target/
8
+ __pycache__/
9
+ *.py[cod]
10
+ *.so
11
+ *.pyd
12
+ .pytest_cache/
13
+ *.egg-info/
14
+ dist/
15
+ build/
16
+ .eggs/
@@ -0,0 +1,57 @@
1
+ # Changelog
2
+
3
+ All notable changes to this project will be documented in this file.
4
+
5
+ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.1.0/),
6
+ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
7
+
8
+ ## [Unreleased]
9
+
10
+ ## [0.2.0] - 2026-10-25
11
+
12
+ ### Added
13
+
14
+ - `PreparedCommand::wrap_with()` to launch the validated command through another program (for example an OS sandbox launcher), plus `launch_program()`/`launch_args()` accessors
15
+ - `PreparedCommand::with_launch_env()` and `launch_env()` for environment variables added after the env policy
16
+ - Python bindings for `wrap_with`, `with_launch_env`, `launch_program`, `launch_args`
17
+
18
+ ### Changed
19
+
20
+ - Commands are spawned in their own process group, and the whole group is killed on timeout or output limits
21
+ - An output limit on one stream no longer waits for the other stream to close
22
+ - Processes the command leaves running in its group are killed when it exits
23
+ - The timeout now also covers waiting for exit after the output pipes close
24
+ - Dropping the future returned by `spawn()` kills the command's process group
25
+
26
+ ### Fixed
27
+
28
+ - `spawn_sync()` no longer deadlocks when called from a current-thread Tokio runtime
29
+ - Python releases now include `abi3` wheels for Linux and macOS on x86-64 and ARM64, plus a source distribution
30
+
31
+ ### Security
32
+
33
+ - Upgraded PyO3 to 0.29.3 to address RUSTSEC-2026-0176 and RUSTSEC-2026-0177
34
+
35
+ ## [0.1.0] - 2026-01-11
36
+
37
+ ### Added
38
+
39
+ - Initial release
40
+ - Core `ProcPolicy` with builder pattern
41
+ - `ArgRules` for argument validation
42
+ - Flag allowlist
43
+ - Subcommand pinning
44
+ - Double-dash injection
45
+ - `EnvPolicy` with ALWAYS_STRIP protection
46
+ - `CwdPolicy` for working directory control
47
+ - `ResourceLimits` (timeout, stdout/stderr caps)
48
+ - `RiskyBinPolicy` for shells, interpreters, spawners, privilege tools
49
+ - Path canonicalization with symlink resolution
50
+ - Python bindings via PyO3
51
+
52
+ ### Security
53
+
54
+ - No shell interpretation (execve-style only)
55
+ - Absolute paths required
56
+ - Fail-closed design
57
+ - Environment variable sanitization