mirror of
https://github.com/KuekHaoYang/KVideo.git
synced 2026-08-15 08:43:44 +08:00
docs: refresh README and align version metadata
This commit is contained in:
@@ -1,46 +1,326 @@
|
||||
# KVideo
|
||||
[](https://github.com/KuekHaoYang/KVideo/actions/workflows/Github_Upstream_Sync.yml)
|
||||
[](https://deepwiki.com/KuekHaoYang/KVideo)
|
||||
[](CHANGELOG.md)
|
||||
[](https://nextjs.org/)
|
||||
[](https://react.dev/)
|
||||
[](https://tailwindcss.com/)
|
||||
[](https://www.typescriptlang.org/)
|
||||
[](LICENSE)
|
||||
|
||||
KVideo is a Next.js 16 + React 19 video aggregation app focused on self-hosted deployments, multi-source search, player ergonomics, IPTV playback, and account-aware local or Redis-backed persistence.
|
||||
[](https://www.buymeacoffee.com/kuekhaoyang)
|
||||
|
||||
This branch aligns the project with the 2026-04-16 audit:
|
||||
# 视频聚合平台 (KVideo)
|
||||
|
||||
- outbound requests now go through a shared server-side policy
|
||||
- relay routes are private by default
|
||||
- auth throttling is enforced
|
||||
- Cloudflare support prefers Workers/OpenNext; `pages:build` remains for legacy Pages Git integrations
|
||||
- Apple TV is no longer a supported product target
|
||||
- the Android wrapper is TV-only
|
||||
- offline support is limited to same-origin shell/static assets
|
||||

|
||||
|
||||
## Support Matrix
|
||||
> 一个基于 Next.js 16、React 19 和 Tailwind CSS v4 构建的现代化视频聚合播放平台,聚焦自托管部署、多源并行搜索、播放器体验、IPTV 播放、账户隔离和 Redis 同步能力。
|
||||
|
||||
Supported:
|
||||
**当前版本:[`4.9.3`](CHANGELOG.md)**
|
||||
|
||||
- Desktop browsers
|
||||
- Mobile browsers / PWA install flow
|
||||
- Android TV wrapper in [`android-tv`](/Users/haoyangkuek/development/KVideo/android-tv)
|
||||
- Self-hosted Node.js
|
||||
- Docker
|
||||
- Cloudflare Workers via OpenNext
|
||||
> [!IMPORTANT]
|
||||
> 这份 README 已按当前主分支和 2026-04-16 审计后的实际行为校正。旧版文案里关于 Apple TV 原生支持、宽松公共代理、以及“完整离线可用”的表述都已经不再成立。
|
||||
|
||||
Not supported:
|
||||
> [!NOTE]
|
||||
> 仓库默认不内置任何视频源、高级源或 IPTV 源。部署者必须自行配置已获授权、可合法使用且允许当前部署方式访问的内容来源。
|
||||
|
||||
- Apple TV / tvOS app packaging
|
||||
## 项目简介
|
||||
|
||||
Apple TV users should use the web app in a browser or an AirPlay-style fallback instead of a native tvOS client.
|
||||
**KVideo** 是一个高性能、现代化的视频聚合与播放应用,核心目标不是“随便能播”,而是在当前代码约束下尽可能把以下几件事做好:
|
||||
|
||||
## Deployment Modes
|
||||
- 多源搜索与结果聚合
|
||||
- 现代播放器交互与大屏适配
|
||||
- 账户隔离、权限控制与跨设备同步
|
||||
- 自托管场景下可控的媒体代理与 IPTV 能力
|
||||
- 在审计后保持更严格、更诚实的运行边界
|
||||
|
||||
### Self-hosted Node.js / Docker
|
||||
### 核心设计语言:Liquid Glass(液态玻璃)
|
||||
|
||||
Recommended when you need the full product surface:
|
||||
项目 UI 延续了 **Liquid Glass** 风格,强调:
|
||||
|
||||
- external media proxy
|
||||
- IPTV relay
|
||||
- account management with Redis-backed managed auth
|
||||
- cross-device config sync
|
||||
- **玻璃拟态效果**:大量使用 `backdrop-filter`、半透明叠层和柔和边框
|
||||
- **统一圆角系统**:主要围绕 `rounded-2xl` 与 `rounded-full` 建立视觉一致性
|
||||
- **光影与层级**:悬停、聚焦、弹层和播放器控制条都有清晰的深度关系
|
||||
- **顺滑动画曲线**:采用更接近物理手感的缓动与过渡,而不是机械线性动画
|
||||
- **大屏可读性**:TV 模式下会主动放大交互目标、焦点态和间距
|
||||
|
||||
Commands:
|
||||
## 支持矩阵
|
||||
|
||||
| 目标 | 状态 | 说明 |
|
||||
|------|------|------|
|
||||
| 桌面浏览器 | 支持 | 主力使用场景 |
|
||||
| 移动浏览器 | 支持 | 包含触摸交互与移动端播放器优化 |
|
||||
| PWA 安装 | 支持 | 但离线能力仅限同源壳与静态资源,不等于完整离线播放器 |
|
||||
| Android TV 壳应用 | 支持 | 仓库内提供 `android-tv/` 工程 |
|
||||
| 自托管 Node.js | 支持 | 完整能力路径 |
|
||||
| Docker | 支持 | 完整能力路径,推荐部署方式之一 |
|
||||
| Cloudflare Workers via OpenNext | 支持 | Cloudflare 主支持路径,但运行时会进入受限托管模式 |
|
||||
| Vercel / 托管 Cloudflare 部署 | 支持但受限 | 自动关闭外部媒体代理、热链转发和 IPTV 流中继 |
|
||||
| Apple TV / tvOS 原生打包 | 不支持 | 旧的 WebView 壳路径已移除,不再宣称支持 |
|
||||
|
||||
Apple TV 用户当前应使用浏览器、AirPlay,或其他已经被支持的投屏路径,而不是依赖仓库内不存在的完整 tvOS 产品链路。
|
||||
|
||||
## 核心功能
|
||||
|
||||
### 智能视频播放
|
||||
|
||||
- **HLS 流媒体支持**:基于 [hls.js](https://github.com/video-dev/hls.js/) 播放 HLS (`.m3u8`) 内容
|
||||
- **完整播放控制**:进度条、音量、倍速、静音、系统全屏、网页全屏
|
||||
- **自动跳过片头/片尾**:支持配置秒数
|
||||
- **自动连播**:可自动播放下一集
|
||||
- **移动端优化**:移动端播放器布局、双击手势、触摸交互单独处理
|
||||
- **Google Cast / Chromecast**:播放器页面加载 Cast SDK
|
||||
- **画中画(PiP)**:桌面浏览器与 Android WebView 都有对应兼容逻辑
|
||||
- **代理播放模式**:直连、仅代理、智能重试等模式可切换
|
||||
- **实际分辨率探测**:会对当前播放源和线路列表中的源做分辨率探测与缓存
|
||||
- **广告过滤回退**:广告过滤失败时会退回原始视频流,而不是直接把播放器打死
|
||||
- **键盘快捷键**:空格/K、F、M、P、方向键、J/L 等常用控制都已接入
|
||||
- **一起看(VideoTogether)**:提供网页脚本集成,但默认不会加载,必须显式启用环境变量并由用户在设置中开启
|
||||
|
||||
### 多源并行搜索与源管理
|
||||
|
||||
- **并行聚合搜索**:多个视频源同时请求,服务端以 SSE 实时推送结果
|
||||
- **自定义视频源**:支持手动添加、编辑、启用、禁用与排序
|
||||
- **个人视频源**:用户可添加只对自己可见的个人源,不影响系统源
|
||||
- **订阅源管理**:支持通过 JSON 链接自动导入与更新
|
||||
- **JSON 批量导入**:可直接粘贴源列表 JSON
|
||||
- **统一解析层**:对不同来源的字段差异做统一收敛
|
||||
- **搜索历史**:自动保存并支持快速重搜
|
||||
- **繁体中文搜索兼容**:使用 `opencc-js` 做繁简转换辅助搜索
|
||||
- **合并同名源显示**:可切换默认卡片模式与合并模式
|
||||
- **实时延迟显示**:可选展示各源网络延迟
|
||||
- **内容过滤**:支持屏蔽关键词类目
|
||||
- **搜索取消与超时保护**:服务端支持 `AbortSignal`、单源超时和总量限制,避免内存暴涨
|
||||
|
||||
### IPTV 直播
|
||||
|
||||
- **M3U / M3U8 播放列表导入**
|
||||
- **JSON 频道列表导入**
|
||||
- **HEVC/H.265 兼容处理**:会优先尝试 H.264 级别以缓解“有声音没画面”
|
||||
- **频道网格与分组浏览**
|
||||
- **多级频道结构**:源分组、分类分组、频道选择
|
||||
- **多线路折叠与快速切换**
|
||||
- **自定义请求头透传**:支持从 M3U 解析 `http-user-agent` 与 `http-referrer`
|
||||
- **代理与重定向处理**:自托管模式下会处理中继、URL 重写和常见 CORS 问题
|
||||
- **超时与并发控制**:频道拉取有限流、分片超时与重试策略
|
||||
- **权限控制**:需要 `iptv_access`
|
||||
- **播放器内搜索优化**:大列表搜索使用 `useTransition` 降低阻塞
|
||||
|
||||
> [!WARNING]
|
||||
> IPTV 与媒体代理在 Vercel / Cloudflare 等托管部署中会被自动关闭。需要完整 IPTV 能力时,直接用 Docker 或传统 Node.js 自托管,别自欺欺人地把受限托管平台当完整功能环境。
|
||||
|
||||
### 豆瓣、推荐与元数据
|
||||
|
||||
- **电影 / 电视剧分类切换**
|
||||
- **豆瓣评分、演员、简介等元数据展示**
|
||||
- **相关推荐**
|
||||
- **首页标签管理与排序**
|
||||
- **演员 / 导演可点击继续检索**
|
||||
- **个性化推荐**:基于观看历史生成“为你推荐”标签
|
||||
|
||||
### 收藏、历史与高级模式
|
||||
|
||||
- **一键收藏**
|
||||
- **独立收藏侧边栏**
|
||||
- **自动记录观看历史**
|
||||
- **断点续播**
|
||||
- **按标题去重的历史记录**
|
||||
- **普通 / 高级模式隔离**
|
||||
- **高级模式独立入口**:直接访问 `/premium`
|
||||
- **高级源与普通源物理隔离**
|
||||
- **高级模式单独推荐、单独设置、单独数据空间**
|
||||
|
||||
### 弹幕(Danmaku)
|
||||
|
||||
- **兼容 `danmu_api` 风格接口**
|
||||
- **Canvas 高性能渲染**
|
||||
- **滚动 / 顶部 / 底部弹幕**
|
||||
- **透明度、字号、显示区域可调**
|
||||
- **暂停、跳转、全屏联动**
|
||||
- **每用户多 API 管理**
|
||||
- **用户选择的弹幕 API 优先于系统默认**
|
||||
|
||||
### 账户、权限与跨设备同步
|
||||
|
||||
- **托管账户模式**:Redis + `AUTH_SECRET`,支持用户名密码登录与 HTTP-only 会话
|
||||
- **环境变量兼容模式**:仍支持 `ADMIN_PASSWORD` / `ACCESS_PASSWORD` / `ACCOUNTS`
|
||||
- **超级管理员账户管理**:创建、修改、重置、删除账户
|
||||
- **独立高级内容密码**:`PREMIUM_PASSWORD`
|
||||
- **配置同步**:使用 Upstash Redis 在设备间同步设置
|
||||
- **多账户数据隔离**:收藏、历史、设置、个人源、弹幕 API 都按 `profileId` 隔离
|
||||
|
||||
### 全端体验
|
||||
|
||||
- **深色 / 浅色主题**
|
||||
- **动态站点名称与图标**
|
||||
- **TV 模式自动检测**
|
||||
- **方向键 / 遥控器空间导航**
|
||||
- **回到顶部、滚动位置记忆**
|
||||
- **PWA 安装能力**
|
||||
- **有限离线壳缓存**
|
||||
|
||||
## 安全与运行默认值
|
||||
|
||||
这部分不是装饰文案,而是当前仓库的真实默认行为。
|
||||
|
||||
- 只允许 `http` / `https` 出站目标
|
||||
- 默认阻止回环、私网、链路本地、保留地址段等高风险目标
|
||||
- 主机名会先解析,再对重定向结果继续做阻断校验
|
||||
- 公开中继默认关闭;未启用认证时,必须显式设置 `KVIDEO_PUBLIC_RELAY_ENABLED=true` 才允许公共访问相关代理路由
|
||||
- 代理路由不会转发 Cookie,也不会伪造客户端 IP / `Origin` / `Referer`
|
||||
- 只要开启认证,`AUTH_SECRET` 就是硬要求
|
||||
- 登录失败会触发节流,接口可能返回 `429` 与 `Retry-After`
|
||||
- Vercel / Cloudflare 运行时会进入受限托管模式,自动关闭外部媒体代理、热链转发和 IPTV 流中继
|
||||
|
||||
## 认证模式与权限
|
||||
|
||||
### 方式一:托管账户模式(推荐)
|
||||
|
||||
启用条件:
|
||||
|
||||
- `AUTH_SECRET`
|
||||
- `UPSTASH_REDIS_REST_URL`
|
||||
- `UPSTASH_REDIS_REST_TOKEN`
|
||||
|
||||
启用后:
|
||||
|
||||
- 登录页使用 **用户名 + 密码**
|
||||
- 服务端使用 HTTP-only 签名会话 Cookie 作为认证真源
|
||||
- 超级管理员可在设置页直接管理账户和权限
|
||||
- 配置同步、历史、收藏等跨设备数据按登录账户自动隔离
|
||||
|
||||
### 方式二:环境变量兼容模式
|
||||
|
||||
未启用托管账户时,继续支持:
|
||||
|
||||
- `ADMIN_PASSWORD`
|
||||
- `ACCESS_PASSWORD`
|
||||
- `ACCOUNTS`
|
||||
|
||||
`ACCESS_PASSWORD` 仍作为 `ADMIN_PASSWORD` 的兼容别名保留。
|
||||
|
||||
### `ACCOUNTS` 格式
|
||||
|
||||
支持两种格式,多个账户之间用逗号分隔:
|
||||
|
||||
- 旧格式:`密码:名称[:角色[:权限1|权限2|...]]`
|
||||
- 新格式:`用户名:密码:名称[:角色[:权限1|权限2|...]]`
|
||||
|
||||
角色:
|
||||
|
||||
- `super_admin`
|
||||
- `admin`
|
||||
- `viewer`
|
||||
|
||||
### 权限矩阵
|
||||
|
||||
| 权限 | 说明 | super_admin | admin | viewer |
|
||||
|------|------|:-----------:|:-----:|:------:|
|
||||
| `source_management` | 管理系统视频源 | ✓ | - | - |
|
||||
| `account_management` | 查看与管理账户 | ✓ | - | - |
|
||||
| `danmaku_api` | 配置系统弹幕 API | ✓ | - | - |
|
||||
| `data_management` | 导出、导入、重置数据 | ✓ | - | - |
|
||||
| `player_settings` | 播放器设置 | ✓ | ✓ | - |
|
||||
| `danmaku_appearance` | 弹幕外观设置 | ✓ | ✓ | - |
|
||||
| `view_settings` | 显示设置 | ✓ | ✓ | ✓ |
|
||||
| `iptv_access` | 访问 IPTV 功能 | ✓ | ✓ | - |
|
||||
| `iptv_source_management` | 管理 IPTV 源 | ✓ | ✓ | - |
|
||||
| `iptv_builtin_sources` | 使用内置 IPTV 源能力 | ✓ | ✓ | - |
|
||||
|
||||
> [!NOTE]
|
||||
> 当前代码里,只要账户拥有 `iptv_access`,权限解析会自动补上 `iptv_source_management`。
|
||||
|
||||
## 关键环境变量
|
||||
|
||||
### 认证与访问
|
||||
|
||||
| 变量名 | 默认值 | 说明 |
|
||||
|--------|--------|------|
|
||||
| `AUTH_SECRET` | - | 启用认证时必填;缺失时受保护的认证/同步/代理流程不会正常工作 |
|
||||
| `ADMIN_PASSWORD` | - | 管理员密码;兼容模式直接生效,也可作为托管模式首批超级管理员种子 |
|
||||
| `ACCESS_PASSWORD` | - | `ADMIN_PASSWORD` 的兼容别名 |
|
||||
| `ACCOUNTS` | - | 多账户配置,支持旧格式和用户名格式 |
|
||||
| `PREMIUM_PASSWORD` | - | `/premium` 的独立密码 |
|
||||
| `PERSIST_SESSION` | `true` | 是否持久化本地登录态 |
|
||||
| `PORT` | `3000` | 自定义端口 |
|
||||
|
||||
### 中继与出站安全
|
||||
|
||||
| 变量名 | 默认值 | 说明 |
|
||||
|--------|--------|------|
|
||||
| `KVIDEO_PUBLIC_RELAY_ENABLED` | `false` | 是否允许未认证场景下的公共代理访问 |
|
||||
| `KVIDEO_OUTBOUND_PRIVATE_HOST_ALLOWLIST` | - | 允许显式访问的私网 / 内网主机白名单,逗号分隔 |
|
||||
|
||||
### Redis 与跨设备同步
|
||||
|
||||
| 变量名 | 默认值 | 说明 |
|
||||
|--------|--------|------|
|
||||
| `UPSTASH_REDIS_REST_URL` | - | 与 Token 配对后启用托管账户与同步能力 |
|
||||
| `UPSTASH_REDIS_REST_TOKEN` | - | 与 URL 配对后启用托管账户与同步能力 |
|
||||
|
||||
### 站点标题与图标
|
||||
|
||||
| 变量名 | 默认值 | 说明 |
|
||||
|--------|--------|------|
|
||||
| `NEXT_PUBLIC_SITE_TITLE` | `KVideo - 视频聚合平台` | 浏览器标题 |
|
||||
| `NEXT_PUBLIC_SITE_DESCRIPTION` | `视频聚合平台` | 站点描述 |
|
||||
| `NEXT_PUBLIC_SITE_NAME` | `KVideo` | 站点名称 |
|
||||
| `SITE_ICON_FILE` | - | Docker 运行时图标文件路径,优先于 `SITE_ICON_URL` |
|
||||
| `SITE_ICON_URL` | - | Docker 运行时图标 URL 或站内路径 |
|
||||
|
||||
### 源、过滤器与集成
|
||||
|
||||
| 变量名 | 默认值 | 说明 |
|
||||
|--------|--------|------|
|
||||
| `SUBSCRIPTION_SOURCES` / `NEXT_PUBLIC_SUBSCRIPTION_SOURCES` | - | 自动订阅源配置 |
|
||||
| `IPTV_SOURCES` / `NEXT_PUBLIC_IPTV_SOURCES` | - | IPTV 源配置 |
|
||||
| `MERGE_SOURCES` / `NEXT_PUBLIC_MERGE_SOURCES` | - | 默认启用合并同名源显示 |
|
||||
| `AD_KEYWORDS` / `NEXT_PUBLIC_AD_KEYWORDS` | - | 广告过滤关键词 |
|
||||
| `AD_KEYWORDS_FILE` | - | 广告关键词文件路径 |
|
||||
| `DANMAKU_API_URL` / `NEXT_PUBLIC_DANMAKU_API_URL` | - | 默认弹幕 API 地址 |
|
||||
| `VIDEOTOGETHER_ENABLED` | `false` | 是否允许加载 VideoTogether 脚本 |
|
||||
| `VIDEOTOGETHER_SCRIPT_URL` | - | 启用 VideoTogether 时必填,必须显式提供脚本地址 |
|
||||
| `VIDEOTOGETHER_SETTING_URL` | - | 可选的设置页地址 |
|
||||
|
||||
## 技术栈
|
||||
|
||||
### 前端核心
|
||||
|
||||
| 技术 | 当前版本 | 用途 |
|
||||
|------|----------|------|
|
||||
| [Next.js](https://nextjs.org/) | `16.2.4` | App Router、服务端组件、构建链路 |
|
||||
| [React](https://react.dev/) | `19.2.5` | UI 组件模型 |
|
||||
| [TypeScript](https://www.typescriptlang.org/) | `5.x` | 类型系统 |
|
||||
| [Tailwind CSS](https://tailwindcss.com/) | `4.2.2` | 样式系统 |
|
||||
| [Zustand](https://github.com/pmndrs/zustand) | `5.0.12` | 轻量状态管理 |
|
||||
| [hls.js](https://github.com/video-dev/hls.js/) | `1.6.16` | HLS 播放 |
|
||||
| [Lucide React](https://lucide.dev/) | `0.577.0` | 图标库 |
|
||||
| [@dnd-kit](https://dndkit.com/) | `6.x / 10.x` | 拖拽排序 |
|
||||
| [@upstash/redis](https://github.com/upstash/redis-js) | `1.37.0` | Redis 同步与托管账户 |
|
||||
| [opencc-js](https://github.com/nk2028/opencc-js) | `1.0.5` | 繁简转换辅助搜索 |
|
||||
|
||||
### 开发工具
|
||||
|
||||
| 工具 | 当前版本 |
|
||||
|------|----------|
|
||||
| ESLint | `9.25.1` |
|
||||
| eslint-config-next | `16.2.4` |
|
||||
| Playwright | `1.56.1` |
|
||||
| OpenNext Cloudflare Adapter | `1.19.1` |
|
||||
| next-on-pages | `1.13.16`(仅保留兼容用途) |
|
||||
| TypeScript Runtime (`tsx`) | `4.20.6` |
|
||||
|
||||
## 快速开始
|
||||
|
||||
### 本地开发
|
||||
|
||||
```bash
|
||||
npm install
|
||||
npm run dev
|
||||
```
|
||||
|
||||
默认地址:`http://localhost:3000`
|
||||
|
||||
### 传统 Node.js 自托管
|
||||
|
||||
```bash
|
||||
npm install
|
||||
@@ -48,121 +328,112 @@ npm run build
|
||||
npm start
|
||||
```
|
||||
|
||||
Docker:
|
||||
### Docker 部署
|
||||
|
||||
```bash
|
||||
docker build -t kvideo .
|
||||
docker run -d -p 3000:3000 --name kvideo kvideo
|
||||
```
|
||||
|
||||
或直接使用 Docker Compose:
|
||||
|
||||
```bash
|
||||
docker compose up -d
|
||||
```
|
||||
|
||||
### Cloudflare Workers
|
||||
### Docker Hub 镜像
|
||||
|
||||
Cloudflare support is provided through OpenNext.
|
||||
```bash
|
||||
docker pull kuekhaoyang/kvideo:latest
|
||||
docker run -d -p 3000:3000 --name kvideo kuekhaoyang/kvideo:latest
|
||||
```
|
||||
|
||||
Commands:
|
||||
### 完整功能与受限功能的边界
|
||||
|
||||
**完整能力路径:**
|
||||
|
||||
- 自托管 Node.js
|
||||
- Docker
|
||||
|
||||
**受限托管路径:**
|
||||
|
||||
- Vercel
|
||||
- Cloudflare 托管运行时
|
||||
- Cloudflare Workers via OpenNext
|
||||
|
||||
这些托管路径默认会进入合规限制模式:
|
||||
|
||||
- 关闭外部媒体代理
|
||||
- 关闭热链转发
|
||||
- 关闭 IPTV 流中继
|
||||
|
||||
如果你需要 `/api/proxy`、IPTV 中继、自定义 `User-Agent` / `Referer` 转发等完整能力,就不要继续拿受限托管环境硬扛,直接换 Docker 或传统 Node.js 自托管。
|
||||
|
||||
### Cloudflare 路径
|
||||
|
||||
当前主要支持路径是 **Cloudflare Workers via OpenNext**:
|
||||
|
||||
```bash
|
||||
npm run cf:build
|
||||
npm run cf:preview
|
||||
```
|
||||
|
||||
Important:
|
||||
`npm run pages:build` 仍然保留,但只是给现存兼容链路兜底的遗留构建脚本,不是这条分支主张的 Cloudflare 主路径。
|
||||
|
||||
- use Workers/OpenNext, not Cloudflare Pages direct upload
|
||||
- managed Cloudflare/Vercel deployments run in restricted mode in this codebase
|
||||
- restricted mode disables external media relay and IPTV relay on those managed platforms
|
||||
### Android TV APK
|
||||
|
||||
## Security Defaults
|
||||
仓库内提供轻量 Android TV WebView 壳工程,位于 `android-tv/`。
|
||||
|
||||
This project no longer behaves like a public generic fetch service.
|
||||
|
||||
- Only `http` and `https` outbound targets are allowed.
|
||||
- Loopback, private, link-local, metadata, and reserved ranges are blocked by default.
|
||||
- Hostnames are resolved before fetch, and redirects into blocked ranges are rejected.
|
||||
- Relay endpoints do not forward cookies or spoof client IP / origin / referer headers.
|
||||
- Public relay access is disabled unless explicitly enabled.
|
||||
- `AUTH_SECRET` is required whenever auth is enabled.
|
||||
- Login failures are throttled and can return `429` with `Retry-After`.
|
||||
|
||||
## Environment Variables
|
||||
|
||||
Core auth and access:
|
||||
|
||||
| Variable | Required | Notes |
|
||||
| --- | --- | --- |
|
||||
| `AUTH_SECRET` | Required when auth is enabled | Session signing secret. Missing secret disables authenticated relay/account flows. |
|
||||
| `ADMIN_PASSWORD` | Optional | Legacy/admin bootstrap password. |
|
||||
| `ACCESS_PASSWORD` | Optional | Legacy compatibility alias for `ADMIN_PASSWORD`. |
|
||||
| `ACCOUNTS` | Optional | Bootstrap account list. Supports legacy and username-based formats. |
|
||||
| `PREMIUM_PASSWORD` | Optional | Separate password for `/premium`. |
|
||||
|
||||
Relay and outbound policy:
|
||||
|
||||
| Variable | Required | Notes |
|
||||
| --- | --- | --- |
|
||||
| `KVIDEO_PUBLIC_RELAY_ENABLED` | Optional | Defaults to disabled. Public unauthenticated relay stays off unless set to `true`. |
|
||||
| `KVIDEO_OUTBOUND_PRIVATE_HOST_ALLOWLIST` | Optional | Comma-separated allowlist for intentional LAN/private targets. Server-only. |
|
||||
|
||||
Redis / managed auth / sync:
|
||||
|
||||
| Variable | Required | Notes |
|
||||
| --- | --- | --- |
|
||||
| `UPSTASH_REDIS_REST_URL` | Optional | Enables managed accounts and sync features when paired with token. |
|
||||
| `UPSTASH_REDIS_REST_TOKEN` | Optional | Enables managed accounts and sync features when paired with URL. |
|
||||
|
||||
Player integrations:
|
||||
|
||||
| Variable | Required | Notes |
|
||||
| --- | --- | --- |
|
||||
| `DANMAKU_API_URL` | Optional | Server-side default Danmaku API URL. |
|
||||
| `NEXT_PUBLIC_DANMAKU_API_URL` | Optional | Client-visible default Danmaku API URL. |
|
||||
| `VIDEOTOGETHER_ENABLED` | Optional | Defaults to disabled unless explicitly set to `true`. |
|
||||
| `VIDEOTOGETHER_SCRIPT_URL` | Required when `VIDEOTOGETHER_ENABLED=true` | Must be an explicit HTTPS URL. No `@latest` default is used anymore. |
|
||||
| `VIDEOTOGETHER_SETTING_URL` | Optional | Explicit settings page URL for the VideoTogether integration. |
|
||||
|
||||
## Runtime Behavior Changes
|
||||
|
||||
- `/api/proxy` and related relay routes now reject unsafe targets with 4xx responses.
|
||||
- `/api/auth` may return `429` after repeated failed login attempts.
|
||||
- `/api/user/config` and `/api/user/sync` silently no-op when Redis is absent.
|
||||
- `clear all data` now also calls `DELETE /api/auth/session` and removes the httpOnly session.
|
||||
|
||||
## Offline / PWA Scope
|
||||
|
||||
Offline support is intentionally narrow.
|
||||
|
||||
- cached: same-origin shell and static assets
|
||||
- fallback: navigation fallback to [`public/offline.html`](/Users/haoyangkuek/development/KVideo/public/offline.html)
|
||||
- not cached for offline playback: remote media, proxy responses, IPTV streams, API data
|
||||
|
||||
## Android TV
|
||||
|
||||
The Android wrapper is TV-only.
|
||||
|
||||
- no standard phone launcher entry
|
||||
- release behavior enforces HTTPS
|
||||
- mixed content is disabled
|
||||
- WebView navigation is restricted to the configured app origin
|
||||
- the remaining JavaScript bridge is only for PiP-related behavior
|
||||
|
||||
Build commands:
|
||||
构建命令:
|
||||
|
||||
```bash
|
||||
cd android-tv
|
||||
./gradlew --no-daemon lint test assembleDebug assembleRelease
|
||||
./gradlew --no-daemon assembleDebug
|
||||
```
|
||||
|
||||
## Development
|
||||
|
||||
Install dependencies:
|
||||
如需在构建时预置默认地址:
|
||||
|
||||
```bash
|
||||
npm install
|
||||
cd android-tv
|
||||
./gradlew --no-daemon assembleDebug -PkvideoUrl="https://your-kvideo-instance.com"
|
||||
```
|
||||
|
||||
Useful commands:
|
||||
GitHub Actions 中的 `Android TV APK` 工作流支持手动触发并发布 APK 资产。
|
||||
|
||||
## PWA 与离线边界
|
||||
|
||||
当前离线支持是 **有限壳缓存**,不是完整离线播放器。
|
||||
|
||||
已缓存:
|
||||
|
||||
- `/`
|
||||
- `offline.html`
|
||||
- `manifest.json`
|
||||
- 图标与同源静态资源
|
||||
|
||||
不会离线缓存:
|
||||
|
||||
- 远程媒体
|
||||
- 代理响应
|
||||
- IPTV 直播流
|
||||
- API 数据
|
||||
|
||||
离线失败时会回退到 `public/offline.html`。
|
||||
|
||||
## Apple TV
|
||||
|
||||
Apple TV 在当前仓库中 **不支持**。
|
||||
|
||||
- 旧的 tvOS WebView 壳路径已经被移除
|
||||
- 仓库内没有完整、受支持、可直接构建的 tvOS 产品链路
|
||||
- 如需在 Apple 生态的大屏上使用,请改用浏览器、AirPlay 或其他已支持设备投屏
|
||||
|
||||
补充说明见 [`apple-tv/README.md`](apple-tv/README.md)。
|
||||
|
||||
## 常用命令
|
||||
|
||||
```bash
|
||||
npm run dev
|
||||
npm run lint
|
||||
npm test
|
||||
npm run test:e2e
|
||||
@@ -173,22 +444,49 @@ docker build -t kvideo .
|
||||
cd android-tv && ./gradlew --no-daemon lint test assembleDebug assembleRelease
|
||||
```
|
||||
|
||||
## CI Gates
|
||||
## 开发与贡献
|
||||
|
||||
This repo is expected to stay green on:
|
||||
提交代码前,至少运行与你改动范围匹配的检查。对较广泛的改动,建议覆盖以下矩阵:
|
||||
|
||||
- ESLint
|
||||
- Node unit tests
|
||||
- Playwright smoke tests
|
||||
- Next.js production build
|
||||
- OpenNext / Workers build
|
||||
- `npm audit --omit=dev`
|
||||
- `npm run lint`
|
||||
- `npm test`
|
||||
- `npm run build`
|
||||
- `npm run cf:build`
|
||||
- `docker compose config`
|
||||
- Docker image build
|
||||
- Android TV lint / test / debug / release builds
|
||||
- `docker build -t kvideo .`
|
||||
- `cd android-tv && ./gradlew --no-daemon lint test assembleDebug assembleRelease`
|
||||
|
||||
## Repository Notes
|
||||
更多开发约束见 [CONTRIBUTING.md](CONTRIBUTING.md)。
|
||||
|
||||
- `npm start` runs the standalone Next.js server output.
|
||||
- `pages:build` remains a legacy `next-on-pages` compatibility build for existing Cloudflare Pages Git projects.
|
||||
- The old Apple TV sample app has been removed from the supported product path on purpose.
|
||||
## 版本与更新
|
||||
|
||||
- 当前版本:[`4.9.3`](CHANGELOG.md)
|
||||
- 更新日志:[`CHANGELOG.md`](CHANGELOG.md)
|
||||
- 应用内“版本与更新”卡片使用仓库内的 `app-release.json` 元数据
|
||||
|
||||
## 许可证
|
||||
|
||||
本项目基于 [MIT 许可证](LICENSE) 开源。
|
||||
|
||||
## 致谢
|
||||
|
||||
感谢以下开源项目:
|
||||
|
||||
- [Next.js](https://nextjs.org/)
|
||||
- [React](https://react.dev/)
|
||||
- [Tailwind CSS](https://tailwindcss.com/)
|
||||
- [Zustand](https://github.com/pmndrs/zustand)
|
||||
- [hls.js](https://github.com/video-dev/hls.js/)
|
||||
- [Lucide](https://lucide.dev/)
|
||||
- [dnd-kit](https://dndkit.com/)
|
||||
- [OpenNext](https://opennext.js.org/)
|
||||
|
||||
## 联系方式
|
||||
|
||||
- 作者:[KuekHaoYang](https://github.com/KuekHaoYang)
|
||||
- 项目主页:[KuekHaoYang/KVideo](https://github.com/KuekHaoYang/KVideo)
|
||||
- 问题反馈:[GitHub Issues](https://github.com/KuekHaoYang/KVideo/issues)
|
||||
|
||||
## Star History
|
||||
|
||||
[](https://www.star-history.com/#KuekHaoYang/KVideo&type=date&legend=top-left)
|
||||
|
||||
+12
-1
@@ -4,8 +4,19 @@
|
||||
"name": "KVideo",
|
||||
"branch": "main"
|
||||
},
|
||||
"currentVersion": "4.9.2",
|
||||
"currentVersion": "4.9.3",
|
||||
"releases": [
|
||||
{
|
||||
"version": "4.9.3",
|
||||
"publishedAt": "2026-04-15",
|
||||
"title": "托管账户模式与线路列表修复",
|
||||
"notes": [
|
||||
"新增 Redis 托管账户模式:支持用户名密码登录、超级管理员账户 CRUD、权限编辑和密码重置。",
|
||||
"认证改为服务端签名 HTTP-only 会话 Cookie,/api/user/config 与 /api/user/sync 不再信任客户端自报 profileId。",
|
||||
"播放页线路列表补齐剩余问题:分辨率探测会按当前集数探测并缓存,打开线路列表时会自动定位当前线路,必要时自动展开隐藏项。",
|
||||
"补充了与新认证和线路列表逻辑对应的单元测试,并修正了本地 eslint 版本与 Next.js 规则链不兼容的问题。"
|
||||
]
|
||||
},
|
||||
{
|
||||
"version": "4.9.2",
|
||||
"publishedAt": "2026-04-12",
|
||||
|
||||
Generated
+2
-2
@@ -1,12 +1,12 @@
|
||||
{
|
||||
"name": "kvideo",
|
||||
"version": "4.9.2",
|
||||
"version": "4.9.3",
|
||||
"lockfileVersion": 2,
|
||||
"requires": true,
|
||||
"packages": {
|
||||
"": {
|
||||
"name": "kvideo",
|
||||
"version": "4.9.2",
|
||||
"version": "4.9.3",
|
||||
"dependencies": {
|
||||
"@dnd-kit/core": "^6.3.1",
|
||||
"@dnd-kit/sortable": "^10.0.0",
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "kvideo",
|
||||
"version": "4.9.2",
|
||||
"version": "4.9.3",
|
||||
"private": true,
|
||||
"scripts": {
|
||||
"dev": "next dev --port ${PORT:-3000}",
|
||||
|
||||
Reference in New Issue
Block a user