upleb.uk

Public git repos — served from a NIP-34 GRASP relay at git.upleb.uk

summaryrefslogtreecommitdiff
path: root/PLAN.md
diff options
context:
space:
mode:
authorYour Name <you@example.com>2026-05-27 15:32:38 +0530
committerYour Name <you@example.com>2026-05-27 15:32:38 +0530
commitd889b890f9e63815c178853ed98a1e31f6cec7f8 (patch)
tree3eda17e8edaf61cc6dba640ae12a24e90c9d8b8c /PLAN.md
parentd60fa03de6edae0667a93ac36be4206e76255a2c (diff)
Fix compile issues for NIP-46 build
- nip46.rs: match on owned RelayPoolNotification (not .as_ref()) - git_mirror.rs: accept shared nostr_sdk::Client for state event publishing - main.rs: pass nostr_client to mirror_repo_to_servers - NIP46-PLAN.md: full implementation checklist and roadmap - PLAN.md: updated
Diffstat (limited to 'PLAN.md')
-rw-r--r--PLAN.md86
1 files changed, 61 insertions, 25 deletions
diff --git a/PLAN.md b/PLAN.md
index ab1ea9f..1911a20 100644
--- a/PLAN.md
+++ b/PLAN.md
@@ -1,25 +1,61 @@
1# grasp-mirror Bugfix Plan 1# grasp-mirror Plan
2 2
3## Bugs Identified from VPS Logs 3## Completed
4 4
5### Bug 1: `remote 'push_target' already exists` 5- [x] Fix `push_mirror` in `src/git_mirror.rs` — reuse existing `push_target` remote via `remote_set_url`
6- **Location**: `src/git_mirror.rs:137` 6- [x] Fix `mirror_cycle` in `src/main.rs` — make per-repo errors non-fatal
7- **Cause**: `repo.remote("push_target", target_url)` creates a new remote every cycle. On subsequent cycles, the bare repo already has a `push_target` remote, so `git2` returns `Exists (-4)`. 7- [x] Add HTTP health endpoint (`/health`, `/api/mirror-health`) on port 7335
8- **Fix**: Use `repo.find_remote("push_target")` first. If it exists, call `repo.remote_set_url()` to update the URL. If not, create it. 8- [x] Mirror repos from 3 npubs
9 9- [x] Ansible role, playbook, systemd unit, config templates
10### Bug 2: Single repo failure aborts entire cycle 10- [x] Dashboard integration on `services.orangesync.tech`
11- **Location**: `src/main.rs:mirror_cycle()` — the `mirror.mirror_repo_to_servers()` call uses `?` which propagates the error and aborts the loop. 11- [x] Watchdog integration
12- **Cause**: When one repo (e.g. `market`) fails to clone from any server, the `?` operator returns early, skipping the remaining ~87 repos. 12
13- **Fix**: Replace `?` with a `match` that logs the error and continues to the next repo. Only the `discover_repos_from_relays` and `persist_discovered_repos` calls should be fatal (if relay queries fail, nothing works). 13## Phase 3: NIP-46 Remote Signing via Amber
14 14
15## Checklist 15### Problem
16 16GRASP servers reject unauthenticated git pushes. Authorization requires a `kind:30618` state event signed by a maintainer's key. The daemon needs to sign these events but should never hold raw nsec keys.
17- [ ] Fix `push_mirror` in `src/git_mirror.rs` — reuse existing `push_target` remote 17
18- [ ] Fix `mirror_cycle` in `src/main.rs` — make per-repo errors non-fatal 18### Solution
19- [ ] Rebuild release binary (`cargo build --release`) 19NIP-46 (Nostr Connect) remote signing via Amber on the user's phone. The daemon acts as a NIP-46 client, sends `sign_event:30618` requests to Amber, and waits for approval before pushing.
20- [ ] Push updated source to all 9 GRASP servers (`git push origin master`) 20
21- [ ] Redeploy via Ansible (`ansible-playbook playbooks/30-grasp-mirror.yml`) 21### Architecture
22- [ ] Verify: `grasp-mirror status` shows repos tracked and sync records 22```
23- [ ] Verify: `journalctl -u grasp-mirror` shows successful mirror cycles without `already exists` errors 23VPS: grasp-mirror ←→ relays ←→ Amber (phone)
24- [ ] Verify: spot-check `git ls-remote` against a few GRASP servers for repos from all 3 npubs 24 - discovers repos - NIP-46 kind:24133
25- [ ] Verify: `https://git.orangesync.tech/api/mirror-health` returns `"status": "ok"` 25 - builds state events - sign_event:30618
26 - queues signing - user approves
27 - publishes event - returns signature
28 - git push
29
30services.orangesync.tech
31 - pairing UI + QR codes
32 - status display
33```
34
35### Config
36```toml
37[nip46]
38relays = ["wss://relay.orangesync.tech", "wss://ngit.orangesync.tech"]
39signing_timeout_secs = 604800 # 7 days
40```
41
42### Checklist
43
44- [ ] Add `nip46_sessions` and `signing_queue` tables to `src/db.rs`
45- [ ] Build `src/nip46.rs` — NIP-46 client with session management
46 - Generate client keypair per npub, persist to SQLite
47 - Build `nostrconnect://` URIs with `perms=sign_event:30618`
48 - Listen for `kind:24133` events on configured relays
49 - Handle connect/get_public_key/sign_event handshake
50 - `sign_state_event(npub, state_event) -> Result<SignedEvent>` method
51 - Auto-reconnect on session drop
52- [ ] Wire NIP-46 into `src/main.rs` daemon startup — connect sessions for all 3 npubs
53- [ ] Modify `src/git_mirror.rs` — before push, build `kind:30618` state event, request signature via NIP-46
54- [ ] Add pairing URI + NIP-46 status to health endpoint (`/api/mirror-health`)
55- [ ] Update dashboard HTML (`static/services/index.html`) with pairing UI + QR codes
56- [ ] Update Ansible config template with `[nip46]` section
57- [ ] Add `health_port` to `[storage]` in config template (already done)
58- [ ] Rebuild release binary
59- [ ] Push to all 9 GRASP servers
60- [ ] Redeploy via Ansible
61- [ ] End-to-end test: pair npub via Amber, verify signing flow works