openmuse-agent 0.3.0a0__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 (99) hide show
  1. openmuse_agent-0.3.0a0/.devcontainer/devcontainer.json +6 -0
  2. openmuse_agent-0.3.0a0/.github/ISSUE_TEMPLATE/bug.yml +11 -0
  3. openmuse_agent-0.3.0a0/.github/ISSUE_TEMPLATE/config.yml +5 -0
  4. openmuse_agent-0.3.0a0/.github/ISSUE_TEMPLATE/connector.yml +12 -0
  5. openmuse_agent-0.3.0a0/.github/ISSUE_TEMPLATE/feature.yml +12 -0
  6. openmuse_agent-0.3.0a0/.github/dependabot.yml +8 -0
  7. openmuse_agent-0.3.0a0/.github/pull_request_template.md +9 -0
  8. openmuse_agent-0.3.0a0/.github/workflows/ci.yml +20 -0
  9. openmuse_agent-0.3.0a0/.github/workflows/codeql.yml +19 -0
  10. openmuse_agent-0.3.0a0/.github/workflows/dependency-review.yml +10 -0
  11. openmuse_agent-0.3.0a0/.github/workflows/release.yml +21 -0
  12. openmuse_agent-0.3.0a0/.github/workflows/security.yml +18 -0
  13. openmuse_agent-0.3.0a0/.gitignore +11 -0
  14. openmuse_agent-0.3.0a0/CHANGELOG.md +35 -0
  15. openmuse_agent-0.3.0a0/CITATION.cff +10 -0
  16. openmuse_agent-0.3.0a0/CODE_OF_CONDUCT.md +2 -0
  17. openmuse_agent-0.3.0a0/CONTRIBUTING.md +33 -0
  18. openmuse_agent-0.3.0a0/GOVERNANCE.md +2 -0
  19. openmuse_agent-0.3.0a0/LICENSE +21 -0
  20. openmuse_agent-0.3.0a0/PKG-INFO +179 -0
  21. openmuse_agent-0.3.0a0/README.md +155 -0
  22. openmuse_agent-0.3.0a0/SECURITY.md +9 -0
  23. openmuse_agent-0.3.0a0/SUPPORT.md +3 -0
  24. openmuse_agent-0.3.0a0/docs/adr/0001-security-first-runtime.md +2 -0
  25. openmuse_agent-0.3.0a0/docs/adr/0002-scoped-connectors.md +39 -0
  26. openmuse_agent-0.3.0a0/docs/architecture.md +15 -0
  27. openmuse_agent-0.3.0a0/docs/assets/openmuse-demo.cast +20 -0
  28. openmuse_agent-0.3.0a0/docs/isolated-worker.md +42 -0
  29. openmuse_agent-0.3.0a0/docs/product-foundation.md +5 -0
  30. openmuse_agent-0.3.0a0/docs/roadmap.md +7 -0
  31. openmuse_agent-0.3.0a0/docs/security/review-checklist.md +31 -0
  32. openmuse_agent-0.3.0a0/docs/security/reviewer-brief.md +13 -0
  33. openmuse_agent-0.3.0a0/docs/threat-model.md +16 -0
  34. openmuse_agent-0.3.0a0/examples/e2e_demo.py +74 -0
  35. openmuse_agent-0.3.0a0/examples/isolated_worker_demo.py +17 -0
  36. openmuse_agent-0.3.0a0/examples/local_planner.py +9 -0
  37. openmuse_agent-0.3.0a0/examples/verify_audit.py +44 -0
  38. openmuse_agent-0.3.0a0/examples/worker_echo.py +17 -0
  39. openmuse_agent-0.3.0a0/pyproject.toml +27 -0
  40. openmuse_agent-0.3.0a0/src/openmuse/__init__.py +3 -0
  41. openmuse_agent-0.3.0a0/src/openmuse/approval_ui.py +14 -0
  42. openmuse_agent-0.3.0a0/src/openmuse/approvals.py +60 -0
  43. openmuse_agent-0.3.0a0/src/openmuse/audit.py +64 -0
  44. openmuse_agent-0.3.0a0/src/openmuse/broker.py +77 -0
  45. openmuse_agent-0.3.0a0/src/openmuse/browser_worker.py +24 -0
  46. openmuse_agent-0.3.0a0/src/openmuse/channels/__init__.py +4 -0
  47. openmuse_agent-0.3.0a0/src/openmuse/channels/base.py +17 -0
  48. openmuse_agent-0.3.0a0/src/openmuse/channels/web.py +21 -0
  49. openmuse_agent-0.3.0a0/src/openmuse/cli.py +27 -0
  50. openmuse_agent-0.3.0a0/src/openmuse/connectors.py +130 -0
  51. openmuse_agent-0.3.0a0/src/openmuse/core.py +65 -0
  52. openmuse_agent-0.3.0a0/src/openmuse/effects.py +39 -0
  53. openmuse_agent-0.3.0a0/src/openmuse/ephemeral.py +32 -0
  54. openmuse_agent-0.3.0a0/src/openmuse/evidence.py +31 -0
  55. openmuse_agent-0.3.0a0/src/openmuse/google_calendar_connector.py +112 -0
  56. openmuse_agent-0.3.0a0/src/openmuse/google_mail_connector.py +116 -0
  57. openmuse_agent-0.3.0a0/src/openmuse/google_oauth.py +166 -0
  58. openmuse_agent-0.3.0a0/src/openmuse/host_events.py +57 -0
  59. openmuse_agent-0.3.0a0/src/openmuse/isolated_worker.py +73 -0
  60. openmuse_agent-0.3.0a0/src/openmuse/keyring_keys.py +54 -0
  61. openmuse_agent-0.3.0a0/src/openmuse/memory.py +192 -0
  62. openmuse_agent-0.3.0a0/src/openmuse/models.py +32 -0
  63. openmuse_agent-0.3.0a0/src/openmuse/policy.py +33 -0
  64. openmuse_agent-0.3.0a0/src/openmuse/providers/__init__.py +3 -0
  65. openmuse_agent-0.3.0a0/src/openmuse/providers/openai_compatible.py +35 -0
  66. openmuse_agent-0.3.0a0/src/openmuse/registry.py +21 -0
  67. openmuse_agent-0.3.0a0/src/openmuse/scheduler.py +133 -0
  68. openmuse_agent-0.3.0a0/src/openmuse/secrets.py +72 -0
  69. openmuse_agent-0.3.0a0/src/openmuse/simulated_connectors.py +69 -0
  70. openmuse_agent-0.3.0a0/src/openmuse/subagents.py +105 -0
  71. openmuse_agent-0.3.0a0/src/openmuse/task_ui.py +16 -0
  72. openmuse_agent-0.3.0a0/src/openmuse/tasks.py +98 -0
  73. openmuse_agent-0.3.0a0/src/openmuse/tools.py +159 -0
  74. openmuse_agent-0.3.0a0/src/openmuse/validation.py +59 -0
  75. openmuse_agent-0.3.0a0/tests/test_approvals.py +115 -0
  76. openmuse_agent-0.3.0a0/tests/test_argument_validation.py +54 -0
  77. openmuse_agent-0.3.0a0/tests/test_audit_verify.py +18 -0
  78. openmuse_agent-0.3.0a0/tests/test_broker.py +98 -0
  79. openmuse_agent-0.3.0a0/tests/test_cli.py +22 -0
  80. openmuse_agent-0.3.0a0/tests/test_connectors.py +170 -0
  81. openmuse_agent-0.3.0a0/tests/test_core.py +43 -0
  82. openmuse_agent-0.3.0a0/tests/test_demo.py +29 -0
  83. openmuse_agent-0.3.0a0/tests/test_fetch_url_security.py +72 -0
  84. openmuse_agent-0.3.0a0/tests/test_google_calendar_connector.py +51 -0
  85. openmuse_agent-0.3.0a0/tests/test_google_mail_connector.py +54 -0
  86. openmuse_agent-0.3.0a0/tests/test_google_oauth.py +61 -0
  87. openmuse_agent-0.3.0a0/tests/test_host_events_and_streams.py +59 -0
  88. openmuse_agent-0.3.0a0/tests/test_isolated_worker.py +41 -0
  89. openmuse_agent-0.3.0a0/tests/test_isolated_worker_demo.py +21 -0
  90. openmuse_agent-0.3.0a0/tests/test_keyring_keys.py +31 -0
  91. openmuse_agent-0.3.0a0/tests/test_memory_verification.py +147 -0
  92. openmuse_agent-0.3.0a0/tests/test_openai_compatible.py +29 -0
  93. openmuse_agent-0.3.0a0/tests/test_packaging.py +8 -0
  94. openmuse_agent-0.3.0a0/tests/test_product_foundation.py +46 -0
  95. openmuse_agent-0.3.0a0/tests/test_safety_capabilities.py +43 -0
  96. openmuse_agent-0.3.0a0/tests/test_scheduler.py +83 -0
  97. openmuse_agent-0.3.0a0/tests/test_simulated_connectors.py +49 -0
  98. openmuse_agent-0.3.0a0/tests/test_subagents.py +105 -0
  99. openmuse_agent-0.3.0a0/tests/test_version.py +7 -0
