@projitive/mcp 2.0.3 → 2.1.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/output/package.json +8 -2
- package/output/source/common/artifacts.js +1 -1
- package/output/source/common/artifacts.test.js +11 -11
- package/output/source/common/errors.js +19 -19
- package/output/source/common/errors.test.js +59 -0
- package/output/source/common/files.js +30 -19
- package/output/source/common/files.test.js +14 -14
- package/output/source/common/index.js +11 -10
- package/output/source/common/linter.js +29 -27
- package/output/source/common/linter.test.js +9 -9
- package/output/source/common/markdown.js +3 -3
- package/output/source/common/markdown.test.js +15 -15
- package/output/source/common/response.js +91 -107
- package/output/source/common/response.test.js +30 -30
- package/output/source/common/store.js +40 -40
- package/output/source/common/store.test.js +72 -72
- package/output/source/common/tool.js +43 -0
- package/output/source/common/types.js +3 -3
- package/output/source/common/utils.js +8 -8
- package/output/source/common/utils.test.js +48 -0
- package/output/source/index.js +16 -16
- package/output/source/index.runtime.test.js +57 -0
- package/output/source/index.test.js +64 -64
- package/output/source/prompts/index.js +3 -3
- package/output/source/prompts/index.test.js +23 -0
- package/output/source/prompts/quickStart.js +96 -96
- package/output/source/prompts/quickStart.test.js +24 -0
- package/output/source/prompts/taskDiscovery.js +184 -184
- package/output/source/prompts/taskDiscovery.test.js +24 -0
- package/output/source/prompts/taskExecution.js +164 -148
- package/output/source/prompts/taskExecution.test.js +27 -0
- package/output/source/resources/designs.js +26 -26
- package/output/source/resources/designs.resources.test.js +52 -0
- package/output/source/resources/designs.test.js +88 -88
- package/output/source/resources/governance.js +19 -19
- package/output/source/resources/governance.test.js +35 -0
- package/output/source/resources/index.js +2 -2
- package/output/source/resources/index.test.js +18 -0
- package/output/source/resources/readme.js +7 -7
- package/output/source/resources/readme.test.js +113 -113
- package/output/source/resources/reports.js +10 -10
- package/output/source/resources/reports.test.js +83 -83
- package/output/source/tools/index.js +3 -3
- package/output/source/tools/index.test.js +23 -0
- package/output/source/tools/project.js +330 -377
- package/output/source/tools/project.test.js +308 -175
- package/output/source/tools/roadmap.js +236 -255
- package/output/source/tools/roadmap.test.js +241 -46
- package/output/source/tools/task.js +770 -652
- package/output/source/tools/task.test.js +433 -105
- package/output/source/types.js +28 -22
- package/package.json +8 -2
|
@@ -1,11 +1,11 @@
|
|
|
1
|
-
import { z } from
|
|
1
|
+
import { z } from 'zod';
|
|
2
2
|
function asUserPrompt(text) {
|
|
3
3
|
return {
|
|
4
4
|
messages: [
|
|
5
5
|
{
|
|
6
|
-
role:
|
|
6
|
+
role: 'user',
|
|
7
7
|
content: {
|
|
8
|
-
type:
|
|
8
|
+
type: 'text',
|
|
9
9
|
text,
|
|
10
10
|
},
|
|
11
11
|
},
|
|
@@ -13,196 +13,196 @@ function asUserPrompt(text) {
|
|
|
13
13
|
};
|
|
14
14
|
}
|
|
15
15
|
export function registerTaskDiscoveryPrompt(server) {
|
|
16
|
-
server.registerPrompt(
|
|
17
|
-
title:
|
|
18
|
-
description:
|
|
16
|
+
server.registerPrompt('taskDiscovery', {
|
|
17
|
+
title: 'Task Discovery',
|
|
18
|
+
description: 'Minimal steps to find, context, and execute the first actionable task',
|
|
19
19
|
argsSchema: {
|
|
20
20
|
projectPath: z.string().optional(),
|
|
21
21
|
},
|
|
22
22
|
}, async ({ projectPath }) => {
|
|
23
23
|
const text = [
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
24
|
+
'# How to Discover Tasks',
|
|
25
|
+
'',
|
|
26
|
+
'You are a Projitive task discovery assistant. Here is the complete workflow to discover and execute your first task:',
|
|
27
|
+
'',
|
|
28
|
+
'## Step 1: Locate the Project',
|
|
29
|
+
'',
|
|
30
30
|
projectPath
|
|
31
31
|
? [
|
|
32
32
|
`- Known project path: "${projectPath}"`,
|
|
33
|
-
|
|
34
|
-
].join(
|
|
33
|
+
'- Call `projectContext(projectPath="' + projectPath + '")` directly to load project context',
|
|
34
|
+
].join('\n')
|
|
35
35
|
: [
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
].join(
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
|
|
205
|
-
].join(
|
|
36
|
+
'- Unknown project path:',
|
|
37
|
+
' 1. Call `projectScan()` to discover all governance roots',
|
|
38
|
+
' 2. Select a project',
|
|
39
|
+
' 3. Call `projectLocate(inputPath="<selected-path>")` to lock governance root',
|
|
40
|
+
' 4. Call `projectContext(projectPath="<project-path>")` to load project context',
|
|
41
|
+
].join('\n'),
|
|
42
|
+
'',
|
|
43
|
+
'## Step 2: Read Project Context',
|
|
44
|
+
'',
|
|
45
|
+
'After loading project context, focus on:',
|
|
46
|
+
'',
|
|
47
|
+
'### Task Summary',
|
|
48
|
+
'- total: Total tasks',
|
|
49
|
+
'- TODO: Pending tasks (highest priority)',
|
|
50
|
+
'- IN_PROGRESS: In-progress tasks (priority to continue)',
|
|
51
|
+
'- BLOCKED: Blocked tasks (need to resolve first)',
|
|
52
|
+
'- DONE: Completed tasks',
|
|
53
|
+
'',
|
|
54
|
+
'### Artifacts',
|
|
55
|
+
'Check if these files exist:',
|
|
56
|
+
'- \u2705 .projitive - Governance store file (required)',
|
|
57
|
+
'- \u2705 tasks.md - Generated task view',
|
|
58
|
+
'- \u2705 roadmap.md - Generated roadmap view',
|
|
59
|
+
'- \u2705 README.md - Project description',
|
|
60
|
+
'- \u2705 designs/ - Design documents directory',
|
|
61
|
+
'- \u2705 reports/ - Reports directory',
|
|
62
|
+
'',
|
|
63
|
+
'## Step 3: Select a Task',
|
|
64
|
+
'',
|
|
65
|
+
'### Priority Order',
|
|
66
|
+
'Select tasks in this priority order:',
|
|
67
|
+
'',
|
|
68
|
+
'1. **IN_PROGRESS** - Priority to continue in-progress tasks first',
|
|
69
|
+
' - These tasks have already started, should continue to finish',
|
|
70
|
+
' - Check updatedAt time, most recent first',
|
|
71
|
+
'',
|
|
72
|
+
'2. **TODO** - Next select pending tasks',
|
|
73
|
+
' - Tasks with roadmapRefs first',
|
|
74
|
+
' - Tasks with explicit owner first',
|
|
75
|
+
'',
|
|
76
|
+
'3. **BLOCKED** - Last consider blocked tasks',
|
|
77
|
+
' - Need to analyze blocker reason first',
|
|
78
|
+
' - May need to create sub-task to resolve blocker',
|
|
79
|
+
'',
|
|
80
|
+
'### Discovery Methods',
|
|
81
|
+
'',
|
|
82
|
+
'#### Method A: Auto-select with taskNext() (Recommended)',
|
|
83
|
+
'',
|
|
84
|
+
'Call `taskNext()`, the tool will automatically:',
|
|
85
|
+
'- Sort all tasks by priority',
|
|
86
|
+
'- Select highest-priority actionable task',
|
|
87
|
+
'- Return task ID and summary',
|
|
88
|
+
'',
|
|
89
|
+
'Then call `taskContext(projectPath="...", taskId="<task-id>")` for task details.',
|
|
90
|
+
'',
|
|
91
|
+
'### Discovery Quality Gate (before creating new tasks)',
|
|
92
|
+
'Only create a TODO when all conditions are true:',
|
|
93
|
+
'- It can be finished in one focused execution cycle',
|
|
94
|
+
'- It has explicit done condition and measurable evidence output',
|
|
95
|
+
'- It links to roadmap/readme/report/design context',
|
|
96
|
+
'- It does not duplicate an existing TODO/IN_PROGRESS/BLOCKED task',
|
|
97
|
+
'- It improves project throughput (unblocks or delivers user-visible value)',
|
|
98
|
+
'',
|
|
99
|
+
'#### Method B: Manual select with taskList()',
|
|
100
|
+
'',
|
|
101
|
+
'1. Call `taskList()` to get all tasks',
|
|
102
|
+
'2. Select based on these factors:',
|
|
103
|
+
' - status (IN_PROGRESS > TODO > BLOCKED)',
|
|
104
|
+
' - updatedAt time (most recent first)',
|
|
105
|
+
' - owner assigned (with owner first)',
|
|
106
|
+
' - roadmapRefs (with refs first)',
|
|
107
|
+
'3. Call `taskContext(projectPath="...", taskId="<selected-id>")` for details',
|
|
108
|
+
'',
|
|
109
|
+
'## Step 4: Understand Task Context',
|
|
110
|
+
'',
|
|
111
|
+
'After getting taskContext, read carefully:',
|
|
112
|
+
'',
|
|
113
|
+
'### Summary',
|
|
114
|
+
'- taskId: Task ID (NEVER modify this)',
|
|
115
|
+
'- status: Current status',
|
|
116
|
+
'- owner: Assignee',
|
|
117
|
+
'- roadmapRefs: Related roadmap',
|
|
118
|
+
'- updatedAt: Last updated time',
|
|
119
|
+
'',
|
|
120
|
+
'### Evidence',
|
|
121
|
+
'- Candidate Files - Related file list',
|
|
122
|
+
'- Reference Locations - Reference locations',
|
|
123
|
+
'',
|
|
124
|
+
'### Suggested Read Order',
|
|
125
|
+
'Read files in order, understand:',
|
|
126
|
+
'- Task background and motivation',
|
|
127
|
+
'- Task acceptance criteria',
|
|
128
|
+
'- Related design decisions',
|
|
129
|
+
'- Previous execution history',
|
|
130
|
+
'',
|
|
131
|
+
'### Lint Suggestions',
|
|
132
|
+
'Check if any warnings need to be resolved first.',
|
|
133
|
+
'',
|
|
134
|
+
'## Step 5: Execute the Task',
|
|
135
|
+
'',
|
|
136
|
+
'After understanding the task:',
|
|
137
|
+
'',
|
|
138
|
+
'1. **If status is TODO',
|
|
139
|
+
' - First call `taskUpdate()` to change status to IN_PROGRESS',
|
|
140
|
+
' - Set owner (if empty)',
|
|
141
|
+
' - Fill subState (optional, Spec v1.1.0)',
|
|
142
|
+
'',
|
|
143
|
+
'2. **If status is IN_PROGRESS',
|
|
144
|
+
' - Continue previous work',
|
|
145
|
+
' - Reference history reports in reports/',
|
|
146
|
+
'',
|
|
147
|
+
'3. **Execute task content**',
|
|
148
|
+
' - Update governance store via MCP tools; edit designs/*.md and reports/*.md as needed',
|
|
149
|
+
' - If immediate markdown snapshots are required by another agent/session, call syncViews(force=true)',
|
|
150
|
+
' - Create execution report (reports/ directory)',
|
|
151
|
+
' - Update task status to DONE',
|
|
152
|
+
'',
|
|
153
|
+
'4. **Verify changes**',
|
|
154
|
+
' - Re-run `taskContext()`',
|
|
155
|
+
' - Confirm all references still valid',
|
|
156
|
+
' - Confirm no new lint suggestions',
|
|
157
|
+
'',
|
|
158
|
+
'## Special Cases',
|
|
159
|
+
'',
|
|
160
|
+
'### Case 1: No tasks at all',
|
|
161
|
+
'',
|
|
162
|
+
'If taskNext() returns empty:',
|
|
163
|
+
'1. Check if .projitive exists',
|
|
164
|
+
'2. Analyze active roadmap milestones and derive 1-3 executable TODO tasks',
|
|
165
|
+
'3. Prioritize milestone slices that unblock multiple downstream tasks',
|
|
166
|
+
'3.5 If roadmap milestone is missing, create it first via `roadmapCreate()`',
|
|
167
|
+
'4. Create tasks via `taskCreate(projectPath="...", taskId="TASK-xxxx", title="...", roadmapRefs=["ROADMAP-xxxx"], summary="...")`',
|
|
168
|
+
'5. Re-run taskNext() and continue execution if tasks are available',
|
|
169
|
+
'6. If still empty, read design documents in designs/ directory',
|
|
170
|
+
'7. Read roadmap.md to understand project goals',
|
|
171
|
+
'8. Create 1-3 new TODO tasks',
|
|
172
|
+
'9. Each task must have:',
|
|
173
|
+
' - Unique TASK-xxxx ID',
|
|
174
|
+
' - Clear title',
|
|
175
|
+
' - Detailed summary',
|
|
176
|
+
' - Linked roadmapRefs (if applicable)',
|
|
177
|
+
'',
|
|
178
|
+
'### Case 2: All tasks are BLOCKED',
|
|
179
|
+
'',
|
|
180
|
+
'1. Select one blocked task and call `taskContext()`',
|
|
181
|
+
'2. Understand blocker reason (check blocker field, Spec v1.1.0)',
|
|
182
|
+
'3. Create a new TODO task via `taskCreate()` to resolve blocker',
|
|
183
|
+
'4. Execute this new task first',
|
|
184
|
+
'',
|
|
185
|
+
'### Case 3: Missing required governance files',
|
|
186
|
+
'',
|
|
187
|
+
'If .projitive does not exist:',
|
|
188
|
+
'1. Call `projectInit(projectPath="...")` to initialize governance structure',
|
|
189
|
+
'2. Then restart discovery flow',
|
|
190
|
+
'',
|
|
191
|
+
'## Quick Reference',
|
|
192
|
+
'',
|
|
193
|
+
'| Tool | Purpose |',
|
|
194
|
+
'|------|---------|',
|
|
195
|
+
'| `projectScan()` | Discover all governance roots |',
|
|
196
|
+
'| `projectLocate()` | Lock governance root |',
|
|
197
|
+
'| `projectContext()` | Load project overview |',
|
|
198
|
+
'| `taskNext()` | Auto-select best task |',
|
|
199
|
+
'| `taskList()` | List all tasks |',
|
|
200
|
+
'| `taskContext()` | Get task details |',
|
|
201
|
+
'| `taskCreate()` | Create a new task |',
|
|
202
|
+
'| `taskUpdate()` | Update task status |',
|
|
203
|
+
'| `roadmapCreate()` | Create a new roadmap milestone |',
|
|
204
|
+
'| `syncViews()` | Force materialize tasks.md/roadmap.md from governance store |',
|
|
205
|
+
].join('\n');
|
|
206
206
|
return asUserPrompt(text);
|
|
207
207
|
});
|
|
208
208
|
}
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
import { describe, expect, it, vi } from 'vitest';
|
|
2
|
+
import { registerTaskDiscoveryPrompt } from './taskDiscovery.js';
|
|
3
|
+
describe('taskDiscovery prompt', () => {
|
|
4
|
+
it('registers the prompt and renders project-specific discovery guidance', async () => {
|
|
5
|
+
const server = { registerPrompt: vi.fn() };
|
|
6
|
+
registerTaskDiscoveryPrompt(server);
|
|
7
|
+
const handler = server.registerPrompt.mock.calls[0][2];
|
|
8
|
+
const result = await handler({ projectPath: '/workspace/app' });
|
|
9
|
+
const text = result.messages[0].content.text;
|
|
10
|
+
expect(server.registerPrompt.mock.calls[0][0]).toBe('taskDiscovery');
|
|
11
|
+
expect(text).toContain('Known project path: "/workspace/app"');
|
|
12
|
+
expect(text).toContain('Method A: Auto-select with taskNext()');
|
|
13
|
+
expect(text).toContain('roadmapCreate');
|
|
14
|
+
});
|
|
15
|
+
it('renders unknown-project discovery steps', async () => {
|
|
16
|
+
const server = { registerPrompt: vi.fn() };
|
|
17
|
+
registerTaskDiscoveryPrompt(server);
|
|
18
|
+
const handler = server.registerPrompt.mock.calls[0][2];
|
|
19
|
+
const result = await handler({});
|
|
20
|
+
const text = result.messages[0].content.text;
|
|
21
|
+
expect(text).toContain('Call `projectScan()` to discover all governance roots');
|
|
22
|
+
expect(text).toContain('Call `projectContext(projectPath="<project-path>")` to load project context');
|
|
23
|
+
});
|
|
24
|
+
});
|