Commit graph

20 commits

Author SHA1 Message Date
Snider
b187cb1df8 chore: add Go repo norms (badges, contributing, lint, taskfile, editorconfig)
All checks were successful
Security Scan / security (push) Successful in 13s
Test / test (push) Successful in 3m48s
Co-Authored-By: Virgil <virgil@lethean.io>
2026-02-23 06:45:49 +00:00
Snider
df5c7a6cad chore: refresh go.sum after upstream tag updates
Some checks are pending
Security Scan / security (push) Waiting to run
Test / test (push) Waiting to run
Co-Authored-By: Virgil <virgil@lethean.io>
2026-02-23 06:35:19 +00:00
Snider
9636396298 feat: modernise to Go 1.26 iterators and stdlib helpers
Some checks failed
Security Scan / security (push) Successful in 12s
Test / test (push) Failing after 37s
Add iter.Seq2 iterators (All, GroupsSeq) for streaming DB rows,
GetSplit/GetFields using strings.SplitSeq/FieldsSeq, slices.DeleteFunc
in event watchers/callbacks, and range-over-int in benchmarks.

Co-Authored-By: Gemini <noreply@google.com>
Co-Authored-By: Virgil <virgil@lethean.io>
2026-02-23 05:21:44 +00:00
Claude
5f5157fb3b
ci: add Forgejo Actions test and security scan workflows
Some checks failed
Security Scan / security (push) Successful in 14s
Test / test (push) Failing after 47s
Uses reusable workflows from core/go-devops for Go testing
(with race detector and coverage) and security scanning
(govulncheck, gitleaks, trivy).

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-23 03:28:08 +00:00
Claude
2126e8bcaa
chore: sync workspace dependency versions
Run go work sync to align dependency versions across workspace.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-22 21:42:03 +00:00
Snider
3c6b2267a3 refactor: apply go fix modernizers for Go 1.26
Automated fixes: interface{} → any, range-over-int, t.Context(),
wg.Go(), strings.SplitSeq, strings.Builder, slices.Contains,
maps helpers, min/max builtins.

Co-Authored-By: Virgil <virgil@lethean.io>
2026-02-22 21:00:17 +00:00
Snider
351f4dfd30 chore: bump go directive to 1.26.0
Co-Authored-By: Virgil <virgil@lethean.io>
2026-02-22 20:33:48 +00:00
Snider
0284110cca docs: add README with quick start and docs links
Co-Authored-By: Virgil <virgil@lethean.io>
2026-02-20 15:11:20 +00:00
Snider
c570f08eba docs: graduate TODO/FINDINGS into production documentation
Replace internal task tracking (TODO.md, FINDINGS.md) with structured
documentation in docs/. Trim CLAUDE.md to agent instructions only.

Co-Authored-By: Virgil <virgil@lethean.io>
2026-02-20 15:01:55 +00:00
Snider
f202cfe218 feat(events): add reactive event hooks for store mutations
Watch/Unwatch API with buffered channels (cap 16) and wildcard matching,
OnChange callback hook for go-ws integration, non-blocking notify on
Set/SetWithTTL/Delete/DeleteGroup. ScopedStore events emit with full
prefixed group names. 16 new tests, race-clean, coverage 94.7% -> 95.5%.

Co-Authored-By: Virgil <virgil@lethean.io>
2026-02-20 08:25:03 +00:00
Snider
6e150f80eb docs: flesh out Phase 3 event hooks task specs
Detailed spec for reactive notification system: Event types,
Watcher API with buffered channels, OnChange callback hook for
go-ws integration, notify() with non-blocking sends, ScopedStore
event passthrough, and 13-item test matrix.

Co-Authored-By: Virgil <virgil@lethean.io>
2026-02-20 08:20:40 +00:00
Snider
175fd6bf83 feat(scope): add namespace isolation with quota enforcement
ScopedStore wraps Store and auto-prefixes groups with a namespace to
prevent key collisions across tenants. QuotaConfig enforces per-namespace
MaxKeys and MaxGroups limits (zero = unlimited). Upserts and expired
keys are excluded from quota counts.

New Store methods: CountAll(prefix) and Groups(prefix) for cross-group
queries. All 93 tests pass with race detector, coverage 94.7%.

