# OPP Python SDK (`opp_py`)
Instrumentation + CLI for ODIN Provenance Passport (OPP).
## Features
- `@stamp(step_type, attrs=..., inputs=..., outputs=...)` decorator emits start/end signed receipts.
- Automatic input/output content IDs (CIDs) via optional callables.
- Fallback lightweight OPE client (no external `odin-sdk` required) using env Ed25519 seed.
- Graph + Passport generation (`opp graph`, `opp passport`).
- Policy evidence aggregation & breach summary (`opp policy`).
- Optional C2PA bridge (`opp.c2pa.embed_bundle_cid`) to embed bundle CID into images (extra deps).
## Install (editable dev)
```bash
pip install -e packages/opp_py
```
Required env for stamping (generate a random 32‑byte seed once):
```bash
export OPP_GATEWAY_URL=http://127.0.0.1:8080
export OPP_SENDER_PRIV_B64=<base64url_32byte_seed>
export OPP_SENDER_KID=opp-sender
```
Generate a seed (PowerShell):
```powershell
$bytes = New-Object byte[] 32; [Security.Cryptography.RandomNumberGenerator]::Create().GetBytes($bytes); \
$seed = [Convert]::ToBase64String($bytes).TrimEnd('=') -replace '\+','-' -replace '/','_'; $seed
```
## Decorator Usage
```python
from opp.decorators import stamp
@stamp(
"train.v1",
attrs={"model":"resnet"},
inputs=lambda args, kwargs: {"hyperparams": kwargs.get("hp")},
outputs=lambda ret: {"metrics": ret.get("metrics")}
)
def train(data, *, hp):
# ... training ...
return {"metrics": {"accuracy": 0.93}}
train([], hp={"lr":1e-3})
```
Emitted start receipt includes `inputs_cid`; end receipt includes `outputs_cid` and `status`.
## CLI
```bash
opp graph --trace TRACE --gateway $OPP_GATEWAY_URL # build minimal graph
opp validate --trace TRACE --gateway $OPP_GATEWAY_URL # continuity + basic validation
opp passport --trace TRACE --gateway $OPP_GATEWAY_URL # rich model/data passport JSON
opp policy --trace TRACE --gateway $OPP_GATEWAY_URL # summarized policy evidence + breaches
```
## Passport Fields (excerpt)
```jsonc
{
"trace_id": "...",
"receipts": 12,
"steps": ["ingest.v1","train.v1"],
"dataset_roots": ["sha256:..."],
"model_id": "model-123",
"metrics": {"accuracy": 0.93},
"safety_flags": {"pii_redacted": true},
"policy_engines": ["opa"],
"policy_breaches": [{"rule":"no_public_data","outcome":"deny"}]
}
```
## Policy Evidence
If receipts carry a normalized `policy` object with `engine` + `decisions[]`, breaches are auto‑derived when an outcome is not in `{allow, pass, ok}`.
## Optional C2PA Bridge
```bash
pip install c2pa Pillow
python examples/c2pa_embed.py image.png
```
Adds a custom assertion with the `bundle_cid` to the image manifest.
## Airflow & Dagster Examples
See `examples/airflow_dag.py` and `examples/dagster_job.py` for task/op instrumentation and trace continuity.
## Testing
```bash
pytest -q packages/opp_py/tests
```
## Backward Compatibility
New fields are additive; existing receipt payload fields preserved. Hashing uses canonical JSON (stable order, no whitespace).
## License
Apache 2.0
Raw data
{
"_id": null,
"home_page": null,
"name": "opp-py",
"maintainer": null,
"docs_url": null,
"requires_python": ">=3.10",
"maintainer_email": null,
"keywords": "provenance, ai, model passport, odin, ope, c2pa, policy",
"author": "Maverick0351a",
"author_email": null,
"download_url": "https://files.pythonhosted.org/packages/21/cc/216fecc91091854b82305372a0b1afdcf2a249d977b29b6e7aabc320b297/opp_py-0.1.1.tar.gz",
"platform": null,
"description": "# OPP Python SDK (`opp_py`)\n\nInstrumentation + CLI for ODIN Provenance Passport (OPP).\n\n## Features\n- `@stamp(step_type, attrs=..., inputs=..., outputs=...)` decorator emits start/end signed receipts.\n- Automatic input/output content IDs (CIDs) via optional callables.\n- Fallback lightweight OPE client (no external `odin-sdk` required) using env Ed25519 seed.\n- Graph + Passport generation (`opp graph`, `opp passport`).\n- Policy evidence aggregation & breach summary (`opp policy`).\n- Optional C2PA bridge (`opp.c2pa.embed_bundle_cid`) to embed bundle CID into images (extra deps).\n\n## Install (editable dev)\n```bash\npip install -e packages/opp_py\n```\n\nRequired env for stamping (generate a random 32\u2011byte seed once):\n```bash\nexport OPP_GATEWAY_URL=http://127.0.0.1:8080\nexport OPP_SENDER_PRIV_B64=<base64url_32byte_seed>\nexport OPP_SENDER_KID=opp-sender\n```\n\nGenerate a seed (PowerShell):\n```powershell\n$bytes = New-Object byte[] 32; [Security.Cryptography.RandomNumberGenerator]::Create().GetBytes($bytes); \\\n$seed = [Convert]::ToBase64String($bytes).TrimEnd('=') -replace '\\+','-' -replace '/','_'; $seed\n```\n\n## Decorator Usage\n```python\nfrom opp.decorators import stamp\n\n@stamp(\n\t\t\"train.v1\",\n\t\tattrs={\"model\":\"resnet\"},\n\t\tinputs=lambda args, kwargs: {\"hyperparams\": kwargs.get(\"hp\")},\n\t\toutputs=lambda ret: {\"metrics\": ret.get(\"metrics\")}\n)\ndef train(data, *, hp):\n\t\t# ... training ...\n\t\treturn {\"metrics\": {\"accuracy\": 0.93}}\n\ntrain([], hp={\"lr\":1e-3})\n```\n\nEmitted start receipt includes `inputs_cid`; end receipt includes `outputs_cid` and `status`.\n\n## CLI\n```bash\nopp graph --trace TRACE --gateway $OPP_GATEWAY_URL # build minimal graph\nopp validate --trace TRACE --gateway $OPP_GATEWAY_URL # continuity + basic validation\nopp passport --trace TRACE --gateway $OPP_GATEWAY_URL # rich model/data passport JSON\nopp policy --trace TRACE --gateway $OPP_GATEWAY_URL # summarized policy evidence + breaches\n```\n\n## Passport Fields (excerpt)\n```jsonc\n{\n\t\"trace_id\": \"...\",\n\t\"receipts\": 12,\n\t\"steps\": [\"ingest.v1\",\"train.v1\"],\n\t\"dataset_roots\": [\"sha256:...\"],\n\t\"model_id\": \"model-123\",\n\t\"metrics\": {\"accuracy\": 0.93},\n\t\"safety_flags\": {\"pii_redacted\": true},\n\t\"policy_engines\": [\"opa\"],\n\t\"policy_breaches\": [{\"rule\":\"no_public_data\",\"outcome\":\"deny\"}]\n}\n```\n\n## Policy Evidence\nIf receipts carry a normalized `policy` object with `engine` + `decisions[]`, breaches are auto\u2011derived when an outcome is not in `{allow, pass, ok}`.\n\n## Optional C2PA Bridge\n```bash\npip install c2pa Pillow\npython examples/c2pa_embed.py image.png\n```\nAdds a custom assertion with the `bundle_cid` to the image manifest.\n\n## Airflow & Dagster Examples\nSee `examples/airflow_dag.py` and `examples/dagster_job.py` for task/op instrumentation and trace continuity.\n\n## Testing\n```bash\npytest -q packages/opp_py/tests\n```\n\n## Backward Compatibility\nNew fields are additive; existing receipt payload fields preserved. Hashing uses canonical JSON (stable order, no whitespace).\n\n## License\nApache 2.0\n",
"bugtrack_url": null,
"license": null,
"summary": "ODIN Provenance Passport \u2014 Python instrumentation + CLI",
"version": "0.1.1",
"project_urls": {
"Documentation": "https://github.com/Maverick0351a/opp-provenance-passport#readme",
"Homepage": "https://github.com/Maverick0351a/opp-provenance-passport",
"Issues": "https://github.com/Maverick0351a/opp-provenance-passport/issues",
"Repository": "https://github.com/Maverick0351a/opp-provenance-passport"
},
"split_keywords": [
"provenance",
" ai",
" model passport",
" odin",
" ope",
" c2pa",
" policy"
],
"urls": [
{
"comment_text": null,
"digests": {
"blake2b_256": "1bb97100f5e879fa97d20cf40298161aa890c5718165d5e4cd9721bc6ee83542",
"md5": "fcbb87e7ef9bc5a6dc5ee105c1dff8cc",
"sha256": "3aa017c3bb2313931d9a9427a49970c5e711be9465d459e62dcadf93f592e646"
},
"downloads": -1,
"filename": "opp_py-0.1.1-py3-none-any.whl",
"has_sig": false,
"md5_digest": "fcbb87e7ef9bc5a6dc5ee105c1dff8cc",
"packagetype": "bdist_wheel",
"python_version": "py3",
"requires_python": ">=3.10",
"size": 11402,
"upload_time": "2025-08-24T01:29:22",
"upload_time_iso_8601": "2025-08-24T01:29:22.531322Z",
"url": "https://files.pythonhosted.org/packages/1b/b9/7100f5e879fa97d20cf40298161aa890c5718165d5e4cd9721bc6ee83542/opp_py-0.1.1-py3-none-any.whl",
"yanked": false,
"yanked_reason": null
},
{
"comment_text": null,
"digests": {
"blake2b_256": "21cc216fecc91091854b82305372a0b1afdcf2a249d977b29b6e7aabc320b297",
"md5": "83818e073102ae3a6463ad27696438da",
"sha256": "d7e2f307ee53eda3d2fff3ab2d235b5bb717b9aa6adacbe26164c2bc5ebb78a9"
},
"downloads": -1,
"filename": "opp_py-0.1.1.tar.gz",
"has_sig": false,
"md5_digest": "83818e073102ae3a6463ad27696438da",
"packagetype": "sdist",
"python_version": "source",
"requires_python": ">=3.10",
"size": 12299,
"upload_time": "2025-08-24T01:29:23",
"upload_time_iso_8601": "2025-08-24T01:29:23.543025Z",
"url": "https://files.pythonhosted.org/packages/21/cc/216fecc91091854b82305372a0b1afdcf2a249d977b29b6e7aabc320b297/opp_py-0.1.1.tar.gz",
"yanked": false,
"yanked_reason": null
}
],
"upload_time": "2025-08-24 01:29:23",
"github": true,
"gitlab": false,
"bitbucket": false,
"codeberg": false,
"github_user": "Maverick0351a",
"github_project": "opp-provenance-passport#readme",
"travis_ci": false,
"coveralls": false,
"github_actions": true,
"lcname": "opp-py"
}