A tiny Cloudflare Worker that renders notes published by the Note publisher Obsidian plugin into public, read-only web pages addressed by UUID.
The Obsidian plugin commits each note as docs/<uuid>/index.md (plus its
images) into your private GitHub repository. This Worker reads that repo
with a read-only token and serves:
GET /v/<uuid>— rendersdocs/<uuid>/index.mdas HTML.GET /v/<uuid>/<file>— serves an image from that document's folder.
Any path that isn't a strict RFC-4122 UUID returns 404, so there are no ranges
to enumerate. The URL is the secret: this is share-by-URL, not authentication —
to revoke access, unpublish the note from Obsidian.
Prefer to host it yourself without Cloudflare? Use the self-hosted worker instead. Pick one — the plugin doesn't care which is behind its "Worker base URL".
Public (non-secret) settings live in wrangler.toml under [vars]:
| Variable | Meaning |
|---|---|
GH_OWNER |
GitHub user/org that owns the private repo. |
GH_REPO |
Private repository name. |
GH_BRANCH |
Branch to read from. |
ROOT_DIR |
Directory holding the published docs (matches the plugin's "Root directory"). |
The token is a secret, never committed:
wrangler secret put GH_PATGH_PAT must be a fine-grained PAT with Contents: Read only on the private
repo. It stays server-side and never reaches the browser.
npm install
cp .dev.vars.example .dev.vars # put a read-only GH_PAT here for local runs
npm run devnpm install
npm run deploy # wrangler deploy
wrangler secret put GH_PAT # set the read-only token onceTo serve it from your own domain, uncomment and adjust the routes block in
wrangler.toml.
Then set the plugin's Worker base URL to your Worker's public URL
(e.g. https://md.example.com) and publish notes as usual.
- Strict UUID matching; anything else is
404. - Image filenames are whitelisted (no path separators → no directory traversal).
- Responses are served with
noindexand a restrictive CSP. - The read-only PAT lives only in the Worker's secret store.
MIT — see LICENSE.