flnxi-Wu/README.md
2026-06-03 18:41:52 +08:00

253 lines
13 KiB
Markdown
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# FLNXI 素材库
本仓库是 `FLNXI 素材库` 的当前主项目,不是旧版素材站,也不是单独的模板系统示例。项目目标是面向企业/团队做私有化交付,默认部署在 NAS 或 Linux 服务器上,通过浏览器给普通用户使用。
## 1. 项目定位
当前项目核心目标:
- 素材上传、检索、预览、下载、分享
- 模板化元数据和动态筛选
- 用户、部门、邀请和后台管理
- 许可证激活、校验、免费版 / 付费版限制
- 系统初始化、外观设置、对象存储配置
- Docker / NAS / Linux 私有化交付
一句话:这是一个可安装、可授权、可交付、可维护的私有化素材管理产品。
## 2. 仓库组成
```text
.
├── app/ # 主应用页面和 API(Next.js App Router)
├── components/ # 主应用 React 组件
├── hooks/ # 主应用前端 Hook
├── lib/ # 主应用核心逻辑、授权、S3、认证、模板等
├── prisma/ # 主应用 Prisma schema 与 seed
├── public/ # 主应用静态资源
├── scripts/ # 构建、迁移、修复、部署辅助脚本
├── docs/ # 当前项目文档入口
├── license-server/ # 独立许可证服务
├── premium-modules/ # 付费模块镜像源码
├── flnxi-agent/ # Node 版安装与运维 Agent
└── flnxi-agent-go/ # Go 版安装与运维 Agent
```
当前主应用是核心产品;`license-server/` 和两个 Agent 是私有化交付链路的一部分,不属于普通用户日常使用入口。
## 3. 当前主应用能力
已在当前项目中存在的能力:
- 素材上传、搜索、预览、下载、分享、收藏、点赞
- 上传模板、字段配置、字段池、首页动态筛选
- 用户注册、登录、个人资料、个人素材、浏览历史
- 部门、邀请、角色、管理员后台
- 授权激活、许可证校验、心跳、免费版限制
- 系统初始化、系统设置、Logo / 外观设置、完整性检查
- 图片、PSD、音频、视频相关处理能力
- 钉钉登录、AI 聊天 / AI 编辑相关接口
注意:钉钉、AI、许可证服务等能力依赖环境变量和外部服务配置;代码存在不等于部署后默认可用。
## 4. 参考源码目录
当前实际存在的参考源码目录:
```text
gongxiangp2-source-reference-old-style-20260513-132942/
```
它是其他版本素材库源码,只用于查实现和做功能对比,不属于当前主项目,不参与构建、测试和提交。
历史上出现过的参考目录名也保留在排除配置中,避免后续重新放回时被工具链误扫:
- `gongxiangp2-source-reference-20260309-202917/`
- `gongxiangp2-source-reference-20260413-172354/`
- `gongxiangp2-source-reference-old-style-20260513-132942/`
参考源码的当前功能吸收结论见:
- `docs/参考源码功能吸收整理_20260513.md`
## 5. 技术栈
主应用:
- Next.js 14
- React 18
- TypeScript
- Prisma 5
- PostgreSQL
- MinIO / S3 兼容对象存储
- NextAuth
- Tailwind CSS
- Jest + React Testing Library
许可证服务:
- Next.js 14
- Prisma
- PostgreSQL
安装 Agent:
- `flnxi-agent/`:Node.js / Express / Socket.IO
- `flnxi-agent-go/`:Go / Gin / Docker SDK
Agent 是实施和运维编排工具,不是普通客户日常入口,也不是当前唯一正式安装器。正式客户首装仍以 `docker-compose.prod.yml + .env` 为主;NAS / Linux 现场优先用 `scripts/customer-install.sh` / `scripts/smoke-install.sh` 做检查和验收,Windows 实施机可用对应 `.ps1` 脚本。Agent 只在交付方案明确采用时启用。
## 6. 本地开发
### 安装依赖
```bash
npm install
```
### 配置环境变量
```bash
cp .env.example .env
```
至少需要确认。下面只表示变量形状,不要把示例占位值用于客户环境:
```env
NEXTAUTH_SECRET=<generate-a-strong-random-secret>
APP_PUBLIC_URL=http://localhost:3000
NEXTAUTH_URL=http://localhost:3000
S3_ENDPOINT=http://localhost:9000
S3_BUCKET=flnxi-materials
S3_ACCESS_KEY_ID=<object-storage-access-key>
S3_SECRET_ACCESS_KEY=<object-storage-secret-key>
LICENSE_SERVER_URL=https://your-license-server.example.com
LICENSE_PROJECT_CODE=flnxi-sucai
LICENSE_REQUEST_SIGNING_SECRET=<same-secret-as-license-server>
LICENSE_PUBLIC_KEY=<license-server-rsa-public-key>
LOCAL_ENCRYPTION_KEY=<generate-a-32-char-or-longer-local-key>
```
内置 PostgreSQL 部署时 `DATABASE_URL` 留空,由 Compose 自动指向内置数据库;只有外部 PostgreSQL 才填写真实连接串。`LICENSE_PROJECT_CODE` 和 `LICENSE_REQUEST_SIGNING_SECRET` 必须和 `license-server` 中的项目配置一致。
授权模块采用“免费基础镜像 + 统一 `paid-core` 付费增强包”的分工。FREE 不拉取模块,人数/素材数上限由基础镜像读取本地已验签许可证执行;STANDARD/PRO 才会从镜像站拉取 `paid-core`,验证服务器只负责发签名模块清单、实例凭证和短期拉包 token。部署 `license-server` 时还要确认 `MODULE_PULL_TOKEN_SECRET`、`PREMIUM_MODULE_REGISTRY_BASE`、`PREMIUM_MODULE_PAID_CORE_IMAGE`、模块版本和模块 digest 指向当前可用镜像站。
当前模块源码入口是 `premium-modules/paid-core`,模块镜像通过 `deploy-registry.ps1 -Action PublishPremiumModule -PremiumModuleId paid-core` 发布,发布后把脚本输出的 `PREMIUM_MODULE_PAID_CORE_IMAGE`、`_TAG` 和 `_DIGEST` 写入 `license-server`。主应用现在不仅检查许可证和模块授权凭证,还会要求 `paid-core` 处于 `running`、模块 `/health` 正常,并通过 `paid-core` 的 `/authorize` 放行自定义模板、部门隔离、系统设置、内网穿透、API 访问等付费能力;自定义模板字段保存前校验/格式化、模板保存请求整体标准化、模板删除前使用中拦截规划、素材提交的自定义字段内容校验、素材 metadata 准备和大小检查、已有素材模板的结构变更风险判断、公开模板展示投影、模板字段填写率统计、素材列表搜索/筛选查询计划、素材列表自定义字段搜索规划、首页自定义筛选字段统计规划、部门隔离范围规划、部门结构创建/重命名/删除联动计划、API 访问运行门禁、模板迁移目标字段投影、兼容性判断、metadata 准备、旧字段备份计算、迁移批次规划、迁移预览和备份字段影响统计已迁入 `paid-core`。其中 `/templates/normalize-save` 负责创建/更新模板前的名称、状态、素材类型、素材大类、字段组、展示配置和字段列表标准化,`/templates/plan-delete` 负责删除模板前按使用素材数量生成放行或拦截计划,`/materials/validate-template-fields` 负责上传/编辑素材时的自定义字段可见性、必填和规则校验,`/materials/prepare-metadata` 负责自定义字段写入 metadata 前的整理、压缩和大小检查,`/templates/plan-migration-batch` 负责迁移批次大小、安全确认、预览模式和分批执行规划,`/templates/prepare-migration-metadata` 负责迁移时从旧素材字段中选出目标模板字段、判断目标模板必填字段是否可自动补齐、生成目标 metadata、计算丢弃字段备份并拦截超限,`/templates/build-migration-preview` 负责迁移预览、备份字段影响统计和样例生成,`/templates/project-public-options` 负责公开模板列表、上传页模板列表和素材类型 tag 的展示投影,`/templates/calculate-field-stats` 负责后台模板详情里的字段填写率和低填写率字段统计,`/materials/plan-list-query` 负责素材列表搜索字段、自定义字段搜索、首页筛选字段和 metadata 筛选的查询计划,`/materials/plan-custom-search` 负责把可搜索字段快照转换成素材列表应查询的自定义字段 key,`/materials/plan-home-filter-fields` 负责把首页筛选字段快照转换成标准列或 metadata 统计来源计划,`/departments/plan-scope` 负责计算部门管理员的可管理部门范围和单个目标部门是否在范围内,`/departments/plan-structure-change` 负责部门创建、重命名、删除时的部门和用户联动计划。注意:`paid-core` 的边界是承接付费能力的规则、计划、校验和展示投影;主程序继续保留登录、权限、Prisma 查询、SQL 执行、数据库事务和最终写入。这是当前商业化安全边界,不表示付费功能没有拆分完成,也不能表述为所有业务执行都离开主程序。
许可证和授权模块不是“客户每次使用都实时联网验证”。联网主要发生在激活、续期心跳、授权变更同步、短期拉包 token 获取、模块镜像拉取和版本升级时;日常上传、创建用户、模板使用等动作优先依赖本地已验签许可证缓存、已缓存的模块授权凭证和本机正在运行的授权模块。也就是说,客户现场短时间断网不应影响已经授权且本地模块正常运行的日常使用,但许可证过期、授权被吊销、需要拉取新模块或升级时仍需要重新连验证服务器。
### 初始化 Prisma
```bash
npm run prisma:generate
npm run prisma:push
```
### 启动主应用
```bash
npm run dev
```
默认访问:
```text
http://localhost:3000
```
## 7. 系统初始化
常规激活流程会自动完成系统初始化。
如果是在尚未有管理员账号的环境里手动初始化,需要先配置 `SYSTEM_INIT_TOKEN`,再调用:
```bash
curl -X POST http://localhost:3000/api/system/init \
-H "x-system-init-token: your-init-token"
```
如果没有提供 `INIT_ADMIN_PASSWORD`,系统会生成一次性初始密码,并且首次登录后强制修改。项目不再内置固定的 `admin@flnxi.com / 88888888`。
## 8. 常用命令
```bash
# 主应用
npm run dev
npm run build
npm start
npm run lint
npm run type-check
npm test
# Prisma
npm run prisma:generate
npm run prisma:push
npm run prisma:validate
npm run prisma:studio
# 模板数据迁移 / 校验
npm run migrate:template-data
npm run verify:template-data
```
## 9. 部署入口
当前主应用生产编排:
```bash
docker compose -f docker-compose.prod.yml up -d
```
`docker-compose.prod.yml` 当前会拉起:
- PostgreSQL
- MinIO
- MinIO 初始化容器
- 主应用容器
主应用镜像通过当前 Registry 发布流程生成和推送,镜像名、容器名、卷名、网络名和端口可通过 `.env` 覆盖,例如 `APP_IMAGE`、`APP_PORT`、`APP_CONTAINER_NAME`。
它不会直接拉起 Nginx / Traefik、独立许可证服务或 Agent。不同 NAS / Linux 现场的反向代理、域名、证书、许可证服务地址,需要按部署文档和实际环境配置。
内部维护环境仍保留:
- `deploy-registry.ps1`
- `scripts/customer-install.sh`
- `scripts/smoke-install.sh`
- `scripts/backup-restore.sh`
- `scripts/customer-acceptance-smoke.mjs`
- `scripts/customer-install.ps1`
- `scripts/smoke-install.ps1`
- `scripts/backup-restore.ps1`
- `scripts/measure-image-size.ps1`
- `deploy-new-fixed.ps1`
- `发布管理.ps1`
- `license-server/deploy.ps1`
其中 `scripts/customer-install.sh` 是 NAS / Linux 客户首装分步骤入口,内部调用 `scripts/smoke-install.sh` 做预检、启动和验收;`scripts/backup-restore.sh` 用于 NAS / Linux 客户环境备份、恢复和恢复后验收;`scripts/customer-acceptance-smoke.mjs` 用于客户业务验收,可只读检查,也可用临时测试账号执行一次真实小素材上传;`.ps1` 版本用于 Windows 实施机或已安装 PowerShell 的现场;`scripts/measure-image-size.ps1` 用于发布前记录镜像体积和分层,也可以设置体积/层数阈值,超限时阻止发布继续。其它脚本执行前必须先读内容和参数,不应把内部固定服务器或固定镜像仓库当成客户默认交付配置。客户交付时要显式写入版本化 `APP_IMAGE` / `IMAGE_TAG`,`latest` 只保留给内部测试或兼容场景。当前新 Registry 发布脚本是主线,旧远程部署脚本只作历史或内部维护参考。AI、钉钉、内网穿透等可选能力依赖真实外部服务和密钥,不能只凭页面入口当成客户验收已完成。
## 10. 文档入口
主入口优先看:
- `docs/README.md`
- `docs/deployment/部署说明.md`
- `docs/deployment/多品牌 NAS 与 Linux 交付差异清单.md`
- `docs/初次部署与出厂设置指南.md`
- `docs/许可证服务接入说明.md`
- `docs/参考源码功能吸收整理_20260513.md`
- `scripts/README.md`
需要追排障、历史收口或版本差异时,再看:
- `docs/客户首装升级坑位排查_20260530.md`
- `docs/商业化地基8项收口记录_20260530.md`
- `docs/商业化地基排查问题清单_20260524.md`
- `docs/许可证链路安全评估_20260312.md`
原则:
- 当前项目事实以当前代码、配置、部署文件和主入口文档为准。
- 阶段记录、旧排障报告、旧交接文档和历史总结不作为默认事实来源。
- 参考源码只用于查思路和做功能吸收判断,不直接参与当前项目运行链路。