Docs: MVP-accurate README, PRIVACY, SECURITY

README gains Features/Usage and the correct minAppVersion badge (1.13.0).
PRIVACY/SECURITY replace the template's no-network-code default with the real
on-device flow: requests only to user-configured feed hosts, redirect targets,
the Substack public profile API, and referenced image/media URLs; no telemetry,
no maintainer server.
This commit is contained in:
Charles Kelsoe 2026-06-14 14:40:39 -04:00
parent 19e47bd9ad
commit 9bd52e729f
3 changed files with 54 additions and 16 deletions

View file

@ -6,30 +6,43 @@ This policy explains what the **RSS Importer** Obsidian plugin ("the plugin") do
## Summary
The plugin collects nothing, stores nothing outside your own vault, and sends nothing anywhere. It contains no network code.
The plugin runs entirely on your device. It makes network requests only to the feed hosts you configure and to the image or media URLs those feeds reference, and only when you ask it to. It has no telemetry, no analytics, and no maintainer server. It never sends your data to the maintainer or to any third party beyond the feed and asset hosts you chose.
## What the plugin does
_Describe the plugin's data flow in plain terms here. Be specific about what files the plugin reads, what files it modifies, when it modifies them, and whether the modifications are triggered by an explicit user action._
RSS Importer reads feeds you add and writes their items into your vault as Markdown notes.
## Data collection
- When you add a feed, the plugin fetches the URL you entered (and, for a Substack handle, the public Substack profile API) to resolve and preview the feed.
- When you import, the plugin fetches the feed and the selected items, converts each to Markdown, and writes a note into the destination folder you chose. If you turn on image download, it also fetches the images referenced by those items and saves them into your vault.
- To avoid re-importing, the plugin scans the frontmatter of notes under your destination folder (through Obsidian's metadata cache) and reads an existing note at a target path before overwriting it. It does not read other files in your vault.
- **No personal data is collected.** The plugin does not collect names, email addresses, file contents, usage statistics, or any other information.
- **No telemetry or analytics.** There is no tracking, crash reporting, or phone-home behavior of any kind.
- **No automatic background activity.** The plugin acts only when you explicitly invoke a command or trigger a documented event.
## Data storage
- The plugin's settings are stored by Obsidian in your vault's local `data.json` file, on your own device. They never leave your device.
- Any other data the plugin reads or writes stays inside your vault, on your own device.
Every fetch is triggered by an explicit action of yours (adding a feed, or running an import). The plugin does no background polling.
## Network use
The plugin contains **no network code**. It makes no HTTP requests, opens no sockets, and contacts no servers. Not the maintainer's, not Obsidian's, not any third party.
The plugin makes outbound HTTP requests through Obsidian's `requestUrl` API. It contacts only:
- the feed hosts you configure (the publications and podcasts you add), and the redirect targets those hosts return;
- `substack.com` public profile API, only when you add a Substack `@handle`, to resolve it to its publication;
- the image and media URLs contained in the items you import (for example `substackcdn.com` for Substack images), and only when you have enabled image or media download.
It contacts no other servers. There is no maintainer endpoint, no analytics host, and no third-party SDK.
## Data collection
- **No personal data is collected.** The plugin does not collect names, email addresses, file contents, or usage statistics.
- **No telemetry or analytics.** There is no tracking, crash reporting, or phone-home behavior of any kind.
- **No automatic background activity.** The plugin acts only when you explicitly add a feed or run an import.
## Data storage
- The plugin's settings (your feed list, destination folders, and per-feed options) and the dismissed-item list are stored by Obsidian in your vault's local `data.json` file, on your own device.
- Imported notes and any downloaded images are written into your vault, on your own device.
- Nothing is stored outside your vault.
## Third parties
The plugin shares no data with any third party. It has no data to share and no means to transmit it.
The plugin shares no data with any third party. The only outbound traffic is the feed and asset requests described above, which go to the hosts you chose by adding those feeds.
## Disclaimer of liability
@ -37,7 +50,7 @@ The plugin is provided free of charge, "AS IS", without warranty of any kind, as
## Information you choose to share
If you open a GitHub issue, discussion, or pull request, anything you paste there (file contents, screenshots, vault structure, system details) becomes **public**. The maintainer does not request this information and is not responsible for content you choose to post. Review and redact anything sensitive before submitting. To report a security vulnerability privately instead, see [SECURITY.md](./SECURITY.md).
If you open a GitHub issue, discussion, or pull request, anything you paste there (note contents, screenshots, vault structure, system details) becomes **public**. The maintainer does not request this information and is not responsible for content you choose to post. Review and redact anything sensitive before submitting. To report a security vulnerability privately instead, see [SECURITY.md](./SECURITY.md).
## Changes to this policy

View file

@ -1,9 +1,27 @@
# RSS Importer
[![CI](https://img.shields.io/github/actions/workflow/status/ckelsoe/obsidian-rss-importer/ci.yml?branch=main&label=CI&logo=github)](https://github.com/ckelsoe/obsidian-rss-importer/actions/workflows/ci.yml) [![Release](https://img.shields.io/github/actions/workflow/status/ckelsoe/obsidian-rss-importer/release.yml?label=Release&logo=github)](https://github.com/ckelsoe/obsidian-rss-importer/actions/workflows/release.yml) [![GitHub Downloads](https://img.shields.io/github/downloads/ckelsoe/obsidian-rss-importer/total?logo=github&label=Downloads)](https://github.com/ckelsoe/obsidian-rss-importer/releases) [![GitHub Stars](https://img.shields.io/github/stars/ckelsoe/obsidian-rss-importer?style=flat&logo=github&label=Stars)](https://github.com/ckelsoe/obsidian-rss-importer) [![Obsidian](https://img.shields.io/badge/Obsidian-v1.5.0%2B-7C3AED?logo=obsidian&logoColor=white)](https://obsidian.md) [![License](https://img.shields.io/github/license/ckelsoe/obsidian-rss-importer)](https://github.com/ckelsoe/obsidian-rss-importer/blob/main/LICENSE) [![Latest Release](https://img.shields.io/github/v/release/ckelsoe/obsidian-rss-importer?label=Latest)](https://github.com/ckelsoe/obsidian-rss-importer/releases/latest)
[![CI](https://img.shields.io/github/actions/workflow/status/ckelsoe/obsidian-rss-importer/ci.yml?branch=main&label=CI&logo=github)](https://github.com/ckelsoe/obsidian-rss-importer/actions/workflows/ci.yml) [![Release](https://img.shields.io/github/actions/workflow/status/ckelsoe/obsidian-rss-importer/release.yml?label=Release&logo=github)](https://github.com/ckelsoe/obsidian-rss-importer/actions/workflows/release.yml) [![GitHub Downloads](https://img.shields.io/github/downloads/ckelsoe/obsidian-rss-importer/total?logo=github&label=Downloads)](https://github.com/ckelsoe/obsidian-rss-importer/releases) [![GitHub Stars](https://img.shields.io/github/stars/ckelsoe/obsidian-rss-importer?style=flat&logo=github&label=Stars)](https://github.com/ckelsoe/obsidian-rss-importer) [![Obsidian](https://img.shields.io/badge/Obsidian-v1.13.0%2B-7C3AED?logo=obsidian&logoColor=white)](https://obsidian.md) [![License](https://img.shields.io/github/license/ckelsoe/obsidian-rss-importer)](https://github.com/ckelsoe/obsidian-rss-importer/blob/main/LICENSE) [![Latest Release](https://img.shields.io/github/v/release/ckelsoe/obsidian-rss-importer?label=Latest)](https://github.com/ckelsoe/obsidian-rss-importer/releases/latest)
Import articles and podcasts from RSS, Atom, and Substack feeds into your vault as Markdown notes, organized by source feed and deduplicated by note identity.
It is an importer, not a reader. It writes notes you own and then gets out of the way.
## Features
- **Multiple sources.** Add any RSS, Atom, or podcast feed. Substack publications are first-class: paste a `@handle`, a subdomain, a custom domain, or a post URL and the plugin resolves it to the right feed.
- **One folder per feed.** Each feed imports into its own destination folder. Reorganize the notes into subfolders however you like; the plugin still finds them.
- **Never re-imports.** Each note carries a stable identity in its frontmatter. Moving or renaming a note does not cause a duplicate on the next import.
- **Three-state item list.** Every item shows as imported, dismissed, or available. Dismiss items you are not interested in; dismissing is reversible.
- **Clean Markdown.** Article HTML is converted to tidy Markdown (headings, lists, tables, code blocks, captions), with subscribe and share widgets stripped.
- **Images your way.** Link to the original image URLs, or download images into your vault.
- **Podcasts.** Podcast items import as notes from the show notes with a link to the episode audio.
## Usage
1. Open **Settings → RSS Importer** and add a feed under **Feeds**. Paste a feed URL or a Substack handle, click **Resolve** to preview it, pick a destination folder, and save.
2. Run the **Import** command (or the ribbon icon) to open the import window.
3. Select the items you want and import them. A summary reports what was created, skipped, or failed.
## Installation
### From Obsidian Community Plugins (recommended)

View file

@ -32,4 +32,11 @@ Reports submitted through GitHub private vulnerability reporting are visible onl
## Security Considerations
_Describe what the plugin does and does not do that's relevant to security: file reads, file writes, network access (none expected), external commands, etc._
What RSS Importer does and does not do, relevant to security:
- **Network access.** The plugin makes outbound HTTP requests through Obsidian's `requestUrl` API. It contacts only the feed hosts you configure, the redirect targets those hosts return, the `substack.com` public profile API (when you add a Substack handle), and the image or media URLs referenced by the items you import (when you enable downloads). It contacts no maintainer server and includes no analytics or telemetry.
- **File reads.** It reads note frontmatter under your destination folder through Obsidian's metadata cache (for deduplication) and reads an existing note at a target path before overwriting it (collision check). It does not read other files in your vault.
- **File writes.** It writes imported notes and, optionally, downloaded images into your vault using the Obsidian vault API (`vault.create`, `vault.process`, `vault.createBinary`). Overwrites use `vault.process` rather than `vault.modify`. It writes nothing outside your vault.
- **No code execution.** The plugin runs no external commands, spawns no processes, and does not use `eval`. Remote HTML is converted to Markdown text; it is never executed. DOM is built with the Obsidian element API, never `innerHTML`.
- **Desktop only.** The plugin is marked desktop-only.
- **No credentials in this version.** Importing free and public feeds requires no login or token. (A later release adds optional Substack paid-post access using your own session cookie, stored in Obsidian's `SecretStorage` and sent only to your configured Substack hosts; this section will be expanded when that ships.)