Skip to content

Ship the beta shelf of companion apps - #115

Open
abhishek-anand wants to merge 87 commits into
betafrom
apps/beta-shelf
Open

Ship the beta shelf of companion apps#115
abhishek-anand wants to merge 87 commits into
betafrom
apps/beta-shelf

Conversation

@abhishek-anand

@abhishek-anand abhishek-anand commented Sep 4, 2026

Copy link
Copy Markdown
Contributor

Summary

  • Land the companion shelf that was verified on the host and the Clara: Flashcards, Frame, Sync, Read Later, Vault, Panels, Deck, and the rest of the catalog apps on this branch, each with a first-run drive script.
  • Companion CLIs (kobo frame, kobo vault, kobo deck, kobo flashcards, kobo sync, and the others on this branch) answer --help and publish onto the private shelf the apps actually read.
  • Frame opens a pushed photograph instead of hanging on the spinner. Vault packs a markdown folder. Deck assigns a 3 by 5 pad grid from the host. Setup screens have a real empty state. Wallabag fills article bodies after a metadata sync.

Test plan

  • Each companion on this branch answers --help
  • Simulator: each app's first-run drive script reaches a real screen, not a crash or a blank splash
  • Frame: kobo frame push PHOTO --sim, open Frame, confirm a photograph appears (refresh once if the first paint is still the spinner)
  • Vault: kobo vault push FOLDER --sim then open Vault onto those notes
  • Deck: kobo deck set / push --sim, open Deck onto the assigned pads
  • Clara BW: present a few shelf apps after kobo session --keep-awake on

abhishek-anand and others added 30 commits September 1, 2026 04:37
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
abhishek-anand and others added 9 commits September 4, 2026 06:22
Empty or --help now prints usage and exits successfully. Parser can validate
a Z-machine file without a reader; Flashcards still refuses Anki packages
rather than write a wrong deck.
Calibre-web, Read Later, Feeds and Flashcards were headings over blank
paper. Name the host command, show a typed address field, and keep the
drive scripts honest about what is on the panel.
…ader.

The app only loads vault-index-v1, but kobo vault was never implemented, so
browse and note screens could not be reached from a real Obsidian vault.

Co-authored-by: Cursor <cursoragent@cursor.com>
Co-authored-by: Cursor <cursoragent@cursor.com>
The queue only asks for detail=metadata, so opening a piece has to
load /api/entries/{id}.json or the reader never sees the extracted text.

Co-authored-by: Cursor <cursoragent@cursor.com>
The companion CLI had no --sim path, so Frame was only ever driven empty.
Write the same shelf the simulator already reads, and give a populated
album one photograph per page instead of a settings dashboard.
The reader was a pairing splash and a two-column list. Pads are assigned
with kobo deck set, pushed into the store, and painted as fifteen recessed
square keys so a bound layout opens as a command deck.
A failed or slow load now leaves a skip banner, and `kobo frame --sim`
can seed the simulator so Open reaches the full-frame photograph.
Companion CLIs and drive-states scripts take Vault, Pub Quiz, Verses,
and the other bundled apps past their first screen without live accounts.
Copilot AI lite review requested due to automatic review settings September 4, 2026 07:46
The shelf already had the Deck reader app. This brings the matching
`kobo deck` companion so a Stream Deck layout can be assigned from the host.
Keep the shelf Vault app and take the companion's index decoder and
`--out` publish path so an Obsidian folder can land on the reader or
the simulator.
The shelf already pushes photographs with `--sim`; the help line now
matches that, including `--fit` and `--delete`.

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🟡 Changes recommended

It introduces at least one build-breaking Rust error (clone_into type mismatch) and a new request-body construction pattern that is unsafe/inconsistent with the repo’s JSON escaping conventions.

Once you've addressed the issues Copilot identified, you can request another Copilot review.

Pull request overview

This PR expands the “beta shelf” of companion apps and supporting platform/tooling updates needed to ship them, including a workspace version bump, new apps and documentation pages, and runtime/tool improvements (rate limiting, Sidekick multi-session support, icon additions).

Changes:

  • Bump workspace/platform version to 0.3.2 and update protocol minimums / docs minimum versions accordingly.
  • Add new beta shelf apps (e.g., Deck, Paperterm, Sync, Vault, Panels, Lichess, etc.) plus their READMEs, drive scripts, and website pages.
  • Improve supporting infrastructure: Sidekick multi-session board, HTTP 429 Retry-After handling, larger cargo metadata buffer, and additional Tabler glyph coverage.
