No description
Find a file
2026-07-18 03:44:34 -05:00
.github/workflows Initial commit: fetch, parse, and archive Substack posts as Markdown with media downloads and threaded comments 2026-06-15 10:30:34 -05:00
src fix: upgrade eslint-plugin-obsidianmd to 0.4.1 and resolve prefer-create-el warnings 2026-07-18 03:44:27 -05:00
.gitignore Initial commit: fetch, parse, and archive Substack posts as Markdown with media downloads and threaded comments 2026-06-15 10:30:34 -05:00
CONTRIBUTING.md Initial commit: fetch, parse, and archive Substack posts as Markdown with media downloads and threaded comments 2026-06-15 10:30:34 -05:00
esbuild.config.mjs Initial commit: fetch, parse, and archive Substack posts as Markdown with media downloads and threaded comments 2026-06-15 10:30:34 -05:00
eslint.config.mjs fix: upgrade eslint-plugin-obsidianmd to 0.4.1 and resolve prefer-create-el warnings 2026-07-18 03:44:27 -05:00
LICENSE Initial commit: fetch, parse, and archive Substack posts as Markdown with media downloads and threaded comments 2026-06-15 10:30:34 -05:00
manifest.json chore: release 0.1.10 2026-07-18 03:44:34 -05:00
package-lock.json fix: upgrade eslint-plugin-obsidianmd to 0.4.1 and resolve prefer-create-el warnings 2026-07-18 03:44:27 -05:00
package.json chore: release 0.1.10 2026-07-18 03:44:34 -05:00
README.md feat: add obsidian:// URI handler for saving posts via protocol link 2026-07-17 20:45:56 -05:00
release.mjs Initial commit: fetch, parse, and archive Substack posts as Markdown with media downloads and threaded comments 2026-06-15 10:30:34 -05:00
styles.css feat: improve history view with search icon/clear button, Notice toasts, and disabled state during re-download 2026-07-11 16:38:33 -05:00
tsconfig.json fix: add ES2017.String and ES2020.Promise to tsconfig lib to resolve unsafe-any lint warnings 2026-07-13 13:40:02 -05:00
version-bump.mjs Initial commit: fetch, parse, and archive Substack posts as Markdown with media downloads and threaded comments 2026-06-15 10:30:34 -05:00
versions.json chore: release 0.1.10 2026-07-18 03:44:34 -05:00

Substack Clipper

Archive Substack posts as Obsidian-flavored Markdown with images, media, and threaded comments.

Features

  • Saves any public Substack post as a Markdown note with YAML frontmatter
  • Downloads images, videos, audio, podcast episodes, transcripts, and PDF attachments
  • Fetches and renders threaded comments as a separate embeddable note
  • Media files use ![[wikilink]] embeds for native Obsidian playback
  • Converts Substack footnotes to standard [^N] Markdown footnotes
  • Strips CDN URL prefixes for clean image references
  • Handles paywalled posts gracefully (saves the available preview)
  • Works on desktop and mobile

Installation

Install from community.obsidian.md

From Obsidian's settings or preferences:

  1. Community Plugins > Browse
  2. Search for "Substack Clipper"

Manually:

  1. download the latest release archive
  2. uncompress the downloaded archive
  3. move the substack-clipper folder to /path/to/vault/.obsidian/plugins/
  4. Settings > Community plugins > reload Installed plugins
  5. enable plugin

or:

  1. download main.js, manifest.json & styles.css from the latest release
  2. create a new folder /path/to/vault/.obsidian/plugins/substack-clipper
  3. move all 3 files to /path/to/vault/.obsidian/plugins/substack-clipper
  4. Settings > Community plugins > reload Installed plugins
  5. enable plugin

Usage

  1. Open the command palette (Ctrl/Cmd + P).
  2. Run Clip substack post.
  3. Paste a Substack post URL (must contain /p/ in the path).
  4. The plugin fetches the post, downloads media, and creates the note.

Output structure

Substacks/
  alice/
    my-article.md
    my-article-comments.md
    my-article/
      image.jpg
      video.mp4
      podcast.mp3
      attachment.pdf

The main note includes frontmatter with title, subtitle, type, audience, date, comment count, and links to all media. Comments are embedded via ![[slug-comments]].

URI protocol

You can save a post directly via an obsidian:// URI without opening the command palette:

obsidian://substack-clipper?vault=MyVault&url=https://alice.substack.com/p/my-article
Parameter Required Description
vault no Target vault name (Obsidian prompts if omitted and multiple vaults exist)
url yes Full Substack post URL (must contain /p/)
open no true or false — override the "open after saving" setting

Spaces in vault names should be percent-encoded (%20). This works from browsers, scripts, iOS Shortcuts, bookmarklets, and anywhere else that can open a URL.

Settings

Setting Default Description
Save directory Substacks Vault-relative folder for saved posts
Download media Off Download videos, audio, podcasts, and transcripts (images and attachments always download)
maxFileSize 0 Skip media files larger than this (MB). 0 = no limit. Only visible when downloadMedia is enabled.
Download comments Off Fetch and save threaded comments
Comment sort order Most recent first Sort order for comments (most recent, oldest, or best)
Save raw JSON Off Save the raw Substack API JSON
Save raw HTML Off Save the raw article HTML

Building from source

git clone https://github.com/gapmiss/substack-clipper.git
cd substack-clipper
npm install
npm run build

License

MIT