Commit graph

48 commits

Author SHA1 Message Date
662610ca28 docs(giellie): add agent design spec and implementation plan
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
2026-09-30 23:31:57 +02:00
6fd11f4af0 feat(rep-visits): FleetAI tracker adapter, nearby-customer matching, stop detection
Groundwork for the rep visit check-in feature: a rep taps "I'm on site",
the vehicle's tracker position surfaces which customers are there, and
the visit is logged against them.

Pure/unit-testable layers only — no PocketBase writes and no UI yet,
both of which are blocked on schema that has to be added in the PB
admin first. Design doc: docs/superpowers/specs/2026-09-05-rep-visit-check-in-design.md

- lib/visit-matching.ts   rankNearbyCustomers: radius match around a
                          point, rep's own customers first
- lib/visit-stops.ts      detectStops: breadcrumb trail -> stops.
                          Anchor-based clustering rather than a running
                          centroid, which would let a slow crawl chain
                          into one bogus stationary stop
- lib/tracker-parsing.ts  Netstar FleetAI response decoding
- lib/server/tracker-service.ts
                          FleetAiAdapter + FakeTrackerAdapter behind a
                          TrackerAdapter seam. The fake is auto-selected
                          when no credentials are configured, so the rest
                          of the feature builds and tests without vendor
                          access.
- lib/geo.ts              isRealGeoPoint, lifting the Null-Island guard
                          that was inlined identically in customers/[id]
                          and companies/[id]

Three FleetAI conventions drive real code here and are each pinned by a
test: errors arrive as HTTP 200 with a failure envelope; "--" means
"unavailable" and is not null (and for IGN, not false); timestamps are
platform-local UTC+2 with no offset marker, so parsing them naively puts
every fresh fix two hours in the past.

FleetAI has no position-history endpoint, so the design polls
getTokenBaseLiveData (whole fleet in one call) and keeps its own trail.
scripts/fleetai-probe.mjs is a throwaway read-only probe to confirm the
three account-shaped assumptions before more is built on top.

102 tests pass. The 9 pre-existing failing test files elsewhere in the
suite were verified identical on a stashed tree and are unrelated.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-09-06 14:22:28 +02:00
024168f90d docs(pos): add design spec for the slip layout editor
Covers the reorderable block-list editor for sale/delivery/cash-up
slips, per-letterhead persistence, and the delivery-note pricing
default, worked out via brainstorming with the visual companion.
2026-09-04 12:42:45 +02:00
66e2fb9856 docs: clarify unit suffix handling in DN items panel header
The 'Total {sumQty}{unitSuffix}' header line now explicitly documents
how mixed / missing units are handled: suffix is omitted when all
items have empty/null units (operator defaults to 'EA'); when units
are mixed, no suffix is shown; when all items share a non-EA unit
(e.g. BOX), the suffix is shown.

Self-review pass; no other changes.

Co-Authored-By: Claude Code <noreply@anthropic.com>
2026-09-01 12:01:42 +02:00
b39614b4da docs: spec for /deliveries DN items expand
Click-to-expand on each delivery-note row reveals an inline items
panel (description + qty) below the row. Operator can match the items
against the printed DN paper in their hand before loading. Pure
client-side render — items already loaded by /api/v1/deliveries are
filtered by delivery_note == dn.id. Empty state with fallback link to
/delivery-notes/[id] for DNs whose items aren't in the page slice.

Single-file edit on src/app/(app)/deliveries/page.tsx. No server,
schema, API, or MCP changes.

Co-Authored-By: Claude Code <noreply@anthropic.com>
2026-09-01 12:01:12 +02:00
3fc9c576bf docs: spec for compact DN row + order age badge
Two small, independent rendering improvements for /deliveries and /orders:

  1. /deliveries — each delivery-note row gets a compact subline with
     customer name, company name, parent order number, and a signed-copy
     indicator (paperclip + filename tooltip). All data already on the
     row payload — no server-side changes.

  2. /orders — order card right-aligned metadata slot gets a colour-
     coded age badge (today / Xd old) replacing the bare date string.
     New src/lib/order-age.ts as a pure function with bucket thresholds
     (green <3d, amber 3-7d, orange 8-14d, red 15+d) and a unit test.

