@gwdn/nexus-mcp 0.8.7 → 0.8.9

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.
Files changed (53) hide show
  1. package/dist/server.js +1 -1
  2. package/dist/tools/create-task.d.ts +1 -1
  3. package/dist/tools/create-task.js +3 -3
  4. package/dist/tools/directives.d.ts +2 -2
  5. package/dist/tools/letters.d.ts +1 -1
  6. package/dist/tools/update-task-status.d.ts +1 -1
  7. package/package.json +8 -2
  8. package/.github/workflows/ci.yml +0 -38
  9. package/.github/workflows/release.yml +0 -57
  10. package/src/__tests__/auth.test.ts +0 -162
  11. package/src/__tests__/decision-comments.test.ts +0 -173
  12. package/src/__tests__/e2e-integration.test.ts +0 -443
  13. package/src/__tests__/helpers.ts +0 -58
  14. package/src/__tests__/layer1-knowledge.test.ts +0 -302
  15. package/src/__tests__/layer2-coordination.test.ts +0 -918
  16. package/src/__tests__/layer3-governance.test.ts +0 -205
  17. package/src/__tests__/machine-id.test.ts +0 -136
  18. package/src/__tests__/nexus-api.test.ts +0 -127
  19. package/src/__tests__/project-list-and-skill-assign.test.ts +0 -282
  20. package/src/__tests__/reviews.test.ts +0 -420
  21. package/src/__tests__/server.test.ts +0 -251
  22. package/src/__tests__/setup.ts +0 -15
  23. package/src/__tests__/task-list-and-doc-list.test.ts +0 -226
  24. package/src/auth.ts +0 -81
  25. package/src/machine-id.ts +0 -60
  26. package/src/nexus-api.ts +0 -149
  27. package/src/server.ts +0 -629
  28. package/src/tools/add-task-note.ts +0 -50
  29. package/src/tools/append-session-entry.ts +0 -113
  30. package/src/tools/classify-document.ts +0 -55
  31. package/src/tools/create-task.ts +0 -66
  32. package/src/tools/decision-comments.ts +0 -103
  33. package/src/tools/delete-document.ts +0 -43
  34. package/src/tools/directives.ts +0 -303
  35. package/src/tools/get-document.ts +0 -80
  36. package/src/tools/get-project-memory.ts +0 -65
  37. package/src/tools/get-related-entities.ts +0 -73
  38. package/src/tools/governance.ts +0 -165
  39. package/src/tools/ingest-document.ts +0 -65
  40. package/src/tools/letter-inbox.ts +0 -157
  41. package/src/tools/letters.ts +0 -144
  42. package/src/tools/list-documents.ts +0 -58
  43. package/src/tools/list-tasks.ts +0 -57
  44. package/src/tools/project-list.ts +0 -52
  45. package/src/tools/reviews.ts +0 -281
  46. package/src/tools/search-knowledge.ts +0 -68
  47. package/src/tools/sessions.ts +0 -157
  48. package/src/tools/skill-assign.ts +0 -142
  49. package/src/tools/skills.ts +0 -255
  50. package/src/tools/update-document.ts +0 -66
  51. package/src/tools/update-task-status.ts +0 -64
  52. package/tsconfig.json +0 -21
  53. package/vitest.config.ts +0 -8