Co-Authored-By: Virgil <virgil@lethean.io>
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-20 08:19:11 +00:00
Snider
22342f0395 docs: flesh out Phase 2 namespace isolation task specs
Detail ScopedStore wrapper with auto-prefixed groups, QuotaConfig
enforcement (MaxKeys, MaxGroups), CountAll/Groups helpers, and
comprehensive test matrix including quota edge cases.

Co-Authored-By: Virgil <virgil@lethean.io>
2026-02-20 07:57:32 +00:00
Snider
4399f8b6d2 bench: add supplemental benchmarks for GetAll scaling, parallel, TTL, Render
Add bench_test.go with benchmarks not covered by store_test.go:
- BenchmarkGetAll_VaryingSize: 4 sub-benchmarks (10/100/1K/10K keys)
  to measure allocation scaling
- BenchmarkSetGet_Parallel: b.RunParallel for throughput under contention
- BenchmarkCount_10K: COUNT(*) on large groups
- BenchmarkDelete: delete throughput
- BenchmarkSetWithTTL: TTL write overhead vs plain Set
- BenchmarkRender: template rendering with 50 keys
All benchmarks use b.ReportAllocs().

Co-Authored-By: Virgil <virgil@lethean.io>
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-20 04:53:52 +00:00
Claude
a6c99a2e0f
test: push coverage from 90.9% to 97.0%
Cover previously unreachable error paths in New(), GetAll(), and Render():
- New: schema conflict when index named "kv" pre-exists
- GetAll: scan error via NULL-key injection after table restructure
- GetAll: rows iteration error via database page corruption
- Render: scan error via same NULL-key technique
- Render: rows iteration error via same corruption technique

GetAll and Render now at 100%. Only 3 stmts remain uncovered in New()
(sql.Open lazy-error and PRAGMA busy_timeout — both genuinely
unreachable without driver mocking).

Co-Authored-By: Charon <charon@lethean.io>
2026-02-20 02:41:54 +00:00
Claude
b866dacdd2
feat(store): add TTL support and harden test coverage to 90.9%
Phase 0 -- Hardening:
- Fix SQLITE_BUSY under concurrent writes by setting SetMaxOpenConns(1)
  and PRAGMA busy_timeout=5000
- Add comprehensive tests: concurrent read/write (10 goroutines),
  edge cases (unicode, null bytes, SQL injection, long keys), error
  paths (closed store, invalid paths, corrupt files), group isolation,
  upsert verification, WAL mode verification, ErrNotFound wrapping
- Add benchmarks: Set, Get, GetAll (10K keys), file-backed Set

Phase 1 -- TTL Support:
- Add expires_at nullable column with schema migration for pre-TTL DBs
- SetWithTTL(group, key, value, duration) stores keys that auto-expire
- Lazy deletion on Get for expired keys
- Background purge goroutine (configurable interval, default 60s)
- Public PurgeExpired() method for manual cleanup
- Count, GetAll, Render all exclude expired entries
- Set clears TTL when overwriting a TTL key

Coverage: 73.1% -> 90.9% (48 tests, 0 races)

Co-Authored-By: Charon <developers@lethean.io>
2026-02-20 01:14:08 +00:00
Snider
49b42b5b10 docs: enrich TODO.md with Phase 0 hardening tasks
Add Phase 0: concurrent Set/Get race tests, edge cases (empty
key, Unicode, binary values), WAL mode verification, benchmarks.

Co-Authored-By: Virgil <virgil@lethean.io>
2026-02-20 00:28:48 +00:00
Virgil
d3d3eab174 docs: add TODO.md and FINDINGS.md for fleet delegation
Co-Authored-By: Virgil <virgil@lethean.io>
2026-02-19 21:36:19 +00:00
Snider
63c37cb801 fix: add modernc.org/sqlite dependency
Co-Authored-By: Virgil <virgil@lethean.io>
2026-02-19 16:10:16 +00:00
Snider
9ebe581069 feat: extract go-store from core/go pkg/store
SQLite key-value store wrapper.
Zero external dependencies (stdlib only).
Module: forge.lthn.ai/core/go-store

Co-Authored-By: Virgil <virgil@lethean.io>
2026-02-19 16:09:15 +00:00