Umbrella issue for Phase 2 of the v2 UI overhaul — the speculative half. Phase 1 (#28) stands on its own regardless of whether Phase 2 happens; Phase 2 explores whether a more template-first experience is right for this project's actual usage. The maintainer's own use is closer to one-off labels, so the homepage flip in slice 2.5 specifically is genuinely uncertain and open to reshaping based on input from labelle-org and other users.
Within Phase 2, slices 2.1–2.4 (server-saved templates, gallery as a route, sequence + date widgets) are useful features even without the homepage flip. Only 2.5 is the speculative big swing.
Builds on Phase 1 (#28) and reuses the Sheet primitive + stacked-row UI from slices 1.2 / 1.3.
Slices
2.1 — Save labels to server, SQLite-backed (M)
GET/POST/DELETE /api/templates, GET /api/templates/:id.
- Storage: SQLite (
templates.db alongside the existing LABELLE_STATE_FILE directory). sqlite3 is stdlib — no new dep.
- Schema (v1):
templates(
id TEXT PRIMARY KEY, -- uuid
name TEXT NOT NULL,
description TEXT,
body_json TEXT NOT NULL, -- v2 label JSON, reuses labelFile.ts format
favorite INTEGER NOT NULL DEFAULT 0,
created_at INTEGER NOT NULL,
updated_at INTEGER NOT NULL,
last_printed_at INTEGER
)
- Wrap CRUD in a tiny
server/templates_store.py mirroring the shape of printer_settings.py. First call creates the table; future schema bumps use PRAGMA user_version + additive migrations.
- Add "Save to library" alongside the existing "Save to file" in
SaveLoadButtons — not a replacement.
- Done when: user saves the current label as a named template, refreshes the page, fetches it back via API.
2.2 — Template gallery as a route (M)
- Add lightweight client-side routing (React Router recommended for shareable template URLs).
/ = current designer (unchanged for now), /templates = gallery with server-rendered thumbnails.
- Tap → load into the designer (
/?template=:id).
- Mobile tab bar / desktop top nav.
- Done when: visiting
/templates shows template thumbnails; tap loads into the designer.
2.3 — New widget: Sequence number (M)
SequenceWidget with start, step, padding (e.g. 04d → 0001), prefix, suffix.
- Single-print mode: current value. Batch mode: increments per output label.
- Establishes the "resolved-at-print-time" pattern that 2.4 reuses.
- Open decision: if a batch is cancelled mid-run, does the sequence resume or restart from
start? Default: restart from start, documented.
- Done when: template with one sequence widget prints
Asset-0001…Asset-0050 on 50 sequential labels.
2.4 — New widget: Date stamp (S)
DateWidget with format (ISO, dd-mm-yyyy, etc.) and offsetDays (e.g. "today + 90" for expiry).
- Resolved server-side at print time. Editor previews "as printed today".
- Done when: label with
Date(today+30, dd-mm-yyyy) prints today's date plus 30 days.
2.5 — Template-first home + variable fill view (L, most speculative slice)
May not happen as described. An alternative shape is to keep the designer at / and surface templates prominently from there. Direction here will be reshaped based on feedback before commitment.
/ would render the gallery; designer moves to /design.
- "New blank label" on the gallery for from-scratch users.
- Templates with variables → a "fill" sheet (reuses 1.2 sheet primitive + 1.3 stacked-row UI) → print without entering designer.
- "Edit template" affordance for tweaks.
- URLs:
/t/:id (fill), /t/:id/edit (designer-with-template-loaded).
- If we go this way, this PR is the v2.0.0 cutover. Major bump.
- Done when (if pursued): first-time mobile user lands on
/, taps a name-badge template, fills "Alice", and prints — never seeing the widget list.
Phase exit criteria
Two possible outcomes depending on how the template-first thesis lands:
- If 2.5 is pursued as described: fresh browser on a phone → land on
/ → see template gallery → tap a template → fill values → print.
- If 2.5 is reshaped: 2.1–2.4 still ship as standalone features; templates live alongside the designer rather than replacing it.
Umbrella issue for Phase 2 of the v2 UI overhaul — the speculative half. Phase 1 (#28) stands on its own regardless of whether Phase 2 happens; Phase 2 explores whether a more template-first experience is right for this project's actual usage. The maintainer's own use is closer to one-off labels, so the homepage flip in slice 2.5 specifically is genuinely uncertain and open to reshaping based on input from labelle-org and other users.
Within Phase 2, slices 2.1–2.4 (server-saved templates, gallery as a route, sequence + date widgets) are useful features even without the homepage flip. Only 2.5 is the speculative big swing.
Builds on Phase 1 (#28) and reuses the Sheet primitive + stacked-row UI from slices 1.2 / 1.3.
Slices
2.1 — Save labels to server, SQLite-backed (M)
GET/POST/DELETE /api/templates,GET /api/templates/:id.templates.dbalongside the existingLABELLE_STATE_FILEdirectory).sqlite3is stdlib — no new dep.server/templates_store.pymirroring the shape ofprinter_settings.py. First call creates the table; future schema bumps usePRAGMA user_version+ additive migrations.SaveLoadButtons— not a replacement.2.2 — Template gallery as a route (M)
/= current designer (unchanged for now),/templates= gallery with server-rendered thumbnails./?template=:id)./templatesshows template thumbnails; tap loads into the designer.2.3 — New widget: Sequence number (M)
SequenceWidgetwithstart,step,padding(e.g.04d→0001),prefix,suffix.start? Default: restart fromstart, documented.Asset-0001…Asset-0050on 50 sequential labels.2.4 — New widget: Date stamp (S)
DateWidgetwithformat(ISO, dd-mm-yyyy, etc.) andoffsetDays(e.g. "today + 90" for expiry).Date(today+30, dd-mm-yyyy)prints today's date plus 30 days.2.5 — Template-first home + variable fill view (L, most speculative slice)
May not happen as described. An alternative shape is to keep the designer at
/and surface templates prominently from there. Direction here will be reshaped based on feedback before commitment./would render the gallery; designer moves to/design./t/:id(fill),/t/:id/edit(designer-with-template-loaded)./, taps a name-badge template, fills "Alice", and prints — never seeing the widget list.Phase exit criteria
Two possible outcomes depending on how the template-first thesis lands:
/→ see template gallery → tap a template → fill values → print.