diff --git a/.claude/settings.local.json b/.claude/settings.local.json
new file mode 100644
index 0000000..4c3fc8a
--- /dev/null
+++ b/.claude/settings.local.json
@@ -0,0 +1,60 @@
+{
+ "permissions": {
+ "allow": [
+ "Bash(bash \"C:/Users/11825/.claude/plugins/cache/claude-plugins-official/superpowers/5.0.5/skills/brainstorming/scripts/start-server.sh\" --project-dir \"C:/code/offer\")",
+ "Bash(cat \"C:/code/offer/.superpowers/brainstorm\"/.*/server-info)",
+ "Bash(python -c \"import sys,json; d=json.load\\(sys.stdin\\); print\\(''''Vue:'''', d.get\\(''''dependencies'''',{}\\).get\\(''''vue'''',''''N/A''''\\)\\); print\\(''''Vite/webpack:'''', list\\(d.get\\(''''devDependencies'''',{}\\).keys\\(\\)\\)[:5]\\)\")",
+ "Bash(git -C /c/code/offer log --oneline)",
+ "Bash(pip install:*)",
+ "Bash(py --version)",
+ "Bash(python3 -m pip install -r /c/code/offer/offer_backend/requirements.txt)",
+ "Bash(python3 -c \"import sys; print\\(sys.executable\\)\")",
+ "Bash(cmd.exe /c \"python --version\")",
+ "Bash(cmd.exe /c \"py --version\")",
+ "Bash(cmd.exe /c \"python --version && python -m pip --version\" 2>&1)",
+ "Read(//c/Users/11825/AppData/Local/Programs/**)",
+ "Bash(ls /c/Python*)",
+ "Read(//c/Users/11825/AppData/Local/Microsoft/WindowsApps//**)",
+ "Read(//c//**)",
+ "Bash(/c/Users/11825/AppData/Local/Microsoft/WindowsApps/python3.exe --version)",
+ "Bash(/c/Users/11825/AppData/Local/Microsoft/WindowsApps/python3.exe -m pip --version)",
+ "Read(//c/miniconda3/bin/**)",
+ "Read(//c/anaconda3/bin/**)",
+ "Bash(/c/software/python3_10/python --version)",
+ "Bash(/c/software/python3_10/python -m pip --version)",
+ "Bash(/c/software/python3_10/python -m ensurepip --upgrade)",
+ "Bash(/c/software/python3_10/python -m pip install -r /c/code/offer/offer_backend/requirements.txt 2>&1)",
+ "Bash(/c/software/python3_10/Scripts/django-admin startproject:*)",
+ "Bash(rm:*)",
+ "Bash(rm /c/code/offer/offer_backend/manage.py)",
+ "Bash(rm -rf /c/code/offer/offer_backend/config)",
+ "Bash(mkdir -p /c/code/offer/offer_backend/config/settings)",
+ "Bash(mkdir -p /c/code/offer/offer_backend/apps)",
+ "Bash(DJANGO_SETTINGS_MODULE=config.settings.development /c/software/python3_10/python manage.py check)",
+ "Bash(git -C /c/code/offer status)",
+ "Bash(git -C /c/code/offer add offer_backend/)",
+ "Bash(git:*)",
+ "Bash(python manage.py startapp accounts apps/accounts)",
+ "Bash(python manage.py makemigrations accounts)",
+ "Bash(python manage.py migrate)",
+ "Bash(python -m pytest apps/accounts/tests/test_auth.py -v)",
+ "Bash(/c/software/python3_10/python -m pytest apps/accounts/tests/test_auth.py -v)",
+ "Bash(/c/software/python3_10/Scripts/pytest --version)",
+ "Bash(ls /c/software/python3_10/Scripts/pytest*)",
+ "Bash(pip show:*)",
+ "Bash(/c/software/python3_10/python -c \"import sys; print\\(sys.path\\)\")",
+ "Bash(/c/software/python3_10/pip3 list:*)",
+ "Bash(/c/software/python3_10/pip3 install:*)",
+ "Bash(ls /c/software/python3_10/Scripts/pip*)",
+ "Read(//c/software/python3_10/**)",
+ "Bash(/c/software/python3_10/Scripts/pip3.exe install:*)",
+ "Bash(/c/software/python3_10/Scripts/pytest.exe apps/accounts/tests/test_auth.py -v)",
+ "Bash(pg_isready)",
+ "Bash(psql -U postgres -c \"SELECT 1\")",
+ "Bash(\"/c/Program Files/PostgreSQL/16/bin/psql.exe\" -U postgres -c \"SELECT version\\(\\);\" 2>&1)",
+ "Bash(PGPASSWORD=zcDsj@2024 \"/c/Program Files/PostgreSQL/16/bin/psql.exe\" -U postgres -c \"SELECT version\\(\\);\" 2>&1)",
+ "Bash(PGPASSWORD=zcDsj@2024 \"/c/Program Files/PostgreSQL/16/bin/psql.exe\" -U postgres -c \"CREATE DATABASE offer_db;\" 2>&1)",
+ "Bash(/c/software/python3_10/python manage.py migrate)"
+ ]
+ }
+}
diff --git a/.superpowers/brainstorm/3597-1774339647/.server-stopped b/.superpowers/brainstorm/3597-1774339647/.server-stopped
new file mode 100644
index 0000000..441de8f
--- /dev/null
+++ b/.superpowers/brainstorm/3597-1774339647/.server-stopped
@@ -0,0 +1 @@
+{"reason":"idle timeout","timestamp":1774342828046}
diff --git a/.superpowers/brainstorm/3597-1774339647/.server.pid b/.superpowers/brainstorm/3597-1774339647/.server.pid
new file mode 100644
index 0000000..d62725a
--- /dev/null
+++ b/.superpowers/brainstorm/3597-1774339647/.server.pid
@@ -0,0 +1 @@
+3597
diff --git a/.superpowers/brainstorm/3597-1774339647/architecture-v2.html b/.superpowers/brainstorm/3597-1774339647/architecture-v2.html
new file mode 100644
index 0000000..000cc6c
--- /dev/null
+++ b/.superpowers/brainstorm/3597-1774339647/architecture-v2.html
@@ -0,0 +1,80 @@
+
系统架构总览
+方案 A:Django 后端 + Vue3 单页应用
+
+
+
+
+
+
前端 — Vue3 SPA
+
+
+
公开门户
+
职位列表 / 搜索 / 职位详情
公司介绍 / 注册登录
+
+
+
求职者中心
+
我的简历 / 投递记录
个人信息管理
+
+
+
管理后台
+
超管:组织架构 / 账号管理
公司管理员:职位 / 投递管理
+
+
+
Vue Router + Pinia + Element Plus
+
+
+
+
⇄
+
+
+
+
后端 — Django + DRF
+
+
+
认证模块
+
JWT 登录 / 注册 / 权限控制
角色:超管 / 公司管理员 / 求职者
+
+
+
职位模块
+
职位 CRUD / 搜索过滤
公司隔离权限
+
+
+
投递模块
+
投递记录 / 状态流转
简历存储(表单 + 文件)
+
+
+
组织架构模块
+
集团 / 子公司 / 管理员绑定
+
+
+
Django 4.2 + DRF + JWT
+
+
+
+
⇄
+
+
+
+
+
+
+
+ 部署方式
+ Nginx 反向代理 → Vue3 静态文件 + Django API (Gunicorn)
+
diff --git a/.superpowers/brainstorm/3597-1774339647/architecture.html b/.superpowers/brainstorm/3597-1774339647/architecture.html
new file mode 100644
index 0000000..a52713d
--- /dev/null
+++ b/.superpowers/brainstorm/3597-1774339647/architecture.html
@@ -0,0 +1,80 @@
+系统架构总览
+方案 A:Django 后端 + Vue3 单页应用
+
+
+
+
+
+
前端 — Vue3 SPA
+
+
+
公开门户
+
职位列表 / 搜索 / 职位详情
公司介绍 / 注册登录
+
+
+
求职者中心
+
我的简历 / 投递记录
个人信息管理
+
+
+
管理后台
+
超管:组织架构 / 账号管理
公司管理员:职位 / 投递管理
+
+
+
Vue Router + Pinia + Element Plus
+
+
+
+
⇄
+
+
+
+
后端 — Django + DRF
+
+
+
认证模块
+
JWT 登录 / 注册 / 权限控制
角色:超管 / 公司管理员 / 求职者
+
+
+
职位模块
+
职位 CRUD / 搜索过滤
公司隔离权限
+
+
+
投递模块
+
投递记录 / 状态流转
简历存储(表单 + 文件)
+
+
+
组织架构模块
+
集团 / 子公司 / 管理员绑定
+
+
+
Django 4.2 + DRF + JWT
+
+
+
+
⇄
+
+
+
+
+
+
+
+ 部署方式
+ Nginx 反向代理 → Vue3 静态文件 + Django API (Gunicorn)
+
diff --git a/.superpowers/brainstorm/3597-1774339647/data-model-v2.html b/.superpowers/brainstorm/3597-1774339647/data-model-v2.html
new file mode 100644
index 0000000..2de328f
--- /dev/null
+++ b/.superpowers/brainstorm/3597-1774339647/data-model-v2.html
@@ -0,0 +1,216 @@
+数据模型设计
+核心表结构与关联关系
+
+
+
+
+
+
+ 🏢
+ Organization 组织架构
+
+
+
+
+ | id |
+ PK |
+
+
+ | name |
+ 公司名称 |
+
+
+ | parent |
+ FK → self(集团/子公司) |
+
+
+ | logo |
+ 公司 Logo |
+
+
+ | description |
+ 公司简介 |
+
+
+ | email |
+ 公司联系邮箱 ✨ |
+
+
+ | is_active |
+ 是否启用 |
+
+
+
+
+
+
+
+
+ 👤
+ User 用户
+
+
+
+
+ | id |
+ PK |
+
+
+ | username |
+ 登录账号 |
+
+
+ | email |
+ 用户邮箱 ✨ |
+
+
+ | phone |
+ 手机号 |
+
+
+ | role |
+ superadmin / admin / seeker |
+
+
+ | organization |
+ FK → Organization(admin 用) |
+
+
+ | is_active |
+ 账号状态 |
+
+
+
+
+
+
+
+
+ 💼
+ Job 职位
+
+
+
+
+ | id |
+ PK |
+
+
+ | organization |
+ FK → Organization |
+
+
+ | title |
+ 职位名称 |
+
+
+ | category |
+ 职位类别 |
+
+
+ | location / salary |
+ 地点 / 薪资 |
+
+
+ | description |
+ 职位描述(富文本) |
+
+
+ | status |
+ draft / published / closed |
+
+
+ | created_at |
+ 发布时间 |
+
+
+
+
+
+
+
+
+ 📄
+ Resume 简历
+
+
+
+
+ | id |
+ PK |
+
+
+ | user |
+ FK → User(求职者) |
+
+
+ | name / gender / birthday |
+ 基本信息 |
+
+
+ | education (JSONB) |
+ 教育经历列表 |
+
+
+ | experience (JSONB) |
+ 工作经历列表 |
+
+
+ | attachment |
+ 简历附件(PDF/Word) |
+
+
+
+
+
+
+
+
+ 📨
+ Application 投递记录
+
+
+
+
+ | id |
+ PK |
+
+
+ | job |
+ FK → Job |
+
+
+ | applicant |
+ FK → User |
+
+
+ | resume |
+ FK → Resume(投递时快照) |
+
+
+ | status |
+ 待查看 → 已查看 → 面试 → 录用/拒绝 |
+
+
+ | note |
+ HR 备注 |
+
+
+ | applied_at |
+ 投递时间 |
+
+
+
+
+
+
+
+
+
关键设计说明:
+
+ - Organization 自关联支持集团→子公司层级
+ - User.role 控制权限:superadmin 管全局,admin 只能操作本公司数据
+ - Resume.education / experience 用 PostgreSQL JSONB 存储,灵活应对结构差异
+ - Application 投递时关联当前简历,保证历史记录不受简历修改影响
+
+
diff --git a/.superpowers/brainstorm/3597-1774339647/data-model.html b/.superpowers/brainstorm/3597-1774339647/data-model.html
new file mode 100644
index 0000000..ae02994
--- /dev/null
+++ b/.superpowers/brainstorm/3597-1774339647/data-model.html
@@ -0,0 +1,208 @@
+数据模型设计
+核心表结构与关联关系
+
+
+
+
+
+
+ 🏢
+ Organization 组织架构
+
+
+
+
+ | id |
+ PK |
+
+
+ | name |
+ 公司名称 |
+
+
+ | parent |
+ FK → self(集团/子公司) |
+
+
+ | logo |
+ 公司 Logo |
+
+
+ | description |
+ 公司简介 |
+
+
+ | is_active |
+ 是否启用 |
+
+
+
+
+
+
+
+
+ 👤
+ User 用户
+
+
+
+
+ | id |
+ PK |
+
+
+ | username / email |
+ 登录账号 |
+
+
+ | phone |
+ 手机号 |
+
+
+ | role |
+ superadmin / admin / seeker |
+
+
+ | organization |
+ FK → Organization(admin 用) |
+
+
+ | is_active |
+ 账号状态 |
+
+
+
+
+
+
+
+
+ 💼
+ Job 职位
+
+
+
+
+ | id |
+ PK |
+
+
+ | organization |
+ FK → Organization |
+
+
+ | title |
+ 职位名称 |
+
+
+ | category |
+ 职位类别 |
+
+
+ | location / salary |
+ 地点 / 薪资 |
+
+
+ | description |
+ 职位描述(富文本) |
+
+
+ | status |
+ draft / published / closed |
+
+
+ | created_at |
+ 发布时间 |
+
+
+
+
+
+
+
+
+ 📄
+ Resume 简历
+
+
+
+
+ | id |
+ PK |
+
+
+ | user |
+ FK → User(求职者) |
+
+
+ | name / gender / birthday |
+ 基本信息 |
+
+
+ | education (JSON) |
+ 教育经历列表 |
+
+
+ | experience (JSON) |
+ 工作经历列表 |
+
+
+ | attachment |
+ 简历附件(PDF/Word) |
+
+
+
+
+
+
+
+
+ 📨
+ Application 投递记录
+
+
+
+
+ | id |
+ PK |
+
+
+ | job |
+ FK → Job |
+
+
+ | applicant |
+ FK → User |
+
+
+ | resume |
+ FK → Resume(投递时快照) |
+
+
+ | status |
+ 待查看 → 已查看 → 面试 → 录用/拒绝 |
+
+
+ | note |
+ HR 备注 |
+
+
+ | applied_at |
+ 投递时间 |
+
+
+
+
+
+
+
+
+
关键设计说明:
+
+ - Organization 自关联支持集团→子公司层级
+ - User.role 控制权限:superadmin 管全局,admin 只能操作本公司数据
+ - Resume.education / experience 用 PostgreSQL JSONB 存储,灵活应对结构差异
+ - Application 投递时关联当前简历,保证历史记录不受简历修改影响
+
+
diff --git a/.superpowers/brainstorm/3597-1774339647/flows.html b/.superpowers/brainstorm/3597-1774339647/flows.html
new file mode 100644
index 0000000..863fbfe
--- /dev/null
+++ b/.superpowers/brainstorm/3597-1774339647/flows.html
@@ -0,0 +1,116 @@
+关键业务流程
+三条核心流程的状态流转
+
+
+
+
+
+
+ 流程 1:求职者投递简历
+
+
+
+
+
→
+
+
→
+
+
检查
+
简历是否完善
+
未完善→提示填写
+
+
→
+
+
→
+
+
+
+
+
+
+
+
+ 流程 2:HR 处理投递(状态流转)
+
+
+
+
+ * 每次状态变更自动发送邮件通知求职者
+
+
+
+
+
+
+
+ 流程 3:公司管理员发布职位
+
+
+
+
+
→
+
+
→
+
+
发布上线
+
status: published
+
+
→
+
+
关闭招聘
+
status: closed
+
+
+
+ * 管理员只能操作本公司职位;超管可查看所有公司职位但不能代发
+
+
+
+
+
diff --git a/.superpowers/brainstorm/3597-1774339647/pages.html b/.superpowers/brainstorm/3597-1774339647/pages.html
new file mode 100644
index 0000000..12c55ed
--- /dev/null
+++ b/.superpowers/brainstorm/3597-1774339647/pages.html
@@ -0,0 +1,114 @@
+页面结构与路由设计
+三个区域的页面划分
+
+
+
+
+
+
+ 公开门户
+ 无需登录
+
+
+
+
+
/
+
首页(职位推荐 + 公司展示 + 搜索入口)
+
+
+
/jobs
+
职位列表(搜索 + 筛选:公司/地点/薪资/类别)
+
+
+
/jobs/:id
+
职位详情(描述 + 要求 + 投递按钮)
+
+
+
+
/companies/:id
+
公司详情 + 该公司在招职位
+
+
+
/login /register
+
求职者登录 / 注册
+
+
+
+
+
+
+
+
+ 求职者中心
+ 需登录(seeker)
+
+
+
+
+
/seeker/resume
+
我的简历(填写/编辑在线简历 + 上传附件)
+
+
+
/seeker/applications
+
我的投递(投递记录 + 状态跟踪)
+
+
+
/seeker/profile
+
账号设置(修改密码/邮箱/手机)
+
+
+
+
+
+
+
+
+ 管理后台
+ 需登录(admin / superadmin)
+
+
+
+
公司管理员
+
+
+
/admin/jobs
+
职位管理(列表 / 新建 / 编辑 / 上下架)
+
+
+
/admin/applications
+
投递管理(查看简历 / 更新状态 / 备注)
+
+
+
+
超管专属
+
+
+
/admin/organizations
+
组织架构管理(增删改查子公司)
+
+
+
/admin/users
+
用户管理(创建公司管理员 / 禁用账号)
+
+
+
/admin/jobs (全局视图)
+
查看所有公司的职位
+
+
+
+
+
+
+
+
+
路由守卫规则:
+
+ - 未登录访问 /seeker/* → 跳转登录页,登录后返回原页面
+ - 未登录访问 /admin/* → 跳转管理员登录页
+ - admin 角色访问超管页面 → 403 提示
+ - seeker 角色访问 /admin/* → 403 提示
+
+
diff --git a/docs/superpowers/plans/2026-03-24-recruitment-website.md b/docs/superpowers/plans/2026-03-24-recruitment-website.md
index c35ee50..f344a9b 100644
--- a/docs/superpowers/plans/2026-03-24-recruitment-website.md
+++ b/docs/superpowers/plans/2026-03-24-recruitment-website.md
@@ -382,7 +382,7 @@ git commit -m "chore: add pytest configuration for Django tests"
---
-## Task 4: accounts app — 自定义用户模型
+## Task 3: accounts app — 自定义用户模型
**Files:**
- Create: `offer_backend/apps/accounts/models.py`
diff --git a/docs/superpowers/specs/2026-03-24-recruitment-website-design.md b/docs/superpowers/specs/2026-03-24-recruitment-website-design.md
index b55b980..d2713bc 100644
--- a/docs/superpowers/specs/2026-03-24-recruitment-website-design.md
+++ b/docs/superpowers/specs/2026-03-24-recruitment-website-design.md
@@ -20,7 +20,7 @@
| 认证 | djangorestframework-simplejwt(JWT) |
| 数据库 | PostgreSQL |
| 缓存 | Redis |
-| 文件存储 | 本地存储 / 对象存储(OSS) |
+| 文件存储 | 本地存储(初期),后期可切换至对象存储(OSS) |
| 部署 | Nginx + Gunicorn |
---
@@ -113,7 +113,7 @@ Nginx
| id | PK | 主键 |
| job | FK(Job) | 投递的职位 |
| applicant | FK(User) | 求职者 |
-| resume | FK(Resume) | 投递时关联的简历(快照) |
+| resume_snapshot | JSONField | 投递时将简历内容序列化复制存储,与 Resume 主表解耦 |
| status | CharField | pending / viewed / interviewing / hired / rejected |
| note | TextField | HR 备注 |
| applied_at | DateTimeField | 投递时间 |
@@ -130,7 +130,7 @@ Nginx
| `/jobs/:id` | 职位详情 | 职位描述、要求、投递按钮 |
| `/companies` | 公司列表 | 所有子公司展示 |
| `/companies/:id` | 公司详情 | 公司介绍 + 在招职位 |
-| `/login` | 求职者登录 | - |
+| `/login` | 求职者登录 | 管理员也使用此页面登录,通过 role 跳转不同后台 |
| `/register` | 求职者注册 | - |
### 求职者中心(seeker 登录后可访问)
@@ -170,7 +170,7 @@ Nginx
待查看(pending) → 已查看(viewed) → 面试中(interviewing) → 已录用(hired)
→ 已拒绝(rejected)
```
-- 每次状态变更自动发送邮件通知求职者
+- 每次状态变更通过 Django 内置邮件后端(SMTP)同步发送通知邮件给求职者
- HR 可在任意阶段填写备注
### 流程 3:公司管理员发布职位