File summaries
File Description
tools/icon-import/src/main.rs Ensure generated glyph matcher includes “no-outline” board-game glyph variants.
tools/icon-import/icons.txt Add heart icon mapping.
tools/check-app-versions.test.mjs Add test to bound command output buffer constant.
tools/check-app-versions.mjs Add COMMAND_MAX_BUFFER, bump protocol minimum to 12→0.3.2, and pass maxBuffer to exec.
THIRD-PARTY.md Update license ledger (incl. shakmaty GPL) and add bundled-content + app service attributions.
SDK.md Document KOBO_SIM_PROFILE usage for simulator panel profiles.
scripts/shoot-shelf-apps.sh New script to batch-drive app drive.kobo scripts and collect screenshots.
README.md Mention Syncthing-based serverless folder sync; document simulator profile override.
examples/store/src/main.rs Adjust denial copy for app management capability.
examples/sidekick/README.md Document multi-terminal/multi-session Sidekick board behavior.
examples/sidekick/drive.txt Add drive script to capture the multi-session board state.
examples/audiobook/src/main.rs Update test expectation to shared consumer-facing “missing account setup” copy.
docs/sitemap.xml Add new app pages to the published docs sitemap.
docs/apps/todo/index.html Update CSP hash, bump app version, and require Cobalt 0.3.2.
docs/apps/tictactoe/index.html Update CSP hash, bump app version, and require Cobalt 0.3.2.
docs/apps/sudoku/index.html Update CSP hash, bump app version, and require Cobalt 0.3.2.
docs/apps/sidekick/index.html Refresh Sidekick description/alt text, bump version/minimum Cobalt, add setup prerequisites section.
docs/apps/rss/index.html Update CSP hash, bump app version, and require Cobalt 0.3.2.
docs/apps/morse/index.html Update CSP hash, bump app version, and require Cobalt 0.3.2.
docs/apps/magnet/index.html Update wording to “sleep-cover sensor”, bump version/minimum Cobalt, refresh CSP hash.
docs/apps/hn/index.html Update CSP hash, bump app version, and require Cobalt 0.3.2.
docs/apps/gutenbird/index.html Adjust description wording, bump version/minimum Cobalt, refresh CSP hash.
docs/apps/gallery/index.html Update CSP hash, bump app version, and require Cobalt 0.3.2.
docs/apps/chat/index.html Update CSP hash, bump app version, and require Cobalt 0.3.2.
docs/apps/brief/index.html Update CSP hash, bump app version, and require Cobalt 0.3.2.
docs/apps/audiobook/index.html Update CSP hash, bump app version, and require Cobalt 0.3.2.
docs/apps/arxiv/index.html Update CSP hash, bump app version, and require Cobalt 0.3.2.
crates/kobod/src/update.rs Map HTTP 429 (rate limited) into a device-unreachable error class.
crates/kobod/src/app_store.rs Map 429 into Unreachable; add heart glyph name mapping.
crates/kobod/src/app_link.rs Treat 429 as Unreachable for app link flow.
crates/kobo-ui/src/vector/tabler.rs Add Heart icon geometry; return empty outlines for board-game glyphs; reorder MINUS constant placement.
crates/kobo-text/Cargo.toml Bump dependency on kobo-ui to 0.3.2.
crates/kobo-stream/README.md New crate README describing kobo stream host behavior and limits.
crates/kobo-stream/Cargo.toml New host crate package manifest for kobo-stream.
crates/kobo-sidekickd/src/main.rs Add deck module.
crates/kobo-sidekickd/src/hooks.rs Include session identity in daemon ask payload; add tests for identity formatting.
crates/kobo-sidekickd/src/board.rs Carry session identity through board asks; add snapshot API with revision counter.
crates/kobo-sidekickd/README.md Expand scope to include Deck; document Deck command safety model.
crates/kobo-sidekickd/Cargo.toml Add deps needed for Deck support (command-group/serde/sha2/toml).
crates/kobo-sdk/Cargo.toml Bump internal deps to 0.3.2.
crates/kobo-protocol/Cargo.toml Bump internal dep kobo-ui to 0.3.2.
crates/kobo-profile/src/lib.rs Enable reap_nickel_supplicant for clara-bw-391 profile; update test expectation.
crates/kobo-policy/src/tasks.rs Add tests asserting per-app root isolation and store key length constraints.
crates/kobo-policy/Cargo.toml Bump internal deps to 0.3.2.
crates/kobo-net/src/lib.rs Parse HTTP 429 into TaskError::RateLimited(retry_after) with bounded Retry-After parsing; add tests.
crates/kobo-net/Cargo.toml Add httpdate dependency for HTTP-date Retry-After parsing.
crates/kobo-frame-host/README.md New host-only crate README for Frame preparation/manifest logic and licensing.
crates/kobo-frame-host/Cargo.toml New host-only crate manifest (image + blake3).
crates/kobo-cli/Cargo.toml Add new CLI dependencies/crates (stream/doc/frame-host/profile) and rusqlite/serde_json.
Cargo.toml Add many new apps to workspace members; add new crates; bump workspace version to 0.3.2.
apps/verses/README.md New Verses app README.
apps/verses/drive.kobo Add Verses drive script.
apps/verses/drive-states.kobo Add Verses extended drive states capture.
apps/verses/Cargo.toml New Verses app manifest.
apps/vault/tests/screenshot.rs Add Vault screenshot rendering test.
apps/vault/tests/app.rs Add Vault markdown/search/layout tests.
apps/vault/src/model.rs Add Vault note model (title/tags/links/search/backlinks).
apps/vault/src/md.rs Add Markdown→HTML→text boundary via pulldown-cmark + kobo-html.
apps/vault/README.md New Vault app README and dependency notes.
apps/vault/drive.kobo Add Vault drive script.
apps/vault/drive-states.kobo Add Vault state-tour drive script.
apps/vault/Cargo.toml New Vault app manifest.
apps/syncthing/THIRD-PARTY.md Add Syncthing third-party notice placeholder requirements for platform release.
apps/syncthing/src/supervisor.rs Define deterministic supervisor cadence/config model; tests assert safe config properties.
apps/syncthing/README.md New Sync app README and host pairing / ARMv7 release path docs.
apps/syncthing/drive.kobo Add Sync drive script for enabling + folders view.
apps/syncthing/drive-states.kobo Add Sync about/folders capture script.
apps/syncthing/Cargo.toml New Sync app manifest.
apps/syncthing/build-armv7.sh Add pinned, build-only Syncthing ARMv7 build script with SHA verification.
apps/rss-miniflux/src/miniflux.rs Add Miniflux API boundary helpers + parsing and tests.
apps/rss-miniflux/README.md New rss-miniflux app README.
apps/rss-miniflux/drive.kobo Add rss-miniflux drive script.
apps/rss-miniflux/Cargo.toml New rss-miniflux app manifest.
apps/readlater/tests/fixtures/entry-7.json Add Wallabag entry fixture.
apps/readlater/tests/fixtures/entries-metadata.json Add Wallabag metadata listing fixture.
apps/readlater/src/wallabag.rs Add Wallabag URL builders + parsing, with tests ensuring bounded metadata behavior.
apps/readlater/README.md New Read Later app README.
apps/readlater/drive.kobo Add Read Later drive script.
apps/readlater/Cargo.toml New Read Later app manifest.
apps/pubquiz/README.md New Pub Quiz README (CC BY-SA data).
apps/pubquiz/QUESTION-DATA-LICENSE.md Add question-pack attribution/license file.
apps/pubquiz/drive.kobo Add Pub Quiz drive script.
apps/pubquiz/drive-states.kobo Add Pub Quiz extended state capture script.
apps/pubquiz/Cargo.toml New Pub Quiz app manifest.
apps/post/src/protocol.rs Add Hermes gateway protocol helpers (fetch inbox + post replies).
apps/post/README.md New Post app README.
apps/post/drive.txt Add Post drive script for configured gateway.
apps/post/drive.kobo Add Post drive script for first-run without secret.
apps/post/Cargo.toml New Post app manifest.
apps/parser/README.md New Parser app README (Z-machine interpreter scope + limitations).
apps/parser/drive.sh Add Parser shell drive helper.
apps/parser/drive.kobo Add Parser drive script.
apps/parser/Cargo.toml New Parser app manifest.
apps/parlor/src/engine.rs Add deterministic alpha-beta search core for board games.
apps/parlor/README.md New Parlor app README and rules references.
apps/parlor/drive.txt Add Parlor drive script (Reversi).
apps/parlor/drive.kobo Add Parlor drive script.
apps/parlor/drive-states.kobo Add Parlor drive states (Draughts).
apps/parlor/Cargo.toml New Parlor app manifest.
apps/paperterm/README.md New Paperterm README describing reader half of kobo stream.
apps/paperterm/drive.txt Add Paperterm drive script.
apps/paperterm/drive.kobo Add Paperterm drive script.
apps/paperterm/Cargo.toml New Paperterm app manifest.
apps/panels/src/transfer.rs Add bounded, restartable CBZ download state.
apps/panels/src/komga.rs Add Komga OPDS fetch/parsing helpers and tests.
apps/panels/src/archive.rs Add CBZ ZIP inspection + page decode helpers with tests.
apps/panels/README.md New Panels app README.
apps/panels/drive.sh Add Panels simulator run + raw framebuffer-to-PNG helper script.
apps/panels/drive.kobo Add Panels drive script.
apps/panels/Cargo.toml New Panels app manifest.
apps/nonograms/src/corpus.rs Add deterministic bundled puzzle corpus generator + solvability tests.
apps/nonograms/README.md New Nonograms app README.
apps/nonograms/drive.txt Add Nonograms drive script.
apps/nonograms/drive.kobo Add Nonograms drive script.
apps/nonograms/Cargo.toml New Nonograms app manifest.
apps/needles/README.md New Needles app README (Ravelry + host PDF-to-text prep pipeline).
apps/needles/drive.sh Add Needles simulator run + framebuffer capture helper.
apps/needles/drive.kobo Add Needles drive script.
apps/needles/Cargo.toml New Needles app manifest.
apps/musicstand/README.md New Music Stand app README.
apps/musicstand/drive.kobo Add Music Stand drive script.
apps/musicstand/drive-states.kobo Add Music Stand state-tour script.
apps/musicstand/Cargo.toml New Music Stand app manifest.
apps/morse/drive.kobo Update Morse drive script for capture timing.
apps/logicpack/README.md New Logic Pack app README.
apps/logicpack/drive.sh Add Logic Pack shell drive helper.
apps/logicpack/drive.kobo Add Logic Pack drive script.
apps/logicpack/Cargo.toml New Logic Pack app manifest.
apps/lichess/src/chess.rs Add FEN/UCI/SAN boundary over shakmaty, plus PGN replay helper and tests.
apps/lichess/README.md New Lichess app README (offline puzzles + correspondence polling).
apps/lichess/drive.sh Add Lichess simulator run + screenshot capture helper.
apps/lichess/drive.kobo Add Lichess drive script.
apps/lichess/Cargo.toml New Lichess app manifest pinned to shakmaty 0.27.3.
apps/kitchencard/THIRD-PARTY.md Add Mealie/AGPL third-party notice.
apps/kitchencard/README.md New Kitchen Card README.
apps/kitchencard/drive.kobo Add Kitchen Card drive script.
apps/kitchencard/drive-states.kobo Add Kitchen Card state-tour script.
apps/kitchencard/Cargo.toml New Kitchen Card app manifest.
apps/inkling/README.md New Inkling app README (offline daily word game).
apps/inkling/drive.sh Add Inkling shell drive helper.
apps/inkling/drive.kobo Add Inkling drive script.
apps/inkling/Cargo.toml New Inkling app manifest.
apps/homepanel/README.md New Home Panel README (Home Assistant tiles).
apps/homepanel/drive.txt Add Home Panel drive instructions.
apps/homepanel/drive.kobo Add Home Panel drive script.
apps/homepanel/Cargo.toml New Home Panel app manifest.
apps/habits/tests/screenshot.rs Add Habits screenshot rendering test.
apps/habits/README.md New Habits README.
apps/habits/drive.kobo Add Habits drive script.
apps/habits/Cargo.toml New Habits app manifest.
apps/grimoire/tools/build_corpus.py Add deterministic SRD corpus build tool producing bounded TSV.
apps/grimoire/THIRD-PARTY.md Add SRD CC-BY attribution notice.
apps/grimoire/src/corpus.rs Add checked-in corpus reader and sorting/bounds tests.
apps/grimoire/README.md New Grimoire app README and scope notes.
apps/grimoire/drive.kobo Add Grimoire drive script.
apps/grimoire/drive-states.kobo Add Grimoire state-tour script.
apps/grimoire/data/SOURCES.md Add source ledger and 2024-records limitations statement.
apps/grimoire/Cargo.toml New Grimoire app manifest.
apps/frame/README.md New Frame app README (host-prepared photo frame).
apps/frame/drive.txt Add Frame drive instructions.
apps/frame/drive.kobo Add Frame seeded-shelf drive script.
apps/frame/drive-states.kobo Add Frame state-tour drive script.
apps/frame/drive-empty.kobo Add Frame honest first-run drive script.
apps/frame/Cargo.toml New Frame app manifest.
apps/flashcards/THIRD-PARTY.md Add Flashcards third-party ledger (fsrs + host-only Anki bridge).
apps/flashcards/src/scheduler.rs Add FSRS scheduling logic and tests.
apps/flashcards/src/import.rs Add device-side transfer format validation with explicit compatibility gate.
apps/flashcards/README.md Document Flashcards import compatibility gate and exact current limitations.
apps/flashcards/drive.kobo Add Flashcards drive script.
apps/flashcards/drive-states.kobo Add Flashcards state-tour drive script.
apps/flashcards/Cargo.toml New Flashcards app manifest.
apps/fieldbook/README.md New Fieldbook app README.
apps/fieldbook/drive.kobo Add Fieldbook drive script.
apps/fieldbook/drive-states.kobo Add Fieldbook state-tour script.
apps/fieldbook/Cargo.toml New Fieldbook app manifest.
apps/fanshelf/README.md New Fanshelf app README (AO3 companion) including rate-limit behavior notes.
apps/fanshelf/drive.kobo Add Fanshelf demo-mode drive script.
apps/fanshelf/Cargo.toml New Fanshelf app manifest.
apps/deck/tests/screenshot.rs Add Deck screenshot rendering test.
apps/deck/tests/app.rs Add Deck decode + layout tests.
apps/deck/src/model.rs Add Deck JSON decode logic for pages/keys and run results.
apps/deck/README.md New Deck app README and security notes.
apps/deck/drive.kobo Add Deck pairing capture script.
apps/deck/Cargo.toml New Deck app manifest.
apps/crossword/README.md New Crossword app README.
apps/crossword/drive.txt Add Crossword drive instructions.
apps/crossword/drive.kobo Add Crossword drive script.
apps/crossword/Cargo.toml New Crossword app manifest.
apps/calibre-web/README.md New calibre-web app README (HTTPS OPDS root setup MVP).
apps/calibre-web/drive.kobo Add calibre-web drive script.
apps/calibre-web/Cargo.toml New calibre-web app manifest.
apps/backgammon/README.md New Backgammon app README.
apps/backgammon/drive.txt Add Backgammon drive instructions.
apps/backgammon/drive.kobo Add Backgammon drive script.
apps/backgammon/Cargo.toml New Backgammon app manifest.
apps/arxiv/src/main.rs Improve busy-state copy; switch empty states to splash; clarify truncation banner text.
apps/arxiv/drive.kobo Add arXiv drive script for capturing subjects/library.
Review details
  • Files reviewed: 118/370 changed files
  • Comments generated: 4
  • Review effort level: Lite

