openspec-mcp 0.1.0 → 0.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +83 -35
- package/README.zh.md +81 -33
- package/dist/api/routes/changes.d.ts.map +1 -1
- package/dist/api/routes/changes.js +54 -0
- package/dist/api/routes/changes.js.map +1 -1
- package/dist/api/routes/project.d.ts +7 -0
- package/dist/api/routes/project.d.ts.map +1 -0
- package/dist/api/routes/project.js +14 -0
- package/dist/api/routes/project.js.map +1 -0
- package/dist/api/routes/specs.d.ts.map +1 -1
- package/dist/api/routes/specs.js +100 -1
- package/dist/api/routes/specs.js.map +1 -1
- package/dist/api/routes/tasks.d.ts.map +1 -1
- package/dist/api/routes/tasks.js +33 -0
- package/dist/api/routes/tasks.js.map +1 -1
- package/dist/api/server.d.ts +5 -1
- package/dist/api/server.d.ts.map +1 -1
- package/dist/api/server.js +107 -14
- package/dist/api/server.js.map +1 -1
- package/dist/core/approval-manager.test.d.ts +5 -0
- package/dist/core/approval-manager.test.d.ts.map +1 -0
- package/dist/core/approval-manager.test.js +114 -0
- package/dist/core/approval-manager.test.js.map +1 -0
- package/dist/core/file-watcher.d.ts.map +1 -1
- package/dist/core/file-watcher.js +13 -0
- package/dist/core/file-watcher.js.map +1 -1
- package/dist/core/hooks-manager.d.ts +43 -0
- package/dist/core/hooks-manager.d.ts.map +1 -0
- package/dist/core/hooks-manager.js +194 -0
- package/dist/core/hooks-manager.js.map +1 -0
- package/dist/core/openspec-cli.d.ts +12 -0
- package/dist/core/openspec-cli.d.ts.map +1 -1
- package/dist/core/openspec-cli.js +85 -0
- package/dist/core/openspec-cli.js.map +1 -1
- package/dist/core/proposal-generator.d.ts +46 -0
- package/dist/core/proposal-generator.d.ts.map +1 -0
- package/dist/core/proposal-generator.js +155 -0
- package/dist/core/proposal-generator.js.map +1 -0
- package/dist/core/review-manager.d.ts +147 -0
- package/dist/core/review-manager.d.ts.map +1 -0
- package/dist/core/review-manager.js +235 -0
- package/dist/core/review-manager.js.map +1 -0
- package/dist/core/spec-parser.d.ts +51 -0
- package/dist/core/spec-parser.d.ts.map +1 -0
- package/dist/core/spec-parser.js +130 -0
- package/dist/core/spec-parser.js.map +1 -0
- package/dist/core/task-parser.test.d.ts +5 -0
- package/dist/core/task-parser.test.d.ts.map +1 -0
- package/dist/core/task-parser.test.js +124 -0
- package/dist/core/task-parser.test.js.map +1 -0
- package/dist/core/template-manager.d.ts +48 -0
- package/dist/core/template-manager.d.ts.map +1 -0
- package/dist/core/template-manager.js +268 -0
- package/dist/core/template-manager.js.map +1 -0
- package/dist/index.js +17 -1
- package/dist/index.js.map +1 -1
- package/dist/server/tools/generator.d.ts +8 -0
- package/dist/server/tools/generator.d.ts.map +1 -0
- package/dist/server/tools/generator.js +121 -0
- package/dist/server/tools/generator.js.map +1 -0
- package/dist/server/tools/hooks.d.ts +8 -0
- package/dist/server/tools/hooks.d.ts.map +1 -0
- package/dist/server/tools/hooks.js +86 -0
- package/dist/server/tools/hooks.js.map +1 -0
- package/dist/server/tools/management.d.ts.map +1 -1
- package/dist/server/tools/management.js +37 -2
- package/dist/server/tools/management.js.map +1 -1
- package/dist/server/tools/reviews.d.ts +8 -0
- package/dist/server/tools/reviews.d.ts.map +1 -0
- package/dist/server/tools/reviews.js +178 -0
- package/dist/server/tools/reviews.js.map +1 -0
- package/dist/server/tools/tasks.d.ts.map +1 -1
- package/dist/server/tools/tasks.js +38 -0
- package/dist/server/tools/tasks.js.map +1 -1
- package/dist/server/tools/templates.d.ts +8 -0
- package/dist/server/tools/templates.d.ts.map +1 -0
- package/dist/server/tools/templates.js +89 -0
- package/dist/server/tools/templates.js.map +1 -0
- package/dist/utils/constants.d.ts +54 -0
- package/dist/utils/constants.d.ts.map +1 -0
- package/dist/utils/constants.js +54 -0
- package/dist/utils/constants.js.map +1 -0
- package/dist/utils/version.d.ts +13 -0
- package/dist/utils/version.d.ts.map +1 -0
- package/dist/utils/version.js +26 -0
- package/dist/utils/version.js.map +1 -0
- package/package.json +2 -6
- package/web/dist/assets/index-BGNTCJhf.css +1 -0
- package/web/dist/assets/index-DKBVRb7-.js +99 -0
- package/web/dist/index.html +2 -2
- package/web/dist/assets/index--LppUKpS.js +0 -67
- package/web/dist/assets/index-DdJQfs9Z.css +0 -1
package/README.md
CHANGED
|
@@ -7,30 +7,35 @@ MCP (Model Context Protocol) server for [OpenSpec](https://github.com/Fission-AI
|
|
|
7
7
|
## Features
|
|
8
8
|
|
|
9
9
|
- **MCP Tools**: Full OpenSpec CLI functionality exposed as MCP tools
|
|
10
|
+
- **Review System**: Add, reply, resolve review comments on proposals/designs
|
|
10
11
|
- **Task Tracking**: Parse tasks.md and track progress in real-time
|
|
11
12
|
- **Approval Workflow**: Request, approve, and reject change proposals
|
|
12
|
-
- **Web Dashboard**: Visual management interface with real-time updates
|
|
13
|
+
- **Web Dashboard**: Visual management interface with real-time updates and Markdown rendering
|
|
13
14
|
|
|
14
15
|
## Quick Start
|
|
15
16
|
|
|
16
17
|
### 1. Add to your MCP configuration
|
|
17
18
|
|
|
18
19
|
**Claude Code CLI (recommended - uses current directory):**
|
|
20
|
+
|
|
19
21
|
```bash
|
|
20
22
|
claude mcp add openspec -- npx openspec-mcp
|
|
21
23
|
```
|
|
22
24
|
|
|
23
25
|
**Claude Code CLI with Dashboard:**
|
|
26
|
+
|
|
24
27
|
```bash
|
|
25
28
|
claude mcp add openspec -- npx openspec-mcp --with-dashboard
|
|
26
29
|
```
|
|
27
30
|
|
|
28
31
|
**Claude Code CLI with specific project path:**
|
|
32
|
+
|
|
29
33
|
```bash
|
|
30
34
|
claude mcp add openspec -- npx openspec-mcp /path/to/your/project
|
|
31
35
|
```
|
|
32
36
|
|
|
33
37
|
**Claude Desktop / Cursor / Other:**
|
|
38
|
+
|
|
34
39
|
```json
|
|
35
40
|
{
|
|
36
41
|
"mcpServers": {
|
|
@@ -43,6 +48,7 @@ claude mcp add openspec -- npx openspec-mcp /path/to/your/project
|
|
|
43
48
|
```
|
|
44
49
|
|
|
45
50
|
**With Dashboard:**
|
|
51
|
+
|
|
46
52
|
```json
|
|
47
53
|
{
|
|
48
54
|
"mcpServers": {
|
|
@@ -73,47 +79,87 @@ claude mcp add openspec -- npx openspec-mcp /path/to/your/project
|
|
|
73
79
|
## Available Tools
|
|
74
80
|
|
|
75
81
|
### Guides
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
|
79
|
-
| `
|
|
82
|
+
|
|
83
|
+
| Tool | Description |
|
|
84
|
+
| ------------------------------ | ------------------------- |
|
|
85
|
+
| `openspec_get_instructions` | Get AGENTS.md usage guide |
|
|
86
|
+
| `openspec_get_project_context` | Get project.md context |
|
|
80
87
|
|
|
81
88
|
### Management
|
|
82
|
-
|
|
83
|
-
|
|
89
|
+
|
|
90
|
+
| Tool | Description |
|
|
91
|
+
| ----------------------- | ------------------------- |
|
|
84
92
|
| `openspec_list_changes` | List all change proposals |
|
|
85
|
-
| `openspec_list_specs`
|
|
86
|
-
| `openspec_show_change`
|
|
87
|
-
| `openspec_show_spec`
|
|
93
|
+
| `openspec_list_specs` | List all specifications |
|
|
94
|
+
| `openspec_show_change` | Show change details |
|
|
95
|
+
| `openspec_show_spec` | Show spec details |
|
|
88
96
|
|
|
89
97
|
### Validation
|
|
90
|
-
|
|
91
|
-
|
|
98
|
+
|
|
99
|
+
| Tool | Description |
|
|
100
|
+
| -------------------------- | ----------------- |
|
|
92
101
|
| `openspec_validate_change` | Validate a change |
|
|
93
|
-
| `openspec_validate_spec`
|
|
94
|
-
| `openspec_validate_all`
|
|
102
|
+
| `openspec_validate_spec` | Validate a spec |
|
|
103
|
+
| `openspec_validate_all` | Batch validation |
|
|
95
104
|
|
|
96
105
|
### Archive
|
|
97
|
-
|
|
98
|
-
|
|
106
|
+
|
|
107
|
+
| Tool | Description |
|
|
108
|
+
| ------------------------- | ------------------------ |
|
|
99
109
|
| `openspec_archive_change` | Archive completed change |
|
|
100
110
|
|
|
101
111
|
### Tasks
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
|
105
|
-
| `
|
|
112
|
+
|
|
113
|
+
| Tool | Description |
|
|
114
|
+
| ------------------------------- | ------------------------ |
|
|
115
|
+
| `openspec_get_tasks` | Get tasks and progress |
|
|
116
|
+
| `openspec_update_task` | Update task status |
|
|
117
|
+
| `openspec_batch_update_tasks` | Batch update task status |
|
|
106
118
|
| `openspec_get_progress_summary` | Get all changes progress |
|
|
107
119
|
|
|
108
120
|
### Approval
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
|
112
|
-
| `
|
|
113
|
-
| `
|
|
114
|
-
| `
|
|
121
|
+
|
|
122
|
+
| Tool | Description |
|
|
123
|
+
| --------------------------------- | ---------------------- |
|
|
124
|
+
| `openspec_get_approval_status` | Get approval status |
|
|
125
|
+
| `openspec_request_approval` | Request approval |
|
|
126
|
+
| `openspec_approve_change` | Approve a change |
|
|
127
|
+
| `openspec_reject_change` | Reject a change |
|
|
115
128
|
| `openspec_list_pending_approvals` | List pending approvals |
|
|
116
129
|
|
|
130
|
+
### Reviews
|
|
131
|
+
|
|
132
|
+
| Tool | Description |
|
|
133
|
+
| ----------------------------------- | ------------------------------------------- |
|
|
134
|
+
| `openspec_add_review` | Add review comment to proposal/design/tasks |
|
|
135
|
+
| `openspec_list_reviews` | List reviews with filters |
|
|
136
|
+
| `openspec_reply_review` | Reply to a review |
|
|
137
|
+
| `openspec_resolve_review` | Mark review as resolved |
|
|
138
|
+
| `openspec_get_review_summary` | Get review statistics |
|
|
139
|
+
| `openspec_check_approval_readiness` | Check if ready for approval |
|
|
140
|
+
|
|
141
|
+
### Templates
|
|
142
|
+
|
|
143
|
+
| Tool | Description |
|
|
144
|
+
| --------------------------- | --------------------------- |
|
|
145
|
+
| `openspec_list_templates` | List available templates |
|
|
146
|
+
| `openspec_create_change` | Create change from template |
|
|
147
|
+
| `openspec_preview_template` | Preview template content |
|
|
148
|
+
|
|
149
|
+
### Generator
|
|
150
|
+
|
|
151
|
+
| Tool | Description |
|
|
152
|
+
| ---------------------------- | ----------------------------------- |
|
|
153
|
+
| `openspec_prepare_proposal` | Prepare proposal structure |
|
|
154
|
+
| `openspec_save_proposal` | Save generated proposal |
|
|
155
|
+
| `openspec_generate_proposal` | Generate proposal from requirements |
|
|
156
|
+
|
|
157
|
+
### Hooks
|
|
158
|
+
|
|
159
|
+
| Tool | Description |
|
|
160
|
+
| ---------------------- | --------------------------- |
|
|
161
|
+
| `openspec_setup_hooks` | Setup git hooks for project |
|
|
162
|
+
|
|
117
163
|
## Approval Workflow
|
|
118
164
|
|
|
119
165
|
```
|
|
@@ -134,7 +180,7 @@ Arguments:
|
|
|
134
180
|
Options:
|
|
135
181
|
--dashboard Start web dashboard only (HTTP mode)
|
|
136
182
|
--with-dashboard Start MCP server with web dashboard
|
|
137
|
-
-p, --port <number> Dashboard port (default: 3000)
|
|
183
|
+
-p, --port <number> Dashboard port (default: 3000; auto-increments if busy, 0 for random)
|
|
138
184
|
-V, --version Output version number
|
|
139
185
|
-h, --help Display help
|
|
140
186
|
```
|
|
@@ -164,20 +210,22 @@ The dashboard provides a visual interface for managing changes, tracking tasks,
|
|
|
164
210
|
|
|
165
211
|
### Dashboard Pages
|
|
166
212
|
|
|
167
|
-
| Route
|
|
168
|
-
|
|
169
|
-
| `/`
|
|
170
|
-
| `/changes`
|
|
171
|
-
| `/changes/:id` | Change detail with task management
|
|
172
|
-
| `/specs`
|
|
173
|
-
| `/approvals`
|
|
213
|
+
| Route | Description |
|
|
214
|
+
| -------------- | -------------------------------------- |
|
|
215
|
+
| `/` | Overview with stats and recent changes |
|
|
216
|
+
| `/changes` | List all changes with progress |
|
|
217
|
+
| `/changes/:id` | Change detail with task management |
|
|
218
|
+
| `/specs` | Browse specifications |
|
|
219
|
+
| `/approvals` | Approval queue management |
|
|
174
220
|
|
|
175
221
|
### Features
|
|
176
222
|
|
|
177
|
-
- **Real-time Updates**: WebSocket connection for live progress updates
|
|
223
|
+
- **Real-time Updates**: WebSocket connection for live progress and review updates
|
|
178
224
|
- **Task Management**: Toggle task status directly from the UI
|
|
179
225
|
- **Approval Actions**: Approve/reject changes with comments
|
|
180
226
|
- **Progress Visualization**: Progress bars and status badges
|
|
227
|
+
- **Review Management**: View, resolve and track reviews with Open/Resolved tabs
|
|
228
|
+
- **Markdown Rendering**: Proposals and designs rendered with full Markdown support
|
|
181
229
|
|
|
182
230
|
## Development
|
|
183
231
|
|
package/README.zh.md
CHANGED
|
@@ -7,30 +7,35 @@
|
|
|
7
7
|
## 功能特性
|
|
8
8
|
|
|
9
9
|
- **MCP 工具**: 将 OpenSpec CLI 完整功能暴露为 MCP 工具
|
|
10
|
+
- **评审系统**: 添加、回复、解决 proposal/design 的评审意见
|
|
10
11
|
- **任务追踪**: 解析 tasks.md 并实时追踪进度
|
|
11
12
|
- **审批流程**: 请求、批准和拒绝变更提案
|
|
12
|
-
- **Web 仪表板**:
|
|
13
|
+
- **Web 仪表板**: 可视化管理界面,支持 Markdown 渲染和实时更新
|
|
13
14
|
|
|
14
15
|
## 快速开始
|
|
15
16
|
|
|
16
17
|
### 1. 添加到 MCP 配置
|
|
17
18
|
|
|
18
19
|
**Claude Code CLI(推荐,使用当前目录):**
|
|
20
|
+
|
|
19
21
|
```bash
|
|
20
22
|
claude mcp add openspec -- npx openspec-mcp
|
|
21
23
|
```
|
|
22
24
|
|
|
23
25
|
**Claude Code CLI 带仪表板:**
|
|
26
|
+
|
|
24
27
|
```bash
|
|
25
28
|
claude mcp add openspec -- npx openspec-mcp --with-dashboard
|
|
26
29
|
```
|
|
27
30
|
|
|
28
31
|
**Claude Code CLI 指定项目路径:**
|
|
32
|
+
|
|
29
33
|
```bash
|
|
30
34
|
claude mcp add openspec -- npx openspec-mcp /path/to/your/project
|
|
31
35
|
```
|
|
32
36
|
|
|
33
37
|
**Claude Desktop / Cursor / 其他:**
|
|
38
|
+
|
|
34
39
|
```json
|
|
35
40
|
{
|
|
36
41
|
"mcpServers": {
|
|
@@ -43,6 +48,7 @@ claude mcp add openspec -- npx openspec-mcp /path/to/your/project
|
|
|
43
48
|
```
|
|
44
49
|
|
|
45
50
|
**带仪表板:**
|
|
51
|
+
|
|
46
52
|
```json
|
|
47
53
|
{
|
|
48
54
|
"mcpServers": {
|
|
@@ -73,47 +79,87 @@ claude mcp add openspec -- npx openspec-mcp /path/to/your/project
|
|
|
73
79
|
## 可用工具
|
|
74
80
|
|
|
75
81
|
### 指南类 (Guides)
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
|
82
|
+
|
|
83
|
+
| 工具 | 描述 |
|
|
84
|
+
| ------------------------------ | -------------------------- |
|
|
85
|
+
| `openspec_get_instructions` | 获取 AGENTS.md 使用指南 |
|
|
79
86
|
| `openspec_get_project_context` | 获取 project.md 项目上下文 |
|
|
80
87
|
|
|
81
88
|
### 管理类 (Management)
|
|
82
|
-
|
|
83
|
-
|
|
89
|
+
|
|
90
|
+
| 工具 | 描述 |
|
|
91
|
+
| ----------------------- | ---------------- |
|
|
84
92
|
| `openspec_list_changes` | 列出所有变更提案 |
|
|
85
|
-
| `openspec_list_specs`
|
|
86
|
-
| `openspec_show_change`
|
|
87
|
-
| `openspec_show_spec`
|
|
93
|
+
| `openspec_list_specs` | 列出所有规格 |
|
|
94
|
+
| `openspec_show_change` | 显示变更详情 |
|
|
95
|
+
| `openspec_show_spec` | 显示规格详情 |
|
|
88
96
|
|
|
89
97
|
### 验证类 (Validation)
|
|
90
|
-
|
|
91
|
-
|
|
98
|
+
|
|
99
|
+
| 工具 | 描述 |
|
|
100
|
+
| -------------------------- | ------------ |
|
|
92
101
|
| `openspec_validate_change` | 验证单个变更 |
|
|
93
|
-
| `openspec_validate_spec`
|
|
94
|
-
| `openspec_validate_all`
|
|
102
|
+
| `openspec_validate_spec` | 验证单个规格 |
|
|
103
|
+
| `openspec_validate_all` | 批量验证 |
|
|
95
104
|
|
|
96
105
|
### 归档类 (Archive)
|
|
97
|
-
|
|
98
|
-
|
|
106
|
+
|
|
107
|
+
| 工具 | 描述 |
|
|
108
|
+
| ------------------------- | -------------- |
|
|
99
109
|
| `openspec_archive_change` | 归档已完成变更 |
|
|
100
110
|
|
|
101
111
|
### 任务类 (Tasks)
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
|
105
|
-
| `
|
|
112
|
+
|
|
113
|
+
| 工具 | 描述 |
|
|
114
|
+
| ------------------------------- | -------------------- |
|
|
115
|
+
| `openspec_get_tasks` | 获取任务列表和进度 |
|
|
116
|
+
| `openspec_update_task` | 更新任务状态 |
|
|
117
|
+
| `openspec_batch_update_tasks` | 批量更新任务状态 |
|
|
106
118
|
| `openspec_get_progress_summary` | 获取所有变更进度汇总 |
|
|
107
119
|
|
|
108
120
|
### 审批类 (Approval)
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
|
112
|
-
| `
|
|
113
|
-
| `
|
|
114
|
-
| `
|
|
121
|
+
|
|
122
|
+
| 工具 | 描述 |
|
|
123
|
+
| --------------------------------- | ------------ |
|
|
124
|
+
| `openspec_get_approval_status` | 获取审批状态 |
|
|
125
|
+
| `openspec_request_approval` | 请求审批 |
|
|
126
|
+
| `openspec_approve_change` | 批准变更 |
|
|
127
|
+
| `openspec_reject_change` | 拒绝变更 |
|
|
115
128
|
| `openspec_list_pending_approvals` | 列出待审批项 |
|
|
116
129
|
|
|
130
|
+
### 评审类 (Reviews)
|
|
131
|
+
|
|
132
|
+
| 工具 | 描述 |
|
|
133
|
+
| ----------------------------------- | ------------------------------------ |
|
|
134
|
+
| `openspec_add_review` | 添加评审意见到 proposal/design/tasks |
|
|
135
|
+
| `openspec_list_reviews` | 列出评审意见(支持过滤) |
|
|
136
|
+
| `openspec_reply_review` | 回复评审意见 |
|
|
137
|
+
| `openspec_resolve_review` | 标记评审为已解决 |
|
|
138
|
+
| `openspec_get_review_summary` | 获取评审统计信息 |
|
|
139
|
+
| `openspec_check_approval_readiness` | 检查是否可以请求审批 |
|
|
140
|
+
|
|
141
|
+
### 模板类 (Templates)
|
|
142
|
+
|
|
143
|
+
| 工具 | 描述 |
|
|
144
|
+
| --------------------------- | -------------- |
|
|
145
|
+
| `openspec_list_templates` | 列出可用模板 |
|
|
146
|
+
| `openspec_create_change` | 从模板创建变更 |
|
|
147
|
+
| `openspec_preview_template` | 预览模板内容 |
|
|
148
|
+
|
|
149
|
+
### 生成器类 (Generator)
|
|
150
|
+
|
|
151
|
+
| 工具 | 描述 |
|
|
152
|
+
| ---------------------------- | -------------- |
|
|
153
|
+
| `openspec_prepare_proposal` | 准备提案结构 |
|
|
154
|
+
| `openspec_save_proposal` | 保存生成的提案 |
|
|
155
|
+
| `openspec_generate_proposal` | 从需求生成提案 |
|
|
156
|
+
|
|
157
|
+
### Hooks 类
|
|
158
|
+
|
|
159
|
+
| 工具 | 描述 |
|
|
160
|
+
| ---------------------- | ----------------- |
|
|
161
|
+
| `openspec_setup_hooks` | 设置项目 Git 钩子 |
|
|
162
|
+
|
|
117
163
|
## 审批流程
|
|
118
164
|
|
|
119
165
|
```
|
|
@@ -134,7 +180,7 @@ openspec-mcp [path] [options]
|
|
|
134
180
|
选项:
|
|
135
181
|
--dashboard 仅启动 Web 仪表板(HTTP 模式)
|
|
136
182
|
--with-dashboard 启动 MCP 服务器并同时启动仪表板
|
|
137
|
-
-p, --port <number> 仪表板端口(默认:3000
|
|
183
|
+
-p, --port <number> 仪表板端口(默认:3000;占用时自动递增,0 为随机端口)
|
|
138
184
|
-V, --version 显示版本号
|
|
139
185
|
-h, --help 显示帮助
|
|
140
186
|
```
|
|
@@ -164,20 +210,22 @@ openspec-mcp --dashboard --port 8080
|
|
|
164
210
|
|
|
165
211
|
### 仪表板页面
|
|
166
212
|
|
|
167
|
-
| 路由
|
|
168
|
-
|
|
169
|
-
| `/`
|
|
170
|
-
| `/changes`
|
|
213
|
+
| 路由 | 描述 |
|
|
214
|
+
| -------------- | ------------------ |
|
|
215
|
+
| `/` | 概览统计和最近变更 |
|
|
216
|
+
| `/changes` | 变更列表及进度 |
|
|
171
217
|
| `/changes/:id` | 变更详情和任务管理 |
|
|
172
|
-
| `/specs`
|
|
173
|
-
| `/approvals`
|
|
218
|
+
| `/specs` | 浏览规格文档 |
|
|
219
|
+
| `/approvals` | 审批队列管理 |
|
|
174
220
|
|
|
175
221
|
### 功能亮点
|
|
176
222
|
|
|
177
|
-
- **实时更新**: WebSocket
|
|
223
|
+
- **实时更新**: WebSocket 连接实现进度和评审的实时更新
|
|
178
224
|
- **任务管理**: 直接在 UI 中切换任务状态
|
|
179
225
|
- **审批操作**: 带备注的批准/拒绝操作
|
|
180
226
|
- **进度可视化**: 进度条和状态徽章
|
|
227
|
+
- **评审管理**: 查看、解决和追踪评审,支持 Open/Resolved 切换
|
|
228
|
+
- **Markdown 渲染**: Proposal 和 Design 内容完整支持 Markdown 渲染
|
|
181
229
|
|
|
182
230
|
## 开发
|
|
183
231
|
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"changes.d.ts","sourceRoot":"","sources":["../../../src/api/routes/changes.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,SAAS,CAAC;AAC/C,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;AAE/C,wBAAgB,qBAAqB,CAAC,OAAO,EAAE,eAAe,EAAE,GAAG,EAAE,UAAU,GAAG,IAAI,
|
|
1
|
+
{"version":3,"file":"changes.d.ts","sourceRoot":"","sources":["../../../src/api/routes/changes.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,SAAS,CAAC;AAC/C,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;AAE/C,wBAAgB,qBAAqB,CAAC,OAAO,EAAE,eAAe,EAAE,GAAG,EAAE,UAAU,GAAG,IAAI,CAqIrF"}
|
|
@@ -51,5 +51,59 @@ export function registerChangesRoutes(fastify, ctx) {
|
|
|
51
51
|
return reply.status(400).send(result);
|
|
52
52
|
}
|
|
53
53
|
});
|
|
54
|
+
/**
|
|
55
|
+
* GET /api/changes/:id/reviews - 获取 Change 的所有 reviews
|
|
56
|
+
*/
|
|
57
|
+
fastify.get('/changes/:id/reviews', async (request) => {
|
|
58
|
+
const { id } = request.params;
|
|
59
|
+
const { reviewManager } = ctx;
|
|
60
|
+
const result = await reviewManager.getChangeReviews(id);
|
|
61
|
+
return result;
|
|
62
|
+
});
|
|
63
|
+
/**
|
|
64
|
+
* POST /api/changes/:id/reviews - 添加 review 到 Change
|
|
65
|
+
*/
|
|
66
|
+
fastify.post('/changes/:id/reviews', async (request, reply) => {
|
|
67
|
+
const { id } = request.params;
|
|
68
|
+
const { targetType, lineNumber, type, severity, body: reviewBody, author } = request.body;
|
|
69
|
+
if (!reviewBody || !type || !targetType) {
|
|
70
|
+
return reply.status(400).send({ error: 'body, type, and targetType are required' });
|
|
71
|
+
}
|
|
72
|
+
try {
|
|
73
|
+
const { reviewManager } = ctx;
|
|
74
|
+
const review = await reviewManager.addReview({
|
|
75
|
+
targetType,
|
|
76
|
+
targetId: id,
|
|
77
|
+
lineNumber,
|
|
78
|
+
type,
|
|
79
|
+
severity,
|
|
80
|
+
body: reviewBody,
|
|
81
|
+
author: author || 'user',
|
|
82
|
+
});
|
|
83
|
+
ctx.broadcast('review:added', { changeId: id, targetType, review }, 'reviews');
|
|
84
|
+
return { review };
|
|
85
|
+
}
|
|
86
|
+
catch (error) {
|
|
87
|
+
const message = error instanceof Error ? error.message : 'Failed to add review';
|
|
88
|
+
return reply.status(400).send({ error: message });
|
|
89
|
+
}
|
|
90
|
+
});
|
|
91
|
+
/**
|
|
92
|
+
* PATCH /api/changes/:id/reviews/:reviewId - 解决 review
|
|
93
|
+
*/
|
|
94
|
+
fastify.patch('/changes/:id/reviews/:reviewId', async (request, reply) => {
|
|
95
|
+
const { id, reviewId } = request.params;
|
|
96
|
+
const { targetType, status, resolvedBy } = request.body;
|
|
97
|
+
if (!['resolved', 'wont_fix'].includes(status) || !targetType) {
|
|
98
|
+
return reply.status(400).send({ error: 'Invalid status or missing targetType' });
|
|
99
|
+
}
|
|
100
|
+
const { reviewManager } = ctx;
|
|
101
|
+
const success = await reviewManager.resolveReview(targetType, id, reviewId, resolvedBy || 'user', status);
|
|
102
|
+
if (!success) {
|
|
103
|
+
return reply.status(404).send({ error: 'Review not found' });
|
|
104
|
+
}
|
|
105
|
+
ctx.broadcast('review:resolved', { changeId: id, targetType, reviewId, status }, 'reviews');
|
|
106
|
+
return { success: true };
|
|
107
|
+
});
|
|
54
108
|
}
|
|
55
109
|
//# sourceMappingURL=changes.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"changes.js","sourceRoot":"","sources":["../../../src/api/routes/changes.ts"],"names":[],"mappings":"AAAA;;GAEG;AAKH,MAAM,UAAU,qBAAqB,CAAC,OAAwB,EAAE,GAAe;IAC7E,MAAM,EAAE,GAAG,EAAE,GAAG,GAAG,CAAC;IAEpB;;OAEG;IACH,OAAO,CAAC,GAAG,CAAC,UAAU,EAAE,KAAK,EAAE,OAAO,EAAE,KAAK,EAAE,EAAE;QAC/C,MAAM,EAAE,eAAe,EAAE,GAAG,OAAO,CAAC,KAAqC,CAAC;QAC1E,MAAM,OAAO,GAAG,MAAM,GAAG,CAAC,WAAW,CAAC;YACpC,eAAe,EAAE,eAAe,KAAK,MAAM;SAC5C,CAAC,CAAC;QACH,OAAO,EAAE,OAAO,EAAE,CAAC;IACrB,CAAC,CAAC,CAAC;IAEH;;OAEG;IACH,OAAO,CAAC,GAAG,CAAC,cAAc,EAAE,KAAK,EAAE,OAAO,EAAE,KAAK,EAAE,EAAE;QACnD,MAAM,EAAE,EAAE,EAAE,GAAG,OAAO,CAAC,MAAwB,CAAC;QAChD,MAAM,MAAM,GAAG,MAAM,GAAG,CAAC,UAAU,CAAC,EAAE,CAAC,CAAC;QAExC,IAAI,CAAC,MAAM,EAAE,CAAC;YACZ,OAAO,KAAK,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC,IAAI,CAAC,EAAE,KAAK,EAAE,kBAAkB,EAAE,CAAC,CAAC;QAC/D,CAAC;QAED,OAAO,EAAE,MAAM,EAAE,CAAC;IACpB,CAAC,CAAC,CAAC;IAEH;;OAEG;IACH,OAAO,CAAC,IAAI,CAAC,uBAAuB,EAAE,KAAK,EAAE,OAAO,EAAE,KAAK,EAAE,EAAE;QAC7D,MAAM,EAAE,EAAE,EAAE,GAAG,OAAO,CAAC,MAAwB,CAAC;QAChD,MAAM,IAAI,GAAG,CAAC,OAAO,CAAC,IAAI,IAAI,EAAE,CAAyB,CAAC;QAC1D,MAAM,EAAE,MAAM,EAAE,GAAG,IAAI,CAAC;QAExB,MAAM,MAAM,GAAG,MAAM,GAAG,CAAC,cAAc,CAAC,EAAE,EAAE,EAAE,MAAM,EAAE,CAAC,CAAC;QACxD,OAAO,MAAM,CAAC;IAChB,CAAC,CAAC,CAAC;IAEH;;OAEG;IACH,OAAO,CAAC,IAAI,CAAC,sBAAsB,EAAE,KAAK,EAAE,OAAO,EAAE,KAAK,EAAE,EAAE;QAC5D,MAAM,EAAE,EAAE,EAAE,GAAG,OAAO,CAAC,MAAwB,CAAC;QAChD,MAAM,IAAI,GAAG,CAAC,OAAO,CAAC,IAAI,IAAI,EAAE,CAA4B,CAAC;QAC7D,MAAM,EAAE,SAAS,EAAE,GAAG,IAAI,CAAC;QAE3B,MAAM,MAAM,GAAG,MAAM,GAAG,CAAC,aAAa,CAAC,EAAE,EAAE,EAAE,SAAS,EAAE,CAAC,CAAC;QAE1D,IAAI,MAAM,CAAC,OAAO,EAAE,CAAC;YACnB,SAAS;YACT,GAAG,CAAC,SAAS,CAAC,iBAAiB,EAAE,EAAE,QAAQ,EAAE,EAAE,EAAE,YAAY,EAAE,MAAM,CAAC,YAAY,EAAE,CAAC,CAAC;YACtF,OAAO,MAAM,CAAC;QAChB,CAAC;aAAM,CAAC;YACN,OAAO,KAAK,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC;QACxC,CAAC;IACH,CAAC,CAAC,CAAC;AACL,CAAC"}
|
|
1
|
+
{"version":3,"file":"changes.js","sourceRoot":"","sources":["../../../src/api/routes/changes.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Project REST API 路由
|
|
3
|
+
*/
|
|
4
|
+
import type { FastifyInstance } from 'fastify';
|
|
5
|
+
import type { ApiContext } from '../server.js';
|
|
6
|
+
export declare function registerProjectRoutes(fastify: FastifyInstance, ctx: ApiContext): void;
|
|
7
|
+
//# sourceMappingURL=project.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"project.d.ts","sourceRoot":"","sources":["../../../src/api/routes/project.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,SAAS,CAAC;AAC/C,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;AAE/C,wBAAgB,qBAAqB,CAAC,OAAO,EAAE,eAAe,EAAE,GAAG,EAAE,UAAU,GAAG,IAAI,CAUrF"}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Project REST API 路由
|
|
3
|
+
*/
|
|
4
|
+
export function registerProjectRoutes(fastify, ctx) {
|
|
5
|
+
const { cli } = ctx;
|
|
6
|
+
/**
|
|
7
|
+
* GET /api/project - 获取项目名称
|
|
8
|
+
*/
|
|
9
|
+
fastify.get('/project', async () => {
|
|
10
|
+
const project = await cli.getProjectName();
|
|
11
|
+
return { project };
|
|
12
|
+
});
|
|
13
|
+
}
|
|
14
|
+
//# sourceMappingURL=project.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"project.js","sourceRoot":"","sources":["../../../src/api/routes/project.ts"],"names":[],"mappings":"AAAA;;GAEG;AAKH,MAAM,UAAU,qBAAqB,CAAC,OAAwB,EAAE,GAAe;IAC7E,MAAM,EAAE,GAAG,EAAE,GAAG,GAAG,CAAC;IAEpB;;OAEG;IACH,OAAO,CAAC,GAAG,CAAC,UAAU,EAAE,KAAK,IAAI,EAAE;QACjC,MAAM,OAAO,GAAG,MAAM,GAAG,CAAC,cAAc,EAAE,CAAC;QAC3C,OAAO,EAAE,OAAO,EAAE,CAAC;IACrB,CAAC,CAAC,CAAC;AACL,CAAC"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"specs.d.ts","sourceRoot":"","sources":["../../../src/api/routes/specs.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,SAAS,CAAC;AAC/C,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;
|
|
1
|
+
{"version":3,"file":"specs.d.ts","sourceRoot":"","sources":["../../../src/api/routes/specs.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,SAAS,CAAC;AAC/C,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;AAG/C,wBAAgB,mBAAmB,CAAC,OAAO,EAAE,eAAe,EAAE,GAAG,EAAE,UAAU,GAAG,IAAI,CAsKnF"}
|
package/dist/api/routes/specs.js
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
* Specs REST API 路由
|
|
3
3
|
*/
|
|
4
4
|
export function registerSpecsRoutes(fastify, ctx) {
|
|
5
|
-
const { cli } = ctx;
|
|
5
|
+
const { cli, reviewManager, specParser } = ctx;
|
|
6
6
|
/**
|
|
7
7
|
* GET /api/specs - 列出所有规格
|
|
8
8
|
*/
|
|
@@ -30,5 +30,104 @@ export function registerSpecsRoutes(fastify, ctx) {
|
|
|
30
30
|
const result = await cli.validateSpec(id, { strict });
|
|
31
31
|
return result;
|
|
32
32
|
});
|
|
33
|
+
/**
|
|
34
|
+
* GET /api/specs/dependencies - 获取 Spec 依赖图
|
|
35
|
+
*/
|
|
36
|
+
fastify.get('/specs/dependencies', async () => {
|
|
37
|
+
const graph = await specParser.buildDependencyGraph();
|
|
38
|
+
const mermaid = await specParser.toMermaid();
|
|
39
|
+
return {
|
|
40
|
+
graph,
|
|
41
|
+
mermaid,
|
|
42
|
+
};
|
|
43
|
+
});
|
|
44
|
+
/**
|
|
45
|
+
* GET /api/specs/:id/dependencies - 获取单个 Spec 的依赖链
|
|
46
|
+
*/
|
|
47
|
+
fastify.get('/specs/:id/dependencies', async (request) => {
|
|
48
|
+
const { id } = request.params;
|
|
49
|
+
const directDeps = await specParser.parseDependencies(id);
|
|
50
|
+
const allDeps = await specParser.getDependencyChain(id);
|
|
51
|
+
return {
|
|
52
|
+
specId: id,
|
|
53
|
+
direct: directDeps,
|
|
54
|
+
transitive: allDeps.filter((d) => !directDeps.includes(d)),
|
|
55
|
+
all: allDeps,
|
|
56
|
+
};
|
|
57
|
+
});
|
|
58
|
+
/**
|
|
59
|
+
* Reviews API for Specs
|
|
60
|
+
*/
|
|
61
|
+
/**
|
|
62
|
+
* GET /api/specs/:id/reviews - 列出 Spec 的评审意见
|
|
63
|
+
*/
|
|
64
|
+
fastify.get('/specs/:id/reviews', async (request) => {
|
|
65
|
+
const { id } = request.params;
|
|
66
|
+
const { status, type } = request.query;
|
|
67
|
+
const reviews = await reviewManager.listReviews('spec', id, {
|
|
68
|
+
status: status,
|
|
69
|
+
type: type,
|
|
70
|
+
});
|
|
71
|
+
return { reviews };
|
|
72
|
+
});
|
|
73
|
+
/**
|
|
74
|
+
* POST /api/specs/:id/reviews - 添加 Spec 评审意见
|
|
75
|
+
*/
|
|
76
|
+
fastify.post('/specs/:id/reviews', async (request, reply) => {
|
|
77
|
+
const { id } = request.params;
|
|
78
|
+
const { lineNumber, type, severity, body, suggestedChange, author } = request.body;
|
|
79
|
+
if (!body || !type) {
|
|
80
|
+
return reply.status(400).send({ error: 'body and type are required' });
|
|
81
|
+
}
|
|
82
|
+
try {
|
|
83
|
+
const review = await reviewManager.addReview({
|
|
84
|
+
targetType: 'spec',
|
|
85
|
+
targetId: id,
|
|
86
|
+
lineNumber,
|
|
87
|
+
type,
|
|
88
|
+
severity,
|
|
89
|
+
body,
|
|
90
|
+
suggestedChange,
|
|
91
|
+
author: author || 'user',
|
|
92
|
+
});
|
|
93
|
+
ctx.broadcast('review:added', { targetType: 'spec', targetId: id, review }, 'reviews');
|
|
94
|
+
return { review };
|
|
95
|
+
}
|
|
96
|
+
catch (error) {
|
|
97
|
+
const message = error instanceof Error ? error.message : 'Failed to add review';
|
|
98
|
+
return reply.status(400).send({ error: message });
|
|
99
|
+
}
|
|
100
|
+
});
|
|
101
|
+
/**
|
|
102
|
+
* POST /api/specs/:id/reviews/:reviewId/reply - 回复评审
|
|
103
|
+
*/
|
|
104
|
+
fastify.post('/specs/:id/reviews/:reviewId/reply', async (request, reply) => {
|
|
105
|
+
const { id, reviewId } = request.params;
|
|
106
|
+
const { body, author } = request.body;
|
|
107
|
+
if (!body) {
|
|
108
|
+
return reply.status(400).send({ error: 'body is required' });
|
|
109
|
+
}
|
|
110
|
+
const result = await reviewManager.addReply('spec', id, reviewId, author || 'user', body);
|
|
111
|
+
if (!result) {
|
|
112
|
+
return reply.status(404).send({ error: 'Review not found' });
|
|
113
|
+
}
|
|
114
|
+
return { reply: result };
|
|
115
|
+
});
|
|
116
|
+
/**
|
|
117
|
+
* PATCH /api/specs/:id/reviews/:reviewId - 解决评审
|
|
118
|
+
*/
|
|
119
|
+
fastify.patch('/specs/:id/reviews/:reviewId', async (request, reply) => {
|
|
120
|
+
const { id, reviewId } = request.params;
|
|
121
|
+
const { status, resolvedBy } = request.body;
|
|
122
|
+
if (!['resolved', 'wont_fix'].includes(status)) {
|
|
123
|
+
return reply.status(400).send({ error: 'Invalid status' });
|
|
124
|
+
}
|
|
125
|
+
const success = await reviewManager.resolveReview('spec', id, reviewId, resolvedBy || 'user', status);
|
|
126
|
+
if (!success) {
|
|
127
|
+
return reply.status(404).send({ error: 'Review not found' });
|
|
128
|
+
}
|
|
129
|
+
ctx.broadcast('review:resolved', { targetType: 'spec', targetId: id, reviewId, status }, 'reviews');
|
|
130
|
+
return { success: true };
|
|
131
|
+
});
|
|
33
132
|
}
|
|
34
133
|
//# sourceMappingURL=specs.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"specs.js","sourceRoot":"","sources":["../../../src/api/routes/specs.ts"],"names":[],"mappings":"AAAA;;GAEG;
|
|
1
|
+
{"version":3,"file":"specs.js","sourceRoot":"","sources":["../../../src/api/routes/specs.ts"],"names":[],"mappings":"AAAA;;GAEG;AAMH,MAAM,UAAU,mBAAmB,CAAC,OAAwB,EAAE,GAAe;IAC3E,MAAM,EAAE,GAAG,EAAE,aAAa,EAAE,UAAU,EAAE,GAAG,GAAG,CAAC;IAE/C;;OAEG;IACH,OAAO,CAAC,GAAG,CAAC,QAAQ,EAAE,KAAK,IAAI,EAAE;QAC/B,MAAM,KAAK,GAAG,MAAM,GAAG,CAAC,SAAS,EAAE,CAAC;QACpC,OAAO,EAAE,KAAK,EAAE,CAAC;IACnB,CAAC,CAAC,CAAC;IAEH;;OAEG;IACH,OAAO,CAAC,GAAG,CAAC,YAAY,EAAE,KAAK,EAAE,OAAO,EAAE,KAAK,EAAE,EAAE;QACjD,MAAM,EAAE,EAAE,EAAE,GAAG,OAAO,CAAC,MAAwB,CAAC;QAChD,MAAM,IAAI,GAAG,MAAM,GAAG,CAAC,QAAQ,CAAC,EAAE,CAAC,CAAC;QAEpC,IAAI,CAAC,IAAI,EAAE,CAAC;YACV,OAAO,KAAK,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC,IAAI,CAAC,EAAE,KAAK,EAAE,gBAAgB,EAAE,CAAC,CAAC;QAC7D,CAAC;QAED,OAAO,EAAE,IAAI,EAAE,CAAC;IAClB,CAAC,CAAC,CAAC;IAEH;;OAEG;IACH,OAAO,CAAC,IAAI,CAAC,qBAAqB,EAAE,KAAK,EAAE,OAAO,EAAE,EAAE;QACpD,MAAM,EAAE,EAAE,EAAE,GAAG,OAAO,CAAC,MAAwB,CAAC;QAChD,MAAM,EAAE,MAAM,EAAE,GAAG,OAAO,CAAC,IAA4B,CAAC;QAExD,MAAM,MAAM,GAAG,MAAM,GAAG,CAAC,YAAY,CAAC,EAAE,EAAE,EAAE,MAAM,EAAE,CAAC,CAAC;QACtD,OAAO,MAAM,CAAC;IAChB,CAAC,CAAC,CAAC;IAEH;;OAEG;IACH,OAAO,CAAC,GAAG,CAAC,qBAAqB,EAAE,KAAK,IAAI,EAAE;QAC5C,MAAM,KAAK,GAAG,MAAM,UAAU,CAAC,oBAAoB,EAAE,CAAC;QACtD,MAAM,OAAO,GAAG,MAAM,UAAU,CAAC,SAAS,EAAE,CAAC;QAE7C,OAAO;YACL,KAAK;YACL,OAAO;SACR,CAAC;IACJ,CAAC,CAAC,CAAC;IAEH;;OAEG;IACH,OAAO,CAAC,GAAG,CAAC,yBAAyB,EAAE,KAAK,EAAE,OAAO,EAAE,EAAE;QACvD,MAAM,EAAE,EAAE,EAAE,GAAG,OAAO,CAAC,MAAwB,CAAC;QAEhD,MAAM,UAAU,GAAG,MAAM,UAAU,CAAC,iBAAiB,CAAC,EAAE,CAAC,CAAC;QAC1D,MAAM,OAAO,GAAG,MAAM,UAAU,CAAC,kBAAkB,CAAC,EAAE,CAAC,CAAC;QAExD,OAAO;YACL,MAAM,EAAE,EAAE;YACV,MAAM,EAAE,UAAU;YAClB,UAAU,EAAE,OAAO,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,UAAU,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC;YAC1D,GAAG,EAAE,OAAO;SACb,CAAC;IACJ,CAAC,CAAC,CAAC;IAEH;;OAEG;IAEH;;OAEG;IACH,OAAO,CAAC,GAAG,CAAC,oBAAoB,EAAE,KAAK,EAAE,OAAO,EAAE,EAAE;QAClD,MAAM,EAAE,EAAE,EAAE,GAAG,OAAO,CAAC,MAAwB,CAAC;QAChD,MAAM,EAAE,MAAM,EAAE,IAAI,EAAE,GAAG,OAAO,CAAC,KAA2C,CAAC;QAE7E,MAAM,OAAO,GAAG,MAAM,aAAa,CAAC,WAAW,CAAC,MAAM,EAAE,EAAE,EAAE;YAC1D,MAAM,EAAE,MAAsD;YAC9D,IAAI,EAAE,IAA8B;SACrC,CAAC,CAAC;QAEH,OAAO,EAAE,OAAO,EAAE,CAAC;IACrB,CAAC,CAAC,CAAC;IAEH;;OAEG;IACH,OAAO,CAAC,IAAI,CAAC,oBAAoB,EAAE,KAAK,EAAE,OAAO,EAAE,KAAK,EAAE,EAAE;QAC1D,MAAM,EAAE,EAAE,EAAE,GAAG,OAAO,CAAC,MAAwB,CAAC;QAChD,MAAM,EAAE,UAAU,EAAE,IAAI,EAAE,QAAQ,EAAE,IAAI,EAAE,eAAe,EAAE,MAAM,EAAE,GAAG,OAAO,CAAC,IAO7E,CAAC;QAEF,IAAI,CAAC,IAAI,IAAI,CAAC,IAAI,EAAE,CAAC;YACnB,OAAO,KAAK,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC,IAAI,CAAC,EAAE,KAAK,EAAE,4BAA4B,EAAE,CAAC,CAAC;QACzE,CAAC;QAED,IAAI,CAAC;YACH,MAAM,MAAM,GAAG,MAAM,aAAa,CAAC,SAAS,CAAC;gBAC3C,UAAU,EAAE,MAAM;gBAClB,QAAQ,EAAE,EAAE;gBACZ,UAAU;gBACV,IAAI;gBACJ,QAAQ;gBACR,IAAI;gBACJ,eAAe;gBACf,MAAM,EAAE,MAAM,IAAI,MAAM;aACzB,CAAC,CAAC;YAEH,GAAG,CAAC,SAAS,CAAC,cAAc,EAAE,EAAE,UAAU,EAAE,MAAM,EAAE,QAAQ,EAAE,EAAE,EAAE,MAAM,EAAE,EAAE,SAAS,CAAC,CAAC;YACvF,OAAO,EAAE,MAAM,EAAE,CAAC;QACpB,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,MAAM,OAAO,GAAG,KAAK,YAAY,KAAK,CAAC,CAAC,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC,CAAC,sBAAsB,CAAC;YAChF,OAAO,KAAK,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC,IAAI,CAAC,EAAE,KAAK,EAAE,OAAO,EAAE,CAAC,CAAC;QACpD,CAAC;IACH,CAAC,CAAC,CAAC;IAEH;;OAEG;IACH,OAAO,CAAC,IAAI,CAAC,oCAAoC,EAAE,KAAK,EAAE,OAAO,EAAE,KAAK,EAAE,EAAE;QAC1E,MAAM,EAAE,EAAE,EAAE,QAAQ,EAAE,GAAG,OAAO,CAAC,MAA0C,CAAC;QAC5E,MAAM,EAAE,IAAI,EAAE,MAAM,EAAE,GAAG,OAAO,CAAC,IAAyC,CAAC;QAE3E,IAAI,CAAC,IAAI,EAAE,CAAC;YACV,OAAO,KAAK,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC,IAAI,CAAC,EAAE,KAAK,EAAE,kBAAkB,EAAE,CAAC,CAAC;QAC/D,CAAC;QAED,MAAM,MAAM,GAAG,MAAM,aAAa,CAAC,QAAQ,CAAC,MAAM,EAAE,EAAE,EAAE,QAAQ,EAAE,MAAM,IAAI,MAAM,EAAE,IAAI,CAAC,CAAC;QAE1F,IAAI,CAAC,MAAM,EAAE,CAAC;YACZ,OAAO,KAAK,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC,IAAI,CAAC,EAAE,KAAK,EAAE,kBAAkB,EAAE,CAAC,CAAC;QAC/D,CAAC;QAED,OAAO,EAAE,KAAK,EAAE,MAAM,EAAE,CAAC;IAC3B,CAAC,CAAC,CAAC;IAEH;;OAEG;IACH,OAAO,CAAC,KAAK,CAAC,8BAA8B,EAAE,KAAK,EAAE,OAAO,EAAE,KAAK,EAAE,EAAE;QACrE,MAAM,EAAE,EAAE,EAAE,QAAQ,EAAE,GAAG,OAAO,CAAC,MAA0C,CAAC;QAC5E,MAAM,EAAE,MAAM,EAAE,UAAU,EAAE,GAAG,OAAO,CAAC,IAGtC,CAAC;QAEF,IAAI,CAAC,CAAC,UAAU,EAAE,UAAU,CAAC,CAAC,QAAQ,CAAC,MAAM,CAAC,EAAE,CAAC;YAC/C,OAAO,KAAK,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC,IAAI,CAAC,EAAE,KAAK,EAAE,gBAAgB,EAAE,CAAC,CAAC;QAC7D,CAAC;QAED,MAAM,OAAO,GAAG,MAAM,aAAa,CAAC,aAAa,CAAC,MAAM,EAAE,EAAE,EAAE,QAAQ,EAAE,UAAU,IAAI,MAAM,EAAE,MAAM,CAAC,CAAC;QAEtG,IAAI,CAAC,OAAO,EAAE,CAAC;YACb,OAAO,KAAK,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC,IAAI,CAAC,EAAE,KAAK,EAAE,kBAAkB,EAAE,CAAC,CAAC;QAC/D,CAAC;QAED,GAAG,CAAC,SAAS,CAAC,iBAAiB,EAAE,EAAE,UAAU,EAAE,MAAM,EAAE,QAAQ,EAAE,EAAE,EAAE,QAAQ,EAAE,MAAM,EAAE,EAAE,SAAS,CAAC,CAAC;QACpG,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,CAAC;IAC3B,CAAC,CAAC,CAAC;AACL,CAAC"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"tasks.d.ts","sourceRoot":"","sources":["../../../src/api/routes/tasks.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,SAAS,CAAC;AAC/C,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;AAE/C,wBAAgB,mBAAmB,CAAC,OAAO,EAAE,eAAe,EAAE,GAAG,EAAE,UAAU,GAAG,IAAI,
|
|
1
|
+
{"version":3,"file":"tasks.d.ts","sourceRoot":"","sources":["../../../src/api/routes/tasks.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,SAAS,CAAC;AAC/C,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;AAE/C,wBAAgB,mBAAmB,CAAC,OAAO,EAAE,eAAe,EAAE,GAAG,EAAE,UAAU,GAAG,IAAI,CA4GnF"}
|