# 02-项目程序开发详细步骤 ## 1. 开发原则 1. 先完整对标 `doc/index.html`,再做工程化拆分。 2. 每一轮开发只领取 `04-任务矩阵.md` 中明确编号的任务,避免重复做。 3. 每一轮必须同步更新: - `03-推进台账.md` - `04-任务矩阵.md` - `05-验收证据.md` - 必要时更新 `06-决策记录.md` 4. 涉及移民、法律、隐私、退款、attorney referral、表单收集的内容,必须留有验收证据和确认记录。 5. 不把明文服务器密码写入长期文档;部署凭据用 SSH key、环境变量或受控密钥库。 ## 2. 当前基线复现 目标:确认 `doc/index.html` 当前 mockup 可回溯、可打开、可作为工程化基准。 步骤: 1. 进入项目目录: ```bash cd /home/mes123456/MeetPaprika ``` 2. 确认文件存在: ```bash test -f doc/index.html && wc -l doc/index.html ``` 3. 检查当前页面路由和脚本入口: ```bash rg -n "pageData|URLSearchParams|data-page|page=start|page=ask|page=terms|page=privacy|page=disclaimer" doc/index.html ``` 4. 浏览器打开以下页面并记录截图: - `doc/index.html?page=home` - `doc/index.html?page=press` - `doc/index.html?page=judging` - `doc/index.html?page=scholarly` - `doc/index.html?page=services` - `doc/index.html?page=why` - `doc/index.html?page=resources` - `doc/index.html?page=faq` - `doc/index.html?page=start` - `doc/index.html?page=ask` - `doc/index.html?page=terms` - `doc/index.html?page=privacy` - `doc/index.html?page=disclaimer` 验收标准: - 所有公开路由能渲染。 - 未识别 `?page=unknown` 回退 `home`。 - 顶部导航 active 状态正确。 - Resources 下拉可见且链接正确。 - 证据记录写入 `05-验收证据.md`。 ## 3. 阶段 A:静态 mockup 修复 目标:不引入构建系统,先修复当前单文件中影响体验和转化的明确问题。 任务: 1. 修复 Services 页面 04/05/06 卡片 CTA。 - 已由 `contact` 改为 `start`。 2. 明确 `blog` 和 `about` 是否保留。 - 若保留,加入导航或 footer。 - 若不保留,记录为隐藏路由。 3. 检查 legal 页面日期。 - 已由 `July 10, 2026` 改为 `July 6, 2026`。 - 当前工作日期为 `2026-07-06`。 4. 检查首页、Press、Judging、Services、FAQ、Legal 移动端布局。 5. 补充基础 SEO: - description - canonical - Open Graph - favicon 占位或正式资源 6. 将 mockup 表单明确标注为占位,或进入阶段 B 改为真实表单。 验收标准: - 无明显死链。 - 所有 CTA 指向存在页面。 - 法务日期有明确确认。 - 桌面和移动端核心页面无明显重叠。 - 变更写入台账和证据。 ## 4. 阶段 B:真实表单与线索收集 目标:Start Here 和 Ask a Question 从视觉 mockup 变成真实可提交入口。 ### 推荐字段 Start Here: - name required - email required - linkedin - company_website - current_role_company - field_or_industry - resume_cv optional upload - reason required - existing_recognition - timeline - consent/disclaimer acknowledgement Ask a Question: - name required - email required - linkedin optional - resume_cv optional upload - question required - consent/disclaimer acknowledgement ### 实现路径选项 | 方案 | 适用 | 优点 | 风险 | | --- | --- | --- | --- | | 第三方表单服务 | 快速上线 | 开发少,有后台记录 | 文件上传和隐私策略受限 | | 自建轻量 API | 需要控制数据 | 可控、可扩展 | 需要安全、日志、备份 | | CRM 直连 | 销售流程明确 | 直接进入业务系统 | 依赖第三方 API 和权限 | 建议优先级: 1. 若目标是快速 HTTPS 上线:先接第三方表单或 webhook。 2. 若会收 CV/敏感信息:优先自建 API,加上传限制和访问控制。 3. 若已有 CRM:按 CRM 字段建映射并保留 submission id。 ### 表单验收标准 - 必填字段缺失时不能提交。 - email 格式错误时提示。 - 文件上传明确限制类型和大小。 - 成功后有 submission id 或后台记录 id。 - 失败时显示错误状态,不静默跳转。 - disclaimer 可见:提交不创建 attorney-client relationship。 - 验收证据包含页面截图、提交记录、job_id/report_id/submission id。 ## 5. 阶段 C:Next.js + React + PostgreSQL 工程化 目标:把单文件 mockup 迁移为 Next.js + React 应用,并接入 PostgreSQL,形成可维护、可部署、可验收的正式工程。 ### 5.1 技术架构 - 前端和服务端框架:Next.js + React - 语言:TypeScript - 样式:先使用全局 CSS / CSS Modules 迁移 `doc/index.html` 视觉;不强行引入 UI 框架 - 数据库:PostgreSQL - ORM:Prisma - 表单校验:Zod 或等价 schema 校验 - 部署:Node.js 进程监听 `8082`,Nginx/Caddy 提供 HTTPS 反向代理 - 验收:Playwright 页面截图 + API/数据库写入验证 ### 5.2 初始化工程 当前已完成初始化。保留建议命令供复建参考: ```bash npx create-next-app@latest paprika-site --ts --eslint --app --src-dir=false cd paprika-site npm install prisma @prisma/client zod npx prisma init ``` 本项目已直接在当前根目录工程化,并保留 `doc/index.html` 为对标基线。 ### 5.3 页面迁移 从 `doc/index.html` 迁移为真实路由: | 旧路由 | Next.js 路由 | | --- | --- | | `?page=home` | `/` | | `?page=press` | `/press` | | `?page=judging` | `/judging` | | `?page=scholarly` | `/scholarly` | | `?page=services` | `/services` | | `?page=why` | `/why` | | `?page=resources` | `/resources` | | `?page=faq` | `/faq` | | `?page=start` | `/start` | | `?page=ask` | `/ask` | | `?page=thanks` | `/thanks` | | `?page=terms` | `/terms` | | `?page=privacy` | `/privacy` | | `?page=disclaimer` | `/disclaimer` | 隐藏路由 `blog`、`about` 先不要公开,除非产品确认。 ### 5.4 PostgreSQL 数据模型初稿 建议最小表: ```prisma model Submission { id String @id @default(cuid()) type String name String email String linkedin String? companyWebsite String? currentRoleCompany String? fieldOrIndustry String? reason String? existingRecognition String? timeline String? question String? consentAccepted Boolean @default(false) sourcePath String? status String @default("new") createdAt DateTime @default(now()) updatedAt DateTime @updatedAt files SubmissionFile[] } model SubmissionFile { id String @id @default(cuid()) submissionId String fileName String mimeType String byteSize Int storageKey String createdAt DateTime @default(now()) submission Submission @relation(fields: [submissionId], references: [id]) } ``` 字段说明: - `type`:`start` 或 `ask` - `sourcePath`:提交来源,如 `/start`、`/ask` - `status`:`new`、`reviewed`、`spam`、`archived` - 文件上传未落地前,可以先不创建 `SubmissionFile` 或禁用上传。 ### 5.5 表单 API 建议 API: ```text POST /api/submissions ``` 请求类型: - `type=start` - `type=ask` 验收: - 必填字段缺失返回 400。 - 邮箱格式错误返回 400。 - 成功写入 PostgreSQL 并返回 `submission_id`。 - 前端成功后跳转 `/thanks?submission_id=...` 或展示成功状态。 - 失败时显示明确错误。 ### 5.6 环境变量 `.env` 至少包含: ```bash DATABASE_URL="postgresql://USER:PASSWORD@HOST:5432/paprika" NEXT_PUBLIC_SITE_URL="https://paprikalaw.com" ``` 规则: - `.env` 不提交。 - 服务器凭据和数据库密码不写入 `working` 文档。 - 生产数据库用户只授予应用所需权限。 ### 5.7 服务器 PostgreSQL 验证 用户已确认 PostgreSQL 在服务器 `170.106.192.152` 安装完成。正式接入前需要在服务器上验证: ```bash ssh ubuntu@170.106.192.152 systemctl status postgresql --no-pager psql --version sudo -u postgres psql -c '\l' ``` 建议创建应用数据库和受限应用用户: ```sql CREATE DATABASE paprika; CREATE USER paprika_app WITH ENCRYPTED PASSWORD 'REPLACE_WITH_SECURE_PASSWORD'; GRANT CONNECT ON DATABASE paprika TO paprika_app; ``` 进入数据库后授予 schema 权限: ```sql \c paprika GRANT USAGE, CREATE ON SCHEMA public TO paprika_app; ``` 生产 `DATABASE_URL` 示例: ```bash DATABASE_URL="postgresql://paprika_app:REPLACE_WITH_SECURE_PASSWORD@127.0.0.1:5432/paprika" ``` 注意: - 不使用 SSH 登录密码作为数据库密码。 - 不把数据库密码写入仓库、`working` 文档或聊天后的可复制文档。 - 如果 PostgreSQL 仅供本机 Next.js 使用,优先监听 `127.0.0.1`,不要对公网开放 5432。 ### 5.8 构建和本地验证 ```bash npm install npm run generate:legacy npm run prisma:generate npm run lint npx tsc --noEmit npm run build npm run start -- -p 8082 ``` 本地生产服务冒烟: ```bash for p in / /press /judging /scholarly /services /why /resources /faq /start /ask /thanks /terms /privacy /disclaimer /robots.txt /sitemap.xml; do code=$(curl -s -o /dev/null -w '%{http_code}' http://localhost:8082$p) printf '%s %s\n' "$code" "$p" done ``` 生产数据库迁移: ```bash npx prisma migrate deploy ``` 验收标准: - `npm run dev` 可本地启动。 - `npm run build` 通过。 - `npm run start -- -p 8082` 可在 8082 启动。 - `npx prisma migrate deploy` 可在生产环境执行。 - 核心页面内容、视觉和 CTA 与 `doc/index.html` 对标。 - Start/Ask 提交能写入 PostgreSQL。当前本地未配置 `DATABASE_URL` 时只能验证 400 校验路径和 500 失败路径,不能关闭入库验收。 ## 6. 阶段 D:部署到云服务器 目标:让 `https://paprikalaw.com/` 访问目标站点,内部服务端口使用 `8082`。 ### 服务器信息 - Host:`170.106.192.152` - User:`ubuntu` - 端口范围:`8080-8099` 已开放 - 本项目端口:`8082` - 密码:不写入文档;使用用户交接的临时凭据登录后立即配置 SSH key ### 建议部署结构 ```text /opt/paprika/ current/ releases/ shared/ .env logs/ ``` ### 基础命令模板 ```bash ssh ubuntu@170.106.192.152 sudo mkdir -p /opt/paprika/releases /opt/paprika/shared/logs sudo chown -R ubuntu:ubuntu /opt/paprika ``` ### Next.js 服务示例 构建并启动: ```bash npm ci npm run build npm run start -- -p 8082 ``` 生产建议用 systemd: ```ini [Unit] Description=Paprika static site After=network.target [Service] Type=simple User=ubuntu WorkingDirectory=/opt/paprika/current Environment=NODE_ENV=production EnvironmentFile=/opt/paprika/shared/.env ExecStart=/usr/bin/npm run start -- -p 8082 Restart=always RestartSec=5 [Install] WantedBy=multi-user.target ``` ### Nginx 反向代理示例 ```nginx server { listen 80; server_name paprikalaw.com www.paprikalaw.com; location / { proxy_pass http://127.0.0.1:8082; proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; proxy_set_header X-Forwarded-Proto $scheme; } } ``` HTTPS: ```bash sudo certbot --nginx -d paprikalaw.com -d www.paprikalaw.com ``` 验收标准: - `curl -I http://127.0.0.1:8082` 在服务器上返回 200。 - `curl -I https://paprikalaw.com/` 返回 200。 - `https://paprikalaw.com/`、`/start`、`/faq` 可访问。 - `POST /api/submissions` 能写入 PostgreSQL 并返回 `submission_id`。 - systemd 服务 `active (running)`。 - Nginx 配置通过 `sudo nginx -t`。 - HTTPS 证书有效。 ## 7. 阶段 E:回归验收 目标:上线前后能证明页面、表单、合规、部署都可用。 ### 页面回归 必测页面: - home - press - judging - scholarly - services - why - resources - faq - start - ask - thanks - terms - privacy - disclaimer ### 设备尺寸 - Desktop:1440x900 - Tablet:768x1024 - Mobile:390x844 ### 验收内容 - 页面可访问。 - 首屏品牌和 CTA 可见。 - Header 不遮挡内容。 - 文本无明显重叠。 - CTA 链接可达。 - 表单可提交或明确是 mockup。 - Footer legal 链接可达。 - Legal disclaimer 可见。 ### 证据格式 每次验收写入 `05-验收证据.md`: ```text EV-YYYYMMDD-序号 时间: 任务: 命令/页面: 结果: 证据文件: job_id/report_id/submission_id: 结论: ``` ## 8. 阶段 F:后续产品增强 可选任务: - 增加真实 Contact 页面。 - 增加 Blog/Resources 内容系统。 - 增加案例或证据包示例,但必须避免误导和隐私泄露。 - 增加 analytics,并同步 Privacy Policy。 - 增加 sitemap、robots、structured data。 - 增加 Playwright screenshot regression。 - 增加后台 leads 管理或 CRM 同步。 ## 9. 阶段 G:邮箱系统配置与验证 目标:确认 `mail.paprikalaw.com` 邮件系统可用,管理员和普通公司邮箱能登录、收发和承接网站通知。 ### 9.1 邮箱入口 - 普通用户网页登录:`https://mail.paprikalaw.com/webmail/` - 管理员网页登录:`https://mail.paprikalaw.com/admin/` - 管理员邮箱:`admin@paprikalaw.com` ### 9.2 需要创建或确认的普通邮箱 ```text info@paprikalaw.com contact@paprikalaw.com support@paprikalaw.com sales@paprikalaw.com marketing@paprikalaw.com hr@paprikalaw.com finance@paprikalaw.com billing@paprikalaw.com legal@paprikalaw.com service@paprikalaw.com ``` 凭据规则: - 用户已提供统一初始密码,但不写入长期文档。 - 建议创建后立即为每个邮箱设置独立强密码。 - 如果邮件系统支持,启用首次登录改密、2FA、登录审计和反垃圾策略。 ### 9.3 DNS 和投递验证 需要确认: - `mail.paprikalaw.com` A/AAAA 记录正确。 - `paprikalaw.com` MX 记录指向邮件服务器。 - SPF 记录包含授权发件源。 - DKIM 已生成并加入 DNS。 - DMARC 已配置,至少先从 `p=none` 观察。 - 反向 DNS/PTR 与邮件服务器发信域名匹配。 建议验证: ```bash dig MX paprikalaw.com dig TXT paprikalaw.com dig TXT default._domainkey.paprikalaw.com dig TXT _dmarc.paprikalaw.com ``` ### 9.4 网站表单通知接入 Next.js 表单写入 PostgreSQL 后,可选邮件通知: - 发件邮箱:建议 `support@paprikalaw.com` 或专用 `no-reply@paprikalaw.com` - 收件邮箱:建议 `support@paprikalaw.com`、`contact@paprikalaw.com` - 表单类型: - `/start` 提交通知 - `/ask` 提交通知 - 邮件内容不得包含完整敏感 CV 文件,只发送 submission id 和后台查看提示。 环境变量示例: ```bash SMTP_HOST="mail.paprikalaw.com" SMTP_PORT="587" SMTP_USER="support@paprikalaw.com" SMTP_PASSWORD="REPLACE_WITH_SECURE_PASSWORD" LEADS_NOTIFY_TO="support@paprikalaw.com,contact@paprikalaw.com" ``` 验收标准: - 管理员能登录 admin。 - 10 个普通邮箱能登录 webmail。 - 至少完成一封内部互发、一封外部收信、一封外部发信测试。 - SPF/DKIM/DMARC 检查通过或有明确待处理项。 - 表单邮件通知如启用,必须记录 message id 或测试截图。 ## 10. 每轮工作固定流程 1. 查看 `04-任务矩阵.md`,领取一个或一组任务。 2. 查看相关决策:`06-决策记录.md`。 3. 修改代码或文档。 4. 执行对应验证。 5. 将证据写入 `05-验收证据.md`。 6. 更新任务状态。 7. 在 `03-推进台账.md` 记录: - 本轮做了什么 - 改了哪些文件 - 验证了什么 - 下一步是什么 ## 11. 完全对标核验清单 每次声称“已完全对标 `doc/index.html`”时,至少执行以下核验。 ### 10.1 源文件结构核验 ```bash wc -l doc/index.html rg -n 'function [A-Za-z0-9_]+\(|const [A-Za-z0-9_]+ =|href="\?page=|Last updated|Packages start|@media|--[a-z-]+:' doc/index.html ``` 验收: - 记录 `doc/index.html` 行数。 - 记录 CSS token、断点、路由、CTA、函数、法务日期、价格文案。 ### 10.2 页面和函数映射核验 ```bash rg -n 'pageData|home:|press:|judging:|scholarly:|services:|why:|resources:|faq:|blog:|start:|ask:|thanks:|about:|terms:|privacy:|disclaimer:' doc/index.html rg -n 'function (hero|heroWithKicker|servicesCta|card|pressPage|judgingPage|scholarlyPage|o1CriteriaPage|faqPage|legalTermsPage|legalPrivacyPage|legalDisclaimerPage)' doc/index.html ``` 验收: - `01-项目功能内容.md` 中的路由清单与 `pageData` 保持一致。 - 使用中函数、未调用函数都有记录。 - 隐藏路由 `blog`、`about` 不被误删。 ### 10.3 链接和 CTA 核验 ```bash rg -n 'href="\?page=|card\("' doc/index.html ``` 验收: - Header、footer、hero、services CTA、form mockup、thanks、service card 链接全部登记。 - 不存在的 `contact` 路由历史缺陷必须保留在风险和任务矩阵中;修复后记录验收证据。 ### 10.4 Legal 和 FAQ 核验 ```bash sed -n '2870,3035p' doc/index.html sed -n '3070,3228p' doc/index.html ``` 验收: - FAQ 4 组 20 个问题记录完整。 - Terms、Privacy、Disclaimer section 数量和标题记录完整。 - Terms 缺少 17、legal 日期晚于当前日期、原文语法风险均进入任务矩阵。 ### 10.5 视觉样式核验 ```bash rg -n '^\\s*\\.[A-Za-z0-9_-]+|@media|grid-template-columns|width: min|border-radius|background:' doc/index.html ``` 验收: - CSS token、布局宽度、卡片、表单、Press、Judging、FAQ、Legal、响应式断点在文档中有对应说明。 - 后续工程化拆分不能只迁移内容,必须迁移视觉规则。