← 返回导航

后端技术架构

v1.0 · 2026-08-01

版本:v1.1(2026-08-16,评审后同步:12 表 / 阿里云短信 / 存储抽象 / WS 鉴权)
服务端环境:CentOS 7.9 / 4核 3.6G / Java 17.0.19 / PostgreSQL 15.17(已在跑)

1. 技术栈决策

决策点选择理由
语言Java 17(Temurin)服务器已装 17.0.19,Spring Boot 3.x 官方要求
框架Spring Boot 3.3.x用户 Java 主栈(EAH 同栈),生态成熟
ORMMyBatis-Plus 3.5.7用户 EAH 项目已用(JPA→MP 迁移经验),BaseMapper 免写 SQL
数据库PostgreSQL 15.17(PGDG,已在跑)服务器现成实例(5432 监听);JSONB 原生支持(milestones);EAH 同款
认证JWT(jjwt 0.12.x)无状态、简单;登录后下发 token(30 天);拦截器查库校验用户状态(2026-08-16 起)
短信验证码阿里云号码认证·短信认证TIMESAKE_SMS_TYPE=aliyun,2026-08-12 定案)个人资质可用、无需企业签名/模板审批;开发期可切 mock(固定码 123456)
实时同步Spring WebSocket(原生)项目级频道 /ws/projects/{id}?token=,JSON 消息协议(见 api.md);握手鉴权 JWT + 项目权限(2026-08-16 修复评审 P0)
推送华为 Push Kit(二期接入)鸿蒙端唯一推送通道,需 AGC 配置;MVP 先做本地提醒
API 文档SpringDoc OpenAPI(swagger-ui)自动生成接口文档,联调自测方便
部署fat jar + systemd(MVP)内存友好(3.6G 总内存)、运维简单;后续可容器化
缓存无(MVP)验证码存 DB(sms_code 表);流量上来后再加 Redis
图片存储ObjectStorage 抽象:local(默认)/ oss / cos@ConditionalOnProperty 装配;云密钥缺失启动即失败不静默降级
工程结构单模块 Maven规模可控,按包分层,避免过度设计

2. 架构图

