@krr2020/taskflow-mcp-server 0.1.0-beta.1

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/dist/index.js ADDED
@@ -0,0 +1,232 @@
1
+ #!/usr/bin/env node
2
+ import { Server } from "@modelcontextprotocol/sdk/server/index.js";
3
+ import { StdioServerTransport } from "@modelcontextprotocol/sdk/server/stdio.js";
4
+ import { CallToolRequestSchema, ListToolsRequestSchema, ErrorCode, McpError, } from "@modelcontextprotocol/sdk/types.js";
5
+ import { z } from "zod";
6
+ import { StateMachine, ConfigLoader, GitManager } from "@krr2020/taskflow-core";
7
+ // Initialize Core Components
8
+ const configLoader = new ConfigLoader();
9
+ const gitManager = new GitManager();
10
+ const stateMachine = new StateMachine(configLoader, gitManager);
11
+ // Initialize MCP Server
12
+ const server = new Server({
13
+ name: "taskflow-mcp-server",
14
+ version: "0.1.0",
15
+ }, {
16
+ capabilities: {
17
+ tools: {},
18
+ },
19
+ });
20
+ // Tool Definitions
21
+ server.setRequestHandler(ListToolsRequestSchema, async () => {
22
+ return {
23
+ tools: [
24
+ {
25
+ name: "start_task",
26
+ description: "Start a new task, checking out the correct story branch and entering PLANNING mode.",
27
+ inputSchema: {
28
+ type: "object",
29
+ properties: {
30
+ taskId: {
31
+ type: "string",
32
+ description: "The ID of the task to start (e.g., '1.2.3')",
33
+ },
34
+ storyId: {
35
+ type: "string",
36
+ description: "The Story ID this task belongs to (e.g., '15')",
37
+ },
38
+ slug: {
39
+ type: "string",
40
+ description: "Short slug for the story (e.g., 'user-auth')",
41
+ },
42
+ },
43
+ required: ["taskId", "storyId", "slug"],
44
+ },
45
+ },
46
+ {
47
+ name: "approve_plan",
48
+ description: "Approve the implementation plan and switch to EXECUTION mode.",
49
+ inputSchema: {
50
+ type: "object",
51
+ properties: {},
52
+ },
53
+ },
54
+ {
55
+ name: "get_status",
56
+ description: "Get the current state machine status and active task.",
57
+ inputSchema: {
58
+ type: "object",
59
+ properties: {},
60
+ },
61
+ },
62
+ {
63
+ name: "generate_prd",
64
+ description: "Generate a PRD template based on project context.",
65
+ inputSchema: {
66
+ type: "object",
67
+ properties: {
68
+ requirements: { type: "string" }
69
+ },
70
+ },
71
+ },
72
+ {
73
+ name: "generate_tasks",
74
+ description: "Generate tasks from a PRD.",
75
+ inputSchema: {
76
+ type: "object",
77
+ properties: {
78
+ prdContent: { type: "string" }
79
+ },
80
+ },
81
+ },
82
+ {
83
+ name: "run_checks",
84
+ description: "Run project validations and enter VERIFICATION state.",
85
+ inputSchema: {
86
+ type: "object",
87
+ properties: {},
88
+ },
89
+ },
90
+ {
91
+ name: "submit_task",
92
+ description: "Submit the current task and complete the workflow.",
93
+ inputSchema: {
94
+ type: "object",
95
+ properties: {},
96
+ },
97
+ },
98
+ ],
99
+ };
100
+ });
101
+ // Tool Execution
102
+ server.setRequestHandler(CallToolRequestSchema, async (request) => {
103
+ const { name, arguments: args } = request.params;
104
+ try {
105
+ switch (name) {
106
+ case "start_task": {
107
+ const schema = z.object({
108
+ taskId: z.string(),
109
+ storyId: z.string(),
110
+ slug: z.string(),
111
+ });
112
+ const { taskId, storyId, slug } = schema.parse(args);
113
+ await stateMachine.startTask(taskId, storyId, slug);
114
+ return {
115
+ content: [
116
+ {
117
+ type: "text",
118
+ text: `Task ${taskId} started on branch story/S${storyId}-${slug}. State is now PLANNING.`,
119
+ },
120
+ ],
121
+ };
122
+ }
123
+ case "approve_plan": {
124
+ stateMachine.approvePlan();
125
+ return {
126
+ content: [
127
+ {
128
+ type: "text",
129
+ text: "Plan approved. State is now EXECUTION. You may now write code.",
130
+ },
131
+ ],
132
+ };
133
+ }
134
+ case "get_status": {
135
+ return {
136
+ content: [
137
+ {
138
+ type: "text",
139
+ text: JSON.stringify({
140
+ state: stateMachine.getState(),
141
+ activeTask: stateMachine.getActiveTask(),
142
+ }, null, 2),
143
+ },
144
+ ],
145
+ };
146
+ }
147
+ case "generate_prd": {
148
+ const template = `# Project Requirements Document
149
+ ## 1. Objective
150
+ [Describe the goal]
151
+
152
+ ## 2. Scope
153
+ - [ ] In Scope
154
+ - [ ] Out of Scope
155
+
156
+ ## 3. Technical Requirements
157
+ - Language: [e.g., TypeScript]
158
+ - Framework: [e.g., React]
159
+
160
+ ## 4. User Stories
161
+ - Story 1: [Description]
162
+ `;
163
+ return {
164
+ content: [
165
+ {
166
+ type: "text",
167
+ text: template,
168
+ },
169
+ ],
170
+ };
171
+ }
172
+ case "generate_tasks": {
173
+ // In a real implementation, this would parse the PRD.
174
+ // For prototype, we return the schema structure.
175
+ return {
176
+ content: [
177
+ {
178
+ type: "text",
179
+ text: "Please provide the tasks in the following JSON format matching the TaskSchema:\n" +
180
+ JSON.stringify({
181
+ id: "1.0",
182
+ title: "Example Task",
183
+ status: "todo",
184
+ subtasks: [{ id: "1.1", title: "Subtask 1" }]
185
+ }, null, 2)
186
+ },
187
+ ],
188
+ };
189
+ }
190
+ case "run_checks": {
191
+ stateMachine.startVerification();
192
+ // TODO: Actually run the validation commands from config
193
+ return {
194
+ content: [{ type: "text", text: "Verification phase started. Running checks... [MOCK PASSED]" }],
195
+ };
196
+ }
197
+ case "submit_task": {
198
+ stateMachine.completeTask();
199
+ return {
200
+ content: [{ type: "text", text: "Task submitted and completed. State is now IDLE." }],
201
+ };
202
+ }
203
+ default:
204
+ throw new McpError(ErrorCode.MethodNotFound, `Unknown tool: ${name}`);
205
+ }
206
+ }
207
+ catch (error) {
208
+ if (error instanceof z.ZodError) {
209
+ throw new McpError(ErrorCode.InvalidParams, `Invalid arguments: ${error.message}`);
210
+ }
211
+ const errorMessage = error instanceof Error ? error.message : String(error);
212
+ return {
213
+ content: [
214
+ {
215
+ type: "text",
216
+ text: `Error executing ${name}: ${errorMessage}`,
217
+ },
218
+ ],
219
+ isError: true,
220
+ };
221
+ }
222
+ });
223
+ // Start Server
224
+ async function main() {
225
+ const transport = new StdioServerTransport();
226
+ await server.connect(transport);
227
+ console.error("Taskflow MCP Server running on stdio");
228
+ }
229
+ main().catch((error) => {
230
+ console.error("Fatal error in main():", error);
231
+ process.exit(1);
232
+ });
package/package.json ADDED
@@ -0,0 +1,27 @@
1
+ {
2
+ "name": "@krr2020/taskflow-mcp-server",
3
+ "version": "0.1.0-beta.1",
4
+ "description": "MCP Server for Taskflow 2.0",
5
+ "license": "MIT",
6
+ "publishConfig": {
7
+ "access": "public"
8
+ },
9
+ "type": "module",
10
+ "main": "dist/index.js",
11
+ "bin": {
12
+ "taskflow-mcp": "./dist/index.js"
13
+ },
14
+ "dependencies": {
15
+ "@modelcontextprotocol/sdk": "^0.6.0",
16
+ "zod": "^3.22.4",
17
+ "@krr2020/taskflow-core": "0.1.0-beta.1"
18
+ },
19
+ "devDependencies": {
20
+ "typescript": "^5.3.3",
21
+ "@types/node": "^20.11.0"
22
+ },
23
+ "scripts": {
24
+ "build": "tsc",
25
+ "start": "node dist/index.js"
26
+ }
27
+ }
package/src/index.ts ADDED
@@ -0,0 +1,261 @@
1
+ #!/usr/bin/env node
2
+ import { Server } from "@modelcontextprotocol/sdk/server/index.js";
3
+ import { StdioServerTransport } from "@modelcontextprotocol/sdk/server/stdio.js";
4
+ import {
5
+ CallToolRequestSchema,
6
+ ListToolsRequestSchema,
7
+ ErrorCode,
8
+ McpError,
9
+ } from "@modelcontextprotocol/sdk/types.js";
10
+ import { z } from "zod";
11
+ import { StateMachine, ConfigLoader, GitManager } from "@krr2020/taskflow-core";
12
+
13
+ // Initialize Core Components
14
+ const configLoader = new ConfigLoader();
15
+ const gitManager = new GitManager();
16
+ const stateMachine = new StateMachine(configLoader, gitManager);
17
+
18
+ // Initialize MCP Server
19
+ const server = new Server(
20
+ {
21
+ name: "taskflow-mcp-server",
22
+ version: "0.1.0",
23
+ },
24
+ {
25
+ capabilities: {
26
+ tools: {},
27
+ },
28
+ }
29
+ );
30
+
31
+ // Tool Definitions
32
+ server.setRequestHandler(ListToolsRequestSchema, async () => {
33
+ return {
34
+ tools: [
35
+ {
36
+ name: "start_task",
37
+ description: "Start a new task, checking out the correct story branch and entering PLANNING mode.",
38
+ inputSchema: {
39
+ type: "object",
40
+ properties: {
41
+ taskId: {
42
+ type: "string",
43
+ description: "The ID of the task to start (e.g., '1.2.3')",
44
+ },
45
+ storyId: {
46
+ type: "string",
47
+ description: "The Story ID this task belongs to (e.g., '15')",
48
+ },
49
+ slug: {
50
+ type: "string",
51
+ description: "Short slug for the story (e.g., 'user-auth')",
52
+ },
53
+ },
54
+ required: ["taskId", "storyId", "slug"],
55
+ },
56
+ },
57
+ {
58
+ name: "approve_plan",
59
+ description: "Approve the implementation plan and switch to EXECUTION mode.",
60
+ inputSchema: {
61
+ type: "object",
62
+ properties: {},
63
+ },
64
+ },
65
+ {
66
+ name: "get_status",
67
+ description: "Get the current state machine status and active task.",
68
+ inputSchema: {
69
+ type: "object",
70
+ properties: {},
71
+ },
72
+ },
73
+ {
74
+ name: "generate_prd",
75
+ description: "Generate a PRD template based on project context.",
76
+ inputSchema: {
77
+ type: "object",
78
+ properties: {
79
+ requirements: { type: "string" }
80
+ },
81
+ },
82
+ },
83
+ {
84
+ name: "generate_tasks",
85
+ description: "Generate tasks from a PRD.",
86
+ inputSchema: {
87
+ type: "object",
88
+ properties: {
89
+ prdContent: { type: "string" }
90
+ },
91
+ },
92
+ },
93
+ {
94
+ name: "run_checks",
95
+ description: "Run project validations and enter VERIFICATION state.",
96
+ inputSchema: {
97
+ type: "object",
98
+ properties: {},
99
+ },
100
+ },
101
+ {
102
+ name: "submit_task",
103
+ description: "Submit the current task and complete the workflow.",
104
+ inputSchema: {
105
+ type: "object",
106
+ properties: {},
107
+ },
108
+ },
109
+ ],
110
+ };
111
+ });
112
+
113
+ // Tool Execution
114
+ server.setRequestHandler(CallToolRequestSchema, async (request) => {
115
+ const { name, arguments: args } = request.params;
116
+
117
+ try {
118
+ switch (name) {
119
+ case "start_task": {
120
+ const schema = z.object({
121
+ taskId: z.string(),
122
+ storyId: z.string(),
123
+ slug: z.string(),
124
+ });
125
+ const { taskId, storyId, slug } = schema.parse(args);
126
+
127
+ await stateMachine.startTask(taskId, storyId, slug);
128
+
129
+ return {
130
+ content: [
131
+ {
132
+ type: "text",
133
+ text: `Task ${taskId} started on branch story/S${storyId}-${slug}. State is now PLANNING.`,
134
+ },
135
+ ],
136
+ };
137
+ }
138
+
139
+ case "approve_plan": {
140
+ stateMachine.approvePlan();
141
+ return {
142
+ content: [
143
+ {
144
+ type: "text",
145
+ text: "Plan approved. State is now EXECUTION. You may now write code.",
146
+ },
147
+ ],
148
+ };
149
+ }
150
+
151
+ case "get_status": {
152
+ return {
153
+ content: [
154
+ {
155
+ type: "text",
156
+ text: JSON.stringify({
157
+ state: stateMachine.getState(),
158
+ activeTask: stateMachine.getActiveTask(),
159
+ }, null, 2),
160
+ },
161
+ ],
162
+ };
163
+ }
164
+
165
+ case "generate_prd": {
166
+ const template = `# Project Requirements Document
167
+ ## 1. Objective
168
+ [Describe the goal]
169
+
170
+ ## 2. Scope
171
+ - [ ] In Scope
172
+ - [ ] Out of Scope
173
+
174
+ ## 3. Technical Requirements
175
+ - Language: [e.g., TypeScript]
176
+ - Framework: [e.g., React]
177
+
178
+ ## 4. User Stories
179
+ - Story 1: [Description]
180
+ `;
181
+ return {
182
+ content: [
183
+ {
184
+ type: "text",
185
+ text: template,
186
+ },
187
+ ],
188
+ };
189
+ }
190
+
191
+ case "generate_tasks": {
192
+ // In a real implementation, this would parse the PRD.
193
+ // For prototype, we return the schema structure.
194
+ return {
195
+ content: [
196
+ {
197
+ type: "text",
198
+ text: "Please provide the tasks in the following JSON format matching the TaskSchema:\n" +
199
+ JSON.stringify({
200
+ id: "1.0",
201
+ title: "Example Task",
202
+ status: "todo",
203
+ subtasks: [{ id: "1.1", title: "Subtask 1" }]
204
+ }, null, 2)
205
+ },
206
+ ],
207
+ };
208
+ }
209
+
210
+ case "run_checks": {
211
+ stateMachine.startVerification();
212
+ // TODO: Actually run the validation commands from config
213
+ return {
214
+ content: [{ type: "text", text: "Verification phase started. Running checks... [MOCK PASSED]" }],
215
+ };
216
+ }
217
+
218
+ case "submit_task": {
219
+ stateMachine.completeTask();
220
+ return {
221
+ content: [{ type: "text", text: "Task submitted and completed. State is now IDLE." }],
222
+ };
223
+ }
224
+
225
+ default:
226
+ throw new McpError(
227
+ ErrorCode.MethodNotFound,
228
+ `Unknown tool: ${name}`
229
+ );
230
+ }
231
+ } catch (error) {
232
+ if (error instanceof z.ZodError) {
233
+ throw new McpError(
234
+ ErrorCode.InvalidParams,
235
+ `Invalid arguments: ${error.message}`
236
+ );
237
+ }
238
+ const errorMessage = error instanceof Error ? error.message : String(error);
239
+ return {
240
+ content: [
241
+ {
242
+ type: "text",
243
+ text: `Error executing ${name}: ${errorMessage}`,
244
+ },
245
+ ],
246
+ isError: true,
247
+ };
248
+ }
249
+ });
250
+
251
+ // Start Server
252
+ async function main() {
253
+ const transport = new StdioServerTransport();
254
+ await server.connect(transport);
255
+ console.error("Taskflow MCP Server running on stdio");
256
+ }
257
+
258
+ main().catch((error) => {
259
+ console.error("Fatal error in main():", error);
260
+ process.exit(1);
261
+ });
package/tsconfig.json ADDED
@@ -0,0 +1,19 @@
1
+ {
2
+ "compilerOptions": {
3
+ "target": "ES2022",
4
+ "module": "NodeNext",
5
+ "moduleResolution": "NodeNext",
6
+ "outDir": "./dist",
7
+ "rootDir": "./src",
8
+ "strict": true,
9
+ "esModuleInterop": true,
10
+ "skipLibCheck": true,
11
+ "forceConsistentCasingInFileNames": true
12
+ },
13
+ "include": [
14
+ "src/**/*"
15
+ ],
16
+ "exclude": [
17
+ "node_modules"
18
+ ]
19
+ }