A first integration test of the model call: Workers AI through the AI
binding, behind the same `complete(messages)` interface as the sim's
fake model. Opt-in (`pnpm test:model`) since it needs `wrangler login`
and costs money.
Red: src/model.ts doesn't exist yet.
Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
The chat and load arrows drew `things: { mower }` whether I lent the
raw mower or the governed one. Name objects by the reply arrow that
introduced them, so the diagram reads `things: { mower: governed }`
and lending the raw mower would fail the trace comparison.
Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
The spec is a sequence diagram of the a2030.md story: I lend a governed
mower; the neighbor's harness shows the model only `about`, runs its
code as a tenant, and the governor stops the tipsy tenant at a 2-cell
fence. The test runs the actors through a causal tracer and compares
the trace with the diagram, then checks the yard and what the model saw.
The tracer comes from agoric-sdk PR #12895, extended to name
participants made mid-sequence (governor, tenant) and to draw thrown
errors as replies.
Red: src/ doesn't exist yet (ERR_MODULE_NOT_FOUND for src/fence.ts).
Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
How a Discord message could carry references to our DOs, after
@endo/chat: names in the text, references beside it in a mailbox DO,
an Adopt button answered ephemerally, and per-user petstores. Webkeys
in markdown work but disclose the capability to every channel reader
and to Discord itself; ephemeral replies still pass through Discord,
so references should never cross it at all.
Generated-by: Claude Opus 5.5
toybox-stories.md: the weekly roundup (#23), album-to-album sync
(endojs/playground#16), and drag-to-archive.org (#118), with the needs
they share. The checklist gains the toybox tree: a changed signal (T1),
Blockly composition by petname (T2), and confined code in Dynamic
Workers (T3).
Generated-by: Claude Opus 5.5
The public cache keeps public items whole, private annotations and
comments included (2,525 of 14,645). Dan finds that acceptable; the
goal is to finish thinking it through, not to fix a leak.
Generated-by: Claude Opus 5.5
1d's query.ts plans to filter while walking diigo's pages, but a filled
cache holds every item: choose before implementing. madmode's public
reads need no cache id, so DiigoBridge's cache-id TODO is moot unless a
private-reading caller wants it.
Generated-by: Claude Opus 5.5
- issues collection (ISO-week slug, week, dek, rich-text body); home,
/issues, and /issues/<week> pages; seed/issues.json holds three
sketched issues (W38-W40) from public diigo bookmarks, editorial
lines marked (draft); issues-sketch.md is the dry run behind them
- microformats: h-feed of h-entry lists; an issue is an h-entry
(p-name, dt-published, p-summary, e-content); off-site links render
as h-cite, /tag/<tag> links as rel-tag p-category (CiteLink.astro)
- diigo tags: shown on each bookmark and attached to issues via the
tag taxonomy (now posts + issues); /tag/<tag> lists issues
- demo blog content gone: posts dropped from the seed, home page lists
issues, site title/tagline, footer About widget, and About page
rewritten; nav is Home / About / Issues; search and RSS cover issues
- .column container gives potluck's pages the header's margins
Generated-by: Claude Opus 5.5
https://www.kmjn.org/notes/modern_plain_html.html and its stylesheet:
system fonts (Verdana; no Google webfonts), one 800px column,
line-height 1.35, links in the text color with a dotted underline, no
rounding, shadows, or tracking; the header is plain, not sticky glass.
Token overrides live in theme.css; per-page scoped styles unchanged.
Generated-by: Claude Opus 5.5
pnpm create emdash@latest potluck --pm pnpm --install --yes, per
https://docs.emdashcms.com/ ("Create your first EmDash site"); the
--yes defaults are cloudflare + blog. Replaces the old madmode/
starter (never committed).
Generated-by: create-emdash 1.2.0, run by Claude Opus 5.5
The existing export (mastodon-archive) reads favourites, bookmarks,
and mentions, which ActivityPub doesn't carry. So the client API with
a narrow read-only token (held in webapp) is the primary source;
items are still keyed by ActivityPub uri, and outbox/follower-actor
sources move to a later portability goal.
Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
Mastodon is one implementation; the cache speaks the protocol: outbox
for backfill, and fedi-cache as a follower actor so Update/Delete are
delivered rather than polled for. Its own keypair replaces an access
token, so webapp drops out of this one.
Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
Both follow the diigo-cache pattern (webapp holds the credential,
read-only and minted narrow at the source; the cache serves a public
page). Zotero's versioned sync answers diigo's stale-head problem;
Mastodon's doesn't announce edits/deletes, so its tree carries that
as a design question.
Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
Comments written for the reader: no restating what the shebang says, no traces of the design conversation; the publish comment no longer mentions a projection that no longer exists.
Generated-by: Claude Opus 5.5
Comments written for the reader: no restating what the shebang says, no traces of the design conversation; the publish comment no longer mentions a projection that no longer exists.
Generated-by: Claude Opus 5.5
compare-export.ts: the manual is a HELP string at the top of the module
(a docstring, as a value) and main prints it on bad usage. No reading
its own source, no regex, one copy; @file points at it.
Generated-by: Claude Opus 5.5
compare-export.ts: the usage message comes from the @file manual's
synopsis line (read from the script's own source, on the bad-usage path
only), docopt-style, so the synopsis lives in one place; if the header
changes shape, it says "see the @file comment".
Generated-by: Claude Opus 5.5
compare-export.ts: the usage exit status is a named constant,
BAD_USAGE = 2, whose JSDoc cites the convention (Bash Reference Manual
§3.7.5); the manual just says "Exits 2 on bad usage".
Generated-by: Claude Opus 5.5
compare-export.ts: exit 2 on bad usage is an external convention, so its
@file cites the source (Bash Reference Manual §3.7.5, Exit Status).
Generated-by: Claude Opus 5.5
compare-export.ts: as a program script, its @file is its manual
(purpose, usage, outputs, exit code), per docs-files-api's exception;
main's JSDoc keeps only the edge and attenuation.
Generated-by: Claude Opus 5.5
Docs per the docs-files-api skill: a 1–2 line @file; what a declaration is or does in JSDoc on it, not in // comments or the file header.
Generated-by: Claude Opus 5.5
Docs per the docs-files-api skill: a 1–2 line @file; what a declaration is or does in JSDoc on it, not in // comments or the file header.
Generated-by: Claude Opus 5.5
Docs per the docs-files-api skill: a 1–2 line @file; what a declaration is or does in JSDoc on it, not in // comments or the file header.
Generated-by: Claude Opus 5.5
Docs per the docs-files-api skill: a 1–2 line @file; what a declaration is or does in JSDoc on it, not in // comments or the file header.
Generated-by: Claude Opus 5.5
Docs per the docs-files-api skill: a 1–2 line @file; what a declaration is or does in JSDoc on it, not in // comments or the file header.
Generated-by: Claude Opus 5.5
Docs per the docs-files-api skill: a 1–2 line @file; what a declaration is or does in JSDoc on it, not in // comments or the file header.
Generated-by: Claude Opus 5.5
Docs per the docs-files-api skill: a 1–2 line @file; what a declaration is or does in JSDoc on it, not in // comments or the file header.
Generated-by: Claude Opus 5.5
Docs per the docs-files-api skill: a 1–2 line @file; what a declaration is or does in JSDoc on it, not in // comments or the file header.
Generated-by: Claude Opus 5.5
Docs per the docs-files-api skill: a 1–2 line @file; what a declaration is or does in JSDoc on it, not in // comments or the file header.
Generated-by: Claude Opus 5.5
/public/<username> reads through the cache's viewer() facet
(PageViewer: stored pages, knownTotal, fill progress — the reader
alone), so it can't fetch from diigo or write storage.
Behavior change, agreed beforehand: an unfetched page no longer fills
itself on a miss; it says "not fetched yet" (JSON: stored: false), and
the owner fills via the webkey page. The HIT/MISS line becomes "stored
<when>". Strangers can no longer make the cache spend the owner's diigo
session; the README's deployment concern shrinks to /api.
Tests: viewing an unfetched page makes no webapp call; the page appears
once stored; fill progress shows after one fill step.
Generated-by: Claude Opus 5.5
No SQL text in the cache logic any more. Statements live in two files,
parsed by sqlStatements (`-- name:` sections, as in finquick's
brcal/gcbook.js) and imported as text (wrangler Text rule for *.sql):
- cache-read.sql: selects only, checked when the module loads
- cache-write.sql: schema, the v2 renumbering, etch, drops
store.ts turns them into two frozen facets with domain methods:
makeReader(sql) runs only the read statements (page, knownTotal,
deepestPageSince, pagesThrough); makeWriter(storage) only the write
ones (migrate, etch, dropPagesThrough), each change one transaction.
The cache migrates in its constructor under blockConcurrencyWhile, as
Cloudflare recommends, so readers never meet missing tables; the
migration test plants v1 storage and evicts to get a fresh activation.
A viewer() facet (PageViewer: stored pages and fill progress, from the
reader alone) is added for the public page.
Pure refactor: stored state and behavior unchanged.
Generated-by: Claude Opus 5.5
capsite-notes gains a map of what a person can do in diigo-cache, where,
by which transport (HTTP route or Cap'n Web RPC), and with what
authority — a flowchart of the pages plus a table — marking the
misalignments: publish and dump are cache-key actions on HTTP forms, not
the RPC facet; the public page can write (a miss fills from diigo).
Input to aligning the admin UX with the RPC interface.
Generated-by: Claude Opus 5.5
1c-vi: the cache proven complete against diigo's RSS export (and the
0-based page_num found on the way); 1e: the password-manager login;
1f: "invalidate the last N days" as today's stopgap; how-to-run: the
webkey page and compare-export.
Generated-by: Claude Opus 5.5
From the "Capsite checklist revisited" session: the root goal becomes
madmode publishing a weekly roundup of diigo bookmarks; goal 2 reads the
public cache (no credential on madmode's side); new 1f (stale head
pages must refresh); goals 3–7 restated around the weekly page,
deployment, cookie expiry, and bib sync.
Generated-by: Claude Code
compare-export.ts does its file I/O asynchronously (node:fs/promises;
main is async), so no sync-I/O precedent. The one exception says why:
node:sqlite has only DatabaseSync.
Generated-by: Claude Opus 5.5
compare-export.ts: Object.fromEntries(Object.entries(…).map(…)) as
objectMap(original, mapFn), with @endo/common's signature.
Generated-by: Claude Opus 5.5
compare-export.ts runs main only under import.meta.main (Node's
`if __name__ == "__main__"`), so importing it — say, from a test —
runs nothing.
Generated-by: Claude Opus 5.5
compare-export.ts per the ocap style guide (dckc/awesome-ocap,
style-guide/): main takes standard authorities under standard names as
default arguments — argv, fs, connect, now, stdout, stderr, exit (the
transitional form of _script_io) — and attenuates them itself:
connect(dbPath) to a read-only cacheItems, the output directory to an
outDir that writes only plain file names inside it. Counts go to
stdout (program output), usage to stderr.
Generated-by: Claude Opus 5.5
compare-export.ts under ocap discipline: parseExport and compare are
pure; main is the program's edge and takes every power it uses (argv,
file reads and writes, the sqlite read, the clock, console, the exit
code) as default arguments. Nothing ambient at module level; the last
line just calls main().
Generated-by: Claude Opus 5.5
scripts/tsconfig.json gives scripts/ node's types (@types/node, a new
devDependency) and allows the .ts import specifiers node's type
stripping needs; the worker's tsconfig still keeps node's types out.
pnpm lint runs it.
Generated-by: Claude Opus 5.5
A diigo note item's body (note_content) renders first, as a Highlight:
line, as the export does: the 6 "export has notes, cache none" items
from the comparison were notes whose bodies the cache had all along.
Generated-by: Claude Opus 5.5