鸿蒙 App(念时 · ArkTS/ArkUI)+ H5/微信小程序(uni-app)
   │  HTTPS (REST /api/v1/**)
   │  WSS   (/ws/projects/{id}?token=<jwt>)
   ▼
┌─────────────────────────────────────────┐
│  timesake-server(Spring Boot 3.3)      │
│  ┌───────────────────────────────────┐  │
│  │ Controller 层(REST + WS 端点)     │  │
│  │  Auth / Project / Record / Todo / │  │
│  │  Share / Invite / Bg / Upload     │  │
│  │  + WsEndpoint                     │  │
│  ├───────────────────────────────────┤  │
│  │ Service 层(业务 + 事务 + 权限)      │  │
│  │  AuthService / SmsService /       │  │
│  │  WeixinService / ProjectService / │  │
│  │  RecordService / TodoService /    │  │
│  │  ShareService / InviteService /   │  │
│  │  BgPresetService / ImageCompressor│  │
│  ├───────────────────────────────────┤  │
│  │ Mapper 层(MyBatis-Plus)          │  │
│  │  UserMapper / ProjectMapper / ... │  │
│  ├───────────────────────────────────┤  │
│  │ 拦截器:JWT 认证(查库校验用户状态)  │  │
│  └───────────────────────────────────┘  │
└──────────────┬──────────────────────────┘
               │ JDBC + WebSocket 会话
               ▼
   PostgreSQL 15.17(timesake 库,12 张表)

3. 工程目录结构

timesake-server/
├── pom.xml                     # Spring Boot 3.3 + MP 3.5.7 + jjwt + springdoc + 阿里云 dypnsapi
├── src/main/java/com/timesake/
│   ├── TimesakeApplication.java
│   ├── config/                 # WebConfig / WebSocketConfig / MybatisPlusConfig / JwtInterceptor
│   ├── controller/             # Auth / Project / Record / Todo / Share / Invite / Bg / Upload
│   ├── service/                # 业务逻辑(Auth / Sms / Weixin / Project / Record / Todo / Share / Invite / BgPreset)
│   ├── mapper/                 # MyBatis-Plus Mapper 接口(12 表各一)
│   ├── entity/                 # PO(@TableName 映射)
│   ├── dto/                    # 请求/响应对象(ProjectDtos / AuthDtos / RecordDtos / TodoDtos)
│   ├── storage/                # ObjectStorage 接口 + local / oss / cos 实现 + StorageProperties
│   ├── ws/                     # WebSocket 端点(WsEndpoint,握手鉴权)
│   ├── common/                 # 统一响应 R<T> / 错误码 / BizException / 全局异常处理 / ImageCompressor
│   └── util/                   # JwtUtil / UserContext
├── src/main/resources/
│   ├── application.yml         # 数据源 / JWT / 短信 / 微信 / 存储 / 前端域名配置
│   ├── db/init.sql             # 建库建表脚本(12 张表 + 幂等迁移段)
│   └── static/bg/              # 内置预设背景(bg-<id>.jpg)
└── server.log                  # 运行日志(排查 500 用)

4. 关键设计

4.1 统一响应

{ "code": 0, "message": "ok", "data": {...} }

4.2 认证流程

1. POST /auth/sms/send {phone} → 阿里云短信认证下发验证码(60s 限频,5min 有效,存 sms_code 表;
   连续错误 5 次锁 15 分钟,2026-08-16 应用层兜底)
2. POST /auth/login {phone, code} → 校验 → 签发 JWT(30 天)→ 返回 {token, user}
   POST /auth/wx-login {code} → 微信小程序 code2session → openid 登录/注册
3. 后续请求带 Authorization: Bearer *** → JwtInterceptor 解析 + 查库校验用户存在且未禁用

4.3 实时同步(WebSocket)

4.4 伙伴加入(邀请)

1. 管理员 POST /projects/{id}/invite → 生成 token(UUID,7 天有效)
2. 好友端扫码/链接 → POST /projects/join {token} → 加入项目(幂等);一念项目仅留「看见」档案
3. WebSocket 广播 member_joined → 所有伙伴刷新成员列表

4.5 数据库(12 张表,详见 database.md)

user / project / project_member / project_record / invite / sms_code / todo / share / wish_participant(一念参与档案)/ wish_suggestion(一念建议)/ wish_suggestion_support(附议)/ wish_suggestion_comment(留言,两层)

5. 部署方案(MVP)

1. 建库建表:psql -f init.sql(PostgreSQL 15.17,timesake 库)
2. 打包:mvn -DskipTests package → timesake-server.jar
3. systemd 常驻(/etc/systemd/system/timesake.service):
   - ExecStart=/usr/bin/java -Xms256m -Xmx512m -jar timesake-server.jar --server.port=18080
   - Environment:TIMESAKE_DB_PASSWORD / TIMESAKE_JWT_SECRET / TIMESAKE_SMS_TYPE=aliyun /
     TIMESAKE_SMS_ALIYUN_* / TIMESAKE_WX_APPID / TIMESAKE_WX_SECRET(密钥只写 systemd,不进仓库)
   - Restart=always,开机自启
4. 端口:**18080**(REST + WebSocket 同端口;8080 已被 EAH Docker 占用,勿用)
   - REST 前缀:/api/v1/*;WebSocket:/ws/projects/{projectId}?token=<jwt>
5. 反向代理:nginx 挂域名 **timesake-api.shihesuian.cn** → 127.0.0.1:18080(HTTPS,已部署)
   - /ws/ 走 upgrade 长连接(proxy_read_timeout 3600s)
6. H5 端静态站点:nginx 托管 **timesake.shihesuian.cn** → /data/timesake-h5/(HTTPS,已部署)
   - 构建:`cd h5 && npm run build:h5`,产物在 h5/dist/build/h5/,拷贝到 /data/timesake-h5/(chmod -R 755)
   - 域名已收敛到 h5/src/utils/config.ts(API_BASE / API_DOMAIN / WS_BASE / H5_BASE)
7. 本地实测:验证码 → 登录链路已通(mock 验证码 123456 / 生产阿里云)

6. 二期预留

方案
Redis 缓存/验证码spring-data-redis,替换 DB 存储
华为 Push KitAGC 配置 + PushService 调 HMS Push API
云存储 deleteOSS/COS 实现 ObjectStorage.delete(当前 local 已实现,云实现静默跳过)
多实例WebSocket 会话改 Redis Pub/Sub,水平扩展
容器化Dockerfile + docker-compose(现有 Docker 26.1.4 支持)
数据统计value_json 聚合查询(JSONB),生长曲线图接口