|
|
@@ -0,0 +1,236 @@
|
|
|
+# 问卷管理合并报告管理 Implementation Plan
|
|
|
+
|
|
|
+> **For agentic workers:** REQUIRED SUB-SKILL: Use superpowers:subagent-driven-development (recommended) or superpowers:executing-plans to implement this plan task-by-task. Steps use checkbox (`- [ ]`) syntax for tracking.
|
|
|
+
|
|
|
+**Goal:** 在 PC 端问卷管理页面内按问卷展开评估记录和报告列表,展示生成状态并支持预览、导出、发送和重新生成。
|
|
|
+
|
|
|
+**Architecture:** 以现有 `questionnaireList.vue` 为主页面,通过 Element UI 表格展开行承载该问卷的团队评估记录;每条评估记录复用 `reportList` 组件展示报告和操作。继续复用现有 API,报告生成使用 DeerFlow `genReport` 接口;旧报告路由保留,菜单入口不通过数据库迁移修改。
|
|
|
+
|
|
|
+**Tech Stack:** Vue 2.7、Vue Router、Element UI、Jest、Vue CLI。
|
|
|
+
|
|
|
+**Spec:** `docs/superpowers/specs/2026-08-30-questionnaire-report-merge-design.md`
|
|
|
+
|
|
|
+## Global Constraints
|
|
|
+
|
|
|
+- 以问卷管理为主入口。
|
|
|
+- 不改变小程序端、报告生成协议和数据库结构。
|
|
|
+- 报告生成必须使用 `/core/team/questionnaire/genReport/{teamQuestionnaireId}`。
|
|
|
+- 复用现有报告预览、导出、发送、删除和重新生成权限逻辑。
|
|
|
+- 旧报告管理路由保持可访问。
|
|
|
+
|
|
|
+---
|
|
|
+
|
|
|
+### Task 1: Define the questionnaire/report expansion contract
|
|
|
+
|
|
|
+**Files:**
|
|
|
+- Create: `tests/unit/questionnaireReportMerge.spec.js`
|
|
|
+- Modify: `src/views/modules/agent/questionnaireList.vue`
|
|
|
+
|
|
|
+**Interfaces:**
|
|
|
+- Produces the page-level behaviors `toggleReportList(row)`, `loadReportEntries(row)`, and `refreshReportEntry(index)`.
|
|
|
+- The questionnaire row stores `reportExpanded` and `reportEntries`; each report entry has the existing team-questionnaire fields plus `showMore` and `reportList`.
|
|
|
+
|
|
|
+- [ ] **Step 1: Write the failing test**
|
|
|
+
|
|
|
+Add source-level regression assertions that the questionnaire page imports team questionnaire/report APIs, renders a `报告列表` action and an expandable report section, and does not rely on the old report-page-only questionnaire selector:
|
|
|
+
|
|
|
+```js
|
|
|
+const fs = require('fs')
|
|
|
+const path = require('path')
|
|
|
+
|
|
|
+const source = fs.readFileSync(
|
|
|
+ path.resolve(__dirname, '../../src/views/modules/agent/questionnaireList.vue'),
|
|
|
+ 'utf8'
|
|
|
+)
|
|
|
+
|
|
|
+test('questionnaire management exposes an inline report list action', () => {
|
|
|
+ expect(source).toContain('报告列表')
|
|
|
+ expect(source).toContain('getTeamQuestionnaireList')
|
|
|
+ expect(source).toContain('getTeamReportWjList')
|
|
|
+ expect(source).toContain('reportList')
|
|
|
+ expect(source).toContain('reportExpanded')
|
|
|
+})
|
|
|
+```
|
|
|
+
|
|
|
+- [ ] **Step 2: Run test to verify it fails**
|
|
|
+
|
|
|
+Run: `npm test -- --runInBand tests/unit/questionnaireReportMerge.spec.js --silent`
|
|
|
+
|
|
|
+Expected: FAIL because `questionnaireList.vue` currently has no report action or report APIs.
|
|
|
+
|
|
|
+- [ ] **Step 3: Write the minimal page contract**
|
|
|
+
|
|
|
+Add the report API imports, a `reportList` component import, a `报告列表` button in the existing operation column, and an Element UI `type="expand"` column whose content renders one `reportList` component per loaded team questionnaire entry. Add row state initialization:
|
|
|
+
|
|
|
+```js
|
|
|
+const prepareQuestionnaireRow = row => ({
|
|
|
+ ...row,
|
|
|
+ reportExpanded: false,
|
|
|
+ reportEntries: [],
|
|
|
+ reportLoading: false
|
|
|
+})
|
|
|
+
|
|
|
+const dataList = ref([])
|
|
|
+
|
|
|
+const toggleReportList = async row => {
|
|
|
+ row.reportExpanded = !row.reportExpanded
|
|
|
+ if (row.reportExpanded && row.reportEntries.length === 0) {
|
|
|
+ await loadReportEntries(row)
|
|
|
+ }
|
|
|
+}
|
|
|
+```
|
|
|
+
|
|
|
+Use `getTeamQuestionnaireList({ page: 1, limit: 100, questionnaireId: row.id })` to load all matching evaluation records for the selected template and map each entry to `{ ...entry, showMore: false, reportList: [] }`.
|
|
|
+
|
|
|
+- [ ] **Step 4: Run test to verify it passes**
|
|
|
+
|
|
|
+Run: `npm test -- --runInBand tests/unit/questionnaireReportMerge.spec.js --silent`
|
|
|
+
|
|
|
+Expected: PASS.
|
|
|
+
|
|
|
+- [ ] **Step 5: Commit**
|
|
|
+
|
|
|
+```bash
|
|
|
+git add tests/unit/questionnaireReportMerge.spec.js src/views/modules/agent/questionnaireList.vue
|
|
|
+git commit -m "feat: 在问卷管理中增加报告列表入口"
|
|
|
+```
|
|
|
+
|
|
|
+### Task 2: Connect report status, preview, and report operations
|
|
|
+
|
|
|
+**Files:**
|
|
|
+- Modify: `src/views/modules/agent/questionnaireList.vue`
|
|
|
+- Modify: `src/components/reportList/index.vue` only if an event/prop compatibility fix is required
|
|
|
+- Test: `tests/unit/questionnaireReportMerge.spec.js`
|
|
|
+
|
|
|
+**Interfaces:**
|
|
|
+- Consumes: `getTeamReportWjList(relationId)`, `deleteTeamReportWj`, `sendReportUsers`, and `reCreateReport` from `src/api/agent/index.js`.
|
|
|
+- Produces: expanded report records whose state is rendered by the existing `reportList` status mapping and whose preview/export actions use existing report artifact fields.
|
|
|
+
|
|
|
+- [ ] **Step 1: Extend the failing test**
|
|
|
+
|
|
|
+Add assertions that the page wires report-list events and invokes the current DeerFlow generation helper rather than the legacy endpoint:
|
|
|
+
|
|
|
+```js
|
|
|
+test('expanded questionnaire reports retain report operations and current generation endpoint', () => {
|
|
|
+ const apiSource = fs.readFileSync(
|
|
|
+ path.resolve(__dirname, '../../src/api/agent/index.js'),
|
|
|
+ 'utf8'
|
|
|
+ )
|
|
|
+ expect(source).toContain('@toggleReport')
|
|
|
+ expect(source).toContain('@reCreateReport')
|
|
|
+ expect(source).toContain('@refreshReportList')
|
|
|
+ expect(apiSource).toContain('/core/team/questionnaire/genReport/${teamQuestionnaireId}')
|
|
|
+})
|
|
|
+```
|
|
|
+
|
|
|
+- [ ] **Step 2: Run test to verify it fails**
|
|
|
+
|
|
|
+Run: `npm test -- --runInBand tests/unit/questionnaireReportMerge.spec.js --silent`
|
|
|
+
|
|
|
+Expected: FAIL because the page does not yet wire the report component events or report refresh behavior.
|
|
|
+
|
|
|
+- [ ] **Step 3: Implement the report event handlers**
|
|
|
+
|
|
|
+Add page handlers matching the existing report page behavior:
|
|
|
+
|
|
|
+```js
|
|
|
+const toggleReportEntry = (entry, index) => {
|
|
|
+ entry.showMore = !entry.showMore
|
|
|
+ if (entry.showMore) {
|
|
|
+ getTeamReportWjList(entry.id).then(res => {
|
|
|
+ if (res.code !== 0) return proxy.$message.error(res.msg)
|
|
|
+ entry.reportList = res.data || []
|
|
|
+ })
|
|
|
+ } else {
|
|
|
+ entry.reportList = []
|
|
|
+ }
|
|
|
+}
|
|
|
+
|
|
|
+const refreshReportEntry = entry => {
|
|
|
+ getTeamReportWjList(entry.id).then(res => {
|
|
|
+ if (res.code !== 0) return proxy.$message.error(res.msg)
|
|
|
+ entry.reportList = res.data || []
|
|
|
+ })
|
|
|
+}
|
|
|
+```
|
|
|
+
|
|
|
+Wire `deleteReport`, `sendReport`, `reCreateReport`, and `refreshReportList` to the same existing API methods and permissions used by `report.vue`. Keep preview and export inside `reportList/index.vue`; do not duplicate PDF modal code in the questionnaire page. Ensure the generation operation remains the already-fixed `genReportById` helper.
|
|
|
+
|
|
|
+- [ ] **Step 4: Run test to verify it passes**
|
|
|
+
|
|
|
+Run: `npm test -- --runInBand tests/unit/questionnaireReportMerge.spec.js --silent`
|
|
|
+
|
|
|
+Expected: PASS.
|
|
|
+
|
|
|
+- [ ] **Step 5: Commit**
|
|
|
+
|
|
|
+```bash
|
|
|
+git add tests/unit/questionnaireReportMerge.spec.js src/views/modules/agent/questionnaireList.vue src/components/reportList/index.vue
|
|
|
+git commit -m "feat: 在问卷页展示报告状态和操作"
|
|
|
+```
|
|
|
+
|
|
|
+### Task 3: Preserve navigation compatibility and verify the integrated page
|
|
|
+
|
|
|
+**Files:**
|
|
|
+- Modify: `src/views/modules/home.vue` if the homepage report shortcut must point to the merged questionnaire page
|
|
|
+- Modify: `src/views/modules/agent/report.vue` only if its legacy route requires a compatibility redirect
|
|
|
+- Modify: `tests/unit/questionnaireReportMerge.spec.js`
|
|
|
+
|
|
|
+**Interfaces:**
|
|
|
+- Consumes: existing dynamic menu and static route behavior.
|
|
|
+- Produces: old report links remain valid while new primary navigation lands on questionnaire management.
|
|
|
+
|
|
|
+- [ ] **Step 1: Write the failing compatibility test**
|
|
|
+
|
|
|
+Add assertions for the chosen compatibility behavior:
|
|
|
+
|
|
|
+```js
|
|
|
+test('homepage report shortcut points to the questionnaire management entry', () => {
|
|
|
+ const homeSource = fs.readFileSync(
|
|
|
+ path.resolve(__dirname, '../../src/views/modules/home.vue'),
|
|
|
+ 'utf8'
|
|
|
+ )
|
|
|
+ expect(homeSource).toContain("toTurn('agent-questionnaire')")
|
|
|
+ expect(homeSource).not.toContain("toTurn('agent-report')")
|
|
|
+})
|
|
|
+```
|
|
|
+
|
|
|
+- [ ] **Step 2: Run test to verify it fails**
|
|
|
+
|
|
|
+Run: `npm test -- --runInBand tests/unit/questionnaireReportMerge.spec.js --silent`
|
|
|
+
|
|
|
+Expected: FAIL because the homepage still has a “更多报告” shortcut that targets the standalone report page.
|
|
|
+
|
|
|
+- [ ] **Step 3: Implement compatibility behavior**
|
|
|
+
|
|
|
+Keep `/agent-report` available for existing links. Update only new homepage navigation if required; do not delete the legacy report component or alter backend menu records. If dynamic menu configuration still exposes “报告管理”, its page remains functional while “问卷管理” becomes the primary merged entry.
|
|
|
+
|
|
|
+- [ ] **Step 4: Run the full verification suite**
|
|
|
+
|
|
|
+Run:
|
|
|
+
|
|
|
+```bash
|
|
|
+npm test -- --runInBand --silent
|
|
|
+npm run build
|
|
|
+```
|
|
|
+
|
|
|
+Expected: all unit suites pass and Vue CLI reports `Build complete` with exit code 0.
|
|
|
+
|
|
|
+- [ ] **Step 5: Inspect the final diff**
|
|
|
+
|
|
|
+Run:
|
|
|
+
|
|
|
+```bash
|
|
|
+git diff --check
|
|
|
+git status --short
|
|
|
+git diff --stat HEAD~3..HEAD
|
|
|
+```
|
|
|
+
|
|
|
+Confirm only the questionnaire/report merge files and plan/spec documents changed; do not stage `node_modules`, unrelated worktree files, or generated files unless deployment is separately requested.
|
|
|
+
|
|
|
+- [ ] **Step 6: Commit**
|
|
|
+
|
|
|
+```bash
|
|
|
+git add src/views/modules/home.vue src/views/modules/agent/report.vue tests/unit/questionnaireReportMerge.spec.js
|
|
|
+git commit -m "test: 验证问卷报告管理合并"
|
|
|
+```
|