ultra-dex 2.2.1 → 3.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 +112 -151
- package/assets/agents/00-AGENT_INDEX.md +1 -1
- package/assets/code-patterns/clerk-middleware.ts +138 -0
- package/assets/code-patterns/prisma-schema.prisma +224 -0
- package/assets/code-patterns/rls-policies.sql +246 -0
- package/assets/code-patterns/server-actions.ts +191 -0
- package/assets/code-patterns/trpc-router.ts +258 -0
- package/assets/cursor-rules/13-ai-integration.mdc +155 -0
- package/assets/cursor-rules/14-server-components.mdc +81 -0
- package/assets/cursor-rules/15-server-actions.mdc +102 -0
- package/assets/cursor-rules/16-edge-middleware.mdc +105 -0
- package/assets/cursor-rules/17-streaming-ssr.mdc +138 -0
- package/assets/docs/LAUNCH-POSTS.md +1 -1
- package/assets/docs/QUICK-REFERENCE.md +9 -4
- package/assets/docs/VISION-V2.md +1 -1
- package/assets/hooks/pre-commit +98 -0
- package/assets/saas-plan/04-Imp-Template.md +1 -1
- package/bin/ultra-dex.js +132 -4
- package/lib/commands/advanced.js +471 -0
- package/lib/commands/agent-builder.js +226 -0
- package/lib/commands/agents.js +102 -42
- package/lib/commands/auto-implement.js +68 -0
- package/lib/commands/banner.js +43 -21
- package/lib/commands/build.js +78 -183
- package/lib/commands/ci-monitor.js +84 -0
- package/lib/commands/config.js +207 -0
- package/lib/commands/dashboard.js +770 -0
- package/lib/commands/diff.js +233 -0
- package/lib/commands/doctor.js +416 -0
- package/lib/commands/export.js +408 -0
- package/lib/commands/fix.js +96 -0
- package/lib/commands/generate.js +105 -78
- package/lib/commands/hooks.js +251 -76
- package/lib/commands/init.js +102 -54
- package/lib/commands/memory.js +80 -0
- package/lib/commands/plan.js +82 -0
- package/lib/commands/review.js +34 -5
- package/lib/commands/run.js +233 -0
- package/lib/commands/scaffold.js +151 -0
- package/lib/commands/serve.js +179 -146
- package/lib/commands/state.js +327 -0
- package/lib/commands/swarm.js +306 -0
- package/lib/commands/sync.js +82 -23
- package/lib/commands/team.js +275 -0
- package/lib/commands/upgrade.js +190 -0
- package/lib/commands/validate.js +34 -0
- package/lib/commands/verify.js +81 -0
- package/lib/commands/watch.js +79 -0
- package/lib/config/theme.js +47 -0
- package/lib/mcp/graph.js +92 -0
- package/lib/mcp/memory.js +95 -0
- package/lib/mcp/resources.js +152 -0
- package/lib/mcp/server.js +34 -0
- package/lib/mcp/tools.js +481 -0
- package/lib/mcp/websocket.js +117 -0
- package/lib/providers/index.js +49 -4
- package/lib/providers/ollama.js +136 -0
- package/lib/providers/router.js +63 -0
- package/lib/quality/scanner.js +128 -0
- package/lib/swarm/coordinator.js +97 -0
- package/lib/swarm/index.js +598 -0
- package/lib/swarm/protocol.js +677 -0
- package/lib/swarm/tiers.js +485 -0
- package/lib/templates/code/clerk-middleware.ts +138 -0
- package/lib/templates/code/prisma-schema.prisma +224 -0
- package/lib/templates/code/rls-policies.sql +246 -0
- package/lib/templates/code/server-actions.ts +191 -0
- package/lib/templates/code/trpc-router.ts +258 -0
- package/lib/templates/custom-agent.md +10 -0
- package/lib/themes/doomsday.js +229 -0
- package/lib/ui/index.js +5 -0
- package/lib/ui/interface.js +241 -0
- package/lib/ui/spinners.js +116 -0
- package/lib/ui/theme.js +183 -0
- package/lib/utils/agents.js +32 -0
- package/lib/utils/files.js +14 -0
- package/lib/utils/graph.js +108 -0
- package/lib/utils/help.js +64 -0
- package/lib/utils/messages.js +35 -0
- package/lib/utils/progress.js +24 -0
- package/lib/utils/prompts.js +47 -0
- package/lib/utils/spinners.js +46 -0
- package/lib/utils/status.js +31 -0
- package/lib/utils/tables.js +41 -0
- package/lib/utils/theme-state.js +9 -0
- package/lib/utils/version-display.js +32 -0
- package/package.json +31 -13
|
@@ -0,0 +1,485 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Ultra-Dex Agent Tier System v3.0
|
|
3
|
+
* Defines the hierarchical structure of agents and their dependencies.
|
|
4
|
+
*/
|
|
5
|
+
|
|
6
|
+
// ============================================================================
|
|
7
|
+
// TIER DEFINITIONS
|
|
8
|
+
// ============================================================================
|
|
9
|
+
|
|
10
|
+
/**
|
|
11
|
+
* Tier structure for all 16 agents.
|
|
12
|
+
* Lower tier numbers indicate higher-level strategic roles.
|
|
13
|
+
*/
|
|
14
|
+
export const TIERS = {
|
|
15
|
+
META: {
|
|
16
|
+
id: 0,
|
|
17
|
+
name: 'Meta Orchestration',
|
|
18
|
+
description: 'Coordinates all other agents',
|
|
19
|
+
agents: ['orchestrator']
|
|
20
|
+
},
|
|
21
|
+
LEADERSHIP: {
|
|
22
|
+
id: 1,
|
|
23
|
+
name: 'Leadership',
|
|
24
|
+
description: 'Strategic planning and technology decisions',
|
|
25
|
+
agents: ['cto', 'planner', 'research']
|
|
26
|
+
},
|
|
27
|
+
DEVELOPMENT: {
|
|
28
|
+
id: 2,
|
|
29
|
+
name: 'Development',
|
|
30
|
+
description: 'Core implementation of features',
|
|
31
|
+
agents: ['backend', 'frontend', 'database']
|
|
32
|
+
},
|
|
33
|
+
SECURITY: {
|
|
34
|
+
id: 3,
|
|
35
|
+
name: 'Security',
|
|
36
|
+
description: 'Authentication, authorization, and security audits',
|
|
37
|
+
agents: ['auth', 'security']
|
|
38
|
+
},
|
|
39
|
+
DEVOPS: {
|
|
40
|
+
id: 4,
|
|
41
|
+
name: 'DevOps',
|
|
42
|
+
description: 'Deployment and infrastructure management',
|
|
43
|
+
agents: ['devops']
|
|
44
|
+
},
|
|
45
|
+
QUALITY: {
|
|
46
|
+
id: 5,
|
|
47
|
+
name: 'Quality',
|
|
48
|
+
description: 'Testing, debugging, and code review',
|
|
49
|
+
agents: ['testing', 'reviewer', 'debugger', 'documentation']
|
|
50
|
+
},
|
|
51
|
+
SPECIALIST: {
|
|
52
|
+
id: 6,
|
|
53
|
+
name: 'Specialist',
|
|
54
|
+
description: 'Advanced optimization and code improvement',
|
|
55
|
+
agents: ['performance', 'refactoring']
|
|
56
|
+
}
|
|
57
|
+
};
|
|
58
|
+
|
|
59
|
+
// ============================================================================
|
|
60
|
+
// AGENT REGISTRY
|
|
61
|
+
// ============================================================================
|
|
62
|
+
|
|
63
|
+
/**
|
|
64
|
+
* Complete agent registry with metadata.
|
|
65
|
+
*/
|
|
66
|
+
export const AGENTS = {
|
|
67
|
+
// Tier 0: Meta
|
|
68
|
+
orchestrator: {
|
|
69
|
+
name: 'Orchestrator',
|
|
70
|
+
tier: 0,
|
|
71
|
+
tierName: 'Meta Orchestration',
|
|
72
|
+
role: 'Coordinate all agents for complete features',
|
|
73
|
+
invocation: '@orchestrator',
|
|
74
|
+
file: '0-orchestration/orchestrator.md',
|
|
75
|
+
capabilities: ['task_decomposition', 'agent_selection', 'pipeline_execution', 'result_synthesis'],
|
|
76
|
+
canInvoke: ['all']
|
|
77
|
+
},
|
|
78
|
+
|
|
79
|
+
// Tier 1: Leadership
|
|
80
|
+
cto: {
|
|
81
|
+
name: 'CTO',
|
|
82
|
+
tier: 1,
|
|
83
|
+
tierName: 'Leadership',
|
|
84
|
+
role: 'Architecture & tech stack decisions',
|
|
85
|
+
invocation: '@cto',
|
|
86
|
+
file: '1-leadership/cto.md',
|
|
87
|
+
capabilities: ['architecture_design', 'tech_selection', 'system_design'],
|
|
88
|
+
canInvoke: ['research']
|
|
89
|
+
},
|
|
90
|
+
planner: {
|
|
91
|
+
name: 'Planner',
|
|
92
|
+
tier: 1,
|
|
93
|
+
tierName: 'Leadership',
|
|
94
|
+
role: 'Task breakdown & sprint planning',
|
|
95
|
+
invocation: '@planner',
|
|
96
|
+
file: '1-leadership/planner.md',
|
|
97
|
+
capabilities: ['task_breakdown', 'estimation', 'prioritization'],
|
|
98
|
+
canInvoke: []
|
|
99
|
+
},
|
|
100
|
+
research: {
|
|
101
|
+
name: 'Research',
|
|
102
|
+
tier: 1,
|
|
103
|
+
tierName: 'Leadership',
|
|
104
|
+
role: 'Technology evaluation & comparison',
|
|
105
|
+
invocation: '@research',
|
|
106
|
+
file: '1-leadership/research.md',
|
|
107
|
+
capabilities: ['technology_evaluation', 'comparison', 'recommendations'],
|
|
108
|
+
canInvoke: []
|
|
109
|
+
},
|
|
110
|
+
|
|
111
|
+
// Tier 2: Development
|
|
112
|
+
backend: {
|
|
113
|
+
name: 'Backend',
|
|
114
|
+
tier: 2,
|
|
115
|
+
tierName: 'Development',
|
|
116
|
+
role: 'API & server implementation',
|
|
117
|
+
invocation: '@backend',
|
|
118
|
+
file: '2-development/backend.md',
|
|
119
|
+
capabilities: ['api_development', 'business_logic', 'integrations'],
|
|
120
|
+
canInvoke: ['database']
|
|
121
|
+
},
|
|
122
|
+
frontend: {
|
|
123
|
+
name: 'Frontend',
|
|
124
|
+
tier: 2,
|
|
125
|
+
tierName: 'Development',
|
|
126
|
+
role: 'UI & component implementation',
|
|
127
|
+
invocation: '@frontend',
|
|
128
|
+
file: '2-development/frontend.md',
|
|
129
|
+
capabilities: ['ui_development', 'components', 'state_management'],
|
|
130
|
+
canInvoke: []
|
|
131
|
+
},
|
|
132
|
+
database: {
|
|
133
|
+
name: 'Database',
|
|
134
|
+
tier: 2,
|
|
135
|
+
tierName: 'Development',
|
|
136
|
+
role: 'Schema design & query optimization',
|
|
137
|
+
invocation: '@database',
|
|
138
|
+
file: '2-development/database.md',
|
|
139
|
+
capabilities: ['schema_design', 'migrations', 'query_optimization'],
|
|
140
|
+
canInvoke: []
|
|
141
|
+
},
|
|
142
|
+
|
|
143
|
+
// Tier 3: Security
|
|
144
|
+
auth: {
|
|
145
|
+
name: 'Auth',
|
|
146
|
+
tier: 3,
|
|
147
|
+
tierName: 'Security',
|
|
148
|
+
role: 'Authentication & authorization',
|
|
149
|
+
invocation: '@auth',
|
|
150
|
+
file: '3-security/auth.md',
|
|
151
|
+
capabilities: ['authentication', 'authorization', 'session_management'],
|
|
152
|
+
canInvoke: ['backend', 'database']
|
|
153
|
+
},
|
|
154
|
+
security: {
|
|
155
|
+
name: 'Security',
|
|
156
|
+
tier: 3,
|
|
157
|
+
tierName: 'Security',
|
|
158
|
+
role: 'Security audits & vulnerability fixes',
|
|
159
|
+
invocation: '@security',
|
|
160
|
+
file: '3-security/security.md',
|
|
161
|
+
capabilities: ['security_audit', 'vulnerability_detection', 'hardening'],
|
|
162
|
+
canInvoke: []
|
|
163
|
+
},
|
|
164
|
+
|
|
165
|
+
// Tier 4: DevOps
|
|
166
|
+
devops: {
|
|
167
|
+
name: 'DevOps',
|
|
168
|
+
tier: 4,
|
|
169
|
+
tierName: 'DevOps',
|
|
170
|
+
role: 'Deployment & infrastructure',
|
|
171
|
+
invocation: '@devops',
|
|
172
|
+
file: '4-devops/devops.md',
|
|
173
|
+
capabilities: ['deployment', 'ci_cd', 'infrastructure', 'monitoring'],
|
|
174
|
+
canInvoke: []
|
|
175
|
+
},
|
|
176
|
+
|
|
177
|
+
// Tier 5: Quality
|
|
178
|
+
testing: {
|
|
179
|
+
name: 'Testing',
|
|
180
|
+
tier: 5,
|
|
181
|
+
tierName: 'Quality',
|
|
182
|
+
role: 'QA & test automation',
|
|
183
|
+
invocation: '@testing',
|
|
184
|
+
file: '5-quality/testing.md',
|
|
185
|
+
capabilities: ['unit_testing', 'integration_testing', 'e2e_testing'],
|
|
186
|
+
canInvoke: []
|
|
187
|
+
},
|
|
188
|
+
reviewer: {
|
|
189
|
+
name: 'Reviewer',
|
|
190
|
+
tier: 5,
|
|
191
|
+
tierName: 'Quality',
|
|
192
|
+
role: 'Code review & quality checks',
|
|
193
|
+
invocation: '@reviewer',
|
|
194
|
+
file: '5-quality/reviewer.md',
|
|
195
|
+
capabilities: ['code_review', 'best_practices', 'quality_gates'],
|
|
196
|
+
canInvoke: []
|
|
197
|
+
},
|
|
198
|
+
debugger: {
|
|
199
|
+
name: 'Debugger',
|
|
200
|
+
tier: 5,
|
|
201
|
+
tierName: 'Quality',
|
|
202
|
+
role: 'Bug investigation & fixes',
|
|
203
|
+
invocation: '@debugger',
|
|
204
|
+
file: '5-quality/debugger.md',
|
|
205
|
+
capabilities: ['debugging', 'root_cause_analysis', 'bug_fixing'],
|
|
206
|
+
canInvoke: ['backend', 'frontend', 'database']
|
|
207
|
+
},
|
|
208
|
+
documentation: {
|
|
209
|
+
name: 'Documentation',
|
|
210
|
+
tier: 5,
|
|
211
|
+
tierName: 'Quality',
|
|
212
|
+
role: 'Technical writing & docs maintenance',
|
|
213
|
+
invocation: '@documentation',
|
|
214
|
+
file: '5-quality/documentation.md',
|
|
215
|
+
capabilities: ['technical_writing', 'api_docs', 'user_guides'],
|
|
216
|
+
canInvoke: []
|
|
217
|
+
},
|
|
218
|
+
|
|
219
|
+
// Tier 6: Specialist
|
|
220
|
+
performance: {
|
|
221
|
+
name: 'Performance',
|
|
222
|
+
tier: 6,
|
|
223
|
+
tierName: 'Specialist',
|
|
224
|
+
role: 'Performance optimization',
|
|
225
|
+
invocation: '@performance',
|
|
226
|
+
file: '6-specialist/performance.md',
|
|
227
|
+
capabilities: ['profiling', 'optimization', 'caching', 'load_testing'],
|
|
228
|
+
canInvoke: ['backend', 'frontend', 'database']
|
|
229
|
+
},
|
|
230
|
+
refactoring: {
|
|
231
|
+
name: 'Refactoring',
|
|
232
|
+
tier: 6,
|
|
233
|
+
tierName: 'Specialist',
|
|
234
|
+
role: 'Code quality & design patterns',
|
|
235
|
+
invocation: '@refactoring',
|
|
236
|
+
file: '6-specialist/refactoring.md',
|
|
237
|
+
capabilities: ['code_cleanup', 'design_patterns', 'architecture_improvement'],
|
|
238
|
+
canInvoke: ['backend', 'frontend']
|
|
239
|
+
}
|
|
240
|
+
};
|
|
241
|
+
|
|
242
|
+
// ============================================================================
|
|
243
|
+
// TIER DEPENDENCY GRAPH
|
|
244
|
+
// ============================================================================
|
|
245
|
+
|
|
246
|
+
/**
|
|
247
|
+
* Defines standard execution flow between tiers.
|
|
248
|
+
* This represents the typical order of operations for a full feature.
|
|
249
|
+
*/
|
|
250
|
+
export const TIER_FLOW = {
|
|
251
|
+
standard: [
|
|
252
|
+
{ tier: 1, phase: 'Planning', required: true },
|
|
253
|
+
{ tier: 2, phase: 'Implementation', required: true },
|
|
254
|
+
{ tier: 3, phase: 'Security', required: false },
|
|
255
|
+
{ tier: 5, phase: 'Quality', required: true },
|
|
256
|
+
{ tier: 4, phase: 'Deployment', required: false },
|
|
257
|
+
{ tier: 6, phase: 'Optimization', required: false }
|
|
258
|
+
],
|
|
259
|
+
hotfix: [
|
|
260
|
+
{ tier: 5, phase: 'Debug', agents: ['debugger'], required: true },
|
|
261
|
+
{ tier: 5, phase: 'Test', agents: ['testing'], required: true },
|
|
262
|
+
{ tier: 4, phase: 'Deploy', agents: ['devops'], required: true }
|
|
263
|
+
],
|
|
264
|
+
optimization: [
|
|
265
|
+
{ tier: 6, phase: 'Optimize', required: true },
|
|
266
|
+
{ tier: 5, phase: 'Test', agents: ['testing'], required: true },
|
|
267
|
+
{ tier: 5, phase: 'Review', agents: ['reviewer'], required: true }
|
|
268
|
+
]
|
|
269
|
+
};
|
|
270
|
+
|
|
271
|
+
/**
|
|
272
|
+
* Agent dependency graph - which agents depend on outputs from others.
|
|
273
|
+
*/
|
|
274
|
+
export const AGENT_DEPENDENCIES = {
|
|
275
|
+
// Leadership tier has no dependencies (entry points)
|
|
276
|
+
planner: [],
|
|
277
|
+
cto: ['planner'],
|
|
278
|
+
research: ['planner'],
|
|
279
|
+
|
|
280
|
+
// Development depends on leadership decisions
|
|
281
|
+
database: ['cto'],
|
|
282
|
+
backend: ['cto', 'database'],
|
|
283
|
+
frontend: ['cto', 'backend'],
|
|
284
|
+
|
|
285
|
+
// Security depends on implementation
|
|
286
|
+
auth: ['backend', 'database'],
|
|
287
|
+
security: ['backend', 'frontend', 'auth'],
|
|
288
|
+
|
|
289
|
+
// Quality depends on implementation
|
|
290
|
+
testing: ['backend', 'frontend'],
|
|
291
|
+
reviewer: ['backend', 'frontend', 'testing'],
|
|
292
|
+
debugger: [], // Can be invoked anytime
|
|
293
|
+
documentation: ['backend', 'frontend'],
|
|
294
|
+
|
|
295
|
+
// DevOps depends on quality approval
|
|
296
|
+
devops: ['testing', 'reviewer'],
|
|
297
|
+
|
|
298
|
+
// Specialist can run after implementation
|
|
299
|
+
performance: ['backend', 'frontend'],
|
|
300
|
+
refactoring: ['backend', 'frontend']
|
|
301
|
+
};
|
|
302
|
+
|
|
303
|
+
// ============================================================================
|
|
304
|
+
// UTILITY FUNCTIONS
|
|
305
|
+
// ============================================================================
|
|
306
|
+
|
|
307
|
+
/**
|
|
308
|
+
* Get agent by name.
|
|
309
|
+
*/
|
|
310
|
+
export function getAgent(name) {
|
|
311
|
+
const normalized = name.toLowerCase().replace('@', '');
|
|
312
|
+
return AGENTS[normalized] || null;
|
|
313
|
+
}
|
|
314
|
+
|
|
315
|
+
/**
|
|
316
|
+
* Get all agents in a tier.
|
|
317
|
+
*/
|
|
318
|
+
export function getAgentsByTier(tierId) {
|
|
319
|
+
return Object.values(AGENTS).filter(agent => agent.tier === tierId);
|
|
320
|
+
}
|
|
321
|
+
|
|
322
|
+
/**
|
|
323
|
+
* Get tier by ID.
|
|
324
|
+
*/
|
|
325
|
+
export function getTier(tierId) {
|
|
326
|
+
return Object.values(TIERS).find(tier => tier.id === tierId) || null;
|
|
327
|
+
}
|
|
328
|
+
|
|
329
|
+
/**
|
|
330
|
+
* Get tier by agent name.
|
|
331
|
+
*/
|
|
332
|
+
export function getTierForAgent(agentName) {
|
|
333
|
+
const agent = getAgent(agentName);
|
|
334
|
+
return agent ? getTier(agent.tier) : null;
|
|
335
|
+
}
|
|
336
|
+
|
|
337
|
+
/**
|
|
338
|
+
* Get dependencies for an agent.
|
|
339
|
+
*/
|
|
340
|
+
export function getAgentDependencies(agentName) {
|
|
341
|
+
const normalized = agentName.toLowerCase().replace('@', '');
|
|
342
|
+
return AGENT_DEPENDENCIES[normalized] || [];
|
|
343
|
+
}
|
|
344
|
+
|
|
345
|
+
/**
|
|
346
|
+
* Check if agent A can invoke agent B.
|
|
347
|
+
*/
|
|
348
|
+
export function canInvoke(agentA, agentB) {
|
|
349
|
+
const a = getAgent(agentA);
|
|
350
|
+
if (!a) return false;
|
|
351
|
+
if (a.canInvoke.includes('all')) return true;
|
|
352
|
+
return a.canInvoke.includes(agentB.toLowerCase().replace('@', ''));
|
|
353
|
+
}
|
|
354
|
+
|
|
355
|
+
/**
|
|
356
|
+
* Get execution order for a set of agents based on dependencies.
|
|
357
|
+
*/
|
|
358
|
+
export function getExecutionOrder(agentNames) {
|
|
359
|
+
const normalized = agentNames.map(n => n.toLowerCase().replace('@', ''));
|
|
360
|
+
const visited = new Set();
|
|
361
|
+
const order = [];
|
|
362
|
+
|
|
363
|
+
function visit(agent) {
|
|
364
|
+
if (visited.has(agent)) return;
|
|
365
|
+
visited.add(agent);
|
|
366
|
+
|
|
367
|
+
const deps = AGENT_DEPENDENCIES[agent] || [];
|
|
368
|
+
for (const dep of deps) {
|
|
369
|
+
if (normalized.includes(dep)) {
|
|
370
|
+
visit(dep);
|
|
371
|
+
}
|
|
372
|
+
}
|
|
373
|
+
order.push(agent);
|
|
374
|
+
}
|
|
375
|
+
|
|
376
|
+
for (const agent of normalized) {
|
|
377
|
+
visit(agent);
|
|
378
|
+
}
|
|
379
|
+
|
|
380
|
+
return order;
|
|
381
|
+
}
|
|
382
|
+
|
|
383
|
+
/**
|
|
384
|
+
* Identify parallel execution opportunities.
|
|
385
|
+
*/
|
|
386
|
+
export function findParallelGroups(agentNames) {
|
|
387
|
+
const order = getExecutionOrder(agentNames);
|
|
388
|
+
const groups = [];
|
|
389
|
+
const scheduled = new Set();
|
|
390
|
+
|
|
391
|
+
while (scheduled.size < order.length) {
|
|
392
|
+
const group = [];
|
|
393
|
+
|
|
394
|
+
for (const agent of order) {
|
|
395
|
+
if (scheduled.has(agent)) continue;
|
|
396
|
+
|
|
397
|
+
const deps = AGENT_DEPENDENCIES[agent] || [];
|
|
398
|
+
const depsInList = deps.filter(d => order.includes(d));
|
|
399
|
+
const depsMet = depsInList.every(d => scheduled.has(d));
|
|
400
|
+
|
|
401
|
+
if (depsMet) {
|
|
402
|
+
group.push(agent);
|
|
403
|
+
}
|
|
404
|
+
}
|
|
405
|
+
|
|
406
|
+
if (group.length === 0) break; // Prevent infinite loop
|
|
407
|
+
|
|
408
|
+
for (const agent of group) {
|
|
409
|
+
scheduled.add(agent);
|
|
410
|
+
}
|
|
411
|
+
groups.push(group);
|
|
412
|
+
}
|
|
413
|
+
|
|
414
|
+
return groups;
|
|
415
|
+
}
|
|
416
|
+
|
|
417
|
+
/**
|
|
418
|
+
* Generate a tier summary for display.
|
|
419
|
+
*/
|
|
420
|
+
export function getTierSummary() {
|
|
421
|
+
return Object.values(TIERS).map(tier => ({
|
|
422
|
+
id: tier.id,
|
|
423
|
+
name: tier.name,
|
|
424
|
+
description: tier.description,
|
|
425
|
+
agentCount: tier.agents.length,
|
|
426
|
+
agents: tier.agents.map(a => AGENTS[a]?.name || a)
|
|
427
|
+
}));
|
|
428
|
+
}
|
|
429
|
+
|
|
430
|
+
/**
|
|
431
|
+
* Validate a pipeline for dependency violations.
|
|
432
|
+
*/
|
|
433
|
+
export function validatePipeline(pipeline) {
|
|
434
|
+
const errors = [];
|
|
435
|
+
const completed = new Set();
|
|
436
|
+
|
|
437
|
+
for (let i = 0; i < pipeline.length; i++) {
|
|
438
|
+
const step = pipeline[i];
|
|
439
|
+
const agent = step.agent?.toLowerCase().replace('@', '');
|
|
440
|
+
const deps = AGENT_DEPENDENCIES[agent] || [];
|
|
441
|
+
|
|
442
|
+
for (const dep of deps) {
|
|
443
|
+
// Check if dependency is in pipeline and comes before
|
|
444
|
+
const depIndex = pipeline.findIndex(s =>
|
|
445
|
+
s.agent?.toLowerCase().replace('@', '') === dep
|
|
446
|
+
);
|
|
447
|
+
|
|
448
|
+
if (depIndex > i) {
|
|
449
|
+
errors.push({
|
|
450
|
+
step: i + 1,
|
|
451
|
+
agent,
|
|
452
|
+
error: `Depends on ${dep} which is scheduled after (step ${depIndex + 1})`
|
|
453
|
+
});
|
|
454
|
+
}
|
|
455
|
+
}
|
|
456
|
+
|
|
457
|
+
completed.add(agent);
|
|
458
|
+
}
|
|
459
|
+
|
|
460
|
+
return {
|
|
461
|
+
valid: errors.length === 0,
|
|
462
|
+
errors
|
|
463
|
+
};
|
|
464
|
+
}
|
|
465
|
+
|
|
466
|
+
// ============================================================================
|
|
467
|
+
// EXPORTS
|
|
468
|
+
// ============================================================================
|
|
469
|
+
|
|
470
|
+
export default {
|
|
471
|
+
TIERS,
|
|
472
|
+
AGENTS,
|
|
473
|
+
TIER_FLOW,
|
|
474
|
+
AGENT_DEPENDENCIES,
|
|
475
|
+
getAgent,
|
|
476
|
+
getAgentsByTier,
|
|
477
|
+
getTier,
|
|
478
|
+
getTierForAgent,
|
|
479
|
+
getAgentDependencies,
|
|
480
|
+
canInvoke,
|
|
481
|
+
getExecutionOrder,
|
|
482
|
+
findParallelGroups,
|
|
483
|
+
getTierSummary,
|
|
484
|
+
validatePipeline
|
|
485
|
+
};
|
|
@@ -0,0 +1,138 @@
|
|
|
1
|
+
// Ultra-Dex Production Pattern: Clerk Middleware
|
|
2
|
+
// Copy to middleware.ts in your Next.js root
|
|
3
|
+
|
|
4
|
+
import { clerkMiddleware, createRouteMatcher } from '@clerk/nextjs/server';
|
|
5
|
+
import { NextResponse } from 'next/server';
|
|
6
|
+
|
|
7
|
+
// =============================================================================
|
|
8
|
+
// ROUTE MATCHERS
|
|
9
|
+
// =============================================================================
|
|
10
|
+
|
|
11
|
+
// Public routes - accessible without authentication
|
|
12
|
+
const isPublicRoute = createRouteMatcher([
|
|
13
|
+
'/',
|
|
14
|
+
'/sign-in(.*)',
|
|
15
|
+
'/sign-up(.*)',
|
|
16
|
+
'/api/webhooks(.*)',
|
|
17
|
+
'/pricing',
|
|
18
|
+
'/about',
|
|
19
|
+
'/blog(.*)',
|
|
20
|
+
]);
|
|
21
|
+
|
|
22
|
+
// Admin routes - require admin role
|
|
23
|
+
const isAdminRoute = createRouteMatcher([
|
|
24
|
+
'/admin(.*)',
|
|
25
|
+
'/api/admin(.*)',
|
|
26
|
+
]);
|
|
27
|
+
|
|
28
|
+
// API routes that need special handling
|
|
29
|
+
const isApiRoute = createRouteMatcher(['/api(.*)']);
|
|
30
|
+
|
|
31
|
+
// =============================================================================
|
|
32
|
+
// MIDDLEWARE
|
|
33
|
+
// =============================================================================
|
|
34
|
+
|
|
35
|
+
export default clerkMiddleware(async (auth, req) => {
|
|
36
|
+
const { userId, sessionClaims } = await auth();
|
|
37
|
+
|
|
38
|
+
// Allow public routes
|
|
39
|
+
if (isPublicRoute(req)) {
|
|
40
|
+
return NextResponse.next();
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
// Protect all non-public routes
|
|
44
|
+
if (!userId) {
|
|
45
|
+
const signInUrl = new URL('/sign-in', req.url);
|
|
46
|
+
signInUrl.searchParams.set('redirect_url', req.url);
|
|
47
|
+
return NextResponse.redirect(signInUrl);
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
// Check admin routes
|
|
51
|
+
if (isAdminRoute(req)) {
|
|
52
|
+
const role = sessionClaims?.metadata?.role as string | undefined;
|
|
53
|
+
|
|
54
|
+
if (role !== 'admin' && role !== 'super_admin') {
|
|
55
|
+
return NextResponse.redirect(new URL('/unauthorized', req.url));
|
|
56
|
+
}
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
// Add user info to headers for API routes
|
|
60
|
+
if (isApiRoute(req)) {
|
|
61
|
+
const requestHeaders = new Headers(req.headers);
|
|
62
|
+
requestHeaders.set('x-user-id', userId);
|
|
63
|
+
|
|
64
|
+
return NextResponse.next({
|
|
65
|
+
request: {
|
|
66
|
+
headers: requestHeaders,
|
|
67
|
+
},
|
|
68
|
+
});
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
return NextResponse.next();
|
|
72
|
+
});
|
|
73
|
+
|
|
74
|
+
export const config = {
|
|
75
|
+
matcher: [
|
|
76
|
+
// Skip Next.js internals and static files
|
|
77
|
+
'/((?!_next|[^?]*\\.(?:html?|css|js(?!on)|jpe?g|webp|png|gif|svg|ttf|woff2?|ico|csv|docx?|xlsx?|zip|webmanifest)).*)',
|
|
78
|
+
// Always run for API routes
|
|
79
|
+
'/(api|trpc)(.*)',
|
|
80
|
+
],
|
|
81
|
+
};
|
|
82
|
+
|
|
83
|
+
// =============================================================================
|
|
84
|
+
// USAGE EXAMPLES
|
|
85
|
+
// =============================================================================
|
|
86
|
+
|
|
87
|
+
/*
|
|
88
|
+
// In a Server Component - get current user:
|
|
89
|
+
|
|
90
|
+
import { auth, currentUser } from '@clerk/nextjs/server';
|
|
91
|
+
|
|
92
|
+
export default async function DashboardPage() {
|
|
93
|
+
const { userId } = await auth();
|
|
94
|
+
const user = await currentUser();
|
|
95
|
+
|
|
96
|
+
if (!userId) {
|
|
97
|
+
redirect('/sign-in');
|
|
98
|
+
}
|
|
99
|
+
|
|
100
|
+
return <div>Welcome, {user?.firstName}!</div>;
|
|
101
|
+
}
|
|
102
|
+
|
|
103
|
+
// In a Client Component - use hooks:
|
|
104
|
+
|
|
105
|
+
'use client';
|
|
106
|
+
|
|
107
|
+
import { useUser, useAuth } from '@clerk/nextjs';
|
|
108
|
+
|
|
109
|
+
export function UserProfile() {
|
|
110
|
+
const { user, isLoaded } = useUser();
|
|
111
|
+
const { signOut } = useAuth();
|
|
112
|
+
|
|
113
|
+
if (!isLoaded) return <div>Loading...</div>;
|
|
114
|
+
|
|
115
|
+
return (
|
|
116
|
+
<div>
|
|
117
|
+
<p>Hello, {user?.firstName}</p>
|
|
118
|
+
<button onClick={() => signOut()}>Sign Out</button>
|
|
119
|
+
</div>
|
|
120
|
+
);
|
|
121
|
+
}
|
|
122
|
+
|
|
123
|
+
// In an API Route:
|
|
124
|
+
|
|
125
|
+
import { auth } from '@clerk/nextjs/server';
|
|
126
|
+
import { NextResponse } from 'next/server';
|
|
127
|
+
|
|
128
|
+
export async function GET() {
|
|
129
|
+
const { userId } = await auth();
|
|
130
|
+
|
|
131
|
+
if (!userId) {
|
|
132
|
+
return NextResponse.json({ error: 'Unauthorized' }, { status: 401 });
|
|
133
|
+
}
|
|
134
|
+
|
|
135
|
+
// Your logic here
|
|
136
|
+
return NextResponse.json({ userId });
|
|
137
|
+
}
|
|
138
|
+
*/
|