mirror of
https://github.com/priyanshujain/margin.git
synced 2026-10-04 03:57:03 +00:00
some more fixes
This commit is contained in:
1 parent
7a3c04f170
commit
2b86a407ba
63 files changed
+12172
-44
No files matched your search
@@ -0,0 +1,104 @@
|
||||
# App facts
|
||||
|
||||
Things true of exactly one app. Everything in the other files applies to all four.
|
||||
|
||||
## Margin, the writing studio
|
||||
|
||||
`python/margin`, package `margin-app`, bundle id `studio.margin.app`, version 0.1.17, FSL-1.1-MIT.
|
||||
The oldest and most polished of the four, and the one that ships first on any new channel.
|
||||
|
||||
Library data is self-contained `{book-id}.margin` JSON files with images embedded as base64, plus
|
||||
`custom-dictionary.txt`, in `~/Library/Application Support/studio.margin.app/library/`. That
|
||||
simplicity is what made the Drive backup feature small.
|
||||
|
||||
Google Drive backup is built and lives in `src-tauri/src/gdrive.rs`, with `src/backup.ts`,
|
||||
`src/store/useBackup.ts`, `BackupButton` and the `BackupSettings` panel on the front. Loopback plus
|
||||
PKCE through the system browser, scope `drive.file` and `openid email`. `drive.file` is
|
||||
non-sensitive, so there is no Google verification review and no CASA audit, and the consent screen is
|
||||
set to Production to avoid the unverified warning and the seven-day refresh token expiry that testing
|
||||
mode imposes.
|
||||
|
||||
The Drive layout is a visible `margin/` folder, one file per book, latest only, because Drive keeps
|
||||
revisions itself. Backup triggers are manual, on app close, and every 15 minutes, all gated on a
|
||||
dirty check so nothing uploads unless something changed. The cloud icon opens the panel rather than
|
||||
backing up in one click, because the panel is the single home for back up, restore, disconnect and
|
||||
account. Restore is offered as an ignorable link on the empty-library state, which doubles as
|
||||
connect-on-a-new-machine.
|
||||
|
||||
The refresh token and sync state sit in plaintext in `backup.json` in the app data directory. That
|
||||
was a deliberate step back from the keychain, for the reasons in [code-style.md](code-style.md), and
|
||||
it matches the app's existing local-data model given the limited scope. The newer apps seal theirs
|
||||
with XChaCha20-Poly1305 instead, and Margin should be brought up to that.
|
||||
|
||||
Margin has no test script at all. It is the only one of the four without one.
|
||||
|
||||
`appstore/` and `target-mas/` are the Mac App Store build track.
|
||||
|
||||
## Margin Calendar
|
||||
|
||||
`python/margin-caledar`, package `margin-calendar`, bundle id `studio.margin.calendar`, MIT. The
|
||||
directory name really is misspelt.
|
||||
|
||||
Its `docs/design.md`, `docs/conventions.md` and `docs/architecture.md` are the model the rest of the
|
||||
suite documents by. When writing docs for another app, follow those.
|
||||
|
||||
Prev and next move one day, never a week. Week view is a rolling seven days from the anchor by
|
||||
default, with `weekMode()` in `src/time.ts` stored under `margincal-week-mode` and `weekAnchor()` as
|
||||
the single source both `spanFor` and `GridView` use. Never reintroduce a bare `startOfWeek` call in
|
||||
either. The snapping "calendar" mode exists in Settings, and only there do the arrows step by a week,
|
||||
because a day step would be invisible.
|
||||
|
||||
The vertical axis has contraction hysteresis for the same reason the horizontal one slides by a day:
|
||||
positional memory is most of the speed of a keyboard-driven calendar.
|
||||
|
||||
Persisted localStorage keys are `margincal-folds`, `margincal-bounds`, `margincal-view` and
|
||||
`margincal-theme`. See [platform.md](platform.md) for how to read them out of the installed app.
|
||||
|
||||
This is the app with the Nix flake, and the one whose Linux story the others should copy.
|
||||
|
||||
## Margin Docs
|
||||
|
||||
`rust/margin-editor`, package `margin-docs`, remote `margin-docs`, MIT. Three names for one thing,
|
||||
and the directory is the odd one out.
|
||||
|
||||
No memory files and no `CLAUDE.md` exist for this app, so nothing was ever written down about it. It
|
||||
is also the largest front end in the suite at 43,000 lines, and it is a near twin of Margin on the
|
||||
Rust side: `pdf.rs`, `fonts.rs`, `macspell.rs` and `writingtools.rs` exist in both. That duplication
|
||||
is the subject of `../typesetting.md`.
|
||||
|
||||
## Margin Mail
|
||||
|
||||
`rust/margin-mail`, bundle id in the same `studio.margin.*` family, FSL-1.1-MIT. Third in the suite
|
||||
and the largest Rust codebase at 46,000 lines. No git remote yet.
|
||||
|
||||
The premise is a keyboard-first email client over Gmail where the user never feels Gmail. HEY and
|
||||
Superhuman are the feature vocabulary. Mailspring is the reliability bar.
|
||||
|
||||
Product decisions locked on 2026-09-03, not to be reopened unless the user does:
|
||||
|
||||
macOS first, then iOS, then minor work for Linux. List plus reading pane in the Superhuman shape,
|
||||
with HEY's Reply Later and Set Aside piles, and Feed and Paper Trail as views. The Inbox is one list
|
||||
in time order under Back, with unseen shown by weight alone: no dot, no band, no groups. Seen on open
|
||||
at once, a new reply makes a thread unseen again, the dock badge stays, and there are no counts in
|
||||
the list. The Screener is on by default with a first-run pass that screens in anyone who has emailed
|
||||
before. No AI in v1, though the design leaves room. Trackers are blocked and never sent, because
|
||||
privacy and ownership are core tenets. Scheduled sending is skipped; snooze and Bubble Up stay,
|
||||
evaluated lazily when a device opens or wakes. Multiple accounts with per-account views and an
|
||||
optional unified view. Backends after Gmail are generic IMAP and SMTP, then JMAP for Fastmail.
|
||||
Calendar invites RSVP inline and hand off to Margin Calendar, with no calendar sidebar. Compose is
|
||||
inline at the end of the thread, or a floating card for new mail. Full local mirror of mail, with
|
||||
attachments on demand.
|
||||
|
||||
App state must not depend on Gmail or any provider. In the user's words: "if I switch to protonmail
|
||||
tomorrow I don't want to lose data." Local data is the truth and cloud stores are backup only, behind
|
||||
one interface, with Google Drive for non-technical friends and Cloudflare R2 for the user. Key
|
||||
portable state on the RFC Message-ID and the sender address, never on provider ids.
|
||||
|
||||
Four Playwright specs fail on a clean tree and are not flakes. `tests/shell.spec.ts` ("New for you
|
||||
above Previously seen"), `tests/snooze.spec.ts` ("Back above New for you") and `tests/triage.spec.ts`
|
||||
("Mark all as seen is a link on the heading") all assert Inbox group heads that the app deliberately
|
||||
no longer draws: `GROUPS` in `src/ipc.ts` has no `new` or `seen` label and `ListColumn` renders
|
||||
`GroupHead` with no action. The fourth, `tests/kit.spec.ts` ("every text field tells the webview not
|
||||
to fill it in"), is a static scan that flags an input in `Kit.tsx` and one in `Settings.tsx`. Match on
|
||||
the test name, not the line number. If exactly these fail, say they are pre-existing and move on.
|
||||
Fixing them means rewriting the assertions to the current design, which is its own piece of work.
|
||||
Reference in new issue
Block a user