docs: Step 7 rename/hygiene pass

- package.json homepage: github.com/avi/Keynctr -> git.atitlan.io/avi/Keynctr
- README: title 'Nostr Feed Manager' -> 'Keynctr', resolve all
  [YOUR_FORGEJO_INSTANCE_URL]/<OWNER>/<REPO> placeholders with the real
  Forgejo URL, fix clone dir and packaged-binary name (nost-feed-manager
  -> keynectr), data dir default ~/.local/share/keynectr, refresh test
  counts (cargo 225+6 e2e, npm 139/19 files) and project layout
  (audit/bunker/feed/updates modules, signer/ dir, Feed+SignerMode screens)
- PRODUCT.md: data dir corrected with migration note
This commit is contained in:
Avi 2026-09-30 11:57:49 -05:00
commit 7891ccce1a
3 changed files with 28 additions and 22 deletions

View file

@ -1,4 +1,4 @@
# Nostr Feed Manager
# Keynctr
> A friendly Linux desktop app for managing Nostr profiles, publishing notes, and acting as a
> **NIP-46 remote signer** — your private keys stay under your control: encrypted in a local
@ -13,18 +13,17 @@
<!--
Forgejo CI badge — enable once a workflow exists in `.forgejo/workflows/ci.yml`:
[![CI]([YOUR_FORGEJO_INSTANCE_URL]/<OWNER>/<REPO>/actions/workflows/ci.yml/badge.svg)]([YOUR_FORGEJO_INSTANCE_URL]/<OWNER>/<REPO>/actions/workflows/ci.yml)
[![CI](https://git.atitlan.io/avi/Keynctr/actions/workflows/ci.yml/badge.svg)](https://git.atitlan.io/avi/Keynctr/actions/workflows/ci.yml)
-->
> **Hosting note:** this project is hosted on **Forgejo**. Throughout this document,
> replace `[YOUR_FORGEJO_INSTANCE_URL]` with your instance's base URL (e.g. `https://codeberg.org`)
> and `<OWNER>/<REPO>` with the actual repository path.
> **Hosting note:** this project is hosted on **Forgejo** at
> [`https://git.atitlan.io/avi/Keynctr`](https://git.atitlan.io/avi/Keynctr).
---
## 📖 Introduction
Nostr Feed Manager pairs a hardened **Rust core** (the same engine behind the original CLI) with a
Keynctr pairs a hardened **Rust core** (the same engine behind the original CLI) with a
polished **Electron + React** desktop interface. All Nostr work — key generation, event signing,
relay communication, encryption — happens inside the Rust backend. The GUI talks to it over a
secure JSON-lines IPC channel and **never sees your secret keys**.
@ -135,8 +134,8 @@ No Docker, database, or account setup is required.
### 1. Clone and build
```sh
git clone [YOUR_FORGEJO_INSTANCE_URL]/<OWNER>/<REPO>.git
cd nost-feed-manager
git clone https://git.atitlan.io/avi/Keynctr.git
cd Keynctr
# Build the Rust backend (release)
cargo build --release
@ -167,7 +166,7 @@ directly, but you can export these from your shell or source an `.env` before la
| --- | --- | --- |
| `NFM_PASSWORD` | Vault password for non-interactive CLI use (create / publish / show-secret) | _prompt_ |
| `NOSTR_GUI_DEV_URL` | Renderer dev-server URL for hot reload (development only) | — |
| `XDG_DATA_HOME` | Override the data directory | `~/.local/share/nost-feed-manager` |
| `XDG_DATA_HOME` | Override the data directory | `~/.local/share/keynectr` |
**`.env.example`** — copy to `.env` and adjust:
@ -180,7 +179,7 @@ NFM_PASSWORD=
# Renderer dev-server URL for hot reload (development only)
NOSTR_GUI_DEV_URL=http://localhost:5173
# Override the data directory (defaults to ~/.local/share/nost-feed-manager)
# Override the data directory (defaults to ~/.local/share/keynectr)
XDG_DATA_HOME=
```
@ -194,13 +193,13 @@ cd frontend
npm run dist # builds renderer + backend and runs electron-builder
```
The unpacked app lands in `frontend/release/linux-unpacked/`; run it with `./nost-feed-manager`.
The unpacked app lands in `frontend/release/linux-unpacked/`; run it with `./keynectr`.
## 🧑‍💻 Usage guide
### Desktop app
Tabs cover **Compose**, **Home**, **Profiles**, **Relays**, **Settings**, and **Signer**. Connect
Tabs cover **Compose**, **Home**, **Feed**, **Profiles**, **Relays**, **Settings**, and **Signer**. Connect
a relay by entering its `wss://` URL, then compose a note, attach an image, and publish to see a
per-relay report.
@ -288,11 +287,11 @@ npm run dev
NOSTR_GUI_DEV_URL=http://localhost:5173 npm start
```
### Verify (all green — `cargo 75`, `npm 71`, clippy/fmt/typecheck/lint/format clean)
### Verify (all green — `cargo 225 + 6 e2e`, `npm 139`, clippy/fmt/typecheck/lint/format clean)
```sh
# Rust
cargo test # 75 unit tests
cargo test # 225 unit tests (+ 6 e2e in tests/)
cargo fmt --check # rustfmt
cargo clippy --all-targets
@ -301,7 +300,7 @@ cd frontend
npm run typecheck # TypeScript (renderer + electron)
npm run lint # ESLint
npm run format:check # Prettier
npm test # Vitest (jsdom) — 71 tests across 13 files
npm test # Vitest (jsdom) — 139 tests across 19 files
```
The test suites exercise the real IPC protocol against a fake backend, so features are tested at
@ -312,22 +311,29 @@ the protocol boundary rather than in isolation.
```
src/ Rust library + CLI + IPC server
app.rs app state, vault password/unlock lifecycle
audit.rs key-export audit log (fail-closed)
bunker.rs NIP-46 bunker (signer server) mode
crypto.rs Argon2id derivation + AES-256-GCM encryption
errors.rs structured AppError
feed.rs feed aggregation (all / contacts, 24h window)
ipc.rs JSON-lines serve() loop and request/reply envelope
main.rs CLI entry point
profiles.rs profile create/list/select, secret recovery
profiles.rs profile create/list/select, secret recovery, auto-naming
publish.rs note publishing with receipts, images and imeta tags
relays.rs default relays, validation, connection tests
settings.rs theme and preferences
signer.rs NIP-46 remote signer + approval gate
updates.rs no-restart self-updater
uploads.rs NIP-98 auth for image-host uploads
vault.rs vault storage (plaintext or password-encrypted)
signer/ external NIP-46 signer client
backend.rs signer backend dispatch (embedded / external)
nip46_client.rs NIP-46 client: pairing, sessions, park/switch
permissions.rs per-remote per-kind permission grants
frontend/
electron/ Electron main + preload (backend spawn, dialogs, clipboard)
src/
screens/ Compose, Home, Profiles, Relays, Settings, Signer
lib/ types, api bridge, media helpers
screens/ Compose, Home, Feed, Profiles, Relays, Settings, Signer, SignerMode
lib/ types, api bridge, media helpers, theme tokens
state/ React context (AppProvider)
test/ Vitest suite over a fake backend
package.json scripts + electron-builder config
@ -341,7 +347,7 @@ respectful and constructive; everyone is expected to follow the
### Reporting bugs
Open an issue on the [issue tracker]([YOUR_FORGEJO_INSTANCE_URL]/<OWNER>/<REPO>/issues) and include:
Open an issue on the [issue tracker](https://git.atitlan.io/avi/Keynctr/issues) and include:
- A clear title and description of expected vs. actual behavior
- Steps to reproduce