Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
27 changes: 27 additions & 0 deletions docs/delivery.md
Original file line number Diff line number Diff line change
Expand Up @@ -229,3 +229,30 @@ company. Remaining boundaries include OS-enforced tool isolation, a real media
capture/publication pilot, provider billing receipts, domain-specific quality and
business-impact evaluations, and distributed-host ownership. These are reported
as unproven, not inferred from the presence of modules or dashboard cards.

## Deployment Gates

A merged PR is not automatically a deployed runtime. `bin/run_autopull.sh` follows
the immutable commit in `runtime/deploy-approved-sha`, not the newest `main`.
Only advance this pin for an explicitly approved release after testing and checking
active workers. Updating the checkout alone is temporary: the next autopull will
restore the approved commit. Keep the guard, dispatcher-only setting and existing
schedules intact during a dashboard rollout.

Read-only monitoring can run independently of that execution release. Export a
reviewed commit with `git archive` into a private persistent release directory,
install its pinned dependencies into that directory's `.venv`, and set the user
service's `WorkingDirectory` and `ExecStart` to that release. Set
`Environment=ORCH_ROOT=%h/agent-os` so observations still read the real runtime.
Do not point a lasting service at a temporary development worktree. This starts
only `orchestrator.dashboard.server`, not the coordinator or queue. A stale
coordinator alert is expected until the execution release is actually enabled.

The GitHub identity used by the runtime needs Project read/write access in
addition to repository access. Reading issues and posting comments can work while
Project updates fail. Inspect scopes with `gh auth status` under the runtime
identity and check whether `GH_TOKEN` or `GITHUB_TOKEN` overrides the stored login;
never print token values. For an OAuth login, the account owner can grant the
missing access with `gh auth refresh --hostname github.com --scopes project`.
That requires an account authorization, not a code retry or GitHub Actions job.
Pending updates stay in the outbox and retry after access is restored.
33 changes: 33 additions & 0 deletions docs/worklog/2026-09-16-delivery-operations.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
# Delivery Operations Rollout, 2026-09-16

Agent-OS PR358 adds persistent intent/program ownership, bounded execution,
independent acceptance, durable notifications and the live Proof dashboard.
Proof PRs 1-3 add operational observations separate from benchmark results and
keep historical reconciliation out of live delivery metrics and activity charts.

The deployment check found two operational gates, not worker failures:

- The host's immutable approved execution pin still selects `dc4559703af49126d2403132601992fff12dd4b1`.
An initial fast-forward was reverted by the intentional autopull guard. Approval
to advance the pin was requested; it was not silently overwritten or bypassed.
- The active GitHub OAuth login has repository access but not Project access.
No environment token override was present. GitHub Project projection remains
queued, rather than being reported as delivered.

The private read-only dashboard is installed as a user service on localhost:8765
from a separate immutable release directory with its own virtual environment.
No new cron, public listener, execution-mode change or worker was added. Monitor
health and execution health are separate: an inactive coordinator raises an alert.

Issue #355 was independently reconciled against merged PR356 and its actual README
diff. Its Telegram completion notice was acknowledged. It remains closed and is
marked historical, not counted as a new task or a near-instant delivery. The live
check exposed a historical-event chart inconsistency, corrected in Proof PR3 and
covered by both Proof and Agent-OS HTTP regression tests.

Validation of the foundation: 794 Agent-OS tests, 43 Proof tests, passing remote
Agent-OS CI, desktop/mobile browser checks, safe rendering of hostile titles,
outage/stale-snapshot behavior, and installed-wheel static assets. The follow-up
adds two Proof regression cases and an Agent-OS HTTP integration case. No claims
of real non-code publication, complete provider billing, OS sandboxing, or measured
business impact are inferred from those checks. See [delivery limits](../delivery.md).
2 changes: 1 addition & 1 deletion requirements.txt
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
PyYAML>=6.0
pytest>=8.0
duckduckgo-search>=7.0
proof @ git+https://github.com/kai-linux/proof.git@1daeef95bd820cf1f0e93d4daf6f3211cf092446
proof @ git+https://github.com/kai-linux/proof.git@466558a3ac9410a93dd3824850c6424fa3fce5bc
20 changes: 20 additions & 0 deletions tests/test_delivery_dashboard.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import http.client
import json
import sys
from pathlib import Path
from threading import Thread
Expand Down Expand Up @@ -67,6 +68,25 @@ def test_real_http_dashboard_and_live_snapshot(server):
assert b"proof.operations.v1" in body


def test_historical_reconciliation_is_not_new_delivery_activity(server, tmp_path):
store = DeliveryStore(store_path({"root_dir": str(tmp_path)}))
goal = store.upsert(
"historical-issue",
"Previously delivered",
"Historical request",
metadata={"historical_import": True},
)
store.record_evidence(goal["id"], 1, "human_acceptance", True, "test", {})
assert store.verify(goal["id"])
status, _, body = request(server, "/api/delivery")
assert status == 200
snapshot = json.loads(body)
assert snapshot["goals"][0]["verified"] is True
assert snapshot["metrics"]["historical_imports"] == 1
assert snapshot["metrics"]["verified_delivery"]["denominator"] == 0
assert snapshot["timeline"] == []


def test_dns_rebinding_host_rejected(server):
status, _, _ = request(server, "/api/delivery", host="evil.example")
assert status == 403
Expand Down
Loading