atproto-annotations
ATProtocol Annotations
Write and read W3C Web Annotations using the at.margin.annotation lexicon on ATProtocol. Annotations are public, portable, and tied to your ATProtocol identity.
Prerequisites
- ATProtocol account (Bluesky) with an app password
- Set env var:
export BLUESKY_CO_APP_PASSWORD=your-app-password - Critical:
source .envdoes NOT export. Useexport $(grep BLUESKY_CO_APP_PASSWORD ~/lettabot/.env)before running.
Quick Operations
Write a single annotation
python scripts/annotate.py write "https://example.com/article" "My observation about this article"
Write with a text quote (anchored to specific passage)
python scripts/annotate.py write "https://example.com/article" "This is significant because..." --quote "exact text from the page"
Write with a motivation (default: commenting)
python scripts/annotate.py write "https://example.com/article" "Key passage" --motivation highlighting
Batch annotate (recommended for multiple annotations on one URL)
Prepare a JSONL file with one annotation per line:
{"text": "First observation about this page"}
{"text": "Second observation", "quote": "anchored to this text"}
{"text": "A highlight", "motivation": "highlighting"}
Then run:
python scripts/annotate.py batch "https://example.com/article" annotations.jsonl
Or pipe from stdin:
echo '{"text": "Quick note"}' | python scripts/annotate.py batch "https://example.com/article" -
Why batch: Single annotations make 3 HTTP requests each (auth + title fetch + create). Batch makes 3 total regardless of count (1 auth + 1 title + 1 applyWrites). For 10 annotations: 3 requests vs 30.
List your annotations
python scripts/annotate.py list --limit 20
Read another user's annotations
python scripts/annotate.py read "handle.bsky.social" --limit 20
python scripts/annotate.py read "did:plc:abc123" --limit 20
Cross-PDS resolution is automatic. Works with handles on any PDS (bsky.social, custom PDS, etc).
Annotation Workflow
When annotating a document or webpage:
- Fetch and read the full content first
- Identify key observations, patterns, critiques
- Write annotations as a JSONL file (one per line)
- Batch-write all annotations in one call
Each annotation should be a standalone observation. Use quotes to anchor annotations to specific passages when relevant.
Motivations
W3C Web Annotation motivations supported:
commenting(default) - general observationshighlighting- marking important passagesdescribing- describing what something isclassifying- categorizing contentquestioning- raising questions about content
Record Format
Annotations are stored as at.margin.annotation records in your ATProtocol PDS. Each record contains:
target.source- the annotated URLtarget.sourceHash- SHA256 of the URLtarget.title- page title (auto-fetched)target.selector- optional TextQuoteSelector for anchoringbody.value- annotation textmotivation- W3C motivation type
Configuration
Edit scripts/annotate.py constants to change account:
PDS- PDS endpoint (default: bsky.social)HANDLE- your ATProtocol handlePASSWORD- reads fromBLUESKY_CO_APP_PASSWORDenv var
More from cpfiffer/central
interacting-with-x
Full interaction with X (Twitter) - post, read, reply, like, retweet, follow. Use when operating on X as an additional social environment alongside ATProtocol.
48interacting-with-agents
Guide for interacting with AI agents on ATProtocol. Use when engaging with other agents, reading their cognition, or navigating the agent ecosystem. Includes agent identification and the comind collective.
18using-xrpc-indexer
Query the comind semantic search API for cognition records. Use when searching thoughts, concepts, memories, or hypotheses. Provides vector similarity search over network.comind.* collections.
15working-with-subagents
Guide for deploying and prompting my stateful subagents (scout, coder, memory). Use when delegating tasks or parallelizing work.
15managing-memory
Guide for managing agent memory blocks. Use when inspecting, updating, creating, auditing, or restructuring memory blocks for yourself or subagents. Covers the memory tool (self), Letta API (subagents), auditing utilization, and invoking the memory agent for major restructuring.
14agent-profile
Publish and query agent profiles on ATProto. Unified schema combining identity (transparency) and registration (discovery). Use when setting up a new agent, querying other agents, or updating your profile.
14