@@ -0,0 +1,6 @@
1
+ {
2
+ "name": "OpenMuse demo",
3
+ "image": "mcr.microsoft.com/devcontainers/python:3.12",
4
+ "postCreateCommand": "pip install -e '.[dev]'",
5
+ "postStartCommand": "printf '\nOpenMuse is ready. Run: python examples/e2e_demo.py\nThen verify: python examples/verify_audit.py\n'"
6
+ }
@@ -0,0 +1,11 @@
1
+ name: Bug report
2
+ description: Report a reproducible defect
3
+ body:
4
+ - type: textarea
5
+ attributes: {label: What happened?}
6
+ validations: {required: true}
7
+ - type: textarea
8
+ attributes: {label: Reproduction steps}
9
+ validations: {required: true}
10
+ - type: input
11
+ attributes: {label: OpenMuse and Python versions}
@@ -0,0 +1,5 @@
1
+ blank_issues_enabled: false
2
+ contact_links:
3
+ - name: Security vulnerability
4
+ url: https://github.com/tahodev/openmuse/security/advisories/new
5
+ about: Report vulnerabilities privately, not in a public issue.
@@ -0,0 +1,12 @@
1
+ name: Connector proposal
2
+ description: Propose a least-privilege integration
3
+ body:
4
+ - type: input
5
+ attributes: {label: Service and use case}
6
+ validations: {required: true}
7
+ - type: textarea
8
+ attributes: {label: Required scopes and data flow}
9
+ validations: {required: true}
10
+ - type: textarea
11
+ attributes: {label: Risks, revocation, and simulation mode}
12
+ validations: {required: true}
@@ -0,0 +1,12 @@
1
+ name: Feature request
2
+ description: Propose a focused improvement
3
+ body:
4
+ - type: textarea
5
+ attributes: {label: Problem, description: What user problem should this solve?}
6
+ validations: {required: true}
7
+ - type: textarea
8
+ attributes: {label: Proposed behavior}
9
+ validations: {required: true}
10
+ - type: textarea
11
+ attributes: {label: Trust-boundary impact, description: Note new data, permissions, side effects, or say none.}
12
+ validations: {required: true}
@@ -0,0 +1,8 @@
1
+ version: 2
2
+ updates:
3
+ - package-ecosystem: pip
4
+ directory: /
5
+ schedule: {interval: weekly}
6
+ - package-ecosystem: github-actions
7
+ directory: /
8
+ schedule: {interval: weekly}
@@ -0,0 +1,9 @@
1
+ ## What changed
2
+ ## Why
3
+ ## Trust-boundary impact
4
+ - [ ] No change
5
+ - [ ] Documented and tested
6
+ ## Checklist
7
+ - [ ] Tests added/updated
8
+ - [ ] Docs updated
9
+ - [ ] `ruff check`, `pytest`, and `python -m build` pass
@@ -0,0 +1,20 @@
1
+ name: CI
2
+ on: [push, pull_request]
3
+ permissions: {contents: read}
4
+ jobs:
5
+ test:
6
+ runs-on: ubuntu-latest
7
+ strategy: {matrix: {python-version: ['3.11','3.12','3.13']}}
8
+ steps:
9
+ - uses: actions/checkout@11d5960a326750d5838078e36cf38b85af677262 # v4
10
+ - uses: actions/setup-python@a26af69be951a213d495a4c3e4e4022e16d87065 # v5
11
+ with: {python-version: '${{ matrix.python-version }}'}
12
+ - run: python -m pip install -e '.[dev]'
13
+ - run: ruff check src tests
14
+ - run: mypy src/openmuse
15
+ - run: pytest --cov=openmuse --cov-report=term-missing --cov-fail-under=85
16
+ - run: python examples/e2e_demo.py --auto-approve
17
+ - run: python examples/verify_audit.py
18
+ - run: python -m build
19
+ - run: python -m pip install --force-reinstall dist/*.whl
20
+ - run: python -c "import importlib.metadata, openmuse; assert openmuse.__version__ == importlib.metadata.version('openmuse-agent')"
@@ -0,0 +1,19 @@
1
+ name: CodeQL
2
+ on:
3
+ push:
4
+ branches: [main]
5
+ pull_request:
6
+ branches: [main]
7
+ schedule:
8
+ - cron: '17 4 * * 1'
9
+ permissions:
10
+ contents: read
11
+ security-events: write
12
+ jobs:
13
+ analyze:
14
+ runs-on: ubuntu-latest
15
+ steps:
16
+ - uses: actions/checkout@11d5960a326750d5838078e36cf38b85af677262 # v4
17
+ - uses: github/codeql-action/init@c20e34f438d671fc35777cc9820dd7adf8252874 # v3
18
+ with: {languages: python}
19
+ - uses: github/codeql-action/analyze@c20e34f438d671fc35777cc9820dd7adf8252874 # v3
@@ -0,0 +1,10 @@
1
+ name: Dependency review
2
+ on: [pull_request]
3
+ permissions:
4
+ contents: read
5
+ jobs:
6
+ review:
7
+ runs-on: ubuntu-latest
8
+ steps:
9
+ - uses: actions/checkout@11d5960a326750d5838078e36cf38b85af677262 # v4
10
+ - uses: actions/dependency-review-action@2031cfc080254a8a887f58cffee85186f0e49e48 # v4
@@ -0,0 +1,21 @@
1
+ name: Release
2
+ on:
3
+ push:
4
+ tags: ['v*']
5
+ permissions:
6
+ contents: read
7
+ id-token: write
8
+ jobs:
9
+ build:
10
+ runs-on: ubuntu-latest
11
+ environment: release
12
+ steps:
13
+ - uses: actions/checkout@11d5960a326750d5838078e36cf38b85af677262 # v4
14
+ - uses: actions/setup-python@a26af69be951a213d495a4c3e4e4022e16d87065 # v5
15
+ with: {python-version: '3.12'}
16
+ - run: python -m pip install build
17
+ - run: python -m build
18
+ - uses: actions/upload-artifact@ea165f8d65b6e75b540449e92b4886f43607fa02
19
+ with: {name: dist, path: dist/}
20
+ - name: Publish to PyPI
21
+ uses: pypa/gh-action-pypi-publish@dc37677b2e1c63e2034f94d8a5b11f265b73ba33 # release/v1
@@ -0,0 +1,18 @@
1
+ name: Python security checks
2
+ on:
3
+ push:
4
+ branches: [main]
5
+ pull_request:
6
+ branches: [main]
7
+ schedule:
8
+ - cron: '41 4 * * 2'
9
+ permissions: {contents: read}
10
+ jobs:
11
+ audit:
12
+ runs-on: ubuntu-latest
13
+ steps:
14
+ - uses: actions/checkout@11d5960a326750d5838078e36cf38b85af677262 # v4
15
+ - uses: actions/setup-python@a26af69be951a213d495a4c3e4e4022e16d87065 # v5
16
+ with: {python-version: '3.12'}
17
+ - run: python -m pip install -e . pip-audit
18
+ - run: pip-audit
@@ -0,0 +1,11 @@
1
+ __pycache__/
2
+ .pytest_cache/
3
+ .venv/
4
+ dist/
5
+ .openmuse/
6
+ *.py[cod]
7
+ .coverage
8
+ coverage.json
9
+ htmlcov/
10
+ build/
11
+ *.egg-info/
@@ -0,0 +1,35 @@
1
+ # Changelog
2
+
3
+ All notable changes are recorded here. OpenMuse follows semantic versioning while using prerelease tags for alpha builds.
4
+
5
+ ## Unreleased
6
+
7
+ ## v0.3.0-alpha - 2026-09-19
8
+
9
+ ### Added
10
+
11
+ - Managed Google OAuth with authorization-code exchange, automatic refresh, encrypted token storage, and OS-keyring-backed master keys.
12
+ - Read-only Gmail and Google Calendar connectors built on scoped, least-privilege grants, plus credential-free local simulation connectors.
13
+ - Searchable and editable working/curated memory with hash-chained remember, promote, edit, and forget events, plus state verification against the audit chain.
14
+ - Five-field cron scheduling with atomic job claims across workers, and subagent grants that can only narrow tools, budgets, expiry, and argument constraints.
15
+ - A secrets broker that passes named secrets to tools through a scoped execution side channel without exposing plaintext to planner context, manifests, action arguments, or audit logs.
16
+ - A fresh-process isolated worker with bounded runtime, memory, file descriptors, output, environment, and workspace.
17
+ - An independent security-review packet with a reviewer brief and checklist.
18
+
19
+ ### Changed
20
+
21
+ - The approval demo now shows the exact tool, path, content preview, and SHA-256 being approved, then verifies that the approved action is the action executed.
22
+ - Connector revocation now clears cached clients and fails closed if cleanup does not complete.
23
+ - Tool arguments are validated before approval, policy checks, and execution.
24
+ - `FetchURL` now resolves once and pins connections to validated public addresses to prevent DNS-rebinding bypasses.
25
+ - Project metadata and runtime version are aligned for this prerelease.
26
+
27
+ ### Fixed
28
+
29
+ - Approval tokens are consumed atomically, preventing concurrent verification from using one approval twice.
30
+ - Approval expiry now rejects tokens at the exact expiry boundary (`now >= exp`).
31
+ - Scheduled jobs are claimed transactionally so parallel workers cannot run the same job twice.
32
+
33
+ ### Known limitations
34
+
35
+ - OpenMuse remains alpha software for test accounts and non-sensitive data. Documentation drift in the security limits is being cleaned up separately.
@@ -0,0 +1,10 @@
1
+ cff-version: 1.2.0
2
+ message: "If you use OpenMuse in research, please cite this software."
3
+ title: "OpenMuse"
4
+ type: software
5
+ authors:
6
+ - name: "tahodev"
7
+ repository-code: "https://github.com/tahodev/openmuse"
8
+ license: MIT
9
+ version: 0.3.0-alpha
10
+ date-released: 2026-09-19
@@ -0,0 +1,2 @@
1
+ # Code of Conduct
2
+ We follow the [Contributor Covenant 2.1](https://www.contributor-covenant.org/version/2/1/code_of_conduct/). Be respectful, assume good intent, and avoid harassment. Report conduct concerns privately through a GitHub security advisory; maintainers will review them promptly and confidentially.
@@ -0,0 +1,33 @@
1
+ # Contributing
2
+
3
+ ## Set up
4
+
5
+ 1. Fork the repository and branch from `main`.
6
+ 2. Use Python 3.11 or newer.
7
+ 3. Run `python -m venv .venv`, activate it, then `pip install -e '.[dev]'`.
8
+ 4. Before opening a pull request, run:
9
+
10
+ ```bash
11
+ ruff check src tests
12
+ mypy src/openmuse
13
+ pytest --cov=openmuse --cov-fail-under=85
14
+ python examples/e2e_demo.py --auto-approve
15
+ python examples/verify_audit.py
16
+ python -m build
17
+ ```
18
+
19
+ ## Changes to trust boundaries
20
+
21
+ Open an issue before changing the permission model, approvals, audit format, connector scopes, data retention, or secret handling. Describe assets, attackers, failure modes, revocation, simulation behavior, and the tests that prove fail-closed behavior. Changes to these boundaries need an ADR in `docs/adr/`, threat-model updates, tests, and maintainer approval.
22
+
23
+ ## Connectors
24
+
25
+ Start read-only, request the smallest scopes, document data flow and deletion/revocation, support simulation where possible, and never put credentials or private payloads in fixtures, logs, or issues.
26
+
27
+ ## Pull requests
28
+
29
+ Keep changes small. Explain the user-visible behavior, trust-boundary impact, compatibility risk, and test evidence. Update docs with behavior changes and complete the pull-request checklist.
30
+
31
+ ## Releases
32
+
33
+ Maintainers use semantic versioning with prerelease tags for alpha work. A release must pass CI, build from a clean checkout, match `openmuse.__version__`, include release notes, and be checked on TestPyPI before PyPI.
@@ -0,0 +1,2 @@
1
+ # Governance
2
+ OpenMuse is maintainer-led. Changes to security boundaries, approval semantics, connector scopes, or data retention require an issue, threat-model review, tests, and maintainer approval. Decisions are recorded as ADRs. Releases use semantic versioning.
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 tahodev
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
@@ -0,0 +1,179 @@
1
+ Metadata-Version: 2.5
2
+ Name: openmuse-agent
3
+ Version: 0.3.0a0
4
+ Summary: A local-first, auditable personal AI agent runtime
5
+ Project-URL: Homepage, https://github.com/tahodev/openmuse
6
+ Project-URL: Issues, https://github.com/tahodev/openmuse/issues
7
+ Author: tahodev
8
+ License-Expression: MIT
9
+ License-File: LICENSE
10
+ Keywords: ai-agent,automation,local-first,personal-agent
11
+ Classifier: Development Status :: 3 - Alpha
12
+ Classifier: License :: OSI Approved :: MIT License
13
+ Classifier: Programming Language :: Python :: 3
14
+ Requires-Python: >=3.11
15
+ Requires-Dist: cryptography>=43
16
+ Requires-Dist: keyring>=25
17
+ Provides-Extra: dev
18
+ Requires-Dist: build>=1.2; extra == 'dev'
19
+ Requires-Dist: mypy>=1.11; extra == 'dev'
20
+ Requires-Dist: pytest-cov>=5; extra == 'dev'
21
+ Requires-Dist: pytest>=8; extra == 'dev'
22
+ Requires-Dist: ruff>=0.6; extra == 'dev'
23
+ Description-Content-Type: text/markdown
24
+
25
+ # OpenMuse
26
+
27
+ [![CI](https://github.com/tahodev/openmuse/actions/workflows/ci.yml/badge.svg)](https://github.com/tahodev/openmuse/actions/workflows/ci.yml)
28
+ [![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](LICENSE)
29
+ [![Open in GitHub Codespaces](https://github.com/codespaces/badge.svg)](https://codespaces.new/tahodev/openmuse?quickstart=1)
30
+
31
+ A local-first, auditable personal AI agent runtime. OpenMuse separates untrusted planners from typed tools, host-issued approvals, durable tasks, encrypted secrets, and redacted audit history.
32
+
33
+ ## Why OpenMuse is different
34
+
35
+ The goal is the smallest readable personal-agent runtime whose safety semantics are verified in code and tests:
36
+
37
+ - **Exact-action approval.** The host signs each approval token against one action's tool and arguments. Tokens expire and can be consumed exactly once. The planner cannot mint approvals, and approving one action never approves a similar-looking one.
38
+ - **Verifiable audit.** Every decision lands in a redacted, hash-chained local log that you can re-verify independently. Change one audited byte and verification fails.
39
+ - **Secrets never reach the model.** Tools receive decrypted secrets through a host callback at execution time. Secret values never appear in planner context, action arguments, tool manifests, or the audit log.
40
+
41
+ ## See the safety boundary in 30 seconds
42
+
43
+ One simple story: the agent starts a task, pauses before one write, the user approves exactly that action, it runs, and the audit chain proves what happened.
44
+
45
+ [![Play the real terminal recording](https://asciinema.org/a/MYdPbeccAUeoC8uy.svg)](https://asciinema.org/a/MYdPbeccAUeoC8uy)
46
+
47
+ This is a real terminal capture. Its raw, replayable cast is also [checked into the repository](docs/assets/openmuse-demo.cast).
48
+
49
+ ## The approval boundary
50
+
51
+ The planner and everything it reads are untrusted. Only the trusted host can issue an approval, and it issues one for the exact action the user approved:
52
+
53
+ ```mermaid
54
+ flowchart TD
55
+ U([User])
56
+ subgraph untrusted["Untrusted"]
57
+ P["Planner (model)"]
58
+ X["External content: pages, messages, files"]
59
+ end
60
+ subgraph host["Trusted host"]
61
+ POL["Policy"]
62
+ AUTH["Approval authority"]
63
+ VAULT["Secret vault"]
64
+ EXEC["Tool executor"]
65
+ AUD["Hash-chained audit log"]
66
+ end
67
+ X -.-> P
68
+ P -->|proposes one typed action| POL
69
+ POL -->|sensitive action: ask| U
70
+ U -->|approves this exact action| AUTH
71
+ AUTH -->|one-time, expiring, action-bound token| EXEC
72
+ POL -->|allow| EXEC
73
+ VAULT -->|decrypts via host callback| EXEC
74
+ EXEC -->|typed result| P
75
+ POL --> AUD
76
+ AUTH --> AUD
77
+ EXEC --> AUD
78
+ ```
79
+
80
+ ## Use a real model
81
+
82
+ `OpenAICompatiblePlanner` supports OpenAI-compatible chat-completions endpoints. Set `OPENAI_API_KEY` and pass the planner to `Agent.run()`. This is an alpha adapter: use a test key and non-sensitive data.
83
+
84
+ ```python
85
+ import os
86
+ from pathlib import Path
87
+ from openmuse.core import Agent
88
+ from openmuse.policy import Policy
89
+ from openmuse.providers import OpenAICompatiblePlanner
90
+ from openmuse.tools import ReadFile
91
+
92
+ agent = Agent([ReadFile(Path.cwd())], Policy(), Path(".openmuse/audit.jsonl"))
93
+ planner = OpenAICompatiblePlanner(api_key=os.environ["OPENAI_API_KEY"])
94
+ print(agent.run("Read README.md and stop", planner))
95
+ ```
96
+
97
+ The deterministic demo remains the recommended first run because it is free and reproducible.
98
+
99
+ **Current scope:** an alpha security-primitives runtime and reproducible demo, not a production personal assistant. Unlike [Digger's deployable OpenMuse assistant](https://github.com/diggerhq/openmuse), this project focuses on host-enforced exact-action approval and verifiable local audit trails. The Python distribution is named `openmuse-agent`.
100
+
101
+ > Independent project. Not affiliated with or endorsed by Meta. No Meta code, branding, or assets are used.
102
+
103
+ ## Run it
104
+
105
+ The quickest path opens a ready Python environment. In the terminal, run `python examples/e2e_demo.py` so you can inspect and approve the exact write yourself:
106
+
107
+ [![Open in GitHub Codespaces](https://github.com/codespaces/badge.svg)](https://codespaces.new/tahodev/openmuse?quickstart=1)
108
+
109
+ Or run locally with Python 3.11+ and Git:
110
+
111
+ ```bash
112
+ git clone https://github.com/tahodev/openmuse.git
113
+ cd openmuse
114
+ python -m venv .venv
115
+ source .venv/bin/activate # Windows: .venv\Scripts\activate
116
+ pip install -e '.[dev]'
117
+ python examples/e2e_demo.py
118
+ ```
119
+
120
+ The deterministic demo needs no API key. It keeps the existing web-channel and durable-task flow, but makes the one sensitive write and its host-issued approval visible.
121
+
122
+ ## Verify, don't trust
123
+
124
+ After the demo, independently recompute every audit hash and link:
125
+
126
+ ```bash
127
+ python examples/verify_audit.py
128
+ ```
129
+
130
+ Expected result:
131
+
132
+ ```text
133
+ VERIFIED: 3 records form an intact hash chain
134
+ ```
135
+
136
+ Change any audited byte and verification fails. The verifier is intentionally small: [examples/verify_audit.py](examples/verify_audit.py) calls the public [`verify_chain`](src/openmuse/audit.py) function. The audit contains a blocked attempt, the approved action, and its execution result.
137
+
138
+ ## Status
139
+
140
+ | Capability | Status |
141
+ |---|---|
142
+ | Typed, budgeted agent loop | Working |
143
+ | Exact-action, expiring, one-time approvals | Working |
144
+ | Workspace file tools + SSRF-resistant public fetch | Working |
145
+ | Redacted hash-chained audit | Working |
146
+ | SQLite task checkpoints/cancel/restart | Working |
147
+ | In-process web channel adapter | Experimental |
148
+ | Envelope-encrypted local secret vault | Experimental |
149
+ | Browser-worker policy envelope | Experimental |
150
+ | Persistent task threads + atomic cron job claims | Working |
151
+ | Credential-free read-only mail/calendar connectors | Working |
152
+ | Production-capable read-only Google Calendar and Gmail connectors | Working |
153
+ | Managed Google OAuth code exchange, refresh, encrypted storage, and OS-keyring master key | Working |
154
+ | [Resource-limited OS process worker](docs/isolated-worker.md) | Working |
155
+ | Kernel/network-isolated browser worker | Not yet |
156
+ | Ephemeral OTP grants + exact-total validation | Working |
157
+ | Searchable, tiered, provenance-verifiable memory + edit/forget | Working |
158
+
159
+ Do not use OpenMuse with sensitive production accounts yet. “Working” means covered by the current test suite, not externally audited.
160
+
161
+ ## How it works
162
+
163
+ `Channel -> durable Task -> Planner -> typed Action -> Policy/Approval -> Tool -> typed Result`
164
+
165
+ The model cannot mint approval tokens. Secret decryption happens through a host callback, not planner context. See [architecture](docs/architecture.md), [threat model](docs/threat-model.md), [product foundation](docs/product-foundation.md), and [roadmap](docs/roadmap.md).
166
+
167
+ ## What OpenMuse is and is not
168
+
169
+ | In scope today | Not yet |
170
+ |---|---|
171
+ | Typed local tools, bounded loops, exact-action approval, encrypted local vault, durable tasks, audit verification, simulated mail/calendar connectors | Production browser isolation, independently deployed OAuth callback, independent security review, unattended use with sensitive accounts |
172
+
173
+ ## Contributing
174
+
175
+ See [CONTRIBUTING.md](CONTRIBUTING.md), [governance](GOVERNANCE.md), and the [code of conduct](CODE_OF_CONDUCT.md). Starter work is tracked with [`good first issue`](https://github.com/tahodev/openmuse/labels/good%20first%20issue) and [`help wanted`](https://github.com/tahodev/openmuse/labels/help%20wanted) labels.
176
+
177
+ ## License
178
+
179
+ MIT.
@@ -0,0 +1,155 @@
1
+ # OpenMuse
2
+
3
+ [![CI](https://github.com/tahodev/openmuse/actions/workflows/ci.yml/badge.svg)](https://github.com/tahodev/openmuse/actions/workflows/ci.yml)
4
+ [![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](LICENSE)
5
+ [![Open in GitHub Codespaces](https://github.com/codespaces/badge.svg)](https://codespaces.new/tahodev/openmuse?quickstart=1)
6
+
7
+ A local-first, auditable personal AI agent runtime. OpenMuse separates untrusted planners from typed tools, host-issued approvals, durable tasks, encrypted secrets, and redacted audit history.
8
+
9
+ ## Why OpenMuse is different
10
+
11
+ The goal is the smallest readable personal-agent runtime whose safety semantics are verified in code and tests:
12
+
13
+ - **Exact-action approval.** The host signs each approval token against one action's tool and arguments. Tokens expire and can be consumed exactly once. The planner cannot mint approvals, and approving one action never approves a similar-looking one.
14
+ - **Verifiable audit.** Every decision lands in a redacted, hash-chained local log that you can re-verify independently. Change one audited byte and verification fails.
15
+ - **Secrets never reach the model.** Tools receive decrypted secrets through a host callback at execution time. Secret values never appear in planner context, action arguments, tool manifests, or the audit log.
16
+
17
+ ## See the safety boundary in 30 seconds
18
+
19
+ One simple story: the agent starts a task, pauses before one write, the user approves exactly that action, it runs, and the audit chain proves what happened.
20
+
21
+ [![Play the real terminal recording](https://asciinema.org/a/MYdPbeccAUeoC8uy.svg)](https://asciinema.org/a/MYdPbeccAUeoC8uy)
22
+
23
+ This is a real terminal capture. Its raw, replayable cast is also [checked into the repository](docs/assets/openmuse-demo.cast).
24
+
25
+ ## The approval boundary
26
+
27
+ The planner and everything it reads are untrusted. Only the trusted host can issue an approval, and it issues one for the exact action the user approved:
28
+
29
+ ```mermaid
30
+ flowchart TD
31
+ U([User])
32
+ subgraph untrusted["Untrusted"]
33
+ P["Planner (model)"]
34
+ X["External content: pages, messages, files"]
35
+ end
36
+ subgraph host["Trusted host"]
37
+ POL["Policy"]
38
+ AUTH["Approval authority"]
39
+ VAULT["Secret vault"]
40
+ EXEC["Tool executor"]
41
+ AUD["Hash-chained audit log"]
42
+ end
43
+ X -.-> P
44
+ P -->|proposes one typed action| POL
45
+ POL -->|sensitive action: ask| U
46
+ U -->|approves this exact action| AUTH
47
+ AUTH -->|one-time, expiring, action-bound token| EXEC
48
+ POL -->|allow| EXEC
49
+ VAULT -->|decrypts via host callback| EXEC
50
+ EXEC -->|typed result| P
51
+ POL --> AUD
52
+ AUTH --> AUD
53
+ EXEC --> AUD
54
+ ```
55
+
56
+ ## Use a real model
57
+
58
+ `OpenAICompatiblePlanner` supports OpenAI-compatible chat-completions endpoints. Set `OPENAI_API_KEY` and pass the planner to `Agent.run()`. This is an alpha adapter: use a test key and non-sensitive data.
59
+
60
+ ```python
61
+ import os
62
+ from pathlib import Path
63
+ from openmuse.core import Agent
64
+ from openmuse.policy import Policy
65
+ from openmuse.providers import OpenAICompatiblePlanner
66
+ from openmuse.tools import ReadFile
67
+
68
+ agent = Agent([ReadFile(Path.cwd())], Policy(), Path(".openmuse/audit.jsonl"))
69
+ planner = OpenAICompatiblePlanner(api_key=os.environ["OPENAI_API_KEY"])
70
+ print(agent.run("Read README.md and stop", planner))
71
+ ```
72
+
73
+ The deterministic demo remains the recommended first run because it is free and reproducible.
74
+
75
+ **Current scope:** an alpha security-primitives runtime and reproducible demo, not a production personal assistant. Unlike [Digger's deployable OpenMuse assistant](https://github.com/diggerhq/openmuse), this project focuses on host-enforced exact-action approval and verifiable local audit trails. The Python distribution is named `openmuse-agent`.
76
+
77
+ > Independent project. Not affiliated with or endorsed by Meta. No Meta code, branding, or assets are used.
78
+
79
+ ## Run it
80
+
81
+ The quickest path opens a ready Python environment. In the terminal, run `python examples/e2e_demo.py` so you can inspect and approve the exact write yourself:
82
+
83
+ [![Open in GitHub Codespaces](https://github.com/codespaces/badge.svg)](https://codespaces.new/tahodev/openmuse?quickstart=1)
84
+
85
+ Or run locally with Python 3.11+ and Git:
86
+
87
+ ```bash
88
+ git clone https://github.com/tahodev/openmuse.git
89
+ cd openmuse
90
+ python -m venv .venv
91
+ source .venv/bin/activate # Windows: .venv\Scripts\activate
92
+ pip install -e '.[dev]'
93
+ python examples/e2e_demo.py
94
+ ```
95
+
96
+ The deterministic demo needs no API key. It keeps the existing web-channel and durable-task flow, but makes the one sensitive write and its host-issued approval visible.
97
+
98
+ ## Verify, don't trust
99
+
100
+ After the demo, independently recompute every audit hash and link:
101
+
102
+ ```bash
103
+ python examples/verify_audit.py
104
+ ```
105
+
106
+ Expected result:
107
+
108
+ ```text
109
+ VERIFIED: 3 records form an intact hash chain
110
+ ```
111
+
112
+ Change any audited byte and verification fails. The verifier is intentionally small: [examples/verify_audit.py](examples/verify_audit.py) calls the public [`verify_chain`](src/openmuse/audit.py) function. The audit contains a blocked attempt, the approved action, and its execution result.
113
+
114
+ ## Status
115
+
116
+ | Capability | Status |
117
+ |---|---|
118
+ | Typed, budgeted agent loop | Working |
119
+ | Exact-action, expiring, one-time approvals | Working |
120
+ | Workspace file tools + SSRF-resistant public fetch | Working |
121
+ | Redacted hash-chained audit | Working |
122
+ | SQLite task checkpoints/cancel/restart | Working |
123
+ | In-process web channel adapter | Experimental |
124
+ | Envelope-encrypted local secret vault | Experimental |
125
+ | Browser-worker policy envelope | Experimental |
126
+ | Persistent task threads + atomic cron job claims | Working |
127
+ | Credential-free read-only mail/calendar connectors | Working |
128
+ | Production-capable read-only Google Calendar and Gmail connectors | Working |
129
+ | Managed Google OAuth code exchange, refresh, encrypted storage, and OS-keyring master key | Working |
130
+ | [Resource-limited OS process worker](docs/isolated-worker.md) | Working |
131
+ | Kernel/network-isolated browser worker | Not yet |
132
+ | Ephemeral OTP grants + exact-total validation | Working |
133
+ | Searchable, tiered, provenance-verifiable memory + edit/forget | Working |
134
+
135
+ Do not use OpenMuse with sensitive production accounts yet. “Working” means covered by the current test suite, not externally audited.
136
+
137
+ ## How it works
138
+
139
+ `Channel -> durable Task -> Planner -> typed Action -> Policy/Approval -> Tool -> typed Result`
140
+
141
+ The model cannot mint approval tokens. Secret decryption happens through a host callback, not planner context. See [architecture](docs/architecture.md), [threat model](docs/threat-model.md), [product foundation](docs/product-foundation.md), and [roadmap](docs/roadmap.md).
142
+
143
+ ## What OpenMuse is and is not
144
+
145
+ | In scope today | Not yet |
146
+ |---|---|
147
+ | Typed local tools, bounded loops, exact-action approval, encrypted local vault, durable tasks, audit verification, simulated mail/calendar connectors | Production browser isolation, independently deployed OAuth callback, independent security review, unattended use with sensitive accounts |
148
+
149
+ ## Contributing
150
+
151
+ See [CONTRIBUTING.md](CONTRIBUTING.md), [governance](GOVERNANCE.md), and the [code of conduct](CODE_OF_CONDUCT.md). Starter work is tracked with [`good first issue`](https://github.com/tahodev/openmuse/labels/good%20first%20issue) and [`help wanted`](https://github.com/tahodev/openmuse/labels/help%20wanted) labels.
152
+
153
+ ## License
154
+
155
+ MIT.
@@ -0,0 +1,9 @@
1
+ # Security
2
+
3
+ OpenMuse is alpha software with no production-supported release. Report vulnerabilities using a [private GitHub security advisory](https://github.com/tahodev/openmuse/security/advisories/new), never a public issue.
4
+
5
+ ## Current limits
6
+
7
+ The local vault encrypts secret values with per-secret AES-256-GCM data keys wrapped by an AES-256-GCM master key. The master key can be stored in the OS keyring through `KeyringMasterKey`, which fails closed when no usable system credential backend exists; hardware-backed storage is not yet integrated, and tools still share the Python process. `FetchURL` resolves a destination once, rejects the entire DNS answer set if any address is non-public, and pins the connection to a validated address while preserving TLS hostname verification; redirects are blocked rather than followed. The hash-chained audit is not externally anchored, and the approval UI is experimental. Use test accounts and non-sensitive data.
8
+
9
+ See the [threat model](docs/threat-model.md) and [production gate](docs/roadmap.md).
@@ -0,0 +1,3 @@
1
+ # Support
2
+
3
+ Use [GitHub issues](https://github.com/tahodev/openmuse/issues) for usage questions and reproducible bug reports. Do not post secrets or vulnerability details publicly. Use a [private GitHub security advisory](https://github.com/tahodev/openmuse/security/advisories/new) for security reports.
@@ -0,0 +1,2 @@
1
+ # ADR 0001: Security-first runtime
2
+ Status: accepted. OpenMuse separates untrusted planners from a trusted executor. Tools declare risk and schema; sensitive effects require host-issued approval. This favors inspectability over autonomous breadth.