No PB schema changes. No /api/v1 route changes. No MCP tool changes.

Co-Authored-By: Claude Code <noreply@anthropic.com>
2026-09-01 01:56:28 +02:00
cc6f63dabb docs: add design spec for rep dashboard (dashboard 2)
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-01 01:25:53 +02:00
Claude
afa4c070b3 docs(stock): reconcile spec with shipped design
Two spec-vs-implementation drifts caught by the final review:
- Move 'per-row validation → 200 with reason in results[]' out of the
  'Reject 400' list. The route enforces body shape (json / empty /
  too-many / bad id / missing actor) as 400; the service enforces
  forbidden_field / non-finite / not_found / pb_error per row so one
  bad sibling never aborts the rest.
- Move the 'realtime-conflict banner' from Page-behaviour to Out of
  scope (the implementation deferred it; the spec still listed it).
2026-08-31 17:19:12 +02:00
Claude
7c3b8f642a docs(stock): bulk cap 100 + clarify selling-derive precedence 2026-08-31 16:14:29 +02:00
Claude
84a97ac7b2 docs(stock): design spec for inline pricing edit on /stock 2026-08-31 16:13:44 +02:00
0ba9e59f82 docs(pos): add design spec for WFSALES POS app
Scopes hardening the existing POS mockup (superuser creds removed,
catalog moved to stock_items, checkout wired to stock_ledger) as a
route inside WFDASH-WEBAPP rather than a separate service.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-08-30 23:50:56 +02:00
4d95b7af8c docs: non-invoiceable extras design + plan, quantity-handling audit
Three documents behind the two features on this branch:

- specs/2026-08-30-non-invoiceable-order-extras-design.md — the design
  the implementation followed, including why the flag must be named for
  the exception (a positively-named field defaults to false and would
  mark every existing row non-billable the moment it is created).
- plans/2026-08-30-non-invoiceable-order-extras.md — the task-by-task
  plan, now fully implemented.
- specs/2026-08-30-quantity-handling-audit.md — the order_qty /
  quantity audit that produced the preceding fix, plus the partial
  collection findings that are still open.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-08-30 18:28:44 +02:00
0083199ed2 docs(orders): spec + plan for delivery-note repeat-order detection 2026-08-29 23:51:52 +02:00
f1c07e8682 docs(orders): spec order↔quote auto-linking and per-line quote context
Design for closing three gaps in the existing order↔quote matcher:

  - The matcher only runs when an operator clicks it, so the ~85% of
    orders that arrive against a quote stay unlinked. Adds a call from
    createOrder plus a catch-up sweep for the backlog.
  - order_items.quote_item is only written when an order is created
    from a quote, so post-hoc links never pair lines. Adds persistence
    for confident pairs.
  - findMatchedQuoteItem re-guesses the pairing at render time using
    exact/substring matching, so buyer notes and per-line attachments
    silently vanish on any wording difference. Replaced with the
    tokenised matcher already in the repo.

Fuzzy candidates are windowed to 90 days before the order's own date
(widening to 12 months only when nothing clears the threshold);
exact-identifier lookups stay unwindowed.

No PocketBase schema changes required.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-08-29 10:49:06 +02:00
918586b6fb docs(boss-dashboard): add phone-first /m dashboard design spec 2026-08-27 23:36:32 +02:00
Dave
d87a007be3 docs(quotes): add approve-and-send-from-list design spec
Lifts the detail-screen "Approve & send email" button behaviour onto
the pending-approvals list rows. Replaces the list's existing
two-step approve + drill-in flow with the existing combined
review-approve endpoint behind the same SendQuoteModal the detail
page already uses.

