Commit Graph
13 Commits
Author SHA1 Message Date
steveandClaude Opus 4.8 3cfa72cb25 REST fill/clear on objects; clear-bed becomes one change set (#82)
Build image / build-and-push (push) Successful in 18s
Gadfly review (reusable) / review (pull_request) Successful in 5m18s
Adversarial Review (Gadfly) / review (pull_request) Successful in 5m19s
FillRegion and ClearObject were reachable only through the agent toolbox, so
on an instance with no model configured the most valuable bulk operation in a
garden planner — and the one carrying the most carefully reasoned geometry in
the codebase — did not exist at all. internal/service/ops.go said these lived
on *Service so "any future REST surface" would inherit the ACL checks; this is
that surface.

POST /objects/:id/fill takes a region EITHER by compass name ("all", "ne",
"south half") or as an explicit rect in the object's local frame, and refuses
both-or-neither: silently preferring one would make a client bug look like a
geometry bug. It answers 200 rather than 201 because a fill can legitimately
create nothing (the region is already planted) and there is no single resource
to point a Location at.

POST /objects/:id/clear replaces a client-side loop of PATCHes. That loop
wrote one change set per plop, so clearing a 40-plop bed took 40 presses of
Undo to put back — while the agent's clear_object, for the identical
user-facing action, undid in one click. CLAUDE.md states the rule it violated:
multi-row operations record together so they undo as one unit. Moving it
server-side also removes the partial-failure case the loop had to reconcile.

TestClearObjectIsOneChangeSetAPI pins that: fill a bed, count change sets,
clear it, assert the count rose by exactly one.

DESIGN.md's API block gains the two new routes, and the four it was already
missing: GET/POST/DELETE /gardens/:id/share-link and the unauthenticated
GET /public/gardens/:token. An unauthenticated surface absent from the
architecture doc is the one worth fixing on sight.

Co-Authored-By: Claude Opus 4.8 (1M context) <[email protected]>
Claude-Session: https://claude.ai/code/session_01H3zbym8Doka2d7D48maSgZ
2026-07-21 18:20:54 -04:00
steveandClaude Opus 4.8 07d598cffd Address fifth round of Gadfly findings on #76
Build image / build-and-push (push) Successful in 5s
- fillLoaded's doc listed what it does and omitted the non-finite-region
  rejection this PR added to it.
- Trim the half-spacing rule's restatement in DESIGN.md to the decision and a
  pointer. The rule, the square-foot arithmetic and the failure mode are
  written out once, in hexCenters, rather than near-verbatim in four places.

Co-Authored-By: Claude Opus 4.8 (1M context) <[email protected]>
Claude-Session: https://claude.ai/code/session_01H3zbym8Doka2d7D48maSgZ
2026-07-21 14:27:58 -04:00
steveandClaude Opus 4.8 45da4b15e2 Fill: honour the half-spacing edge rule when packing plops (#75)
Build image / build-and-push (push) Successful in 7s
Gadfly review (reusable) / review (pull_request) Successful in 10m7s
Adversarial Review (Gadfly) / review (pull_request) Successful in 10m8s
Filling a bed left the outer row too far from the edge, and staggered rows
worse still. Two defects, both from anchoring the lattice at the region's min
corner:

- Odd rows offset by `radius` started at `MinX + 2·radius`, leaving a bare
  strip a whole plop wide down one side of every other row.
- All the leftover slack piled up on the far edge, where plops hung 13cm
  outside the bed on a 4×8ft garlic bed. Nothing clips them, so they drew
  over the bed outline.

Spacing is a constraint between neighbouring plants competing for the same
soil, light and water. A bed edge is not a competitor, so the outer row owes
it half the spacing — the arithmetic inside every square-foot-gardening chart
(4/square = 6" apart, 3" from the square's edge).

The wrinkle: a plop is a CLUMP, not a plant. defaultPlopRadius is 1.5×spacing,
so keeping the whole circle inside the bed insets the outer row by 1.5
spacings, three times what the rule allows. So centre the lattice and set the
minimum centre-inset to `radius - spacing/2`: the clump may cross the edge by
up to half a spacing, putting its outermost plants exactly the half-spacing
from the edge the rule asks for. Capped there — a clump mostly outside the bed
would be a drawing of plants in the path.

Same bed, same 15 plops, now symmetric with a deliberate 6.5cm overhang inside
the 7.5cm budget instead of an accidental 13cm on one side only. The stagger
falls out of the centring for free: an offset row holds one fewer plop, and
centring that run puts it exactly half a pitch off its neighbours.

TestFillRegionDeterministicPacking expected 4 plops in a 60×60 bed; the fourth
was centred ON the east edge with half of it outside, well past the budget.
It is 3 now — the fix working, not a regression in it.

Co-Authored-By: Claude Opus 4.8 (1M context) <[email protected]>
Claude-Session: https://claude.ai/code/session_01H3zbym8Doka2d7D48maSgZ
2026-07-21 10:11:08 -04:00
steve 8dbbc5439d Chat panel in the garden editor (#57) (#71)
Build image / build-and-push (push) Successful in 6s
Co-authored-by: Steve Dudenhoeffer <[email protected]>
2026-07-21 06:43:22 +00:00
steve 3a3ce16fce Agent runtime: majordomo in-process, Ollama Cloud config, chat endpoint (#56) (#70)
Build image / build-and-push (push) Successful in 6s
Co-authored-by: Steve Dudenhoeffer <[email protected]>
2026-07-21 06:22:10 +00:00
steve 7f8b5254d0 Journal UI: write and read season notes where you're already looking (#53) (#67)
Build image / build-and-push (push) Successful in 11s
Co-authored-by: Steve Dudenhoeffer <[email protected]>
2026-07-21 05:55:45 +00:00
steve 8c5ddb21ec Season view: filter the editor to a year (#54) (#66)
Build image / build-and-push (push) Successful in 17s
Co-authored-by: Steve Dudenhoeffer <[email protected]>
2026-07-21 05:47:34 +00:00
steve b96ca1ec0a Grow journal: time-stamped notes on gardens, beds and plantings (#52) (#65)
Build image / build-and-push (push) Successful in 6s
Co-authored-by: Steve Dudenhoeffer <[email protected]>
2026-07-21 05:40:17 +00:00
steve 78a04672b5 Seed provenance + inventory: source links and seed lots (#50) (#64)
Build image / build-and-push (push) Successful in 8s
Co-authored-by: Steve Dudenhoeffer <[email protected]>
2026-07-21 05:39:24 +00:00
steve 2a8fe24766 History panel + undo in the editor (#49) (#63)
Build image / build-and-push (push) Successful in 9s
Co-authored-by: Steve Dudenhoeffer <[email protected]>
2026-07-21 05:23:25 +00:00
steve f208da94d6 Revision history: change sets + revisions + revert — the undo substrate (#48) (#61)
Build image / build-and-push (push) Successful in 5s
Co-authored-by: Steve Dudenhoeffer <[email protected]>
2026-07-21 05:07:30 +00:00
steve e22bdd6cab Copy a garden (deep duplicate) from the gardens list (#46)
Build image / build-and-push (push) Successful in 16s
Co-authored-by: Steve Dudenhoeffer <[email protected]>
2026-07-21 03:58:39 +00:00
steveandClaude Fable 5 e71443311e Add DESIGN.md and README overview
Capture the v1 architecture: domain model, geometry, SVG editor with
semantic zoom, REST API with version-guarded sync, service-layer seam
for future majordomo/executus agent tools, OIDC-first auth (Authentik),
and the phased roadmap.

Co-Authored-By: Claude Fable 5 <[email protected]>
2026-07-18 14:11:46 -04:00