@youmind-openlab/reddit-api
v1.1.0
Published
Reddit API for Browser Extensions - TypeScript library to fetch Reddit saved content using browser cookies
Maintainers
Readme
Reddit Saved API for Browser Extensions
一个轻量级的 TypeScript 库,用于在浏览器插件中获取 Reddit 保存的内容。
基于 PRAW (Python Reddit API Wrapper) 的设计理念,专门为浏览器插件环境改造。
🎯 快速体验
本项目包含一个完整的示例浏览器插件,可以直接使用:
# 1. 克隆或下载本项目
# 2. 安装依赖
npm install
# 3. 构建库和插件
npm run build:extension
# 4. 在 Chrome 中加载插件
# - 打开 chrome://extensions/
# - 开启"开发者模式"
# - 点击"加载已解压的扩展程序"
# - 选择 extension/ 目录插件功能:
- 🔐 自动检测 Reddit 登录状态
- 👤 展示用户信息(头像、用户名、bio、Karma)确认身份
- 📚 查看保存的 Reddit 帖子和评论,按类型过滤
- 📝 查看自己发过的帖子,按排序方式切换
- 🎨 三步交互流程(登录检查 → 用户确认 → 内容浏览)
特性
- 🔐 Cookie 认证 - 直接使用用户已登录的 Reddit 会话,无需 OAuth2 配置
- 📦 TypeScript 支持 - 完整的类型定义
- 👤 用户信息 - 获取用户头像、bio、Karma 等详细信息
- 📝 用户帖子 - 获取用户发过的帖子,支持排序和分页
- 🚀 轻量级 - 无外部依赖
- ⚡ 自动分页 - 支持获取所有保存的内容
- 🔄 速率限制 - 自动处理 Reddit API 的速率限制
- 🔁 重试机制 - 网络错误自动重试
安装
npm install @youmind-openlab/reddit-api
# 或
pnpm add @youmind-openlab/reddit-api前置要求
你的浏览器插件需要在 manifest.json 中声明以下权限:
{
"permissions": ["cookies"],
"host_permissions": ["https://*.reddit.com/*"]
}快速开始
基本使用
import { createRedditClient, isSubmission, isComment } from '@youmind-openlab/reddit-api';
// 创建客户端
const reddit = createRedditClient();
// 检查用户是否已登录
if (await reddit.isLoggedIn()) {
// 获取保存的内容(分页)
const { items, after } = await reddit.getSaved({ limit: 25 });
for (const item of items) {
if (isSubmission(item)) {
console.log('帖子:', item.title);
} else if (isComment(item)) {
console.log('评论:', item.body.slice(0, 100));
}
}
}获取所有保存的内容
// 使用异步迭代器(推荐,内存效率高)
for await (const item of reddit.getAllSaved()) {
console.log(item.name, item.subreddit);
}
// 或者一次性获取所有内容
const allItems = await reddit.getAllSavedArray();
console.log(`共保存了 ${allItems.length} 条内容`);仅获取帖子或评论
// 仅获取保存的帖子
const { items: submissions } = await reddit.getSavedSubmissions({ limit: 10 });
// 仅获取保存的评论
const { items: comments } = await reddit.getSavedComments({ limit: 10 });
// 使用异步迭代器获取所有帖子
for await (const submission of reddit.getAllSavedSubmissions()) {
console.log(submission.title);
}保存/取消保存内容
// 保存帖子或评论
await reddit.save('t3_abc123'); // 帖子
await reddit.save('t1_xyz789'); // 评论
// 取消保存
await reddit.unsave('t3_abc123');获取用户信息
const user = await reddit.getMe();
console.log(`用户名: ${user.name}`);
console.log(`Karma: ${user.total_karma}`);
// 便捷方法
const avatar = await reddit.getAvatarUrl();
const bio = await reddit.getBio();获取用户发过的帖子
// 获取当前用户的帖子
const { items } = await reddit.getMySubmissions({ limit: 25, sort: 'new' });
// 获取指定用户的帖子
const { items: posts } = await reddit.getUserSubmissions('username', {
sort: 'top',
time: 'year',
});
// 自动分页获取所有帖子
for await (const post of reddit.getAllMySubmissions()) {
console.log(post.title);
}API 参考
createRedditClient(config?)
创建 Reddit 客户端实例。
参数:
config.userAgent- 用户代理字符串(可选)config.timeout- 请求超时时间,毫秒(默认 30000)config.redditUrl- Reddit URL(默认 'https://www.reddit.com')
RedditClient
方法
| 方法 | 描述 |
|------|------|
| isLoggedIn() | 检查用户是否已登录 |
| getMe() | 获取当前用户信息(头像、Karma、bio 等) |
| getUsername() | 获取当前用户名 |
| getAvatarUrl() | 获取用户头像 URL |
| getBio() | 获取用户个人简介 |
| getSaved(options?) | 获取保存的内容(单页) |
| getAllSaved(options?) | 获取所有保存的内容(异步迭代器) |
| getAllSavedArray(options?) | 获取所有保存的内容(数组) |
| getSavedSubmissions(options?) | 获取保存的帖子 |
| getAllSavedSubmissions(options?) | 获取所有保存的帖子 |
| getSavedComments(options?) | 获取保存的评论 |
| getAllSavedComments(options?) | 获取所有保存的评论 |
| getMySubmissions(options?) | 获取当前用户的帖子(单页) |
| getUserSubmissions(username, options?) | 获取指定用户的帖子(单页) |
| getAllMySubmissions(options?) | 获取当前用户所有帖子(异步迭代器) |
| getAllUserSubmissions(username, options?) | 获取指定用户所有帖子(异步迭代器) |
| save(fullname, category?) | 保存内容 |
| unsave(fullname) | 取消保存 |
| getRateLimitInfo() | 获取速率限制信息 |
| clearCache() | 清除缓存 |
GetSavedOptions
interface GetSavedOptions {
limit?: number; // 获取数量限制
after?: string; // 分页游标(下一页)
before?: string; // 分页游标(上一页)
count?: number; // 已获取数量
time?: 'hour' | 'day' | 'week' | 'month' | 'year' | 'all';
type?: 'links' | 'comments';
}GetSubmissionsOptions
interface GetSubmissionsOptions {
limit?: number; // 获取数量限制
sort?: 'hot' | 'new' | 'top' | 'controversial';
time?: 'hour' | 'day' | 'week' | 'month' | 'year' | 'all';
after?: string; // 分页游标(下一页)
before?: string; // 分页游标(上一页)
count?: number; // 已获取数量
}类型
// 判断类型
import { isSubmission, isComment } from '@youmind-openlab/reddit-api';
isSubmission(item) // 是否是帖子
isComment(item) // 是否是评论在 Background Script 中使用
// background.ts
import { createRedditClient, isSubmission, isComment } from '@youmind-openlab/reddit-api';
const reddit = createRedditClient();
chrome.runtime.onMessage.addListener((message, sender, sendResponse) => {
if (message.type === 'GET_SAVED') {
reddit.getAllSavedArray({ limit: 100 })
.then(items => sendResponse({ success: true, items }))
.catch(error => sendResponse({ success: false, error: error.message }));
return true; // 保持消息通道开启
}
});与 PRAW 的对比
| 功能 | PRAW | 本库 | |------|------|------| | 语言 | Python | TypeScript | | 运行环境 | 服务器/命令行 | 浏览器插件 | | 认证方式 | OAuth2 | Cookies | | 功能范围 | 完整 Reddit API | saved、用户信息、用户帖子 | | 大小 | 完整库 | 轻量级 |
项目结构
praw-for-browser-extension/
├── src/ # TypeScript 源码
│ ├── types/ # 类型定义
│ ├── auth.ts # Cookie 认证模块
│ ├── requestor.ts # HTTP 请求模块
│ ├── reddit.ts # Reddit 客户端
│ └── index.ts # 导出入口
├── dist/ # 构建产物
├── extension/ # 示例浏览器插件
│ ├── manifest.json # 插件配置
│ ├── background/ # 后台脚本
│ ├── popup/ # 弹窗界面
│ └── icons/ # 图标
├── examples/ # 代码示例
└── scripts/ # 构建脚本许可证
MIT
