mirror of
https://github.com/svemagie/blog-eleventy-indiekit.git
synced 2026-04-02 16:44:56 +02:00
docs: document reply-to-interactions feature
Add Reply-to-Interactions section to README with architecture diagram, threading mechanism, reply routing table, and plugin dependencies. Update CLAUDE.md with interaction API sources and reply architecture. Add conversations and comments plugins to the plugin integration table. Confab-Link: http://localhost:8080/sessions/184584f4-67e1-485a-aba8-02ac34a600fe
This commit is contained in:
21
CLAUDE.md
21
CLAUDE.md
@@ -158,7 +158,7 @@ Most plugin-dependent data files:
|
|||||||
| `blog-sidebar.njk` | Sidebar for blog/post pages (recent posts, categories) |
|
| `blog-sidebar.njk` | Sidebar for blog/post pages (recent posts, categories) |
|
||||||
| `h-card.njk` | Microformat2 h-card for author identity |
|
| `h-card.njk` | Microformat2 h-card for author identity |
|
||||||
| `reply-context.njk` | Displays reply-to/like-of/repost-of/bookmark-of context with h-cite |
|
| `reply-context.njk` | Displays reply-to/like-of/repost-of/bookmark-of context with h-cite |
|
||||||
| `webmentions.njk` | Renders likes, reposts, replies from webmention.io + send form |
|
| `webmentions.njk` | Renders likes, reposts, replies from webmention.io + conversations API, with threaded owner replies |
|
||||||
| `empty-collection.njk` | Fallback message when a post type collection is empty |
|
| `empty-collection.njk` | Fallback message when a post type collection is empty |
|
||||||
|
|
||||||
#### Sections (_includes/components/sections/)
|
#### Sections (_includes/components/sections/)
|
||||||
@@ -315,14 +315,27 @@ Generates OpenGraph images for posts without photos using Satori (Yoga WASM →
|
|||||||
- **h-feed** (feed markup): Machine-readable post lists
|
- **h-feed** (feed markup): Machine-readable post lists
|
||||||
- **h-cite** (reply context): Cites external content in replies/likes/reposts
|
- **h-cite** (reply context): Cites external content in replies/likes/reposts
|
||||||
|
|
||||||
#### Webmentions
|
#### Webmentions & Interactions
|
||||||
|
|
||||||
- Build-time caching via `@chrisburnell/eleventy-cache-webmentions`
|
- Build-time caching via `@chrisburnell/eleventy-cache-webmentions`
|
||||||
- Client-side real-time fetching via `/js/webmentions.js`
|
- Client-side real-time fetching via `/js/webmentions.js` from three APIs:
|
||||||
- Displays likes, reposts, replies with avatars
|
- `/webmentions/api/mentions` — IndieWeb webmentions (webmention.io)
|
||||||
|
- `/conversations/api/mentions` — Mastodon/Bluesky/AP interactions (conversations plugin)
|
||||||
|
- `/comments/api/comments` — Native authenticated comments (comments plugin)
|
||||||
|
- Displays likes, reposts, replies with avatars and platform badges
|
||||||
|
- **Owner reply threading** — owner replies appear nested under parent interactions with amber Author badge
|
||||||
- Send webmention form on every post
|
- Send webmention form on every post
|
||||||
- Legacy URL support via `urlAliases` (for micro.blog and old blog URLs)
|
- Legacy URL support via `urlAliases` (for micro.blog and old blog URLs)
|
||||||
|
|
||||||
|
#### Reply-to-Interactions Architecture
|
||||||
|
|
||||||
|
The conversations API enriches its response with owner replies (`is_owner: true`, `parent_url`). The frontend's `threadOwnerReplies()` function matches `parent_url` to reply `<li>` elements via `data-wm-url` attributes and inserts threaded reply cards into `wm-owner-reply-slot` divs.
|
||||||
|
|
||||||
|
Reply routing is provenance-aware:
|
||||||
|
- **Mastodon/Bluesky replies** — `POST /micropub` with `mp-syndicate-to` for platform threading
|
||||||
|
- **IndieWeb webmention replies** — `POST /micropub` without syndication (webmention sent automatically)
|
||||||
|
- **Native comment replies** — `POST /comments/api/reply` (stored in comments collection)
|
||||||
|
|
||||||
#### IndieAuth
|
#### IndieAuth
|
||||||
|
|
||||||
- `rel="me"` links in `<head>` for identity verification
|
- `rel="me"` links in `<head>` for identity verification
|
||||||
|
|||||||
68
README.md
68
README.md
@@ -52,6 +52,8 @@ Integrates with custom Indiekit endpoint plugins:
|
|||||||
| `@rmdes/indiekit-endpoint-podroll` | Podcast episode aggregator |
|
| `@rmdes/indiekit-endpoint-podroll` | Podcast episode aggregator |
|
||||||
| `@rmdes/indiekit-endpoint-rss` | RSS feed reader with MongoDB caching |
|
| `@rmdes/indiekit-endpoint-rss` | RSS feed reader with MongoDB caching |
|
||||||
| `@rmdes/indiekit-endpoint-microsub` | Social reader with channels and timeline |
|
| `@rmdes/indiekit-endpoint-microsub` | Social reader with channels and timeline |
|
||||||
|
| `@rmdes/indiekit-endpoint-conversations` | Multi-platform interaction aggregation + owner reply threading |
|
||||||
|
| `@rmdes/indiekit-endpoint-comments` | IndieAuth visitor comments with owner replies |
|
||||||
|
|
||||||
### Modern Tech Stack
|
### Modern Tech Stack
|
||||||
|
|
||||||
@@ -428,6 +430,72 @@ See `indiekit-deploy` repository for Docker Compose deployment with this theme a
|
|||||||
- [IndieAuth](https://indieauth.com/) — Authentication protocol
|
- [IndieAuth](https://indieauth.com/) — Authentication protocol
|
||||||
- [Bridgy](https://brid.gy/) — Backfeed social interactions
|
- [Bridgy](https://brid.gy/) — Backfeed social interactions
|
||||||
|
|
||||||
|
## Reply-to-Interactions
|
||||||
|
|
||||||
|
The theme supports threaded owner replies on all interaction types: IndieWeb webmentions, Mastodon/Bluesky backfills, and native authenticated comments.
|
||||||
|
|
||||||
|
### How It Works
|
||||||
|
|
||||||
|
```
|
||||||
|
Visitor interaction (Mastodon reply, Bluesky like, webmention, native comment)
|
||||||
|
│
|
||||||
|
v
|
||||||
|
Conversations API (/conversations/api/mentions)
|
||||||
|
│ Enriches response with owner replies from posts collection
|
||||||
|
│ Adds is_owner: true + parent_url for threading
|
||||||
|
v
|
||||||
|
webmentions.js (client-side)
|
||||||
|
│ processWebmentions() separates owner replies from regular interactions
|
||||||
|
│ Renders regular interactions (likes, reposts, replies)
|
||||||
|
│ threadOwnerReplies() inserts owner reply cards under parent interactions
|
||||||
|
v
|
||||||
|
Threaded display:
|
||||||
|
┌─────────────────────────────────┐
|
||||||
|
│ Jane Doe [Mastodon] Mar 11 │
|
||||||
|
│ Great post! │
|
||||||
|
│ [Reply] │
|
||||||
|
│ ┌─────────────────────────────┐ │
|
||||||
|
│ │ Ricardo Mendes [Author] │ │
|
||||||
|
│ │ Thanks! │ │
|
||||||
|
│ └─────────────────────────────┘ │
|
||||||
|
└─────────────────────────────────┘
|
||||||
|
```
|
||||||
|
|
||||||
|
### Key Files
|
||||||
|
|
||||||
|
| File | Role |
|
||||||
|
|------|------|
|
||||||
|
| `js/webmentions.js` | Fetches interactions from 3 APIs (webmentions, conversations, comments), deduplicates, renders, and threads owner replies |
|
||||||
|
| `js/comments.js` | Alpine.js component for native comment form, IndieAuth flow, and inline reply UI |
|
||||||
|
| `_includes/components/webmentions.njk` | Server-side template with `data-wm-url` attributes and `wm-owner-reply-slot` divs for threading |
|
||||||
|
|
||||||
|
### Threading Mechanism
|
||||||
|
|
||||||
|
1. **`processWebmentions(allChildren)`** separates items with `is_owner: true` and `parent_url` from regular interactions
|
||||||
|
2. Regular interactions render normally (likes, reposts, reply cards)
|
||||||
|
3. Each reply `<li>` gets a `data-wm-url` attribute matching the interaction's source URL
|
||||||
|
4. Each reply `<li>` includes an empty `<div class="wm-owner-reply-slot">` for threading
|
||||||
|
5. **`threadOwnerReplies(ownerReplies)`** matches each owner reply's `parent_url` to a reply `<li>`'s `data-wm-url`, then inserts an amber-bordered reply card into the slot
|
||||||
|
|
||||||
|
### Reply Routing
|
||||||
|
|
||||||
|
When the site owner clicks "Reply" on an interaction, the routing depends on the interaction's source:
|
||||||
|
|
||||||
|
| Source | Route | Syndication |
|
||||||
|
|--------|-------|-------------|
|
||||||
|
| Mastodon reply | `POST /micropub` with `in-reply-to` | `mp-syndicate-to: mastodon` |
|
||||||
|
| Bluesky reply | `POST /micropub` with `in-reply-to` | `mp-syndicate-to: bluesky` |
|
||||||
|
| IndieWeb webmention | `POST /micropub` with `in-reply-to` | No syndication (webmention sent) |
|
||||||
|
| Native comment | `POST /comments/api/reply` | Stored in comments collection |
|
||||||
|
|
||||||
|
### Plugin Dependencies
|
||||||
|
|
||||||
|
| Plugin | Role |
|
||||||
|
|--------|------|
|
||||||
|
| [`@rmdes/indiekit-endpoint-conversations`](https://github.com/rmdes/indiekit-endpoint-conversations) | Serves interactions with owner reply enrichment (`is_owner`, `parent_url`) |
|
||||||
|
| [`@rmdes/indiekit-endpoint-comments`](https://github.com/rmdes/indiekit-endpoint-comments) | Handles native comment replies and owner detection (`/api/is-owner`) |
|
||||||
|
| `@rmdes/indiekit-endpoint-webmention-io` | Serves webmention.io data (likes, reposts, replies from IndieWeb) |
|
||||||
|
|
||||||
## Troubleshooting
|
## Troubleshooting
|
||||||
|
|
||||||
### Webmentions not appearing
|
### Webmentions not appearing
|
||||||
|
|||||||
Reference in New Issue
Block a user