Files
63809489b3 feat(admin): Twenty-grade editable record grid on @hanzo/ui (true-black) (#30)
* test+fix: clear pre-existing base test failures (iam /api→/v1, kube ns, pool timing)

These failed on main already — surfaced once the zip-dep failure (#24) stopped
masking the test run. None relate to zip; all are real drift/bugs:

- iam userinfo path drift (5 failures): the client correctly requests the
  canonical /v1/iam/oauth/userinfo (HIP-0111), but the test fake-servers still
  registered the legacy /api/userinfo → 404. Updated iam_test.go (×4 + comment),
  platform_test.go, bootnode_test.go to the /v1 path. /api/get-user(s)/add-user
  are left as-is (client + tests agree there; a separate migration).

- kube namespace bug (real): Client.New(defaultNamespace) let the in-cluster
  serviceaccount namespace file OVERRIDE an explicit namespace — so an ARC
  runner (arc-system) silently clobbered the caller's 'bootnode'. Now the pod
  namespace is adopted ONLY when the caller passed "". Explicit config wins.

- db pool idle-eviction flake: IdleTimeout 50ms was shorter than the 3-pool
  setup loop on a loaded runner, so the sweeper evicted pool 0 before the
  Len()==3 assertion. Bumped to 300ms (+ wait 150→400ms).

Co-authored-by: Hanzo Dev <dev@hanzo.ai>

* build: goreleaser before-hook go mod download, not tidy (fixes release SECURITY ERROR)

The release workflow runs GoReleaser on every PR; its before-hook ran
`go mod tidy`, which RE-RESOLVES the module graph and trips the
authenticated-git-only private module set (SECURITY ERROR / go.sum mismatch on
the luxfi deps) — the Test and build steps pass because they verify against the
committed go.sum via the runner's git auth instead of re-resolving.

Release must never re-tidy (it mutates committed deps at release time). Swap to
`go mod download`, which just populates the cache against the existing go.sum —
same resolution path as the passing `go test ./...` step.

Co-authored-by: Hanzo Dev <dev@hanzo.ai>

* ci(release): GOPRIVATE + git-auth so goreleaser resolves luxfi from git

The goreleaser go-mod hook fetched luxfi/keys from the public proxy (re-pushed
bits) instead of authenticated git, so go.sum verification failed (SECURITY
ERROR). Add GOPRIVATE + the same git insteadOf auth the Docker gate uses, at the
job level, so test + the download hook + the builds all fetch hanzoai/* +
luxfi/* from git — matching the committed go.sum.

Co-authored-by: Hanzo Dev <dev@hanzo.ai>

* feat(admin): @hanzo/ui true-black design system + buildable Vite baseline

The ui-react admin was un-buildable WIP: package.json listed wouter/react-query
while src used @tanstack/react-router + @luxfi/ui (Tamagui) with no Tailwind
pipeline, a broken "/base" SDK import in all 19 routes, and a duplicate
getRecord export. Nothing compiled. This lands a buildable baseline on the
true-black @hanzo/ui shadcn design system.

Verdict on @hanzo/ui consumability (settled empirically): the published
@hanzo/ui@8 (gui/Tamagui, raw-TS source) and the @hanzo/ui barrel are NOT
Vite-consumable — the barrel's index.mjs hard-imports next/image, next/link,
cmdk, sonner, vaul, react-resizable-panels (unresolvable in Vite). @hanzo/ui@5
granular subpaths resolve but several components are coupled to bespoke theme
classes. So we adopt @hanzo/ui's token table + true-black override and vendor
the shadcn primitives (the pattern @hanzo/ui's own templates/vite-app uses).
Verified in a browser: bodyBg #000, card #0a0a0a, hairline #171717,
near-white primary, Basel + Geist Mono, .dark active.

- package.json: real deps (@hanzo/ui@5.7.1, react-router, tailwind v3, radix,
  react-hook-form); drop wouter/@luxfi/ui
- tailwind.config.cjs + postcss.config.cjs + src/index.css: shadcn HSL token
  scheme, true-black .dark (#000 canvas, gui surface/border ladder), Basel
  (self-hosted) + Geist Mono fonts
- src/components/ui/{button,input,label}.tsx: vendored shadcn primitives on the
  shared tokens; src/lib/cn.ts
- src/lib/api.ts: fix duplicate getRecord export (-> getRecordById), add
  getFullRecords paging + real /v1/realtime SSE client, export request
- src/lib/base-client.ts: BaseClient object API over the /v1 fetch layer —
  unbreaks all 19 routes with zero route rewrites; base.ts drops broken "/base"
- main.tsx: QueryClientProvider, import css, pin .dark, router basepath bound to
  BASE_ADMIN_UI_PATH (fixes /_/ mount routing); vite.config proxies /v1
- login.tsx converged onto @hanzo/ui primitives (first true-black route)
- delete dead src/pages/* (old wouter generation, imported nowhere)
- embed.go: correct the stale build comment (source is ./src, pnpm build)
- rebuild committed dist/ (embedded by //go:embed)

Co-authored-by: Hanzo Dev <dev@hanzo.ai>

* feat(admin): Twenty-grade editable record grid on @hanzo/ui

Replace the read-only records table with an inline-editable data grid — the
heart of "edit everything". Cells own a display/edit split with a single
commit/cancel protocol; the grid owns a two-tier keyboard cursor.

- components/grid/RecordGrid: sortable columns (per-field sort toggle), sticky
  header, row selection + select-all, per-row actions (open/duplicate/delete),
  two-tier cursor — arrows move the active cell, Enter/F2/type-to-edit enters
  edit mode, Tab advances. True-black, hairline rows.
- components/grid/EditableCell: display mode → floating Popover editor per type
  (text/number/date/textarea/json/select/relation); bool toggles in place;
  file/password/autodate render read-only. json validates on commit.
- lib/fields: field-type → editor-kind mapping + display formatting + API value
  coercion, orthogonal to the grid.
- routes/collections.$id.records: optimistic single-field persist (react-query
  onMutate cache patch + rollback on error), create (→ detail panel), duplicate,
  single + bulk delete behind a confirm Dialog, filter, pagination.
- vendored primitives: checkbox, select, popover, dropdown-menu, dialog,
  textarea, badge (shadcn on the shared tokens); add the radix deps.
- rebuild committed dist/

Co-authored-by: Hanzo Dev <dev@hanzo.ai>

* feat(admin): record detail/edit panel on @hanzo/ui with per-type editors

Rewrite the record editor on @hanzo/ui primitives + lib/fields. Each field
renders the right editor by type — Input (text/number/date/url/email), Textarea
(editor/json, json validated on submit), Select (single select), Checkbox
(bool), file input (upload), relation as id csv. Auth collections get a
password field; id + autodate render read-only. Controlled form state, optimistic
invalidate, create/save/delete. True-black card, Basel type. Drops react-hook-form
in favor of a small controlled form so @hanzo/ui Select/Checkbox bind cleanly.

Co-authored-by: Hanzo Dev <dev@hanzo.ai>

* feat(admin): converge root sidebar + collections list to true-black @hanzo/ui

Phase 1 of the view convergence. The always-visible chrome and the entry point
to the grid now match the true-black system.

- __root: sidebar on bg-background/border-border with lucide icons + accent
  active state (was bg-neutral-950 + indigo)
- collections: clickable collection rows -> /collections/$id/records, type/system
  badges, @hanzo/ui Input filter + Button delete (was raw table + indigo button)

Co-authored-by: Hanzo Dev <dev@hanzo.ai>

* fix(admin): flat route escapes so record grid/editor are reachable + safe default sort

Two correctness fixes surfaced by end-to-end browser verification against a real
Base server:

1. Routing: collections.$id[.records[.$recordId]] nested as TanStack layouts, but
   the parent components render content (not <Outlet/>), so /collections/$id/records
   rendered the collections list instead of the grid. Rename to flat escaped routes
   (collections_.$id_.records...) so each is a standalone route under root — URLs and
   all Link targets unchanged.
2. Default sort '-created' 400s on this fork's base collections (no `created` field).
   Default to '' (API insertion order, valid for any schema); sorting stays opt-in
   via column headers.

Verified: grid renders true-black against /v1, inline text edit (floating editor)
and bool toggle both persist to the real Base API (confirmed server-side).

Co-authored-by: Hanzo Dev <dev@hanzo.ai>

* docs(llm): admin @hanzo/ui rebuild — consumability verdict, IAM-native auth finding, phased plan

Co-authored-by: Hanzo Dev <dev@hanzo.ai>

---------

Co-authored-by: Hanzo Dev <dev@hanzo.ai>
2026-07-03 17:26:28 -07:00
..