💡 Add a code-review agent skill or configure MCP servers for context-aware, tailored reviews. Learn more in the docs.

Comment thread apps/post/src/protocol.rs Outdated
Comment on lines +1 to +39
use kobo_sdk::{Credential, Task};

pub const SECRET: &str = "hermes-post";
pub fn endpoint(gateway: &str, route: &str) -> String {
format!(
"{}/{}",
gateway.trim_end_matches('/'),
route.trim_start_matches('/')
)
}
pub fn inbox(gateway: &str) -> Task {
Task::Fetch {
url: endpoint(gateway, "/letters"),
offset: 0,
max_bytes: 64 * 1024,
credential: Some(Credential::bearer(SECRET)),
headers: Vec::new(),
}
}
pub fn reply(gateway: &str, letter: &str, body: &str) -> Task {
Task::Post {
url: endpoint(gateway, "/replies"),
body: format!(
r#"{{"letter_id":"{}","body":"{}"}}"#,
escape(letter),
escape(body)
),
content_type: "application/json".to_owned(),
credential: Some(Credential::bearer(SECRET)),
headers: Vec::new(),
max_bytes: 4096,
}
}
fn escape(value: &str) -> String {
value
.replace('\\', "\\\\")
.replace('"', "\\\"")
.replace('\n', "\\n")
}
Comment thread crates/kobo-sidekickd/src/board.rs
Comment thread scripts/shoot-shelf-apps.sh Outdated
Comment on lines +6 to +8
KOBO="${CARGO_TARGET_DIR:-/private/tmp/cobalt-beta-shelf-target}/debug/kobo"
SHOTS="${SHOTS:-/tmp/cobalt-app-shots}"
export CARGO_TARGET_DIR="${CARGO_TARGET_DIR:-/private/tmp/cobalt-beta-shelf-target}"
Comment thread SDK.md Outdated
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants