Skip to content

feat: standard.site publisher for blog records#5

Merged
fmalcher merged 1 commit into
mainfrom
feat/standard-site-publisher
Jul 22, 2026
Merged

feat: standard.site publisher for blog records#5
fmalcher merged 1 commit into
mainfrom
feat/standard-site-publisher

Conversation

@fmalcher

Copy link
Copy Markdown
Member

What

Adds a standard.site (AT Protocol) publisher to the shared build. During npm run build it upserts:

  • one site.standard.publication record (rkey self) for the blog
  • one site.standard.document record per non-hidden post (rkey = slug)

to the configured Bluesky/PDS account, and prunes records for removed/hidden posts.

Design

  • standard-site/atproto.ts — minimal XRPC client (createSession / putRecord / listRecords / deleteRecord). No new deps (global fetch). validate: false because a PDS doesn't natively know third-party lexicons like site.standard.*.
  • standard-site/publish.ts — fully config-driven (all account/publication values from env) and opt-in: if BSKY_APP_PASSWORD / BSKY_HANDLE / STANDARD_SITE_URL aren't set, it's a no-op. Idempotent (stable rkeys → re-runs update in place), prunes stale documents, and supports STANDARD_SITE_DRY_RUN=true for a preview.
  • build.ts — calls the publisher after the blog build.
  • Reuses existing stripHtmlTags / extractFirstBigParagraph / hidden-filter.

Publication-agnostic on purpose: this submodule is shared (angular.schule now, angular-buch.com later). Each consuming repo supplies its own env/secrets — no submodule change needed to onboard another site.

Verification

  • npm run typecheck clean.
  • Dry run against real content: 1 publication + 50 documents, 0 stale — no PDS writes.
  • Auth + custom-rkey write/delete confirmed against bsky.social.

Docs: STANDARD-SITE.md (setup + config keys), .env.example.

Publish the blog to the standard.site AT Protocol lexicons: one
site.standard.publication record and one site.standard.document record per
non-hidden post (rkey = slug), written to a Bluesky/PDS account during the
build.

- standard-site/atproto.ts: minimal XRPC client (createSession/putRecord/
  listRecords/deleteRecord), validate:false for third-party lexicons, no deps
- standard-site/publish.ts: config-driven, opt-in (no-op unless configured),
  idempotent upsert + prune of stale documents, dry-run mode
- build.ts: publish after the blog build (skipped when unconfigured)
- STANDARD-SITE.md + .env.example: setup and config docs

Publication-agnostic so the shared submodule can serve multiple sites; each
consumer supplies its own env/secrets.
@fmalcher
fmalcher merged commit ec78038 into main Jul 22, 2026
1 check passed
@fmalcher
fmalcher deleted the feat/standard-site-publisher branch July 22, 2026 12:32
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant