From 66fc47cc2819107eff9c503ecdfbc2d38be47af7 Mon Sep 17 00:00:00 2001 From: SkateSpots Date: Wed, 28 Oct 2026 11:02:47 +0700 Subject: [PATCH] feat: restore map footer, inline crew roles, Cordn reactions/push - Keep the map footer links permanently visible; remove the hide toggle. - Publish inline founder promote/demote from the member row. - Add encrypted MLS reaction/delete/read control messages and UI. - Add the minute Cordn join watcher: NIP-17 DMs + encrypted bell notices. - Add the browser translation-matrix runner and a low-end performance finding. --- AGENTS.md | 50 ++- package.json | 3 +- scripts/cordn-join-watcher.sh | 10 + scripts/cordn-join-watcher.ts | 361 ++++++++++++++++++ scripts/install-cordn-watcher-timer.sh | 9 + .../systemd/skatespots-cordn-watcher.service | 9 + .../systemd/skatespots-cordn-watcher.timer | 10 + scripts/translation-matrix.mjs | 166 ++++++++ src/components/CordnJoinRequestCard.tsx | 67 ++++ src/components/MapFooterStrip.tsx | 24 +- src/components/NotificationBell.tsx | 37 +- src/components/crew/CordnNativePanel.tsx | 145 ++++++- src/hooks/useCordnJoinNotifications.ts | 116 ++++++ src/hooks/useCordnNative.ts | 104 ++++- src/hooks/useMapFooterHidden.ts | 30 -- src/i18n/ca/batch1.ts | 13 + src/i18n/cs/drift.ts | 13 + src/i18n/de/drift.ts | 13 + src/i18n/el/drift.ts | 13 + src/i18n/eu/batch1.ts | 13 + src/i18n/fr/drift.ts | 13 + src/i18n/gl/batch1.ts | 13 + src/i18n/hi/batch1.ts | 13 + src/i18n/id/drift.ts | 13 + src/i18n/it/drift.ts | 13 + src/i18n/ja/drift.ts | 13 + src/i18n/ko/drift.ts | 13 + src/i18n/legacy/cordnUi.ts | 26 ++ src/i18n/nl/drift.ts | 13 + src/i18n/pl/drift.ts | 13 + src/i18n/pt/drift.ts | 13 + src/i18n/ro/drift.ts | 13 + src/i18n/ru/drift.ts | 13 + src/i18n/sv/drift.ts | 13 + src/i18n/th/drift.ts | 13 + src/i18n/tr/drift.ts | 13 + src/i18n/uk/drift.ts | 13 + src/i18n/vi/drift.ts | 13 + src/i18n/zh-CN/drift.ts | 13 + src/i18n/zh-TW/drift.ts | 13 + src/lib/cordn/native/session.ts | 27 +- src/lib/cordn/watch.ts | 27 ++ src/pages/SettingsPage.tsx | 9 - 43 files changed, 1459 insertions(+), 83 deletions(-) create mode 100755 scripts/cordn-join-watcher.sh create mode 100644 scripts/cordn-join-watcher.ts create mode 100755 scripts/install-cordn-watcher-timer.sh create mode 100644 scripts/systemd/skatespots-cordn-watcher.service create mode 100644 scripts/systemd/skatespots-cordn-watcher.timer create mode 100755 scripts/translation-matrix.mjs create mode 100644 src/components/CordnJoinRequestCard.tsx create mode 100644 src/hooks/useCordnJoinNotifications.ts delete mode 100644 src/hooks/useMapFooterHidden.ts create mode 100644 src/lib/cordn/watch.ts diff --git a/AGENTS.md b/AGENTS.md index 6fbbfee..b72ed35 100644 --- a/AGENTS.md +++ b/AGENTS.md @@ -1542,19 +1542,38 @@ session with **no other memory of this project**. So: it (`QRScannerModal`), calls `addMemberByIdentifier(gid, kpRef)`, and the new device's `checkInvite` accepts the Welcome — no join request/founder round trip. Member leaves can be removed by `leafIndex` (`removeMemberFromGroup` → - `createCommit` with `defaultProposalTypes.remove`); the founder gets an - **Edit Crew** link for admin-role changes. Messages have copy/reply actions - (reply is quoted text; reactions/delete are still open). Live benchmark - (`scripts/cordn-benchmark.ts`, 30 msgs): ~489ms/send, ~20ms/fetch, snapshot - ~13.8KB (~460 B/message) — fine for hundreds of messages. + `createCommit` with `defaultProposalTypes.remove`). **Inline promote/demote + (2026-10-28):** the founder gets a shield button on each non-founder member row; + it republishes the **existing crew event tags** with the target's `p` tag + switched between plain and `admin` (only the founder can do this — an admin's + republish would fork the crew). Messages have copy/reply, **reactions + (👍/❤️/🔥/😂)**, **delete-for-everyone**, and **read receipts**. These are + encrypted MLS **control messages** (empty content + `reaction`/`unreact`/ + `delete`/`read` tags) sent via `sendControl`; `useCordnNative` filters them out + of the visible list and derives reaction/read maps. Delete is a local + tombstone, not a relay hard-delete; automatic read receipts are silent-signer + only (Amber would prompt). Live benchmark (`scripts/cordn-benchmark.ts`, 30 + msgs): ~489ms/send, ~20ms/fetch, snapshot ~13.8KB (~460 B/message). +- **Cordn join-request push (2026-10-28):** `scripts/cordn-join-watcher.ts` + runs every minute (user timer) and polls the coordinator for known crew gids. + New requests become (a) a **NIP-17 DM** to the founder/admins (push service + wakes the phone) and (b) an **encrypted NIP-78** notice (`t=cordnjoinrequest`, + authored by the dedicated watcher key `82ce71cf…`). `useCordnJoinNotifications` + decrypts it; the bell's Crews/All tabs show a `CordnJoinRequestCard` with + Review/Dismiss, and count it by `seenAt`. Key `~/.config/skatespots/cordn-watcher.env` + (600); state `~/.local/state/skatespots-cordn-watcher/state.json`. Crews with a + **custom coordinator** are skipped (only the SkateSpots embedded coordinator is + queried); approved requests leave the coordinator but the bell card remains + until dismissed. - **Map site-links strip (2026-10-05):** the desktop footer is hidden on the map (full-bleed), so `components/MapFooterStrip.tsx` surfaces the same links - (Newsletter/License/Privacy/Collaborators + "not sponsored by OpenSats") as an - overlay inside the map container: a **slim full-width bar on desktop** and a - **tiny collapsed "Links" chip on mobile** (expands to a compact scrollable row). - Dismissible via `useMapFooterHidden` (`skatespots:map-footer-hidden`, same-tab - synced), restorable in **Settings → Appearance**. The map's OpenStreetMap - attribution moved to `md:bottom-7` so the bar doesn't cover it. + (DIY/Newsletter/License/Privacy + "not sponsored by OpenSats") as an overlay + inside the map container: a **slim full-width bar on desktop** and a **tiny + collapsed "Links" chip on mobile** (expands to a compact scrollable row). + **Always visible (2026-10-28):** the old dismissible `useMapFooterHidden` + behavior/setting was removed — it was easy to hide the only footer on the map + forever and then report it missing. The map's OpenStreetMap attribution moved + to `md:bottom-7` so the bar doesn't cover it. - **Map layout — controls float (2026-09-29):** on mobile the `MapPage` toolbar is **`absolute` over the map** (`pointer-events-none` wrapper + gradient + `pointer-events-auto` inner) so the map fills the whole container; `md:static` @@ -2627,6 +2646,15 @@ Rules: - **Conversion:** Docker Python 3.11 + torch 2.4.1 + transformers 4.46.3 + optimum 1.24; dynamic q8; `tokenizer.json` generated from the SentencePiece models (needs protobuf + `sentencepiece_model_pb2.py`). +- **Browser matrix runner (2026-10-28):** `scripts/translation-matrix.mjs` + (`npm run translation:matrix`) serves `dist` and drives the built + `translate.worker` in headless Chromium; `MATRIX_LANGUAGES=es,ca` limits it. + It writes `/tmp/opencode/translation-matrix.json` and a per-language partial. + First runs on this box: en↔es **~54s**, en↔ca **~21s** (model download + included for es); Basque downloads did not finish in a 25-minute run. This is a + real performance finding, not just missing test coverage: the 617 MB M2M100 + single-threaded WASM is too slow for low-end phones. Low-end/APK verification + still needs a device (and likely a smaller model or native ONNX). - **Still to do:** verify all 24 pairs in the browser/APK and measure speed/memory on low-end phones. **1.7.2 and 1.7.3 are released** (the phone needs the Zapstore update; the web deploy timer batches for 24h unless forced). diff --git a/package.json b/package.json index 74b1df4..d77ac11 100644 --- a/package.json +++ b/package.json @@ -27,7 +27,8 @@ "android:version": "node scripts/sync-android-version.mjs", "android:build": "npm run android:build:apk && npx cap sync android && node scripts/sync-android-version.mjs && node scripts/inject-amber-queries.mjs && node scripts/inject-main-activity.mjs && node scripts/inject-network-security.mjs && node scripts/inject-signing-config.mjs && cd android && ./gradlew assembleRelease", "android:build:apk": "CAPACITOR_BUILD=1 vite build && sed -i 's|||g' dist/index.html && sed -i 's|