@@ -1,144 +0,0 @@
1
- /**
2
- * vl_create + vl_reply -- Layer 2 Coordination
3
- *
4
- * Vault letter management for agent coordination.
5
- * Delegates to POST /api/mcp/letters (actions: vl_create, vl_reply).
6
- */
7
-
8
- import { z } from 'zod'
9
- import { nexusPost } from '../nexus-api.js'
10
-
11
- // ---------------------------------------------------------------------------
12
- // create_letter
13
- // ---------------------------------------------------------------------------
14
-
15
- export const createLetterSchema = {
16
- project_id: z.string().uuid().describe('Project UUID'),
17
- from_actor: z.string().max(200).describe('Sender identifier (agent name or user)'),
18
- to_actor: z.string().max(200).describe('Recipient identifier (agent name or user)'),
19
- subject: z.string().max(500).describe('Letter subject'),
20
- body: z.string().max(100_000).describe('Initial message body'),
21
- priority: z
22
- .enum(['low', 'normal', 'high', 'urgent'])
23
- .default('normal')
24
- .describe('Letter priority'),
25
- blocking: z
26
- .boolean()
27
- .default(false)
28
- .describe('Whether this letter blocks the sender'),
29
- thread_id: z
30
- .string()
31
- .uuid()
32
- .optional()
33
- .describe('Optional thread UUID to group related letters'),
34
- agent_id: z.string().max(200).optional().describe('Agent identifier if applicable'),
35
- }
36
-
37
- type CreateLetterArgs = {
38
- project_id: string
39
- from_actor: string
40
- to_actor: string
41
- subject: string
42
- body: string
43
- priority?: string
44
- blocking?: boolean
45
- thread_id?: string
46
- user_id: string
47
- agent_id?: string
48
- }
49
-
50
- export async function createLetter(args: CreateLetterArgs) {
51
- const result = await nexusPost('/api/mcp/letters', {
52
- action: 'vl_create',
53
- project_id: args.project_id,
54
- from_actor: args.from_actor,
55
- to_actor: args.to_actor,
56
- subject: args.subject,
57
- body: args.body,
58
- priority: args.priority ?? 'normal',
59
- blocking: args.blocking ?? false,
60
- thread_id: args.thread_id,
61
- agent_id: args.agent_id,
62
- })
63
-
64
- if (!result.ok) {
65
- return {
66
- content: [
67
- {
68
- type: 'text' as const,
69
- text: JSON.stringify({ error: result.error }, null, 2),
70
- },
71
- ],
72
- isError: true,
73
- }
74
- }
75
-
76
- return {
77
- content: [
78
- { type: 'text' as const, text: JSON.stringify(result.data, null, 2) },
79
- ],
80
- }
81
- }
82
-
83
- // ---------------------------------------------------------------------------
84
- // reply_letter
85
- // ---------------------------------------------------------------------------
86
-
87
- export const replyLetterSchema = {
88
- letter_id: z.string().uuid().describe('Letter UUID to reply to'),
89
- body: z.string().max(100_000).describe('Reply message body'),
90
- message_type: z
91
- .enum(['response', 'clarification', 'review_note', 'follow_up', 'context'])
92
- .default('response')
93
- .describe('Type of reply message'),
94
- agent_id: z.string().max(200).optional().describe('Agent identifier if applicable'),
95
- new_status: z
96
- .enum([
97
- 'acknowledged',
98
- 'in_progress',
99
- 'answered',
100
- 'blocked',
101
- 'needs_review',
102
- 'closed',
103
- ])
104
- .optional()
105
- .describe('Optionally update the letter status'),
106
- }
107
-
108
- type ReplyLetterArgs = {
109
- letter_id: string
110
- body: string
111
- message_type?: string
112
- user_id: string
113
- agent_id?: string
114
- new_status?: string
115
- }
116
-
117
- export async function replyLetter(args: ReplyLetterArgs) {
118
- const result = await nexusPost('/api/mcp/letters', {
119
- action: 'vl_reply',
120
- letter_id: args.letter_id,
121
- body: args.body,
122
- message_type: args.message_type ?? 'response',
123
- agent_id: args.agent_id,
124
- new_status: args.new_status,
125
- })
126
-
127
- if (!result.ok) {
128
- return {
129
- content: [
130
- {
131
- type: 'text' as const,
132
- text: JSON.stringify({ error: result.error }, null, 2),
133
- },
134
- ],
135
- isError: true,
136
- }
137
- }
138
-
139
- return {
140
- content: [
141
- { type: 'text' as const, text: JSON.stringify(result.data, null, 2) },
142
- ],
143
- }
144
- }
@@ -1,58 +0,0 @@
1
- /**
2
- * doc_list -- Layer 2 Coordination
3
- *
4
- * List ingested documents for a project with optional source filtering.
5
- * Delegates to POST /api/mcp/documents (action: doc_list).
6
- */
7
-
8
- import { z } from 'zod'
9
- import { nexusPost } from '../nexus-api.js'
10
-
11
- export const listDocumentsSchema = {
12
- project_id: z.string().uuid().describe('Project UUID'),
13
- source: z
14
- .string()
15
- .max(200)
16
- .optional()
17
- .describe('Filter by source (e.g., "mcp-agent", "research", "session-extract")'),
18
- limit: z
19
- .number()
20
- .min(1)
21
- .max(100)
22
- .default(50)
23
- .describe('Maximum number of documents to return (default 50)'),
24
- }
25
-
26
- type ListDocumentsArgs = {
27
- project_id: string
28
- source?: string
29
- limit?: number
30
- user_id: string
31
- }
32
-
33
- export async function listDocuments(args: ListDocumentsArgs) {
34
- const result = await nexusPost('/api/mcp/documents', {
35
- action: 'doc_list',
36
- project_id: args.project_id,
37
- source: args.source,
38
- limit: args.limit ?? 50,
39
- })
40
-
41
- if (!result.ok) {
42
- return {
43
- content: [
44
- {
45
- type: 'text' as const,
46
- text: JSON.stringify({ error: result.error }, null, 2),
47
- },
48
- ],
49
- isError: true,
50
- }
51
- }
52
-
53
- return {
54
- content: [
55
- { type: 'text' as const, text: JSON.stringify(result.data, null, 2) },
56
- ],
57
- }
58
- }
@@ -1,57 +0,0 @@
1
- /**
2
- * task_list -- Layer 2 Coordination
3
- *
4
- * List tasks for a project with optional status filtering.
5
- * Delegates to POST /api/mcp/tasks (action: task_list).
6
- */
7
-
8
- import { z } from 'zod'
9
- import { nexusPost } from '../nexus-api.js'
10
-
11
- export const listTasksSchema = {
12
- project_id: z.string().uuid().describe('Project UUID'),
13
- status_filter: z
14
- .array(z.enum(['open', 'in_progress', 'blocked', 'done', 'cancelled']))
15
- .optional()
16
- .describe('Filter by task status (default: all statuses)'),
17
- limit: z
18
- .number()
19
- .min(1)
20
- .max(100)
21
- .default(50)
22
- .describe('Maximum number of tasks to return (default 50)'),
23
- }
24
-
25
- type ListTasksArgs = {
26
- project_id: string
27
- status_filter?: string[]
28
- limit?: number
29
- user_id: string
30
- }
31
-
32
- export async function listTasks(args: ListTasksArgs) {
33
- const result = await nexusPost('/api/mcp/tasks', {
34
- action: 'task_list',
35
- project_id: args.project_id,
36
- status_filter: args.status_filter,
37
- limit: args.limit ?? 50,
38
- })
39
-
40
- if (!result.ok) {
41
- return {
42
- content: [
43
- {
44
- type: 'text' as const,
45
- text: JSON.stringify({ error: result.error }, null, 2),
46
- },
47
- ],
48
- isError: true,
49
- }
50
- }
51
-
52
- return {
53
- content: [
54
- { type: 'text' as const, text: JSON.stringify(result.data, null, 2) },
55
- ],
56
- }
57
- }
@@ -1,52 +0,0 @@
1
- /**
2
- * project_list -- Layer 1 Knowledge Access
3
- *
4
- * List accessible projects for the authenticated user/agent.
5
- * Delegates to GET /api/mcp/projects.
6
- */
7
-
8
- import { z } from 'zod'
9
- import { nexusGet } from '../nexus-api.js'
10
-
11
- export const projectListSchema = {
12
- limit: z
13
- .number()
14
- .int()
15
- .min(1)
16
- .max(100)
17
- .optional()
18
- .describe('Maximum number of projects to return'),
19
- }
20
-
21
- type ProjectListArgs = {
22
- limit?: number
23
- }
24
-
25
- export async function projectList(args: ProjectListArgs) {
26
- const params = new URLSearchParams()
27
- if (args.limit !== undefined) {
28
- params.set('limit', String(args.limit))
29
- }
30
- const qs = params.toString()
31
- const path = `/api/mcp/projects${qs ? `?${qs}` : ''}`
32
-
33
- const result = await nexusGet(path)
34
-
35
- if (!result.ok) {
36
- return {
37
- content: [
38
- {
39
- type: 'text' as const,
40
- text: JSON.stringify({ error: result.error }, null, 2),
41
- },
42
- ],
43
- isError: true,
44
- }
45
- }
46
-
47
- return {
48
- content: [
49
- { type: 'text' as const, text: JSON.stringify(result.data, null, 2) },
50
- ],
51
- }
52
- }
@@ -1,281 +0,0 @@
1
- /**
2
- * rv_list + rv_get + rv_create + rv_decide + rv_comment -- Layer 4 Reviews
3
- *
4
- * Review lifecycle management tools for the Nexus platform.
5
- * Reviews cover skills, agents, and other governed entities.
6
- * Delegates to POST /api/mcp/reviews.
7
- */
8
-
9
- import { z } from 'zod'
10
- import { nexusPost } from '../nexus-api.js'
11
-
12
- // ---------------------------------------------------------------------------
13
- // rv_list
14
- // ---------------------------------------------------------------------------
15
-
16
- export const rvListSchema = {
17
- entity_type: z
18
- .enum(['skill', 'agent'])
19
- .optional()
20
- .describe('Filter by entity type (skill or agent)'),
21
- status: z
22
- .string()
23
- .max(50)
24
- .optional()
25
- .describe('Filter by review status'),
26
- limit: z
27
- .number()
28
- .int()
29
- .min(1)
30
- .max(100)
31
- .optional()
32
- .describe('Maximum number of reviews to return'),
33
- }
34
-
35
- type RvListArgs = {
36
- entity_type?: string
37
- status?: string
38
- limit?: number
39
- user_id: string
40
- }
41
-
42
- export async function rvList(args: RvListArgs) {
43
- const result = await nexusPost('/api/mcp/reviews', {
44
- action: 'rv_list',
45
- entity_type: args.entity_type,
46
- status: args.status,
47
- limit: args.limit,
48
- })
49
-
50
- if (!result.ok) {
51
- return {
52
- content: [
53
- {
54
- type: 'text' as const,
55
- text: JSON.stringify({ error: result.error }, null, 2),
56
- },
57
- ],
58
- isError: true,
59
- }
60
- }
61
-
62
- return {
63
- content: [
64
- { type: 'text' as const, text: JSON.stringify(result.data, null, 2) },
65
- ],
66
- }
67
- }
68
-
69
- // ---------------------------------------------------------------------------
70
- // rv_get
71
- // ---------------------------------------------------------------------------
72
-
73
- export const rvGetSchema = {
74
- review_id: z
75
- .string()
76
- .uuid()
77
- .optional()
78
- .describe('Review UUID (look up by review ID)'),
79
- entity_type: z
80
- .string()
81
- .max(50)
82
- .optional()
83
- .describe('Entity type (used with entity_id for lookup by entity)'),
84
- entity_id: z
85
- .string()
86
- .uuid()
87
- .optional()
88
- .describe('Entity UUID (used with entity_type for lookup by entity)'),
89
- }
90
-
91
- type RvGetArgs = {
92
- review_id?: string
93
- entity_type?: string
94
- entity_id?: string
95
- user_id: string
96
- }
97
-
98
- export async function rvGet(args: RvGetArgs) {
99
- const result = await nexusPost('/api/mcp/reviews', {
100
- action: 'rv_get',
101
- review_id: args.review_id,
102
- entity_type: args.entity_type,
103
- entity_id: args.entity_id,
104
- })
105
-
106
- if (!result.ok) {
107
- return {
108
- content: [
109
- {
110
- type: 'text' as const,
111
- text: JSON.stringify({ error: result.error }, null, 2),
112
- },
113
- ],
114
- isError: true,
115
- }
116
- }
117
-
118
- return {
119
- content: [
120
- { type: 'text' as const, text: JSON.stringify(result.data, null, 2) },
121
- ],
122
- }
123
- }
124
-
125
- // ---------------------------------------------------------------------------
126
- // rv_create
127
- // ---------------------------------------------------------------------------
128
-
129
- export const rvCreateSchema = {
130
- entity_type: z
131
- .enum(['skill', 'agent'])
132
- .describe('Type of entity to create a review for'),
133
- entity_id: z
134
- .string()
135
- .uuid()
136
- .describe('UUID of the entity to review'),
137
- }
138
-
139
- type RvCreateArgs = {
140
- entity_type: string
141
- entity_id: string
142
- user_id: string
143
- }
144
-
145
- export async function rvCreate(args: RvCreateArgs) {
146
- const result = await nexusPost('/api/mcp/reviews', {
147
- action: 'rv_create',
148
- entity_type: args.entity_type,
149
- entity_id: args.entity_id,
150
- })
151
-
152
- if (!result.ok) {
153
- return {
154
- content: [
155
- {
156
- type: 'text' as const,
157
- text: JSON.stringify({ error: result.error }, null, 2),
158
- },
159
- ],
160
- isError: true,
161
- }
162
- }
163
-
164
- return {
165
- content: [
166
- { type: 'text' as const, text: JSON.stringify(result.data, null, 2) },
167
- ],
168
- }
169
- }
170
-
171
- // ---------------------------------------------------------------------------
172
- // rv_decide
173
- // ---------------------------------------------------------------------------
174
-
175
- export const rvDecideSchema = {
176
- review_id: z.string().uuid().describe('Review UUID'),
177
- transition: z
178
- .enum(['submit', 'accept', 'reject', 'request_revision', 'resubmit', 'archive'])
179
- .describe('State transition to apply'),
180
- rationale: z
181
- .string()
182
- .max(10_000)
183
- .optional()
184
- .describe('Optional rationale for the decision'),
185
- }
186
-
187
- type RvDecideArgs = {
188
- review_id: string
189
- transition: string
190
- rationale?: string
191
- user_id: string
192
- }
193
-
194
- export async function rvDecide(args: RvDecideArgs) {
195
- const result = await nexusPost('/api/mcp/reviews', {
196
- action: 'rv_decide',
197
- review_id: args.review_id,
198
- transition: args.transition,
199
- rationale: args.rationale,
200
- })
201
-
202
- if (!result.ok) {
203
- return {
204
- content: [
205
- {
206
- type: 'text' as const,
207
- text: JSON.stringify({ error: result.error }, null, 2),
208
- },
209
- ],
210
- isError: true,
211
- }
212
- }
213
-
214
- return {
215
- content: [
216
- { type: 'text' as const, text: JSON.stringify(result.data, null, 2) },
217
- ],
218
- }
219
- }
220
-
221
- // ---------------------------------------------------------------------------
222
- // rv_comment
223
- // ---------------------------------------------------------------------------
224
-
225
- export const rvCommentSchema = {
226
- review_id: z.string().uuid().describe('Review UUID'),
227
- body: z.string().max(100_000).describe('Comment body (markdown supported)'),
228
- agent_id: z
229
- .string()
230
- .max(200)
231
- .optional()
232
- .describe('Agent identifier if comment is posted by an agent'),
233
- line_start: z
234
- .number()
235
- .int()
236
- .optional()
237
- .describe('Start line number for inline comments'),
238
- line_end: z
239
- .number()
240
- .int()
241
- .optional()
242
- .describe('End line number for inline comments'),
243
- }
244
-
245
- type RvCommentArgs = {
246
- review_id: string
247
- body: string
248
- agent_id?: string
249
- line_start?: number
250
- line_end?: number
251
- user_id: string
252
- }
253
-
254
- export async function rvComment(args: RvCommentArgs) {
255
- const result = await nexusPost('/api/mcp/reviews', {
256
- action: 'rv_comment',
257
- review_id: args.review_id,
258
- body: args.body,
259
- agent_id: args.agent_id,
260
- line_start: args.line_start,
261
- line_end: args.line_end,
262
- })
263
-
264
- if (!result.ok) {
265
- return {
266
- content: [
267
- {
268
- type: 'text' as const,
269
- text: JSON.stringify({ error: result.error }, null, 2),
270
- },
271
- ],
272
- isError: true,
273
- }
274
- }
275
-
276
- return {
277
- content: [
278
- { type: 'text' as const, text: JSON.stringify(result.data, null, 2) },
279
- ],
280
- }
281
- }
@@ -1,68 +0,0 @@
1
- /**
2
- * kb_search -- Layer 1 Knowledge Access
3
- *
4
- * Searches project knowledge using keyword, semantic, or hybrid mode.
5
- * Delegates to POST /api/mcp/search.
6
- */
7
-
8
- import { z } from 'zod'
9
- import { nexusPost } from '../nexus-api.js'
10
-
11
- export const searchKnowledgeSchema = {
12
- query: z.string().max(1000).describe('Free-text search query'),
13
- project_id: z.string().uuid().describe('Project UUID to scope the search'),
14
- entity_types: z
15
- .array(
16
- z.enum([
17
- 'session',
18
- 'decision',
19
- 'letter',
20
- 'task',
21
- 'research_note',
22
- 'planning_item',
23
- 'ingest_item',
24
- ]),
25
- )
26
- .optional()
27
- .describe('Filter to specific entity types'),
28
- search_mode: z
29
- .enum(['keyword', 'semantic', 'hybrid'])
30
- .default('keyword')
31
- .describe('Search mode: keyword, semantic, or hybrid'),
32
- limit: z
33
- .number()
34
- .int()
35
- .min(1)
36
- .max(50)
37
- .default(10)
38
- .describe('Maximum results to return'),
39
- }
40
-
41
- type SearchArgs = {
42
- query: string
43
- project_id: string
44
- entity_types?: string[]
45
- search_mode?: string
46
- limit?: number
47
- }
48
-
49
- export async function searchKnowledge(args: SearchArgs) {
50
- const result = await nexusPost('/api/mcp/search', {
51
- project_id: args.project_id,
52
- query: args.query,
53
- entity_types: args.entity_types,
54
- search_mode: args.search_mode ?? 'keyword',
55
- limit: args.limit ?? 10,
56
- })
57
-
58
- if (!result.ok) {
59
- return {
60
- content: [{ type: 'text' as const, text: JSON.stringify({ error: result.error }, null, 2) }],
61
- isError: true,
62
- }
63
- }
64
-
65
- return {
66
- content: [{ type: 'text' as const, text: JSON.stringify(result.data, null, 2) }],
67
- }
68
- }