FeedCraft: a self-hosted RSS middleware for full text, translation and AI summaries
craft your feed at ease! 轻量级rss中间件, 提取全文, 翻译、摘要一站式服务
At a glance
- What is it?
- FeedCraft is a Go-based RSS processing service that sits between your feed reader and the original feed, rewriting items through composable crafts. It is aimed at self-hosters who already run Docker and have an OpenAI-compatible LLM endpoint.
- Who is it for?
- Adopt FeedCraft if you already run Docker, Redis and a browser rendering service, and you have an OpenAI-compatible LLM key you are willing to spend on feed processing. Skip it if you want a zero-dependency reader plugin or you cannot host Redis and browserless alongside it.
- Can I use it commercially?
- Yes, with conditions. GPL-3.0 is a copyleft licence: if you distribute software that includes it, you must release that software's source code under the same licence. Running it internally without distributing it does not trigger that obligation.
- Is it still maintained?
- Yes. The repository last received commits 5 days ago.
- What is it written in?
- Mainly Go, according to GitHub's language statistics.
Answers come from the project's GitHub data, last synced on September 15, 2026, and from our analysis. They are not legal advice.
DEEP OPEN-SOURCE ANALYSIS
What FeedCraft actually does to a feed
FeedCraft is a middleware, not a reader. It takes an RSS or Atom URL, runs the items through one or more processing steps, and returns a new feed that your existing reader can subscribe to. The README describes the intended workflow as "craft your feed at ease", and the core vocabulary is three terms: AtomCraft for a single processing step, FlowCraft for a sequence of steps, and Recipe for a saved pairing of a craft with a specific source feed. That vocabulary matters because it explains the two operating modes. Portable mode needs no configuration at all: you take the original feed URL and prepend a craft path. Dock mode is the admin console where you define recipes and deeper parameters, and it is the mode that produces a stable new feed address you can hand to a reader. The audience is narrow but real. If you read feeds in a client that cannot extract article bodies or translate them, and you are willing to run a container, FeedCraft fills that gap server-side rather than per-device. If you use a reader that already bundles readability extraction and translation, the overlap is large.
The craft pipeline: from input_url to a rewritten feed
The data flow visible in the README and go.mod is a request-scoped pipeline. A request arrives at /craft/{craft_name} with an input_url query parameter. The service fetches that feed, parses it with gofeed, and hands the items to the named craft. Full-text extraction uses go-readability and goquery, with html-to-markdown available for conversion. When the plain extraction fails on JavaScript-rendered pages, the fulltext-plus craft drives chromedp against a browser endpoint instead. AI crafts run through langchaingo, which is why the configuration exposes an API type of openai or ollama and a base URL that must end in /v1. Redis sits in front of the LLM calls: the .env.example notes that FC_LLM_MAX_CONCURRENCY defaults to 3 and is shared by all feeds and features, so a large feed will queue rather than fan out. Persistence is SQLite through glebarez/sqlite and gorm, mounted at /usr/local/feed-craft/db in the compose example. The set of built-in AtomCrafts is unusually wide for a project this size: proxy, limit, fulltext, fulltext-plus, introduction, summary, translate-title, translate-content, translate-content-immersive, beautify-content and ignore-advertorial. The last two are the interesting ones, because they are not mechanical transformations. They ask a model to judge which parts of an article are advertising or filler and to drop them, which means the output depends on the model you point it at.
Installing FeedCraft with Docker Compose
The README gives a minimal compose file and a fuller one that also deploys Redis and browserless. The minimal version expects you to supply Redis and a browser service yourself through FC_REDIS_URI and FC_BROWSER_ENDPOINT, so for a first run the longer file is the safer starting point. Save it as docker-compose.yml and bring it up.
services:
app.feed-craft:
image: ghcr.io/colin-xkl/feed-craft
container_name: feed-craft
restart: always
ports:
- "10088:80"
volumes:
- ./feed-craft-db:/usr/local/feed-craft/db
environment:
FC_BROWSER_PROVIDER: browserless-restful
FC_BROWSER_ENDPOINT: http://service.browserless:3000
FC_REDIS_URI: redis://service.redis:6379/
FC_LLM_API_BASE: https://xxxxxx
FC_LLM_API_KEY: skxxxxxx
FC_LLM_API_MODEL: gemini-pro/chatgpt-3.5/...
FC_LLM_API_TYPE: openai
FC_DEFAULT_TARGET_LANG: zh-CN
service.redis:
image: redis:6-alpine
container_name: feedcraft_redis
restart: always
service.browserless:
image: browserless/chrome
container_name: feedcraft_browserless
environment:
USE_CHROME_STABLE: true
restart: unless-stoppedRun docker compose up -d and then open http://localhost:10088. The console accepts the account admin with the password adminadmin, and the README says to change that password soon after logging in. The first real use is the portable path, which needs no console work at all. The README gives this example: take the Visual Capitalist feed and prefix it with the translate-title craft, producing the address https://feed-craft.colinx.one/craft/translate-title?input_url=https://feeds.feedburner.com/visualcapitalist. Point your reader at that URL and the item titles come back rewritten by the model. The README notes that some RSS clients do not escape characters automatically and that the admin console includes a tool to escape the URL for you, which is worth knowing before you paste a feed URL containing query parameters of its own.
The AI crafts cost money and depend on your model
Every craft whose name starts with translate, summary, introduction, beautify or ignore-advertorial makes outbound calls to your LLM endpoint. There is no local model bundled and no fallback. The .env.example exposes FC_LLM_MAX_CONCURRENCY with a default of 3, described as a global cap shared by all feeds and features, so the throughput ceiling is set by that number rather than by your provider's limits. A feed with fifty items going through translate-content will produce fifty model calls, serialized in groups of three. That is a design choice with a cost attached, and the README does not document a per-feed budget, a token accounting view, or a dry-run mode. There is also a correctness caveat that follows from the design: beautify-content and ignore-advertorial delegate editorial judgement to the model, so a weaker or cheaper model will silently produce worse filtering, and the feed will look fine. The project does not publish an evaluation of how often those crafts misclassify. If you route an important feed through ignore-advertorial, you are trusting the model with content selection, and nothing in the repository as described provides a way to audit which items were dropped.
Where FeedCraft is the wrong tool
FeedCraft needs Redis and, for fulltext-plus and the enhanced HTML-to-RSS mode, a browser rendering service. The README's minimal compose file lists FC_REDIS_URI and FC_BROWSER_ENDPOINT as environment variables you must point at your own instances, and the fuller file deploys redis:6-alpine and browserless/chrome as separate containers. That is three services for what a reader plugin might do in-process. If you are running on a small VPS with tight memory, browserless/chrome alone is a meaningful footprint. The second boundary is the LLM dependency. There is no offline mode for the AI crafts; without a working endpoint at a base URL ending in /v1, those crafts cannot run, and the README does not describe a degraded path that returns the original text. Third, the project is a middleware, so it does not replace a reader and does not manage subscriptions. Finally, the fulltext-plus craft is described as simulating a browser for sites where normal extraction fails, which means it is slower and heavier by design; using it on every feed is the wrong trade.
How it compares to RSSHub and reader-side extraction
RSSHub is the closest well-known project in the same self-hosted space, and the difference in approach is clear from the README's own description. RSSHub generates feeds for sites that do not publish one, through routes written per site. FeedCraft does the opposite direction: it accepts an existing feed and rewrites its contents, and its built-in generator (HTML/JSON/Search to RSS) is a secondary feature rather than the core. If your problem is that a site has no feed, RSSHub is the tool. If your problem is that a feed exists but arrives without full text, in a language you cannot skim, or buried in promotional paragraphs, FeedCraft operates on that feed directly. The other comparison is reader-side extraction, which tools like Miniflux or FreshRSS perform in the reader itself. That approach avoids running a second service, but it cannot easily chain steps, cannot translate with a custom prompt, and cannot produce a shareable rewritten feed URL. FeedCraft's FlowCraft concept exists precisely to chain steps, for example full-text extraction followed by AI filtering followed by summarization under a single recipe name.
Licence, maintenance and what an upgrade costs you
FeedCraft is licensed under GPL-3.0, which is a copyleft licence. If you modify the source and distribute the modified version, the GPL's terms apply to that distribution; running it as a self-hosted service for yourself does not trigger distribution obligations in the ordinary case. This is a summary of the licence identifier from the repository, not legal advice, and anyone embedding FeedCraft in a commercial product should read the full text in LICENSE. On maintenance, the repository is not archived and the last push was on 2026-09-11. The release history shows v3.0.0 in January 2026, v3.1.0 in March and v3.2.0 on 2026-08-30, so the cadence is roughly a major release every few months. The repository carries a CHANGELOG.md and a release-please-config.json, and the .github directory contains a docker-publish workflow, which suggests releases are cut through automation. Upgrade cost is mostly operational: the compose file mounts a SQLite database at /usr/local/feed-craft/db, so a version bump means backing up that directory before pulling a new image. The README does not document rollback, and it does not state whether the SQLite schema is migrated forward automatically.
Editorial conclusion
Adopt FeedCraft if you already run Docker, Redis and a browser rendering service, and you have an OpenAI-compatible LLM key you are willing to spend on feed processing. Skip it if you want a zero-dependency reader plugin or you cannot host Redis and browserless alongside it. Before committing, verify that your LLM endpoint accepts the /v1 base path, confirm the browser endpoint answers on port 3000, and change the default admin password after the first login.
Frequently asked questions
What is FeedCraft and who is it for?
FeedCraft is a self-hosted RSS middleware that processes existing feeds: extracting full text, translating, summarizing with an LLM, and filtering articles. It is aimed at people who already run Docker and want feed processing to happen server-side rather than inside their reader.
How do I install FeedCraft?
The README gives a Docker Compose deployment using the image ghcr.io/colin-xkl/feed-craft, with an alternative image on Docker Hub. You also need Redis and a browser rendering service, either supplied through FC_REDIS_URI and FC_BROWSER_ENDPOINT or deployed alongside it in the same compose file.
Does FeedCraft require an OpenAI API key?
The AI crafts do. The configuration exposes FC_LLM_API_BASE, FC_LLM_API_KEY, FC_LLM_API_MODEL and FC_LLM_API_TYPE, where the type is openai or ollama, and the base URL must end in /v1. The non-AI crafts such as proxy, limit and fulltext do not call a model.
What is the default FeedCraft admin password?
The console account is admin with the password adminadmin, according to the README. It says to change the default password soon after logging in.
Can FeedCraft translate an RSS feed without a reader plugin?
Yes. The portable mode prepends a craft to the original feed URL, so /craft/translate-title?input_url=... returns a feed with translated titles that any reader can subscribe to. Other translation crafts handle content, including an immersive mode that appends the translation after each original paragraph.
What are AtomCraft, FlowCraft and Recipe in FeedCraft?
An AtomCraft is a single processing step such as fulltext or summary. A FlowCraft is a sequence of AtomCrafts combined into one named operation, and a Recipe records which craft or flow applies to a specific source feed, producing a new subscribable address.
Community notes