mirror of
https://github.com/svemagie/obsidian-micropub.git
synced 2026-05-15 11:58:51 +02:00
docs: update README with IndieAuth, interaction posts, WikiLinks, photo
Add documentation for features added since the original README: - IndieAuth PKCE sign-in flow (replaces manual token as primary path) - Interaction posts (bookmark, like, reply, repost) - WikiLink resolution in body and related field - photo frontmatter property - Post type detection logic - evergreen-since auto-stamp - Updated architecture section with IndieAuth.ts Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -9,56 +9,67 @@ Forked and generalised from [svemagie/obsidian-microblog](https://github.com/sve
|
|||||||
## Features
|
## Features
|
||||||
|
|
||||||
- **Any Micropub endpoint** — not locked to Micro.blog; works with Indiekit and other servers
|
- **Any Micropub endpoint** — not locked to Micro.blog; works with Indiekit and other servers
|
||||||
|
- **IndieAuth sign-in** — browser-based PKCE login, no token copy-paste required
|
||||||
- **Auto-discovery** — reads `<link rel="micropub">` from your site to find the endpoint automatically
|
- **Auto-discovery** — reads `<link rel="micropub">` from your site to find the endpoint automatically
|
||||||
- **Digital Garden stage mapping** — Obsidian tags `#garden/plant`, `#garden/cultivate`, etc. become a `gardenStage` property on the published post, matching the Eleventy blog's garden system
|
- **Article vs. note** — auto-detected from frontmatter; override with `postType`
|
||||||
- **Create + Update** — if the note has a `mp-url` frontmatter key, Publish will update the existing post instead of creating a new one
|
- **Digital Garden stage mapping** — Obsidian tags `#garden/plant`, `#garden/cultivate`, etc. become a `gardenStage` property on the published post
|
||||||
- **Image upload** — local images (wiki-embeds and markdown) are uploaded to the media endpoint and URLs rewritten
|
- **Create + Update** — if the note has an `mp-url` frontmatter key, Publish updates the existing post instead of creating a new one
|
||||||
|
- **Image upload** — local images (`![[file.png]]` and ``) are uploaded to the media endpoint and rewritten to remote URLs in the post content
|
||||||
|
- **WikiLink resolution** — `[[Note Name]]` links in the body are resolved to their published blog URLs via `mp-url` frontmatter
|
||||||
|
- **Interaction posts** — bookmark, like, reply, repost using standard Micropub properties
|
||||||
|
- **AI disclosure** — `ai-text-level`, `ai-tools`, etc. pass through as Micropub properties
|
||||||
- **URL write-back** — the returned post URL is saved to `mp-url` in the note's frontmatter after publishing
|
- **URL write-back** — the returned post URL is saved to `mp-url` in the note's frontmatter after publishing
|
||||||
|
|
||||||
---
|
---
|
||||||
|
|
||||||
## Installation
|
## Installation
|
||||||
|
|
||||||
### From source (development)
|
|
||||||
|
|
||||||
```bash
|
|
||||||
cd /path/to/your/obsidian/vault/.obsidian/plugins
|
|
||||||
git clone https://github.com/yourname/obsidian-micropub
|
|
||||||
cd obsidian-micropub
|
|
||||||
npm install
|
|
||||||
npm run dev
|
|
||||||
```
|
|
||||||
|
|
||||||
Then enable the plugin in Obsidian → Settings → Community plugins.
|
|
||||||
|
|
||||||
### Manual
|
### Manual
|
||||||
|
|
||||||
1. Download the latest release (main.js + manifest.json)
|
1. Download the latest release (`main.js` + `manifest.json`)
|
||||||
2. Create a folder `.obsidian/plugins/obsidian-micropub/` in your vault
|
2. Create a folder `.obsidian/plugins/obsidian-micropub/` in your vault
|
||||||
3. Copy both files there
|
3. Copy both files there
|
||||||
4. Enable in Obsidian → Settings → Community plugins
|
4. Enable in Obsidian → Settings → Community plugins
|
||||||
|
|
||||||
|
### From source
|
||||||
|
|
||||||
|
```bash
|
||||||
|
cd /path/to/your/obsidian/vault/.obsidian/plugins
|
||||||
|
git clone https://github.com/svemagie/obsidian-micropub
|
||||||
|
cd obsidian-micropub
|
||||||
|
npm install
|
||||||
|
npm run build
|
||||||
|
```
|
||||||
|
|
||||||
---
|
---
|
||||||
|
|
||||||
## Configuration
|
## Configuration
|
||||||
|
|
||||||
Open **Settings → Micropub Publisher**.
|
Open **Settings → Micropub Publisher**.
|
||||||
|
|
||||||
| Setting | Description |
|
### Sign in with IndieAuth (recommended)
|
||||||
|---|---|
|
|
||||||
| **Site URL** | Your site's home page — used for endpoint auto-discovery |
|
|
||||||
| **Micropub endpoint** | e.g. `https://example.com/micropub` |
|
|
||||||
| **Media endpoint** | For image uploads; auto-discovered if blank |
|
|
||||||
| **Access token** | Bearer token from your IndieAuth token endpoint |
|
|
||||||
| **Default visibility** | `public` / `unlisted` / `private` |
|
|
||||||
| **Write URL to note** | Save the published post URL as `mp-url` in frontmatter |
|
|
||||||
| **Map #garden/* tags** | Convert `#garden/plant` → `garden-stage: plant` property |
|
|
||||||
|
|
||||||
### Getting a token from Indiekit
|
1. Enter your **Site URL** (e.g. `https://blog.example.com`).
|
||||||
|
2. Click **Sign in** — your browser opens your site's IndieAuth login page.
|
||||||
|
3. Log in. The browser redirects back to Obsidian automatically.
|
||||||
|
4. The plugin stores your access token and fills in the endpoint URLs.
|
||||||
|
|
||||||
1. Log into your Indiekit admin panel
|
The flow uses [PKCE](https://oauth.net/2/pkce/) and a GitHub Pages relay page as the redirect URI, so it works without a local HTTP server.
|
||||||
2. Go to **Tokens** → Create new token with `create update` scope
|
|
||||||
3. Paste the token into the plugin settings
|
### Manual token (advanced)
|
||||||
|
|
||||||
|
Expand **Or paste a token manually** and enter a bearer token from your Indiekit admin panel (`create update media` scope). Click **Verify** to confirm it works.
|
||||||
|
|
||||||
|
### Settings reference
|
||||||
|
|
||||||
|
| Setting | Default | Description |
|
||||||
|
|---|---|---|
|
||||||
|
| Site URL | — | Your site's homepage; used for IndieAuth endpoint discovery |
|
||||||
|
| Micropub endpoint | — | e.g. `https://example.com/micropub` |
|
||||||
|
| Media endpoint | — | For image uploads; auto-discovered from Micropub config if blank |
|
||||||
|
| Default visibility | `public` | Applied when the note has no `visibility` field |
|
||||||
|
| Write URL back to note | on | Saves the published post URL as `mp-url` in frontmatter |
|
||||||
|
| Map #garden/* tags | on | Converts `#garden/plant` → `gardenStage: plant` Micropub property |
|
||||||
|
|
||||||
---
|
---
|
||||||
|
|
||||||
@@ -102,24 +113,48 @@ mp-url: "https://example.com/articles/2026/on-building-in-public"
|
|||||||
|
|
||||||
## Frontmatter properties recognised
|
## Frontmatter properties recognised
|
||||||
|
|
||||||
### Standard properties
|
### Post identity
|
||||||
|
|
||||||
| Property | Effect |
|
| Property | Effect |
|
||||||
|---|---|
|
|---|---|
|
||||||
| `title` | Sets the post `name` (article mode) |
|
| `mp-url` / `url` | Existing post URL — triggers an **update** rather than create |
|
||||||
| `created` / `date` | Sets `published` date (`created` takes priority — matches Obsidian's default date field) |
|
| `postType` | Force post type: `article` (sets `name`), `note` (skips `name`) |
|
||||||
| `postType` | Force post type: `article` sends a title (uses filename if none set), `note` skips title |
|
| `title` / `name` | Sets the post `name`; presence auto-detects post type as article |
|
||||||
| `tags` + `category` | Both merged into Micropub `category` (excluding `garden/*` and bare `garden` tags, deduplicated) |
|
|
||||||
| `summary` / `excerpt` | Sets `summary` property |
|
If no `postType` is set: a note with a `title` or `name` field publishes as an article; a note without one publishes as a note.
|
||||||
|
|
||||||
|
### Content
|
||||||
|
|
||||||
|
| Property | Effect |
|
||||||
|
|---|---|
|
||||||
|
| `created` / `date` | Sets `published` date; `created` takes priority (matches Obsidian's default) |
|
||||||
|
| `tags` + `category` | Both merged into Micropub `category`; `garden/*` and bare `garden` tags are filtered out |
|
||||||
|
| `summary` / `excerpt` | Sets the `summary` property |
|
||||||
| `visibility` | `public` / `unlisted` / `private` |
|
| `visibility` | `public` / `unlisted` / `private` |
|
||||||
| `gardenStage` | Explicit garden stage — see table below |
|
| `photo` | Featured photo: a URL string, array of URLs, or `[{url, alt}]` objects |
|
||||||
| `mp-url` | Triggers an **update** rather than create |
|
| `related` | List of `[[WikiLinks]]` or URLs to related posts; WikiLinks are resolved to `mp-url` |
|
||||||
| `mp-syndicate-to` / `mpSyndicateTo` | Pre-fills syndication target list |
|
|
||||||
| `mp-*` | Any other `mp-*` keys passed through verbatim |
|
|
||||||
|
|
||||||
### AI disclosure properties
|
### Syndication
|
||||||
|
|
||||||
Use flat kebab-case properties (camelCase fallback supported for backward compatibility):
|
| Property | Effect |
|
||||||
|
|---|---|
|
||||||
|
| `mp-syndicate-to` / `mpSyndicateTo` | Per-note syndication targets, merged with the default targets in settings |
|
||||||
|
| `mp-*` | Any other `mp-*` key (except `mp-url`) is passed through verbatim |
|
||||||
|
|
||||||
|
### Interaction posts
|
||||||
|
|
||||||
|
Set one of these to publish a bookmark, like, reply, or repost. Adding body text to an interaction note includes it as a comment or quote; bare likes and reposts omit `content` entirely.
|
||||||
|
|
||||||
|
| Property | Effect |
|
||||||
|
|---|---|
|
||||||
|
| `bookmarkOf` / `bookmark-of` | URL being bookmarked |
|
||||||
|
| `likeOf` / `like-of` | URL being liked |
|
||||||
|
| `inReplyTo` / `in-reply-to` | URL being replied to |
|
||||||
|
| `repostOf` / `repost-of` | URL being reposted |
|
||||||
|
|
||||||
|
### AI disclosure
|
||||||
|
|
||||||
|
Flat kebab-case keys are recommended; camelCase and a nested `ai:` object are also supported.
|
||||||
|
|
||||||
| Property | Values | Meaning |
|
| Property | Values | Meaning |
|
||||||
|---|---|---|
|
|---|---|---|
|
||||||
@@ -128,27 +163,6 @@ Use flat kebab-case properties (camelCase fallback supported for backward compat
|
|||||||
| `ai-tools` | string | Tools used, e.g. `"Claude"` |
|
| `ai-tools` | string | Tools used, e.g. `"Claude"` |
|
||||||
| `ai-description` | string | Free-text disclosure note |
|
| `ai-description` | string | Free-text disclosure note |
|
||||||
|
|
||||||
Nested `ai:` objects (e.g. `ai: {textLevel: "1"}`) also work but flat keys are recommended.
|
|
||||||
|
|
||||||
**Example article template:**
|
|
||||||
|
|
||||||
```yaml
|
|
||||||
---
|
|
||||||
title: "My Post"
|
|
||||||
created: 2026-03-15T10:00:00
|
|
||||||
postType: article
|
|
||||||
tags:
|
|
||||||
- garden/evergreen
|
|
||||||
category:
|
|
||||||
- indieweb
|
|
||||||
- lang/en
|
|
||||||
ai-text-level: "1"
|
|
||||||
ai-code-level: "0"
|
|
||||||
ai-tools: "Claude"
|
|
||||||
ai-description: "AI helped refine the structure"
|
|
||||||
---
|
|
||||||
```
|
|
||||||
|
|
||||||
### Digital Garden stages
|
### Digital Garden stages
|
||||||
|
|
||||||
Set via `gardenStage` frontmatter or a `#garden/<stage>` tag:
|
Set via `gardenStage` frontmatter or a `#garden/<stage>` tag:
|
||||||
@@ -163,6 +177,25 @@ Set via `gardenStage` frontmatter or a `#garden/<stage>` tag:
|
|||||||
| `revitalize` | ✨ Revitalizing | Being refreshed |
|
| `revitalize` | ✨ Revitalizing | Being refreshed |
|
||||||
| `revisit` | 🔄 Revisit | Flagged to come back to |
|
| `revisit` | 🔄 Revisit | Flagged to come back to |
|
||||||
|
|
||||||
|
When a note is first published with `gardenStage: evergreen`, an `evergreen-since` date is stamped automatically.
|
||||||
|
|
||||||
|
**Example article template:**
|
||||||
|
|
||||||
|
```yaml
|
||||||
|
---
|
||||||
|
title: "My Post"
|
||||||
|
created: 2026-03-15T10:00:00
|
||||||
|
postType: article
|
||||||
|
tags:
|
||||||
|
- garden/evergreen
|
||||||
|
category:
|
||||||
|
- indieweb
|
||||||
|
- lang/en
|
||||||
|
ai-text-level: "1"
|
||||||
|
ai-tools: "Claude"
|
||||||
|
---
|
||||||
|
```
|
||||||
|
|
||||||
---
|
---
|
||||||
|
|
||||||
## Development
|
## Development
|
||||||
@@ -176,11 +209,12 @@ npm run build # production bundle (minified)
|
|||||||
|
|
||||||
```
|
```
|
||||||
src/
|
src/
|
||||||
main.ts Plugin entry point, command/ribbon registration
|
main.ts Plugin entry point, commands, ribbon, protocol handler
|
||||||
types.ts Shared interfaces and constants
|
types.ts Shared interfaces and constants
|
||||||
MicropubClient.ts Low-level HTTP (create, update, upload, discover)
|
MicropubClient.ts Low-level HTTP (create, update, upload, discover)
|
||||||
Publisher.ts Orchestrates publish flow (parse → upload → send → write-back)
|
Publisher.ts Orchestrates publish flow (parse → upload → send → write-back)
|
||||||
SettingsTab.ts Obsidian settings UI
|
IndieAuth.ts PKCE IndieAuth sign-in via GitHub Pages relay
|
||||||
|
SettingsTab.ts Obsidian settings UI
|
||||||
```
|
```
|
||||||
|
|
||||||
---
|
---
|
||||||
|
|||||||
Reference in New Issue
Block a user