Record registry-submission process + start-cli/prepare.sh; capture eval P2 backlog
Refresh AGENTS Current state for the full-eval session; document the email-based community-registry submission flow and the start-cli installer in the packaging guide; add a ROADMAP Security & hardening section so the eval P2s survive EVALUATION.md overwrites.
This commit is contained in:
@@ -95,9 +95,11 @@ Operator-specific memories at `~/.claude/projects/-Users-macpro-Projects-keysat/
|
||||
- `riscv` build target is unverified and not declared in the manifest; the wrapper `Makefile`
|
||||
now pins `ARCHES` to `x86 arm` so no target (even a bare `make`) attempts it. Revisit only if
|
||||
a riscv StartOS target appears.
|
||||
- StartOS Community Registry submission — remaining gap is a `prepare.sh` for the clean-Debian
|
||||
first build (plus the on-box manual verification); functional criteria otherwise pass. Detail
|
||||
in ROADMAP. Submission criteria themselves still unpublished; reach out when ready.
|
||||
- StartOS Community Registry submission — `prepare.sh` shipped (2026-06-18). Submission is
|
||||
**email-based** (no PR, no form): mail `submissions@start9labs.com` a link to the public wrapper
|
||||
repo; Start9 builds-from-source on a clean box → Community Beta → production-on-reply. Resolve two
|
||||
unknowns with Start9 *before* submitting: (1) source-available `LicenseRef-Keysat-1.0` acceptability,
|
||||
(2) whether the 0.4.x build still invokes `prepare.sh`. On-box manual verification still pending. Detail in ROADMAP.
|
||||
- Split `audit:read` out of the blanket `:read` scope into its own tier so a
|
||||
Read-only scoped key can read dashboards/licenses but NOT the full audit log
|
||||
(`api/api_keys.rs::Role::grants`). Deferred from the scoped-keys session.
|
||||
@@ -110,17 +112,19 @@ Operator-specific memories at `~/.claude/projects/-Users-macpro-Projects-keysat/
|
||||
public sites (keysat.xyz, docs.keysat.xyz) live. All repos synced to **both** GitHub + gitea.
|
||||
`keysat-registry-landing` remotes deleted by the operator.
|
||||
|
||||
- **Shipped `:60` — Zaprite auto-charge silent-lapse fix.** `try_auto_charge_zaprite` suppresses manual-pay
|
||||
only for a settled status (`PAID`/`COMPLETE`/`OVERPAID`, via the new `zaprite_charge_settled` helper + unit
|
||||
test); any other/unknown status falls through to the manual-pay pay link. Allowlist by design. No schema/SDK change.
|
||||
- **Decided — Keysat sends no buyer email.** Buyer email + the per-profile SMTP send path are dropped
|
||||
(`plans/keysat-smtp-emails.md` superseded; dormant `merchant_profiles.smtp_*` flagged in code). The surviving
|
||||
kernel, operator failure alerts, is reframed onto StartOS notifications/health (ROADMAP "Operability & alerts").
|
||||
- **Docs reconciled:** false "Keysat emails the license" claim removed from docs.keysat.xyz; `HOW_IT_WORKS.md`
|
||||
corrected (subscriptions + merchant profiles shipped, no email); new design-checker-clean Merchant profiles
|
||||
docs section. `unlimited_merchant_profiles` confirmed live on Pro + Patron policies (Creator excluded).
|
||||
- **Next (priority):** 1) automated multi-profile webhook routing test (ROADMAP, Effort S). 2) split `audit:read`
|
||||
from the blanket `:read` scope. 3) operator-alerts-via-StartOS (verify the start-sdk 1.3.2 API first).
|
||||
4) registry-submission `prepare.sh` + on-box verification.
|
||||
- **Tests/build:** `cargo check` + wrapper `tsc` clean; `zaprite_charge_settled` unit test green; full suite
|
||||
through 0025 last green. Pre-existing docs.css radius drift (10px vs 12px `r-lg`, 3 spots) noted; not blocking.
|
||||
- **This session — full eval + three P1 fixes (all committed & pushed).** Ran the five-agent `/full-eval`
|
||||
(evaluator, security-auditor, exerciser, doc-auditor, start9-spec-checker); report in `EVALUATION.md`
|
||||
(no P0s; strong crypto/auth/webhook posture). Fixed all three P1s: (1) crosscheck harness `run_ts.mjs`
|
||||
hardcoded `/sessions/...` path → resolves relative to repo (keysat-root); (2) Rust SDK + `keysat-docs`
|
||||
imported `licensing_client` not `keysat_licensing_client` — fixed, plus two latent bugs it masked (example's
|
||||
undeclared `anyhow` → stdlib; doctest `include_str!` of a missing file → inline PEM); (3) added
|
||||
`licensing-service-startos/prepare.sh` clean-Debian build bootstrap. Reviewer-approved; verified green.
|
||||
- **Registry submission mechanism researched.** Email-based (no PR/form) — see Open TODOs + ROADMAP. Two
|
||||
blocking unknowns to clear with Start9 first: license acceptability + whether 0.4.x still uses `prepare.sh`.
|
||||
- **Prior context still current:** `:60` Zaprite silent-lapse fix shipped; Keysat sends no buyer email
|
||||
(SMTP path dormant); docs reconciled; `unlimited_merchant_profiles` live on Pro+Patron (not Creator).
|
||||
- **Next (priority):** 1) email Start9 re: license + 0.4.x build flow (gates the whole submission). 2) eval
|
||||
P2 hardening — XFF rate-limit bypass, dep-advisory bumps, admin/public port split (ROADMAP "Security &
|
||||
hardening"). 3) automated multi-profile webhook routing test (Effort S). 4) split `audit:read` scope.
|
||||
- **Tests/build:** daemon `cargo test` ~117–131 green across 8 suites; wrapper `tsc` clean; Rust SDK
|
||||
`cargo build --examples` + doctest now green; crosscheck harness passes end-to-end. No CI enforces any of it.
|
||||
|
||||
+36
-6
@@ -28,12 +28,18 @@ Longer-term backlog. Near-term state lives in `AGENTS.md` → Current state.
|
||||
|
||||
## Packaging & distribution
|
||||
|
||||
- Start9 Community Registry submission — a 2026-06-17 spec check found the wrapper passes the functional
|
||||
criteria (manifest, interfaces, health check, backup/restore, BTCPay dep, actions). Remaining gap before
|
||||
submission: add a `prepare.sh` to set up a clean Debian box for the first build (copy the one from
|
||||
`hello-world-startos`), then run the on-box manual verification (install / backup / restore / logs).
|
||||
Submission criteria themselves remain unpublished; reach out to Start9 when ready. (Icon-render and the
|
||||
source-available license are intentionally not treated as blockers.)
|
||||
- **Start9 Community Registry submission.** Mechanism (researched 2026-06-18): **email-based, not a PR or
|
||||
form.** Mail `submissions@start9labs.com` (the 0.3.5.x docs say `submissions@start9.com` — addresses are
|
||||
inconsistent) a link to the public wrapper repo (+ detailed README); both wrapper and upstream source must
|
||||
be public. Start9 snapshots the repo, **builds from source on a clean Debian box** (`prepare.sh` + `make`; a
|
||||
failed first build bounces the submission), installs + tests on real hardware (metadata, install/uninstall,
|
||||
interfaces, health, backup/restore, low-resource device), lands it in Community **Beta**, and promotes to
|
||||
production when you reply asking. Updates follow the same loop. `start-cli s9pk publish` is **self-hosted-registry
|
||||
only** — unrelated to community intake. `prepare.sh` shipped this session (`licensing-service-startos/prepare.sh`).
|
||||
**Clear with Start9 before submitting:** (1) is the custom source-available `LicenseRef-Keysat-1.0` acceptable
|
||||
(docs conflict: "source available" vs "Open Source License") — highest-leverage; a hard No blocks regardless of
|
||||
build-readiness; (2) does the 0.4.x build flow still invoke `prepare.sh` (a 0.3.5.x concept, absent from 0.4.x
|
||||
docs). Then the on-box manual verification. Functional criteria otherwise pass (2026-06-17 spec check).
|
||||
|
||||
## Operability & alerts
|
||||
|
||||
@@ -53,6 +59,30 @@ Longer-term backlog. Near-term state lives in `AGENTS.md` → Current state.
|
||||
The dormant `merchant_profiles.smtp_*` columns (migration 0020) are now dead weight — left in place (a removal
|
||||
migration isn't worth it) and flagged in `src/merchant_profiles.rs`.
|
||||
|
||||
## Security & hardening (2026-06-18 full-eval P2s; EVALUATION.md has full detail but is overwritten each run, so the durable list lives here)
|
||||
|
||||
- **X-Forwarded-For rate-limit bypass.** Login/recover/validate buckets key off the raw first XFF value
|
||||
(`api/auth.rs:137`, `api/recover.rs:65`, `api/admin.rs:63`, `api/validate.rs:95`); rotating XFF defeats the
|
||||
throttle. First confirm whether the StartOS front proxy overwrites XFF (decides real-world reachability), then
|
||||
derive client IP from the trusted-proxy connection with a peer-socket fallback.
|
||||
- **Dependency advisories** (mechanical, low-risk): bump `sqlx 0.7.4` → ≥0.8.1 (RUSTSEC-2024-0363),
|
||||
`rustls-webpki 0.101.7` → ≥0.103.13 (RUSTSEC-2026-0098/0099/0104), update start-sdk for the wrapper's
|
||||
`fast-xml-parser` (GHSA-5wm8-gmm8-39j9); re-run `cargo audit` / `npm audit`.
|
||||
- **Admin UI co-located with the public API** on the single `:8080` interface (`startos/interfaces.ts`) — operator
|
||||
can't network-isolate admin. Split the admin SPA + `/v1/admin/*` onto their own port/interface.
|
||||
- **Webhook-endpoint registration accepts `file://` / loopback URLs** (`webhooks.rs:106`, admin-gated) — add a
|
||||
scheme + host allowlist (reject non-http(s), loopback, link-local).
|
||||
- **Runtime-prepared SQL** in `db/repo.rs` + `subscriptions.rs` (no compile-time column check; this class already
|
||||
500'd every paid purchase once on `:52`) — migrate the money-path queries to compile-checked `sqlx::query!`.
|
||||
- **`rate_buckets` grows unbounded** (`rate_limit.rs:63`, one row per client IP on a public endpoint, no reaper) —
|
||||
add a reaper mirroring the session/redemption reapers in `main.rs`.
|
||||
- **No CI.** Stand up one job (`cargo test && cargo clippy && tsc --noEmit`, ideally `cargo fmt --check`); the suite
|
||||
is good but unenforced, so green depends on the operator remembering to run it before `publish.sh`.
|
||||
- Doc-drift P3 cluster (each one-liners, see EVALUATION.md): BUILDING.md Node 20→22 / Rust 1.75→1.88, broken docs
|
||||
`/changelog` footer link, README "Show credentials" → "Show admin API key", PORTING_SDK stale (Python/Go shipped;
|
||||
crate renamed), testing.md stale test counts, and the `unlimited_merchant_profiles` guide/code-comment ("still
|
||||
needs adding") vs AGENTS ("confirmed live") contradiction — resolve with a live `GET /v1/products/keysat/policies`.
|
||||
|
||||
## Licensing model
|
||||
|
||||
- Evaluate Elastic License v2 vs the current custom `LicenseRef-Keysat-1.0` (parked decision).
|
||||
|
||||
@@ -28,6 +28,18 @@ npm run prettier # prettier --write startos (NOT enforced; see testing.md)
|
||||
Auth for `make install` is the developer key at `~/.startos/developer.key.pem`
|
||||
(private — never commit/share).
|
||||
|
||||
## Clean-box build bootstrap (`prepare.sh`)
|
||||
|
||||
`prepare.sh` (in `licensing-service-startos/`) installs every HOST prerequisite a
|
||||
fresh Debian/Ubuntu box needs before `make`: apt prereqs (build-essential, jq, git,
|
||||
squashfs-tools(-ng)), Node 22 (NodeSource), Docker (+ QEMU binfmt for cross-arch),
|
||||
and **start-cli** via the official installer —
|
||||
`curl -fsSL https://start9.com/start-cli/install.sh | sh` (drops the binary in
|
||||
`~/.local/bin`). Rust is **not** installed on the host; the daemon compiles inside
|
||||
the Dockerfile (`FROM rust:1.88`). Idempotent; apt-based only. Caveat: `prepare.sh`
|
||||
is a 0.3.5.x submission convention — the 0.4.x docs never mention it, so Start9's
|
||||
0.4.x build flow may not actually invoke it (confirm before relying on it).
|
||||
|
||||
## ALWAYS: bump the version before building
|
||||
|
||||
Edit `startos/versions/v0.2.0.ts` — increment `version: '0.2.0:N'` and prepend a
|
||||
|
||||
Reference in New Issue
Block a user