diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml new file mode 100644 index 0000000..a043a52 --- /dev/null +++ b/.github/workflows/ci.yml @@ -0,0 +1,73 @@ +name: CI/CD Pipeline + +on: + push: + branches: [ "main", "master" ] + pull_request: + branches: [ "main", "master" ] + +jobs: + build-and-lint: + runs-on: ubuntu-latest + + steps: + - name: Checkout Repository + uses: actions/checkout@v4 + + - name: Setup Node.js + uses: actions/setup-node@v4 + with: + node-version: 22 + + - name: Setup pnpm + uses: pnpm/action-setup@v3 + with: + version: 9 + run_install: false + + - name: Get pnpm store directory + shell: bash + run: | + echo "STORE_PATH=$(pnpm store path --silent)" >> $GITHUB_ENV + + - name: Setup pnpm cache + uses: actions/cache@v4 + with: + path: ${{ env.STORE_PATH }} + key: ${{ runner.os }}-pnpm-store-${{ hashFiles('**/pnpm-lock.yaml') }} + restore-keys: | + ${{ runner.os }}-pnpm-store- + + - name: Install dependencies + run: pnpm install --frozen-lockfile + + - name: Run Linter + run: pnpm run lint + + - name: Build Next.js App + run: pnpm run build + env: + # 如果构建时需要避免由于缺少环境变量导致的验证错误,可以在此添加 mock 环境变量 + NEXT_TELEMETRY_DISABLED: 1 + + docker-build: + needs: build-and-lint + runs-on: ubuntu-latest + # 仅在推送到主分支时测试构建 Docker 镜像 + if: github.event_name == 'push' && (github.ref == 'refs/heads/main' || github.ref == 'refs/heads/master') + + steps: + - name: Checkout Repository + uses: actions/checkout@v4 + + - name: Set up Docker Buildx + uses: docker/setup-buildx-action@v3 + + - name: Build Docker Image + uses: docker/build-push-action@v5 + with: + context: . + push: false # 改为 true 并且添加 Docker Hub 登录步骤以推送到镜像仓库 + tags: aounapp:latest + cache-from: type=gha + cache-to: type=gha,mode=max diff --git a/README.md b/README.md index 7bfe951..a48bbc7 100644 --- a/README.md +++ b/README.md @@ -1,15 +1,17 @@ -# AounApp - 个人资源付费系统 +# SHUMOX - 个人资源付费系统 这是一个基于 Next.js 全栈开发的个人资源付费与会员系统。支持文章/资源发布、会员订阅、积分充值、以及支付宝/微信支付集成。 ## 🛠 技术栈 (Tech Stack) ### 核心框架 + - **Framework**: [Next.js 16](https://nextjs.org/) (Pages Router) - **Language**: [TypeScript](https://www.typescriptlang.org/) - **Database**: [MongoDB](https://www.mongodb.com/) (via [Mongoose](https://mongoosejs.com/)) ### 前端 UI & 交互 + - **UI Library**: [Shadcn UI](https://ui.shadcn.com/) (基于 Radix UI) - **Styling**: [Tailwind CSS v4](https://tailwindcss.com/) - **Icons**: [Lucide React](https://lucide.dev/) @@ -18,11 +20,12 @@ - **Editor**: [Tiptap](https://tiptap.dev/) (Headless 富文本编辑器) ### 后端 & 工具 + - **Authentication**: JWT (JSON Web Tokens) - 自定义实现,存储于 HttpOnly Cookie - **Payment**: Native Alipay Integration (Node.js `crypto` 实现,无第三方 SDK 依赖) -- **Markdown Processing**: - - `unified`, `remark`, `rehype` (服务端处理) - - `shiki` (代码高亮) +- **Markdown Processing**: + - `unified`, `remark`, `rehype` (服务端处理) + - `shiki` (代码高亮) - **Date Handling**: `date-fns` ## ✨ 核心功能 (Key Features) @@ -40,8 +43,8 @@ 3. **会员与支付** - **会员订阅**:不同等级会员享受不同折扣和每日下载限制。 - **支付集成**: - - **支付宝**:原生集成,支持当面付/电脑网站支付(根据配置)。 - - **积分支付**:站内虚拟货币支付。 + - **支付宝**:原生集成,支持当面付/电脑网站支付(根据配置)。 + - **积分支付**:站内虚拟货币支付。 - **订单系统**:完整的订单创建、支付回调、状态流转。 4. **管理后台 (Admin)** @@ -52,28 +55,33 @@ ## ⚠️ 关键架构与注意事项 (Architecture & Notes) ### 1. Markdown 渲染架构 -* **服务端渲染 (SSR)**:为了解决 `rehype-pretty-code` 在客户端运行时的兼容性问题,并将繁重的 Markdown 解析逻辑移出前端 bundle,我们采用了**服务端预处理**方案。 -* **流程**: - 1. API (`/api/articles/[id]`) 接收请求。 - 2. 后端读取 Markdown 内容,使用 `unified` + `remark` + `rehype` + `shiki` 转换为 HTML。 - 3. API 返回预渲染好的 HTML 字符串。 - 4. 前端 (`pages/article/[id].tsx`) 使用 `dangerouslySetInnerHTML` 直接渲染。 + +- **服务端渲染 (SSR)**:为了解决 `rehype-pretty-code` 在客户端运行时的兼容性问题,并将繁重的 Markdown 解析逻辑移出前端 bundle,我们采用了**服务端预处理**方案。 +- **流程**: + 1. API (`/api/articles/[id]`) 接收请求。 + 2. 后端读取 Markdown 内容,使用 `unified` + `remark` + `rehype` + `shiki` 转换为 HTML。 + 3. API 返回预渲染好的 HTML 字符串。 + 4. 前端 (`pages/article/[id].tsx`) 使用 `dangerouslySetInnerHTML` 直接渲染。 ### 2. 编辑器 (Tiptap) -* **SSR 兼容性**:Tiptap 在 Next.js 中使用时,必须在 `useEditor` 中设置 `immediatelyRender: false`,以避免服务端渲染与客户端水合不匹配 (Hydration Mismatch) 导致的运行时错误。 -* **Markdown 支持**:集成了 `tiptap-markdown` 扩展,确保编辑器内容可以作为 Markdown 格式保存到数据库,保持数据格式的通用性。 + +- **SSR 兼容性**:Tiptap 在 Next.js 中使用时,必须在 `useEditor` 中设置 `immediatelyRender: false`,以避免服务端渲染与客户端水合不匹配 (Hydration Mismatch) 导致的运行时错误。 +- **Markdown 支持**:集成了 `tiptap-markdown` 扩展,确保编辑器内容可以作为 Markdown 格式保存到数据库,保持数据格式的通用性。 ### 3. 支付系统 -* **去 SDK 化**:为了避免 `alipay-sdk` 等库的潜在依赖问题和体积,我们使用 Node.js 原生 `crypto` 模块实现了支付宝的签名和验签逻辑 (`src/lib/alipay.ts`)。 -* **安全性**:支付回调 (`notify`) 必须严格验证签名,防止伪造请求。 + +- **去 SDK 化**:为了避免 `alipay-sdk` 等库的潜在依赖问题和体积,我们使用 Node.js 原生 `crypto` 模块实现了支付宝的签名和验签逻辑 (`src/lib/alipay.ts`)。 +- **安全性**:支付回调 (`notify`) 必须严格验证签名,防止伪造请求。 ### 4. 样式系统 -* **Tailwind v4**:项目配置了 Tailwind CSS v4。 -* **Typography**:使用了 `@tailwindcss/typography` 插件来美化文章详情页的 HTML 内容渲染 (`prose` 类)。 + +- **Tailwind v4**:项目配置了 Tailwind CSS v4。 +- **Typography**:使用了 `@tailwindcss/typography` 插件来美化文章详情页的 HTML 内容渲染 (`prose` 类)。 ## 🚀 快速开始 (Getting Started) 1. **安装依赖** + ```bash pnpm install ``` @@ -82,6 +90,7 @@ 复制 `.env.example` 到 `.env.local` 并填入 MongoDB URI 和 JWT Secret 等信息。 3. **运行开发服务器** + ```bash pnpm run dev ```