File: README.md
Folo is an open-source AI RSS reader that brings everything you follow into one calm timeline, then helps you read it. Follow blogs, news sites, newsletters, podcasts, video channels and social feeds in one place, ask AI about what you read, get a digest of your day, and let summaries and translations do the heavy lifting.
๐๐ป Getting Started & Join Our Community
Folo runs in the browser and on iOS, Android, macOS, Windows and Linux, and keeps your subscriptions, read status and stars in sync across all of them. It is under active development, and feedback is welcome for any issue you run into.
| Platform | Download |
|---|---|
| Web | |
| iOS | |
| Android | |
| macOS | |
| Windows | |
| Linux |
You can also install using the following methods maintained by our community:
- If you are using Arch Linux, you can install the package folo-appimage that is maintained by timochan and grtsinry43.
- If you are using Linux with Flatpak, you can install Folo from FlatPark that is maintained by Komh.
- If you are using Nix, you can install the package follow that is maintained by iosmanthus.
- If you are using macOS with Homebrew, you can install the cask folo that is maintained by realSunyz.
- If you are using Windows with Scoop, you can install the manifest folo that is maintained by cscnk52.
| Join our Discord server to connect with developers, request features, and receive support. | |
|---|---|
| Follow us on X for product updates. |
[!IMPORTANT]
Star Us, You will receive all release notifications from GitHub without any delay ~
โจ Features
Folo AI
Ask about an article, a feed, a folder or everything you follow. Pick your AI model or bring your own API key, and connect MCP services to bring your other tools into Folo AI.
Timeline Summary
Turn hundreds of new entries into one quick digest of what matters.
AI Translation and Summaries
Read articles side by side with an AI translation in English, Chinese, Japanese or French, and get an AI summary of any article, on demand or automatically.
Every Format
Articles, social posts, pictures, videos and podcasts each get a layout made for them, and text-to-speech reads any article aloud with natural voices.
AI Tasks
Schedule AI tasks that write daily or weekly briefings and deliver them to chat or email.
Integrations
Send articles to Obsidian, Readwise, Instapaper, Zotero, Cubox, Outline, Readeck or Eagle, and let Actions filter, star, rewrite, notify or summarize new entries with your own rules.
On Your Phone
Folo for iPhone, iPad and Android brings AI summaries, read-aloud and discovery with you, and picks up where you left off on your computer.
And More
- Subscribe to any RSS, Atom or JSON feed, plus thousands of RSSHub routes for sites without a feed
- Import and export OPML to move from any other reader
- An inbox with its own email address for newsletters
- Customizable keyboard shortcuts and a command menu
- Themes, reading fonts, custom CSS and code highlighting
- Spotlight highlights the keywords you care about
- Open source, with no ads
๐ค Contributing
You are welcome to join the open source community to build together, please check our Contributing Guide for more details.
๐ Code signing policy
Folo for Windows uses free code signing provided by SignPath.io, a certificate by SignPath Foundation.
Folo for macOS and iOS is signed and notarized by Apple Developer Program.
All released files are verified with GitHub artifact attestations to ensure their provenance and integrity.
๐ License
Folo is licensed under the GNU Affero General Public License version 3 with the addition of the following special exception:
All content in the icons/mgc directory is copyrighted by https://mgc.mingcute.com/ and cannot be redistributed.
File: AGENTS.md
AGENTS.md
This file provides concise, agent-focused guidance for working in this monorepo. It consolidates the repository's CLAUDE.md guides, .cursor rules, Cursor rules improvements, and modern agent best practices.
Project overview
- Monorepo managed by pnpm workspaces + Turbo.
- Apps:
apps/desktopโ Electron app (Vite + React renderer is the primary web app)apps/mobileโ React Native app via Expoapps/ssrโ Minimal SSR site for external sharing
- Shared packages:
packages/internal(components, atoms, hooks, store, utils, database, etc.).
Setup commands
# Install deps
pnpm install
# Desktop โ recommended (browser renderer)
cd apps/desktop && pnpm run dev:web
# Desktop โ full Electron
cd apps/desktop && pnpm run dev:electron
# Mobile โ Expo
cd apps/mobile && pnpm run dev
# or target platforms
cd apps/mobile && pnpm run ios
cd apps/mobile && pnpm run android
# SSR
cd apps/ssr && pnpm run dev
# Build web version (desktop renderer)
pnpm run build:webQuality gates (must-pass before commit/PR)
# 1) Typecheck first (required)
pnpm run typecheck
# 2) Lint and auto-fix
pnpm run lint:fix
# 3) Tests
pnpm run test- Run the above at the root, or use per-package variants as needed.
- Follow this order strictly: typecheck โ lint โ test.
- After every modification, run the following checks to catch errors early:
npm exec turbo run format:check typecheck lint
npm exec turbo run testCode style and conventions
- TypeScript strict; avoid
any(use precise types). Comments in English. Keep solutions simple and maintainable. - Prefer CSS transitions/animations for simple UI interactions. Use JS-driven motion only when necessary to avoid frame drops.
- Imports: use
patheinstead ofnode:pathfor crossโplatform paths. - Organize shared, reusable UI in
packages/internal/components; app-specific UI stays in its app. - Style extraction: Avoid inline styles in JSX. Extract complex styles (especially those using CSS variables, gradients, or multiple properties) to external style objects similar to React Native's
StyleSheet.create. Place style objects in astyles.tsfile alongside the component, usingCSSPropertiestype for type safety.
Team preferences
- Prefer CSS transitions/animations over JS-based motion for simple interactions to avoid frame drops.
- Prefer simple, easy-to-maintain solutions.
- Avoid using the
anytype in TypeScript. - Write code comments in English.
Architecture quick reference
- State: Jotai for atoms, Zustand for complex stores, TanStack Query for server state.
- Database: Drizzle + SQLite (see
packages/internal/database). - Error handling: custom utils in
packages/internal/utils; Sentry integrated. - i18n: i18next with flat keys only; no
defaultValue. Provideen,zh-CN,jafor each feature. Avoid conflicting dotted keys.
UI system and design tokens
Tailwind + Apple UIKit colors (Desktop/Web)
- Use Tailwind classes bound to Apple UIKit color tokens (light/dark adaptive). Prefix by CSS property:
- System colors:
text-red,bg-blue,border-gray, etc. forred|orange|yellow|green|mint|teal|cyan|blue|indigo|purple|pink|brown|gray. - Fill:
bg-fill[-secondary|-tertiary|-quaternary|-quinary]andbg-fill-vibrant[-secondary|-tertiary|-quaternary|-quinary](andborder-*as needed). - Text:
text-text,text-text-secondary|tertiary|quaternary|quinary,text-text-vibrant(-secondary|-tertiary|-quaternary|-quinary). - Material:
bg-material-ultra-thick|thick|medium|thin|ultra-thin|opaque. - Control:
bg-control-enabled|disabled. - Interface:
bg-menu|popover|titlebar|sidebar|selection-focused|selection-focused-fill|selection-unfocused|selection-unfocused-fill|header-view|tooltip|under-window-background.
- System colors:
These classes map to the UIKit color variables (see .cursor rules/color and apps/desktop/AGENTS.md).
Icons (Desktop/Web)
- Prefer MingCute with
i-mgc-prefix (e.g.,i-mgc-copy-cute-re). Usei-mingcute-only if noi-mgc-exists.
Motion (Desktop/Web)
- Use Framer Motion with LazyMotion via
mfrommotion/react(e.g.,m.div). - Prefer spring presets from
@follow/components/constants/spring.js(Spring.presets.smooth|snappy|bouncy). - For simple micro-interactions, prefer CSS transitions first.
React Native (Mobile)
- Styling: NativewindCSS; do not use external
StyleSheet.createfor new UI. - Icons: use
@/apps/mobile/iconsonly. - Colors: use React Native UIKit color system (via
react-native-uikit-colors) with Tailwind utilities:- Backgrounds:
system-background,secondary-system-background,tertiary-system-background. - Grouped backgrounds:
system-grouped-background,secondary-system-grouped-background,tertiary-system-grouped-background. - Labels:
label,secondary-label,tertiary-label,quaternary-label. - Fills:
system-fill,secondary-system-fill,tertiary-system-fill,quaternary-system-fill. - Separators:
separator,opaque-separator,non-opaque-separator. - Semantic colors:
red|orange|yellow|green|mint|teal|cyan|blue|indigo|purple|pink|brown, graysgray..gray6, and interactivelink,placeholder-text.
- Backgrounds:
Component placement
- Check existing components in
apps/desktop/layer/renderer/src/modules/renderer/componentsfor app-specific UI. - If generic and reusable, implement in
packages/internal/componentsand export from the package index.
Testing & CI tips
- Use Vitest for unit tests; co-locate tests near source files.
- After moving files or changing imports, run
pnpm lintandpnpm typecheckfor the affected package. - CI expects
pnpm typecheck,pnpm lint, andpnpm testto pass before merge.
Agent workflow (Cursor-oriented improvements)
- Status updates: provide brief progress notes when running tool batches.
- Prefer semantic code search to explore unfamiliar areas; use exact grep only for symbols.
- Default to parallelizing independent searches/reads to reduce latency.
- Avoid multi-line speculative edits; keep edits minimal and targeted; preserve existing indentation.
- When editing TypeScript, do not introduce
any; keep types precise. - For UI, prefer CSS transitions for simple effects; use Framer Motion
m.*only when needed.
Context7 (up-to-date docs)
- Use Context7 to fetch current library docs before using APIs prone to change.
- Workflow:
- Resolve a library ID: resolve the library (e.g., React Native, Vite, TanStack Query).
- Fetch docs scoped to the topic (e.g., hooks, routing).
- Integrate code examples following our style rules.
Sequential Thinking (step-by-step problem solving)
- Break work into small thought steps:
- Define immediate goal/assumption.
- Use suitable tool (search, code edit, error explainer, docs).
- Record the output/results.
- Decide next step or branch alternatives; compare trade-offs.
- Encourage rollback/iteration if new information contradicts prior steps.
Subproject guides
- This root AGENTS.md sets global rules. Each app/package should include its own
AGENTS.md(e.g.,apps/desktop/AGENTS.md,apps/mobile/AGENTS.md). The closest guide to the edited file takes precedence when rules conflict.
Quick checklists
Implementation
- Is code placed in the right package/app?
- Type-safe (no
any), readable names, English comments where needed. - Uses correct UIKit Tailwind tokens and icon sources.
- For motion: CSS first;
m.*only if necessary.
Validation
-
pnpm typecheckpasses -
pnpm lint:fixpasses cleanly - Tests updated and pass
-
File: buildServer.json
{
"name": "xcode build server",
"version": "0.2",
"bspVersion": "2.0",
"languages": ["c", "cpp", "objective-c", "objective-cpp", "swift"],
"argv": ["/opt/homebrew/bin/xcode-build-server"],
"workspace": "/Users/innei/git/work/rss3/follow/apps/mobile/ios/Folo.xcworkspace",
"build_root": "/Users/innei/Library/Developer/Xcode/DerivedData/Folo-dtqltpwzjnyxzeeeuvortyjqrpno",
"scheme": "Folo",
"kind": "xcode"
}
File: CODE_OF_CONDUCT.md
Contributor Covenant Code of Conduct
Our Pledge
In the interest of fostering an open and welcoming environment, we as
contributors and maintainers pledge to making participation in our project and
our community a harassment-free experience for everyone, regardless of age, body
size, disability, ethnicity, sex characteristics, gender identity and expression,
level of experience, education, socio-economic status, nationality, personal
appearance, race, religion, or sexual identity and orientation.
Our Standards
Examples of behavior that contributes to creating a positive environment
include:
- Using welcoming and inclusive language
- Being respectful of differing viewpoints and experiences
- Gracefully accepting constructive criticism
- Focusing on what is best for the community
- Showing empathy towards other community members
Examples of unacceptable behavior by participants include:
- The use of sexualized language or imagery and unwelcome sexual attention or
advances - Trolling, insulting/derogatory comments, and personal or political attacks
- Public or private harassment
- Publishing others' private information, such as a physical or electronic
address, without explicit permission - Other conduct which could reasonably be considered inappropriate in a
professional setting
Our Responsibilities
Project maintainers are responsible for clarifying the standards of acceptable
behavior and are expected to take appropriate and fair corrective action in
response to any instances of unacceptable behavior.
Project maintainers have the right and responsibility to remove, edit, or
reject comments, commits, code, wiki edits, issues, and other contributions
that are not aligned to this Code of Conduct, or to ban temporarily or
permanently any contributor for other behaviors that they deem inappropriate,
threatening, offensive, or harmful.
Scope
This Code of Conduct applies both within project spaces and in public spaces
when an individual is representing the project or its community. Examples of
representing a project or community include using an official project e-mail
address, posting via an official social media account, or acting as an appointed
representative at an online or offline event. Representation of a project may be
further defined and clarified by project maintainers.
Enforcement
Instances of abusive, harassing, or otherwise unacceptable behavior may be
reported by contacting the project team at [email protected]. All
complaints will be reviewed and investigated and will result in a response that
is deemed necessary and appropriate to the circumstances. The project team is
obligated to maintain confidentiality with regard to the reporter of an incident.
Further details of specific enforcement policies may be posted separately.
Project maintainers who do not follow or enforce the Code of Conduct in good
faith may face temporary or permanent repercussions as determined by other
members of the project's leadership.
Attribution
This Code of Conduct is adapted from the Contributor Covenant, version 1.4,
available at https://www.contributor-covenant.org/version/1/4/code-of-conduct.html
For answers to common questions about this code of conduct, see
https://www.contributor-covenant.org/faq
File: conductor.json
{
"scripts": {
"setup": "pnpm i; cp $CONDUCTOR_ROOT_PATH/apps/desktop/.env.local apps/desktop/.env.local",
"run": "pnpm dev:web"
}
}
File: CONTRIBUTING.md
Contributing to Folo
Thank you for considering contributing to Folo! We welcome contributions from the community to help improve and expand the project.
Getting Started
Before you start contributing, please ensure you have enabled Corepack. Corepack ensures you are using the correct version of the package manager specified in the package.json.
corepack enable && corepack prepareInstalling Dependencies
To install the necessary dependencies, run:
pnpm installDevelopment Setup
Develop in the Browser
For a more convenient development experience, we recommend developing in the browser:
cd apps/desktop && pnpm run dev:webThis will open the browser at https://app.folo.is/__debug_proxy, allowing you to access the online API environment for development and debugging.
Develop in Electron
If you prefer to develop in Electron, follow these steps:
Go to the
apps/desktopdirectory:shcd apps/desktopCopy the example environment variables file:
shcp .env.example .envSet
VITE_API_URLtohttps://api.follow.isin your.envfile.Run the development server:
shpnpm run dev:electron
Tip: If you encounter login issues, copy the
__Secure-better-auth.session_tokenfrom your browser's cookies into the app.
Develop in External SSR Web App
To develop in SSR, follow these steps:
Go to the
apps/ssrdirectory:shcd apps/ssrRun the development server:
shpnpm run dev
Develop in Mobile App
To develop in the mobile app, follow these steps:
[!NOTE]
You need to have a Mac device to develop in the mobile app.And already installed Xcode and the necessary dependencies.
Go to the
apps/mobiledirectory:shcd apps/mobileCopy the example environment variables file:
shcp .env.example .envThen set the required environment variables in your
.envfile:shecho 'EXPO_PUBLIC_APP_CHECK_DEBUG_TOKEN="xxx"' >> .envOr manually edit the
.envfile to add:textEXPO_PUBLIC_APP_CHECK_DEBUG_TOKEN="xxx"the value is any string.
Build and install Folo(dev) app from source: (This step will take a while and only need to be done once)
shpnpm expo prebuild --clean # Optional pnpm run iosRun the development server:
shpnpm run dev
Development Native Modules
To develop native iOS modules, follow these steps:
Go to the
apps/mobiledirectory:shcd apps/mobile/iosOpen project in Xcode:
shopen Folo.xcworkspaceOpen
Podsin left sidebar and selectFollowNative:Build and run the project.
Contribution Guidelines
- Ensure your code follows the project's coding standards and conventions.
- Write clear, concise commit messages.
- Include relevant tests for your changes.
- Update documentation as necessary.
Community
Join our community to discuss ideas, ask questions, and share your contributions:
We look forward to your contributions!
License
By contributing to Folo, you agree that your contributions will be licensed under the GNU Affero General Public License version 3, with the special exceptions noted in the README.md.
File: package.json
{
"name": "@follow/monorepo",
"type": "module",
"private": true,
"packageManager": "[email protected]",
"description": "Follow everything in one place",
"author": "Folo Team",
"license": "AGPL-3.0-only",
"homepage": "https://github.com/RSSNext",
"repository": {
"url": "https://github.com/RSSNext/follow",
"type": "git"
},
"scripts": {
"build:packages": "turbo run build --filter="./packages//*"",
"build:web": "turbo run Folo#build:web",
"dedupe:locales": "eslint --fix locales/",
"depcheck": "npx depcheck --quiet",
"dev:web": "turbo run @follow/web#dev @follow/ssr#dev",
"format": "prettier --write .",
"format:check": "prettier --check .",
"icons:sync": "tsx scripts/svg-to-rn.ts && prettier --write apps/mobile/src/icons//*.tsx && eslint --fix apps/mobile/src/icons//.tsx",
"icons:update": "tsx scripts/update-icon.ts",
"lint": "pnpm run lint:tsl && eslint",
"lint:fix": "eslint --fix",
"lint:tsl": "tsslint --project apps//tsconfig.json",
"mitproxy": "bash scripts/run-proxy.sh",
"polyfill-optimize": "pnpx nolyfill install",
"postinstall": "node scripts/link-cf-build-tools.mjs && pnpm run build:packages",
"prepare": "simple-git-hooks && corepack prepare",
"reinstall": "rm -rf node_modules && rm -rf apps//node_modules && rm -rf packages//node_modules && pnpm install",
"test": "cross-env CI=1 pnpm --recursive run test",
"typecheck": "turbo typecheck"
},
"devDependencies": {
"@electron-toolkit/tsconfig": "2.0.0",
"@eslint/compat": "2.1.1",
"@stylistic/eslint-plugin": "5.10.0",
"@tsslint/cli": "3.1.4",
"@tsslint/compat-eslint": "3.1.4",
"@tsslint/config": "3.1.4",
"@types/node": "26.6.2",
"@types/react": "19.2.18",
"@types/react-dom": "19.2.7",
"@vercel/node": "12.0.1",
"cross-env": "10.1.0",
"eslint": "10.11.0",
"eslint-config-hyoban": "7.0.3",
"eslint-plugin-react-native": "5.0.0",
"fast-glob": "3.3.3",
"glob": "13.0.6",
"lint-staged": "17.5.1",
"prettier": "3.9.8",
"prettier-plugin-tailwindcss": "0.8.1",
"raw-body": "4.0.0",
"react": "19.2.8",
"react-dom": "19.2.8",
"rimraf": "6.1.3",
"simple-git-hooks": "2.14.0",
"svg-parser": "2.1.0",
"tar": "7.5.22",
"tsl": "1.0.30",
"tsx": "4.23.15",
"turbo": "2.11.2",
"typescript": "catalog:",
"vite": "7.3.6",
"vitest": "5.0.1"
},
"simple-git-hooks": {
"pre-commit": "pnpm exec lint-staged"
},
"lint-staged": {
"": [
"eslint --fix",
"prettier --ignore-unknown --write"
],
"apps/mobile/src/**/": [
"bash scripts/increment-build-id.sh"
],
"locales/**/*.json": [
"npm run dedupe:locales",
"git add locales"
]
}
}