Out of scope: "approve without send" toggle in the modal, inline
markup-edit on a row.

Co-Authored-By: Claude <noreply@anthropic.com>
2026-08-27 00:33:50 +02:00
Dave
670ed791ec docs(quotes): add no-quote feature design spec
Adds is_no_quote boolean to quotes collection so operators can send
an official decline letter on a quote the company cannot price.
Spec covers schema, service-layer gate relaxations, PDF rendering,
UI toggle placement, error edges, tests, and rollout.

Approach A (surgical flag relaxation) chosen over B/C during
brainstorming to keep v1 minimal and reversible.

Co-Authored-By: Claude <noreply@anthropic.com>
2026-08-26 23:08:08 +02:00
Claude
3f82b0784d docs(spec): order-item context block (sprint modal + orders page)
Replaces the AI Insights section in order-sprint-process-modal with a
deterministic PocketBase-derived context block (last quote, last order,
last invoiced, stock). Same backend exposed as a popover trigger on
the orders detail page, replacing the existing AI-history ⓘ there.

Backend: new src/lib/server/order-item-context-service.ts +
GET /api/v1/order-items/[id]/context. Reuses pure helpers from
item-history-service (normaliseSkuForHistory, findBestDescriptionMatch,
aggregateSuppliers, computeCheapest).

UI: new <OrderItemContextPanel/> (inline expandable for the sprint
modal) and <OrderItemContextPopoverTrigger/> (ⓘ popover for orders
page). Apply = cost + supplier only; selling stays locked to the order.

Co-Authored-By: Claude <noreply@anthropic.com>

Co-authored-by: Orca <help@stably.ai>
2026-08-07 02:16:31 +02:00
SJCoetz
3a954982d0 docs(spec): add Re-Send button on PO Sent tab of buyer-tasks
Co-authored-by: Orca <help@stably.ai>
2026-08-06 17:33:25 +02:00
SJCoetz
a663de2d36 docs(spec): clarify placement of vat computation
Co-authored-by: Orca <help@stably.ai>
2026-08-06 11:45:11 +02:00
SJCoetz
3beedc7ad6 docs(spec): add 15% VAT to supplier-facing PO PDF
Co-authored-by: Orca <help@stably.ai>
2026-08-06 11:44:54 +02:00
SJCoetz
286043cace docs(stock-orders): design spec for cell wrap + PDF downloads
Two small additions to /stock-orders:
- Wrap long text in Number + Supplier columns
- Two PDF download buttons (Stocktake PDF, Orders PDF)

Both PDFs always include all rows, ignore the active status
filter and pagination. No persistence — throwaway reports.

Design reviewed: covers architecture, data model, API contract,
error handling, testing, and manual smoke. No new PB schema,
no new types.

Co-authored-by: Orca <help@stably.ai>
2026-08-03 15:54:24 +02:00
SJCoetz
9489cf3a44 docs(stock-orders): design total-value columns on list table
Add an Approved design doc for the /stock-orders list table: two new
currency columns (Ordered, Received) showing sum(line.quantity *
line.cost_price) and sum(line.quantity_received * line.cost_price) per
stock purchase. Migrates the page from client-side direct PB read to
the service layer per AGENTS.md.

Co-authored-by: Orca <help@stably.ai>
2026-08-03 14:09:10 +02:00
SJCoetz
fc17b46f9a docs(buyer-tasks): design for mail-failed PO recovery in PO Draft tab
Mail-failed POs currently vanish from every buyer-tasks tab because
the po_draft and po_sent filters both exclude the 'mail_failed' status.
This adds a focused design that surfaces them in place inside PO Draft
with a red warning row + 'Resend' button that re-opens the shared
SendPoModal.

Co-Authored-By: Claude <noreply@anthropic.com>

