cognitive-workflow-mcp 1.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/src/index.js ADDED
@@ -0,0 +1,233 @@
1
+ #!/usr/bin/env node
2
+
3
+ import { Server } from '@modelcontextprotocol/sdk/server/index.js';
4
+ import { StdioServerTransport } from '@modelcontextprotocol/sdk/server/stdio.js';
5
+ import {
6
+ ListToolsRequestSchema,
7
+ CallToolRequestSchema,
8
+ ErrorCode,
9
+ McpError
10
+ } from '@modelcontextprotocol/sdk/types.js';
11
+
12
+ import { analyzeCommits } from './analyzer.js';
13
+ import { generateDashboard } from './generator.js';
14
+ import { configureTerminals } from './configurator.js';
15
+ import { getInsights } from './insights.js';
16
+
17
+ /**
18
+ * Cognitive Workflow MCP Server
19
+ *
20
+ * Provides tools for analyzing git commits and generating
21
+ * identity-based cognitive workflow dashboards.
22
+ */
23
+ class CognitiveWorkflowServer {
24
+ constructor() {
25
+ this.server = new Server(
26
+ {
27
+ name: 'cognitive-workflow-mcp',
28
+ version: '1.0.0',
29
+ },
30
+ {
31
+ capabilities: {
32
+ tools: {},
33
+ },
34
+ }
35
+ );
36
+
37
+ this.setupToolHandlers();
38
+
39
+ this.server.onerror = (error) => console.error('[MCP Error]', error);
40
+ process.on('SIGINT', async () => {
41
+ await this.server.close();
42
+ process.exit(0);
43
+ });
44
+ }
45
+
46
+ setupToolHandlers() {
47
+ this.server.setRequestHandler(ListToolsRequestSchema, async () => ({
48
+ tools: [
49
+ {
50
+ name: 'cognitive-analyze',
51
+ description: 'Analyze git commit history and categorize into 6 cognitive identities (Builder, Discoverer, Operator, Teacher, Strategist, Experimenter)',
52
+ inputSchema: {
53
+ type: 'object',
54
+ properties: {
55
+ daysBack: {
56
+ type: 'number',
57
+ description: 'Number of days of commit history to analyze',
58
+ default: 60
59
+ },
60
+ outputPath: {
61
+ type: 'string',
62
+ description: 'Optional path to save analysis results'
63
+ }
64
+ }
65
+ }
66
+ },
67
+ {
68
+ name: 'cognitive-generate-dashboard',
69
+ description: 'Generate HTML dashboard and individual room pages for each cognitive identity',
70
+ inputSchema: {
71
+ type: 'object',
72
+ properties: {
73
+ outputDir: {
74
+ type: 'string',
75
+ description: 'Output directory for generated files',
76
+ default: '.workflow'
77
+ },
78
+ openAfter: {
79
+ type: 'boolean',
80
+ description: 'Open dashboard in browser after generation',
81
+ default: true
82
+ }
83
+ }
84
+ }
85
+ },
86
+ {
87
+ name: 'cognitive-configure-terminals',
88
+ description: 'Configure terminal application mappings for each cognitive identity',
89
+ inputSchema: {
90
+ type: 'object',
91
+ properties: {
92
+ mappings: {
93
+ type: 'object',
94
+ description: 'Map of identity names to terminal applications',
95
+ properties: {
96
+ builder: { type: 'string' },
97
+ discoverer: { type: 'string' },
98
+ operator: { type: 'string' },
99
+ teacher: { type: 'string' },
100
+ strategist: { type: 'string' },
101
+ experimenter: { type: 'string' }
102
+ }
103
+ }
104
+ },
105
+ required: ['mappings']
106
+ }
107
+ },
108
+ {
109
+ name: 'cognitive-get-insights',
110
+ description: 'Get insights about your cognitive work patterns and recommendations for better balance',
111
+ inputSchema: {
112
+ type: 'object',
113
+ properties: {
114
+ includeRecommendations: {
115
+ type: 'boolean',
116
+ description: 'Include actionable recommendations',
117
+ default: true
118
+ }
119
+ }
120
+ }
121
+ }
122
+ ]
123
+ }));
124
+
125
+ this.server.setRequestHandler(CallToolRequestSchema, async (request) => {
126
+ try {
127
+ switch (request.params.name) {
128
+ case 'cognitive-analyze':
129
+ return await this.handleAnalyze(request.params.arguments);
130
+
131
+ case 'cognitive-generate-dashboard':
132
+ return await this.handleGenerateDashboard(request.params.arguments);
133
+
134
+ case 'cognitive-configure-terminals':
135
+ return await this.handleConfigureTerminals(request.params.arguments);
136
+
137
+ case 'cognitive-get-insights':
138
+ return await this.handleGetInsights(request.params.arguments);
139
+
140
+ default:
141
+ throw new McpError(
142
+ ErrorCode.MethodNotFound,
143
+ `Unknown tool: ${request.params.name}`
144
+ );
145
+ }
146
+ } catch (error) {
147
+ return {
148
+ content: [
149
+ {
150
+ type: 'text',
151
+ text: `Error: ${error.message}\n\nStack: ${error.stack}`
152
+ }
153
+ ],
154
+ isError: true
155
+ };
156
+ }
157
+ });
158
+ }
159
+
160
+ async handleAnalyze(args) {
161
+ const { daysBack = 60, outputPath } = args || {};
162
+
163
+ const analysis = await analyzeCommits(daysBack);
164
+
165
+ if (outputPath) {
166
+ const fs = await import('fs/promises');
167
+ await fs.writeFile(outputPath, JSON.stringify(analysis, null, 2));
168
+ }
169
+
170
+ return {
171
+ content: [
172
+ {
173
+ type: 'text',
174
+ text: JSON.stringify(analysis, null, 2)
175
+ }
176
+ ]
177
+ };
178
+ }
179
+
180
+ async handleGenerateDashboard(args) {
181
+ const { outputDir = '.workflow', openAfter = true } = args || {};
182
+
183
+ const result = await generateDashboard(outputDir, openAfter);
184
+
185
+ return {
186
+ content: [
187
+ {
188
+ type: 'text',
189
+ text: JSON.stringify(result, null, 2)
190
+ }
191
+ ]
192
+ };
193
+ }
194
+
195
+ async handleConfigureTerminals(args) {
196
+ const { mappings } = args;
197
+
198
+ const result = await configureTerminals(mappings);
199
+
200
+ return {
201
+ content: [
202
+ {
203
+ type: 'text',
204
+ text: JSON.stringify(result, null, 2)
205
+ }
206
+ ]
207
+ };
208
+ }
209
+
210
+ async handleGetInsights(args) {
211
+ const { includeRecommendations = true } = args || {};
212
+
213
+ const insights = await getInsights(includeRecommendations);
214
+
215
+ return {
216
+ content: [
217
+ {
218
+ type: 'text',
219
+ text: JSON.stringify(insights, null, 2)
220
+ }
221
+ ]
222
+ };
223
+ }
224
+
225
+ async run() {
226
+ const transport = new StdioServerTransport();
227
+ await this.server.connect(transport);
228
+ console.error('Cognitive Workflow MCP server running on stdio');
229
+ }
230
+ }
231
+
232
+ const server = new CognitiveWorkflowServer();
233
+ server.run().catch(console.error);
@@ -0,0 +1,127 @@
1
+ import { analyzeCommits } from './analyzer.js';
2
+
3
+ /**
4
+ * Generates insights about cognitive work patterns
5
+ *
6
+ * @param {boolean} includeRecommendations - Whether to include recommendations
7
+ * @returns {Promise<Object>} Insights and recommendations
8
+ */
9
+ export async function getInsights(includeRecommendations = true) {
10
+ const analysis = await analyzeCommits(60);
11
+
12
+ const identitiesArray = Object.entries(analysis.identities);
13
+ const dominantIdentity = identitiesArray[0][0];
14
+
15
+ // Calculate balance score
16
+ const percentages = identitiesArray.map(([_, data]) => data.percentage);
17
+ const idealPercentage = 100 / 6;
18
+ const balanceScore = 1 - (percentages.reduce((sum, p) => sum + Math.abs(p - idealPercentage), 0) / 100);
19
+
20
+ const insights = {
21
+ dominantIdentity,
22
+ balanceScore,
23
+ identityDistribution: identitiesArray.map(([id, data]) => ({
24
+ identity: id,
25
+ commits: data.commits,
26
+ percentage: data.percentage,
27
+ commitsPerDay: data.commitsPerDay
28
+ })),
29
+ trends: analyzeTrends(identitiesArray)
30
+ };
31
+
32
+ if (includeRecommendations) {
33
+ insights.recommendations = generateRecommendations(identitiesArray, balanceScore);
34
+ }
35
+
36
+ return insights;
37
+ }
38
+
39
+ /**
40
+ * Analyzes trends in identity usage
41
+ */
42
+ function analyzeTrends(identitiesArray) {
43
+ const trends = {};
44
+
45
+ // Identify increasing/decreasing patterns
46
+ // (Would require historical data to properly implement)
47
+
48
+ // For now, just flag extremes
49
+ for (const [identity, data] of identitiesArray) {
50
+ if (data.percentage > 40) {
51
+ trends[`${identity}High`] = true;
52
+ }
53
+ if (data.percentage < 5) {
54
+ trends[`${identity}Low`] = true;
55
+ }
56
+ }
57
+
58
+ return trends;
59
+ }
60
+
61
+ /**
62
+ * Generates actionable recommendations
63
+ */
64
+ function generateRecommendations(identitiesArray, balanceScore) {
65
+ const recommendations = [];
66
+
67
+ // Low balance score
68
+ if (balanceScore < 0.6) {
69
+ recommendations.push(
70
+ `Work is concentrated in ${identitiesArray[0][0]} (${identitiesArray[0][1].percentage}%). Consider distributing effort across more identities.`
71
+ );
72
+ }
73
+
74
+ // Underutilized identities
75
+ const underutilized = identitiesArray.filter(([_, data]) => data.percentage < 5);
76
+ if (underutilized.length > 0) {
77
+ for (const [identity] of underutilized) {
78
+ recommendations.push(
79
+ `${capitalize(identity)} is underutilized (${identitiesArray.find(([id]) => id === identity)[1].percentage}%). ${getIdentityRecommendation(identity)}`
80
+ );
81
+ }
82
+ }
83
+
84
+ // Dominant identity warnings
85
+ const [dominantId, dominantData] = identitiesArray[0];
86
+ if (dominantData.percentage > 50) {
87
+ recommendations.push(
88
+ `${capitalize(dominantId)} dominance may indicate tunnel vision. Schedule dedicated time for other identities.`
89
+ );
90
+ }
91
+
92
+ // Specific identity recommendations
93
+ const strategistData = identitiesArray.find(([id]) => id === 'strategist');
94
+ if (strategistData && strategistData[1].percentage < 10) {
95
+ recommendations.push(
96
+ 'Low strategic thinking detected. Block time for market analysis and competitive positioning.'
97
+ );
98
+ }
99
+
100
+ const experimenterData = identitiesArray.find(([id]) => id === 'experimenter');
101
+ if (experimenterData && experimenterData[1].percentage < 5) {
102
+ recommendations.push(
103
+ 'Low experimentation rate. Consider rapid prototyping sessions before committing to implementations.'
104
+ );
105
+ }
106
+
107
+ return recommendations;
108
+ }
109
+
110
+ /**
111
+ * Gets specific recommendation for an identity
112
+ */
113
+ function getIdentityRecommendation(identity) {
114
+ const recommendations = {
115
+ builder: 'Schedule focused implementation sessions with iTerm2.',
116
+ discoverer: 'Block time for deep research with WezTerm.',
117
+ operator: 'Review operations dashboard and handle administrative tasks with Kitty.',
118
+ teacher: 'Write documentation or blog content with Terminal.',
119
+ strategist: 'Analyze market trends and competitive landscape with VS Code.',
120
+ experimenter: 'Run quick prototyping sessions with Cursor.'
121
+ };
122
+ return recommendations[identity] || 'Consider dedicating time to this mode.';
123
+ }
124
+
125
+ function capitalize(str) {
126
+ return str.charAt(0).toUpperCase() + str.slice(1);
127
+ }