17 Commits

Author SHA1 Message Date
Andrey Epifancev
bfe44fa648 feat(core): provider settings, response classification, secret redaction
Refs #5

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01QKHeGuAYh4W1jNdjMConZa
2026-09-28 00:18:33 +04:00
Andrey Epifancev
3f6debc18b feat(core): HttpClient port and byte-exact multipart builder
Refs #5

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01QKHeGuAYh4W1jNdjMConZa
2026-09-28 00:00:08 +04:00
Andrey Epifancev
aecab7627c fix: typecheck src/core without Node types; pin exact dependency versions (T1.1, O-2)
T1.1: tsconfig.core.json (types: []) covers src/core; typecheck runs both
passes, so process/Buffer in core fail compilation. tests/core-types.test.ts
compiles a fixture with Node globals under both configs and rejects config
errors as false positives. The fixture is excluded from the root tsconfig.

O-2: devDependencies pinned to the locked versions, .npmrc save-exact=true.
Lock updated only in the root specifiers: npm install on macOS would prune
optional rolldown binaries for other platforms.

Refs #3

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01QKHeGuAYh4W1jNdjMConZa
2026-09-27 20:08:57 +04:00
Andrey Epifancev
972976b16a fix(core): claimAll reclaims own work; isolate per-record queue errors
- I-1 (F-1): claimAll() now also moves this device's own `retry` records
  and own stale `sent` records to `saved` via the `claim` transition
  (device = own), same as it already does for other devices' claimable
  records, then runs a normal tick() so everything sends without waiting
  for the next retry time. The returned count still only reflects records
  reassigned from other devices. Adds `ownReclaimable()` to schedule.ts.
- M-1 (F-2): pass() wraps each per-record operation (staleOwn update and
  each send) in try/catch, remembers the first error, keeps processing the
  rest of the due queue, and rethrows the first error after both loops
  complete — so one permanently failing record no longer blocks newer
  records behind it. list()/load() failures still reject tick()
  immediately, as before.
- F-4a: send()'s post-request update now also requires
  `r.device === env.deviceId && r.sentAt === sent.sentAt`, so a late
  transcription result can never overwrite a record another device (or a
  newer send) has since taken over.
- F-4b: pass()'s staleOwn loop now also stops when the abort signal fires;
  retry() and claimAll() return early (false / 0) without writing once
  disposed.
- F-4d: retry() no-op it.each now also covers `sent` (own, fresh).

Refs #1

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-09-27 17:12:31 +04:00
Andrey Epifancev
1b23554658 test(core): golden test-01 end-to-end capture → queue → note
Refs #1

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-09-27 16:54:51 +04:00
Andrey Epifancev
88ef2bde24 feat(core): manual retry and claim-all commands
Refs #1

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-09-27 16:47:08 +04:00
Andrey Epifancev
626d832bd1 fix(core): stop sending after QueueRunner.dispose()
Refs #1

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-09-27 16:42:57 +04:00
Andrey Epifancev
97a560820f feat(core): queue runner with retries, stale-sent recovery and re-entrancy guard
Refs #1

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-09-27 16:38:46 +04:00
Andrey Epifancev
b126e4bf8b feat(core): save captured audio and initial note; in-memory port fakes
Refs #1

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-09-27 16:32:34 +04:00
Andrey Epifancev
0cd683d5df feat(core): due, stale-sent and claimable selection
Refs #1

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-09-27 16:29:28 +04:00
Andrey Epifancev
d579ffd4a1 feat(core): note body with status region and transcript insertion
Refs #1

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-09-27 16:24:30 +04:00
Andrey Epifancev
83236c4118 feat(core): read, parse and patch voice-* frontmatter
Refs #1

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-09-27 16:19:57 +04:00
Andrey Epifancev
a4163fa5fe feat(core): voice record state machine with backoff
Refs #1

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-09-27 16:12:31 +04:00
Andrey Epifancev
6b2466cf05 feat(core): record ids, file paths, time formatting
Refs #1

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-09-27 16:08:28 +04:00
Andrey Epifancev
7cd3811ead chore: scaffold build and vitest, add core ports and boundary guard
Refs #1

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-09-27 15:52:20 +04:00
Andrey Epifancev
1cd72201e2 test: track test-01.m4a fixture so golden tests pass on a clean clone
Refs #1

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-09-27 15:08:33 +04:00
Andrey Epifancev
72c942f667 chore: bootstrap project skeleton, openspec, fixtures 2026-09-27 14:06:01 +04:00