Co-authored-by: Orca <help@stably.ai>
2026-08-03 10:25:51 +02:00
SJCoetz
d1c5ea0643 docs(specs): add collection confirm revamp design
Removes the Adjust Quantity modal, surfaces invoice photos in a per-PO
strip, exposes inline-editable cost prices, and migrates the page to a
thin service layer (listCollectedItems, updateOrderItemCost,
confirmOrderItemsForInvoicing) with three new /api/v1 routes. Cost edits
are audited in the existing notes feed as category=cost entries; confirm
is one PocketBase batch.

Co-authored-by: Orca <help@stably.ai>
2026-08-02 23:23:11 +02:00
SJCoetz
23e8e94d7c docs(specs): stock quick-draft modal design
Adds spec for the new item-first quick-draft modal on /stock-orders:
item-first stock-order entry, accumulates per supplier into draft POs,
reuses existing Send/Receive flow. No schema changes.

Co-authored-by: Orca <help@stably.ai>
2026-07-30 21:26:47 +02:00
SJCoetz
fe1af217e0 docs: buyer tasks page design spec
Co-authored-by: Orca <help@stably.ai>
2026-07-29 19:35:44 +02:00
SJCoetz
03ca2c8d29 docs: clarify customer non-nullable, full-order scope, collision link, partial-fail UX
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>

Co-authored-by: Orca <help@stably.ai>
2026-07-29 13:54:21 +02:00
SJCoetz
20533bcddf docs: design for orders review modal (amber icon + inline edit + attachment preview)
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>

Co-authored-by: Orca <help@stably.ai>
2026-07-29 13:53:36 +02:00
SJCoetz
74b7d4433f docs(spec): item history popover redesign — build both data sources, compare for 1 week
Redesign the per-item ⓘ popover on /sprint so it surfaces actionable history
(cheapest supplier, other quotes to this company, last sold, recommendation)
instead of the current decorative rainbow card.

- Deterministic PB-join service (new) computes suppliers, other quotes, last
  sold, stock from existing collections.
- Existing n8n AI blob keeps running — render side by side for comparison.
- After 1 week: delete whichever data source loses on speed / freshness /
  cost.
- Process orders section is a separate follow-up round.

Also ignore .superpowers/ (visual companion mockups are local-only).

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>

Co-authored-by: Orca <help@stably.ai>
2026-07-29 13:51:25 +02:00
SJCoetz
046683c506 feat: add tangerine theme, new docs and plugin stubs
Add full Tangerine brand theme with light and dark mode variants to the app theme system.
Add four new design and integration documents for collection pool, map and driver app workflows.
Add initial scaffolding for three new plugin source directories for the collection pool bulk assignment feature.
2026-07-14 11:48:10 +02:00
SJCoetz
02458909f7 docs(collection-map): tighten Refresh-button open question wording 2026-07-11 23:31:41 +02:00
SJCoetz
191668088c docs(collection-map): spec — drop filter console + collapse pin taxonomy
Two-pin model per supplier bucket: blue circle + letter per driver,
amber circle + ✓/✕ for unassigned. Filters (status, readiness, driver
multi-select, search) all leave; date picker stays. No backend or
schema changes. Awaiting user review before plan + implementation.
2026-07-11 23:31:17 +02:00
SJCoetz
47b01bddfa feat: add picking slips, bulk print tracking, supplier map
- Add Supplier Map component to suppliers page and reorganize sidebar navigation
- Implement picking slip PDF generation with supplier per line item and picked-by signature footer
- Add invoice bulk print tracking API and view models to track printed invoice state
- Extend company search and form to support email/telephone fields and improve searchability
- Fix data table debounce race condition by using useRef for onSearch handler
- Fix supplier page fetch race condition with debounced timeout
- Reduce list page item counts to 10 per page for customers, companies, and suppliers
- Update company search filter to include email and telephone in search queries
- Add comprehensive test suite for new and existing components and APIs
- Add pdf-lib dependency for PDF generation and update related tooling
- Clean up unused code and fix minor linting issues
2026-07-10 10:47:11 +02:00
SJCoetz
0d508095f0 Add order color stripe spec 2026-07-10 02:03:16 +02:00
SJCoetz
683b6c8d0a Add collection confirm rewrite spec 2026-07-10 00:59:26 +02:00
SJCoetz
728bab1671 Add collection map date filter and unassign spec 2026-07-10 00:47:42 +02:00
SJCoetz
72b2ec09e2 test(collection-pool): simplify operational sort test + correct spec reasoning 2026-07-10 00:38:31 +02:00
SJCoetz
8d742e5e87 Add collection pool nearby sort spec 2026-07-10 00:30:14 +02:00
SJCoetz
dbbb3e2b2c Add collection pool mark-ready notes spec 2026-07-10 00:00:40 +02:00
SJCoetz
e19bb7dbf7 Add PO additional attachments spec 2026-07-09 22:55:16 +02:00
SJCoetz
538986d7db Add PO PDF token-vs-filename spec 2026-07-09 22:13:53 +02:00
SJCoetz
1a3ce560c6 Add customer search company-disambiguation spec 2026-07-09 21:31:45 +02:00
SJCoetz
1992b0f4af Add new quote form redesign spec 2026-07-09 17:53:44 +02:00
SJCoetz
18334721cb feat(invoicing): add QuickBooks invoicing flow and print functionality
Add complete end-to-end QuickBooks invoicing workflow for the invoicing page:
- Add `jspdf` dependency for client-side PDF generation
- Implement updated item status handling with fallback for new invoice statuses
- Add server-side proxy API for secure QuickBooks customer lookup
- Build utilities to combine QuickBooks invoices and picking slips into a single PDF
- Add invoicing view models for row grouping, payload construction, and status checks
- Add full test coverage for all new components, APIs, and utilities
- Include feature design documentation and sample n8n workflow config
2026-07-09 09:44:55 +02:00
SJCoetz
9378685164 feat(collection-confirm): add full collection confirm workflow
Implement the complete collection confirm feature set:
- Add new `/collection-confirm` operational page for reviewing and confirming collected order items
- Add sidebar navigation entries for Collection Confirm and Invoicing
- Add `order_items` to the file proxy API whitelist for attachment access
- Install required testing dependencies and configure Vitest test setup
- Add full design documentation, test suite, and page overview screenshot
- Update package.json and build configuration files
2026-07-08 01:35:00 +02:00
SJCoetz
5f1838051f feat(collection-pool): add nearby supplier cluster sort mode
Add optional nearby-supplier cluster sort mode to the collection pool table, keeping operational sort as the default. Also includes:
- Update UserSearch component to support fallback selected label for pre-selected values
- Refactor AssignDriverDialog into a separate inner component with intent and pre-filled driver label support
- Add assignment badge helper types and functions
- Add full test coverage for new sort logic and component behaviors
- Update implementation plans and documentation files
- Fix minor code consistency and lint issues across touched files
2026-07-07 21:56:29 +02:00
SJCoetz
b9828def38 feat(collection-pool): add unified redesigned collection pool view
Remove redundant Assign Drivers top-level navigation link since driver assignment is now embedded directly in the collection pool page per-row, and add an Other nav section for leftover navigation items
Extract collection pool view logic into a dedicated view-model module with full Vitest test coverage for assignment state classification, row sorting, pool age labeling, and proximity marker grouping
Flatten the collection pool page into a single unified list replacing the old grouped assigned/unassigned layout, with updated row UI showing all required operational details and context-aware actions
Add database migration to add optional `collection_photo` field to order_items for driver pickup proof photos
Add complete design documentation, planning artifacts, and brainstorming session files for the collection pool redesign project
2026-07-07 20:49:31 +02:00