@skillsmith/mcp-server 0.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/dist/.tsbuildinfo +1 -0
- package/dist/src/__tests__/get-skill.test.d.ts +6 -0
- package/dist/src/__tests__/get-skill.test.d.ts.map +1 -0
- package/dist/src/__tests__/get-skill.test.js +88 -0
- package/dist/src/__tests__/get-skill.test.js.map +1 -0
- package/dist/src/__tests__/middleware/errorFormatter.test.d.ts +7 -0
- package/dist/src/__tests__/middleware/errorFormatter.test.d.ts.map +1 -0
- package/dist/src/__tests__/middleware/errorFormatter.test.js +304 -0
- package/dist/src/__tests__/middleware/errorFormatter.test.js.map +1 -0
- package/dist/src/__tests__/middleware/license.test.d.ts +7 -0
- package/dist/src/__tests__/middleware/license.test.d.ts.map +1 -0
- package/dist/src/__tests__/middleware/license.test.js +500 -0
- package/dist/src/__tests__/middleware/license.test.js.map +1 -0
- package/dist/src/__tests__/search.test.d.ts +6 -0
- package/dist/src/__tests__/search.test.d.ts.map +1 -0
- package/dist/src/__tests__/search.test.js +86 -0
- package/dist/src/__tests__/search.test.js.map +1 -0
- package/dist/src/__tests__/test-utils.d.ts +19 -0
- package/dist/src/__tests__/test-utils.d.ts.map +1 -0
- package/dist/src/__tests__/test-utils.js +87 -0
- package/dist/src/__tests__/test-utils.js.map +1 -0
- package/dist/src/context/index.d.ts +19 -0
- package/dist/src/context/index.d.ts.map +1 -0
- package/dist/src/context/index.js +25 -0
- package/dist/src/context/index.js.map +1 -0
- package/dist/src/context/project-detector.d.ts +145 -0
- package/dist/src/context/project-detector.d.ts.map +1 -0
- package/dist/src/context/project-detector.js +321 -0
- package/dist/src/context/project-detector.js.map +1 -0
- package/dist/src/context.d.ts +100 -0
- package/dist/src/context.d.ts.map +1 -0
- package/dist/src/context.js +157 -0
- package/dist/src/context.js.map +1 -0
- package/dist/src/core-shim.d.ts +7 -0
- package/dist/src/core-shim.d.ts.map +1 -0
- package/dist/src/core-shim.js +9 -0
- package/dist/src/core-shim.js.map +1 -0
- package/dist/src/health/healthCheck.d.ts +88 -0
- package/dist/src/health/healthCheck.d.ts.map +1 -0
- package/dist/src/health/healthCheck.js +117 -0
- package/dist/src/health/healthCheck.js.map +1 -0
- package/dist/src/health/index.d.ts +21 -0
- package/dist/src/health/index.d.ts.map +1 -0
- package/dist/src/health/index.js +21 -0
- package/dist/src/health/index.js.map +1 -0
- package/dist/src/health/readinessCheck.d.ts +139 -0
- package/dist/src/health/readinessCheck.d.ts.map +1 -0
- package/dist/src/health/readinessCheck.js +266 -0
- package/dist/src/health/readinessCheck.js.map +1 -0
- package/dist/src/index.d.ts +8 -0
- package/dist/src/index.d.ts.map +1 -0
- package/dist/src/index.js +178 -0
- package/dist/src/index.js.map +1 -0
- package/dist/src/index.test.d.ts +2 -0
- package/dist/src/index.test.d.ts.map +1 -0
- package/dist/src/index.test.js +43 -0
- package/dist/src/index.test.js.map +1 -0
- package/dist/src/logger.d.ts +26 -0
- package/dist/src/logger.d.ts.map +1 -0
- package/dist/src/logger.js +179 -0
- package/dist/src/logger.js.map +1 -0
- package/dist/src/middleware/__tests__/csp.test.d.ts +2 -0
- package/dist/src/middleware/__tests__/csp.test.d.ts.map +1 -0
- package/dist/src/middleware/__tests__/csp.test.js +389 -0
- package/dist/src/middleware/__tests__/csp.test.js.map +1 -0
- package/dist/src/middleware/csp.d.ts +87 -0
- package/dist/src/middleware/csp.d.ts.map +1 -0
- package/dist/src/middleware/csp.js +273 -0
- package/dist/src/middleware/csp.js.map +1 -0
- package/dist/src/middleware/degradation.d.ts +99 -0
- package/dist/src/middleware/degradation.d.ts.map +1 -0
- package/dist/src/middleware/degradation.js +315 -0
- package/dist/src/middleware/degradation.js.map +1 -0
- package/dist/src/middleware/errorFormatter.d.ts +119 -0
- package/dist/src/middleware/errorFormatter.d.ts.map +1 -0
- package/dist/src/middleware/errorFormatter.js +294 -0
- package/dist/src/middleware/errorFormatter.js.map +1 -0
- package/dist/src/middleware/index.d.ts +10 -0
- package/dist/src/middleware/index.d.ts.map +1 -0
- package/dist/src/middleware/index.js +14 -0
- package/dist/src/middleware/index.js.map +1 -0
- package/dist/src/middleware/license.d.ts +161 -0
- package/dist/src/middleware/license.d.ts.map +1 -0
- package/dist/src/middleware/license.js +281 -0
- package/dist/src/middleware/license.js.map +1 -0
- package/dist/src/middleware/toolFeatureMapping.d.ts +36 -0
- package/dist/src/middleware/toolFeatureMapping.d.ts.map +1 -0
- package/dist/src/middleware/toolFeatureMapping.js +90 -0
- package/dist/src/middleware/toolFeatureMapping.js.map +1 -0
- package/dist/src/onboarding/first-run.d.ts +64 -0
- package/dist/src/onboarding/first-run.d.ts.map +1 -0
- package/dist/src/onboarding/first-run.js +77 -0
- package/dist/src/onboarding/first-run.js.map +1 -0
- package/dist/src/onboarding/index.d.ts +7 -0
- package/dist/src/onboarding/index.d.ts.map +1 -0
- package/dist/src/onboarding/index.js +7 -0
- package/dist/src/onboarding/index.js.map +1 -0
- package/dist/src/suggestions/index.d.ts +21 -0
- package/dist/src/suggestions/index.d.ts.map +1 -0
- package/dist/src/suggestions/index.js +20 -0
- package/dist/src/suggestions/index.js.map +1 -0
- package/dist/src/suggestions/suggestion-engine.d.ts +185 -0
- package/dist/src/suggestions/suggestion-engine.d.ts.map +1 -0
- package/dist/src/suggestions/suggestion-engine.js +352 -0
- package/dist/src/suggestions/suggestion-engine.js.map +1 -0
- package/dist/src/suggestions/types.d.ts +88 -0
- package/dist/src/suggestions/types.d.ts.map +1 -0
- package/dist/src/suggestions/types.js +21 -0
- package/dist/src/suggestions/types.js.map +1 -0
- package/dist/src/tools/analyze.d.ts +151 -0
- package/dist/src/tools/analyze.d.ts.map +1 -0
- package/dist/src/tools/analyze.js +205 -0
- package/dist/src/tools/analyze.js.map +1 -0
- package/dist/src/tools/compare.d.ts +149 -0
- package/dist/src/tools/compare.d.ts.map +1 -0
- package/dist/src/tools/compare.js +464 -0
- package/dist/src/tools/compare.js.map +1 -0
- package/dist/src/tools/get-skill.d.ts +116 -0
- package/dist/src/tools/get-skill.d.ts.map +1 -0
- package/dist/src/tools/get-skill.js +224 -0
- package/dist/src/tools/get-skill.js.map +1 -0
- package/dist/src/tools/index.d.ts +20 -0
- package/dist/src/tools/index.d.ts.map +1 -0
- package/dist/src/tools/index.js +20 -0
- package/dist/src/tools/index.js.map +1 -0
- package/dist/src/tools/install.d.ts +122 -0
- package/dist/src/tools/install.d.ts.map +1 -0
- package/dist/src/tools/install.js +314 -0
- package/dist/src/tools/install.js.map +1 -0
- package/dist/src/tools/recommend.d.ts +171 -0
- package/dist/src/tools/recommend.d.ts.map +1 -0
- package/dist/src/tools/recommend.js +325 -0
- package/dist/src/tools/recommend.js.map +1 -0
- package/dist/src/tools/search.d.ts +121 -0
- package/dist/src/tools/search.d.ts.map +1 -0
- package/dist/src/tools/search.js +249 -0
- package/dist/src/tools/search.js.map +1 -0
- package/dist/src/tools/suggest.d.ts +181 -0
- package/dist/src/tools/suggest.d.ts.map +1 -0
- package/dist/src/tools/suggest.js +342 -0
- package/dist/src/tools/suggest.js.map +1 -0
- package/dist/src/tools/uninstall.d.ts +123 -0
- package/dist/src/tools/uninstall.d.ts.map +1 -0
- package/dist/src/tools/uninstall.js +250 -0
- package/dist/src/tools/uninstall.js.map +1 -0
- package/dist/src/tools/validate.d.ts +122 -0
- package/dist/src/tools/validate.d.ts.map +1 -0
- package/dist/src/tools/validate.js +497 -0
- package/dist/src/tools/validate.js.map +1 -0
- package/dist/src/utils/installed-skills.d.ts +101 -0
- package/dist/src/utils/installed-skills.d.ts.map +1 -0
- package/dist/src/utils/installed-skills.js +220 -0
- package/dist/src/utils/installed-skills.js.map +1 -0
- package/dist/src/utils/validation.d.ts +76 -0
- package/dist/src/utils/validation.d.ts.map +1 -0
- package/dist/src/utils/validation.js +153 -0
- package/dist/src/utils/validation.js.map +1 -0
- package/dist/src/webhooks/index.d.ts +8 -0
- package/dist/src/webhooks/index.d.ts.map +1 -0
- package/dist/src/webhooks/index.js +9 -0
- package/dist/src/webhooks/index.js.map +1 -0
- package/dist/src/webhooks/webhook-endpoint.d.ts +149 -0
- package/dist/src/webhooks/webhook-endpoint.d.ts.map +1 -0
- package/dist/src/webhooks/webhook-endpoint.js +339 -0
- package/dist/src/webhooks/webhook-endpoint.js.map +1 -0
- package/dist/tests/compare.test.d.ts +6 -0
- package/dist/tests/compare.test.d.ts.map +1 -0
- package/dist/tests/compare.test.js +225 -0
- package/dist/tests/compare.test.js.map +1 -0
- package/dist/tests/context/project-detector.test.d.ts +6 -0
- package/dist/tests/context/project-detector.test.d.ts.map +1 -0
- package/dist/tests/context/project-detector.test.js +719 -0
- package/dist/tests/context/project-detector.test.js.map +1 -0
- package/dist/tests/e2e/compare.e2e.test.d.ts +10 -0
- package/dist/tests/e2e/compare.e2e.test.d.ts.map +1 -0
- package/dist/tests/e2e/compare.e2e.test.js +286 -0
- package/dist/tests/e2e/compare.e2e.test.js.map +1 -0
- package/dist/tests/e2e/install-flow.e2e.test.d.ts +10 -0
- package/dist/tests/e2e/install-flow.e2e.test.d.ts.map +1 -0
- package/dist/tests/e2e/install-flow.e2e.test.js +209 -0
- package/dist/tests/e2e/install-flow.e2e.test.js.map +1 -0
- package/dist/tests/e2e/recommend.e2e.test.d.ts +12 -0
- package/dist/tests/e2e/recommend.e2e.test.d.ts.map +1 -0
- package/dist/tests/e2e/recommend.e2e.test.js +347 -0
- package/dist/tests/e2e/recommend.e2e.test.js.map +1 -0
- package/dist/tests/e2e/skill-flow.e2e.test.d.ts +10 -0
- package/dist/tests/e2e/skill-flow.e2e.test.d.ts.map +1 -0
- package/dist/tests/e2e/skill-flow.e2e.test.js +280 -0
- package/dist/tests/e2e/skill-flow.e2e.test.js.map +1 -0
- package/dist/tests/e2e/suggest.e2e.test.d.ts +13 -0
- package/dist/tests/e2e/suggest.e2e.test.d.ts.map +1 -0
- package/dist/tests/e2e/suggest.e2e.test.js +347 -0
- package/dist/tests/e2e/suggest.e2e.test.js.map +1 -0
- package/dist/tests/e2e/utils/baseline-collector.d.ts +107 -0
- package/dist/tests/e2e/utils/baseline-collector.d.ts.map +1 -0
- package/dist/tests/e2e/utils/baseline-collector.js +211 -0
- package/dist/tests/e2e/utils/baseline-collector.js.map +1 -0
- package/dist/tests/e2e/utils/hardcoded-detector.d.ts +46 -0
- package/dist/tests/e2e/utils/hardcoded-detector.d.ts.map +1 -0
- package/dist/tests/e2e/utils/hardcoded-detector.js +255 -0
- package/dist/tests/e2e/utils/hardcoded-detector.js.map +1 -0
- package/dist/tests/e2e/utils/index.d.ts +7 -0
- package/dist/tests/e2e/utils/index.d.ts.map +1 -0
- package/dist/tests/e2e/utils/index.js +7 -0
- package/dist/tests/e2e/utils/index.js.map +1 -0
- package/dist/tests/e2e/utils/linear-reporter.d.ts +60 -0
- package/dist/tests/e2e/utils/linear-reporter.d.ts.map +1 -0
- package/dist/tests/e2e/utils/linear-reporter.js +232 -0
- package/dist/tests/e2e/utils/linear-reporter.js.map +1 -0
- package/dist/tests/health.test.d.ts +9 -0
- package/dist/tests/health.test.d.ts.map +1 -0
- package/dist/tests/health.test.js +308 -0
- package/dist/tests/health.test.js.map +1 -0
- package/dist/tests/integration/analyze.integration.test.d.ts +2 -0
- package/dist/tests/integration/analyze.integration.test.d.ts.map +1 -0
- package/dist/tests/integration/analyze.integration.test.js +244 -0
- package/dist/tests/integration/analyze.integration.test.js.map +1 -0
- package/dist/tests/integration/compare.integration.test.d.ts +2 -0
- package/dist/tests/integration/compare.integration.test.d.ts.map +1 -0
- package/dist/tests/integration/compare.integration.test.js +120 -0
- package/dist/tests/integration/compare.integration.test.js.map +1 -0
- package/dist/tests/integration/fixtures/test-skills.d.ts +62 -0
- package/dist/tests/integration/fixtures/test-skills.d.ts.map +1 -0
- package/dist/tests/integration/fixtures/test-skills.js +644 -0
- package/dist/tests/integration/fixtures/test-skills.js.map +1 -0
- package/dist/tests/integration/get-skill.integration.test.d.ts +6 -0
- package/dist/tests/integration/get-skill.integration.test.d.ts.map +1 -0
- package/dist/tests/integration/get-skill.integration.test.js +203 -0
- package/dist/tests/integration/get-skill.integration.test.js.map +1 -0
- package/dist/tests/integration/github-api.integration.test.d.ts +14 -0
- package/dist/tests/integration/github-api.integration.test.d.ts.map +1 -0
- package/dist/tests/integration/github-api.integration.test.js +190 -0
- package/dist/tests/integration/github-api.integration.test.js.map +1 -0
- package/dist/tests/integration/install.integration.test.d.ts +6 -0
- package/dist/tests/integration/install.integration.test.d.ts.map +1 -0
- package/dist/tests/integration/install.integration.test.js +282 -0
- package/dist/tests/integration/install.integration.test.js.map +1 -0
- package/dist/tests/integration/recommend.integration.test.d.ts +2 -0
- package/dist/tests/integration/recommend.integration.test.d.ts.map +1 -0
- package/dist/tests/integration/recommend.integration.test.js +215 -0
- package/dist/tests/integration/recommend.integration.test.js.map +1 -0
- package/dist/tests/integration/search.integration.test.d.ts +6 -0
- package/dist/tests/integration/search.integration.test.d.ts.map +1 -0
- package/dist/tests/integration/search.integration.test.js +229 -0
- package/dist/tests/integration/search.integration.test.js.map +1 -0
- package/dist/tests/integration/setup.d.ts +71 -0
- package/dist/tests/integration/setup.d.ts.map +1 -0
- package/dist/tests/integration/setup.js +124 -0
- package/dist/tests/integration/setup.js.map +1 -0
- package/dist/tests/integration/uninstall.integration.test.d.ts +6 -0
- package/dist/tests/integration/uninstall.integration.test.d.ts.map +1 -0
- package/dist/tests/integration/uninstall.integration.test.js +296 -0
- package/dist/tests/integration/uninstall.integration.test.js.map +1 -0
- package/dist/tests/integration/validate.integration.test.d.ts +2 -0
- package/dist/tests/integration/validate.integration.test.d.ts.map +1 -0
- package/dist/tests/integration/validate.integration.test.js +181 -0
- package/dist/tests/integration/validate.integration.test.js.map +1 -0
- package/dist/tests/onboarding/first-run.test.d.ts +7 -0
- package/dist/tests/onboarding/first-run.test.d.ts.map +1 -0
- package/dist/tests/onboarding/first-run.test.js +258 -0
- package/dist/tests/onboarding/first-run.test.js.map +1 -0
- package/dist/tests/performance/search-performance.test.d.ts +10 -0
- package/dist/tests/performance/search-performance.test.d.ts.map +1 -0
- package/dist/tests/performance/search-performance.test.js +218 -0
- package/dist/tests/performance/search-performance.test.js.map +1 -0
- package/dist/tests/recommend.test.d.ts +6 -0
- package/dist/tests/recommend.test.d.ts.map +1 -0
- package/dist/tests/recommend.test.js +208 -0
- package/dist/tests/recommend.test.js.map +1 -0
- package/dist/tests/suggestions/suggestion-engine.test.d.ts +6 -0
- package/dist/tests/suggestions/suggestion-engine.test.d.ts.map +1 -0
- package/dist/tests/suggestions/suggestion-engine.test.js +448 -0
- package/dist/tests/suggestions/suggestion-engine.test.js.map +1 -0
- package/dist/tests/test-utils.d.ts +74 -0
- package/dist/tests/test-utils.d.ts.map +1 -0
- package/dist/tests/test-utils.js +98 -0
- package/dist/tests/test-utils.js.map +1 -0
- package/dist/tests/tools.test.d.ts +5 -0
- package/dist/tests/tools.test.d.ts.map +1 -0
- package/dist/tests/tools.test.js +138 -0
- package/dist/tests/tools.test.js.map +1 -0
- package/dist/tests/unit/installed-skills.test.d.ts +6 -0
- package/dist/tests/unit/installed-skills.test.d.ts.map +1 -0
- package/dist/tests/unit/installed-skills.test.js +285 -0
- package/dist/tests/unit/installed-skills.test.js.map +1 -0
- package/dist/tests/unit/logger.test.d.ts +6 -0
- package/dist/tests/unit/logger.test.d.ts.map +1 -0
- package/dist/tests/unit/logger.test.js +281 -0
- package/dist/tests/unit/logger.test.js.map +1 -0
- package/dist/tests/validate.test.d.ts +5 -0
- package/dist/tests/validate.test.d.ts.map +1 -0
- package/dist/tests/validate.test.js +303 -0
- package/dist/tests/validate.test.js.map +1 -0
- package/dist/tests/webhooks/proxy-trust.security.test.d.ts +8 -0
- package/dist/tests/webhooks/proxy-trust.security.test.d.ts.map +1 -0
- package/dist/tests/webhooks/proxy-trust.security.test.js +145 -0
- package/dist/tests/webhooks/proxy-trust.security.test.js.map +1 -0
- package/dist/tests/webhooks/rate-limiter.security.test.d.ts +8 -0
- package/dist/tests/webhooks/rate-limiter.security.test.d.ts.map +1 -0
- package/dist/tests/webhooks/rate-limiter.security.test.js +122 -0
- package/dist/tests/webhooks/rate-limiter.security.test.js.map +1 -0
- package/dist/vitest.config.d.ts +6 -0
- package/dist/vitest.config.d.ts.map +1 -0
- package/dist/vitest.config.js +13 -0
- package/dist/vitest.config.js.map +1 -0
- package/package.json +63 -0
|
@@ -0,0 +1,342 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @fileoverview MCP Skill Suggest Tool for proactive skill recommendations
|
|
3
|
+
* @module @skillsmith/mcp-server/tools/suggest
|
|
4
|
+
* @see Phase 4: Trigger System Architecture
|
|
5
|
+
*
|
|
6
|
+
* Provides proactive skill suggestions based on user context including:
|
|
7
|
+
* - Current file being edited
|
|
8
|
+
* - Recent terminal commands
|
|
9
|
+
* - Error messages
|
|
10
|
+
* - Project structure analysis
|
|
11
|
+
*
|
|
12
|
+
* Features:
|
|
13
|
+
* - Rate limiting (max 1 suggestion per 5 minutes per session)
|
|
14
|
+
* - Context scoring to filter low-relevance suggestions
|
|
15
|
+
* - Integration with CodebaseAnalyzer
|
|
16
|
+
* - Semantic skill matching
|
|
17
|
+
*
|
|
18
|
+
* @example
|
|
19
|
+
* // Client calls suggest when user is working
|
|
20
|
+
* const result = await executeSuggest({
|
|
21
|
+
* project_path: '/path/to/project',
|
|
22
|
+
* current_file: 'src/App.test.tsx',
|
|
23
|
+
* recent_commands: ['npm test'],
|
|
24
|
+
* installed_skills: ['anthropic/commit']
|
|
25
|
+
* }, toolContext);
|
|
26
|
+
*/
|
|
27
|
+
import { z } from 'zod';
|
|
28
|
+
import { TriggerDetector, ContextScorer } from '@skillsmith/core';
|
|
29
|
+
import { CodebaseAnalyzer } from '@skillsmith/core';
|
|
30
|
+
import { SkillMatcher } from '@skillsmith/core';
|
|
31
|
+
import { RateLimiter } from '@skillsmith/core';
|
|
32
|
+
/**
|
|
33
|
+
* Zod schema for suggest tool input validation
|
|
34
|
+
*/
|
|
35
|
+
export const suggestInputSchema = z.object({
|
|
36
|
+
/** Root path of the project */
|
|
37
|
+
project_path: z.string().min(1),
|
|
38
|
+
/** Current file being edited (optional) */
|
|
39
|
+
current_file: z.string().optional(),
|
|
40
|
+
/** Recent terminal commands (last 5) */
|
|
41
|
+
recent_commands: z.array(z.string()).max(10).default([]),
|
|
42
|
+
/** Recent error message if any */
|
|
43
|
+
error_message: z.string().optional(),
|
|
44
|
+
/** Currently installed skill IDs */
|
|
45
|
+
installed_skills: z.array(z.string()).default([]),
|
|
46
|
+
/** Maximum suggestions to return (default 3) */
|
|
47
|
+
limit: z.number().min(1).max(10).default(3),
|
|
48
|
+
/** Session ID for rate limiting */
|
|
49
|
+
session_id: z.string().default('default'),
|
|
50
|
+
});
|
|
51
|
+
/**
|
|
52
|
+
* MCP tool schema definition for skill_suggest
|
|
53
|
+
*/
|
|
54
|
+
export const suggestToolSchema = {
|
|
55
|
+
name: 'skill_suggest',
|
|
56
|
+
description: 'Proactively suggest relevant skills based on current context (files, commands, errors, project structure). Rate-limited to max 1 per 5 minutes per session.',
|
|
57
|
+
inputSchema: {
|
|
58
|
+
type: 'object',
|
|
59
|
+
properties: {
|
|
60
|
+
project_path: {
|
|
61
|
+
type: 'string',
|
|
62
|
+
description: 'Root path of the project to analyze',
|
|
63
|
+
},
|
|
64
|
+
current_file: {
|
|
65
|
+
type: 'string',
|
|
66
|
+
description: 'Current file being edited (e.g., "src/App.test.tsx")',
|
|
67
|
+
},
|
|
68
|
+
recent_commands: {
|
|
69
|
+
type: 'array',
|
|
70
|
+
items: { type: 'string' },
|
|
71
|
+
description: 'Recent terminal commands (last 5, e.g., ["npm test", "git commit"])',
|
|
72
|
+
},
|
|
73
|
+
error_message: {
|
|
74
|
+
type: 'string',
|
|
75
|
+
description: 'Recent error message if any',
|
|
76
|
+
},
|
|
77
|
+
installed_skills: {
|
|
78
|
+
type: 'array',
|
|
79
|
+
items: { type: 'string' },
|
|
80
|
+
description: 'Currently installed skill IDs (for filtering)',
|
|
81
|
+
},
|
|
82
|
+
limit: {
|
|
83
|
+
type: 'number',
|
|
84
|
+
description: 'Maximum suggestions to return (default 3, max 10)',
|
|
85
|
+
minimum: 1,
|
|
86
|
+
maximum: 10,
|
|
87
|
+
default: 3,
|
|
88
|
+
},
|
|
89
|
+
session_id: {
|
|
90
|
+
type: 'string',
|
|
91
|
+
description: 'Session ID for rate limiting (default: "default")',
|
|
92
|
+
default: 'default',
|
|
93
|
+
},
|
|
94
|
+
},
|
|
95
|
+
required: ['project_path'],
|
|
96
|
+
},
|
|
97
|
+
};
|
|
98
|
+
/**
|
|
99
|
+
* Map database trust tier to MCP trust tier
|
|
100
|
+
*/
|
|
101
|
+
function mapTrustTierFromDb(dbTier) {
|
|
102
|
+
switch (dbTier) {
|
|
103
|
+
case 'verified':
|
|
104
|
+
return 'verified';
|
|
105
|
+
case 'community':
|
|
106
|
+
return 'community';
|
|
107
|
+
case 'experimental':
|
|
108
|
+
return 'standard';
|
|
109
|
+
case 'unknown':
|
|
110
|
+
default:
|
|
111
|
+
return 'unverified';
|
|
112
|
+
}
|
|
113
|
+
}
|
|
114
|
+
/**
|
|
115
|
+
* Transform a database skill to SkillData format for matching
|
|
116
|
+
*/
|
|
117
|
+
function transformSkillToMatchData(skill) {
|
|
118
|
+
// Generate trigger phrases from name and first few tags
|
|
119
|
+
const triggerPhrases = [
|
|
120
|
+
skill.name,
|
|
121
|
+
`use ${skill.name}`,
|
|
122
|
+
`${skill.name} help`,
|
|
123
|
+
...skill.tags.slice(0, 3).map((tag) => `${tag} ${skill.name}`),
|
|
124
|
+
];
|
|
125
|
+
return {
|
|
126
|
+
id: skill.id,
|
|
127
|
+
name: skill.name,
|
|
128
|
+
description: skill.description || '',
|
|
129
|
+
triggerPhrases,
|
|
130
|
+
keywords: skill.tags,
|
|
131
|
+
qualityScore: Math.round((skill.qualityScore ?? 0.5) * 100),
|
|
132
|
+
trustTier: mapTrustTierFromDb(skill.trustTier),
|
|
133
|
+
// Use tags as categories for filtering
|
|
134
|
+
categories: skill.tags,
|
|
135
|
+
};
|
|
136
|
+
}
|
|
137
|
+
/**
|
|
138
|
+
* Load skills from database via ToolContext
|
|
139
|
+
* Returns skills transformed to SkillData format for matching
|
|
140
|
+
*/
|
|
141
|
+
async function loadSkillsFromDatabase(context, limit = 500) {
|
|
142
|
+
const result = context.skillRepository.findAll(limit, 0);
|
|
143
|
+
return result.items.map(transformSkillToMatchData);
|
|
144
|
+
}
|
|
145
|
+
// Rate limiter instance (singleton)
|
|
146
|
+
let rateLimiter = null;
|
|
147
|
+
/**
|
|
148
|
+
* Get or create the rate limiter
|
|
149
|
+
*/
|
|
150
|
+
function getRateLimiter() {
|
|
151
|
+
if (!rateLimiter) {
|
|
152
|
+
// Use STRICT preset: 10 requests per minute = ~1 per 6 seconds
|
|
153
|
+
// For suggestions, we want max 1 per 5 minutes, so we'll use custom config
|
|
154
|
+
rateLimiter = new RateLimiter({
|
|
155
|
+
maxTokens: 1, // Only 1 suggestion at a time
|
|
156
|
+
refillRate: 1 / 300, // 1 token per 300 seconds (5 minutes)
|
|
157
|
+
windowMs: 300000, // 5 minute window
|
|
158
|
+
keyPrefix: 'suggest',
|
|
159
|
+
failMode: 'open', // Allow on errors (graceful degradation)
|
|
160
|
+
});
|
|
161
|
+
}
|
|
162
|
+
return rateLimiter;
|
|
163
|
+
}
|
|
164
|
+
/**
|
|
165
|
+
* Execute skill suggestion based on context.
|
|
166
|
+
*
|
|
167
|
+
* @param input - Suggestion parameters
|
|
168
|
+
* @param context - Tool context with database access
|
|
169
|
+
* @returns Promise resolving to suggestion response
|
|
170
|
+
*
|
|
171
|
+
* @example
|
|
172
|
+
* const response = await executeSuggest({
|
|
173
|
+
* project_path: '/path/to/project',
|
|
174
|
+
* current_file: 'src/App.test.tsx',
|
|
175
|
+
* recent_commands: ['npm test'],
|
|
176
|
+
* installed_skills: ['anthropic/commit'],
|
|
177
|
+
* limit: 3
|
|
178
|
+
* }, toolContext);
|
|
179
|
+
*/
|
|
180
|
+
export async function executeSuggest(input, context) {
|
|
181
|
+
const startTime = performance.now();
|
|
182
|
+
// Validate input
|
|
183
|
+
const validated = suggestInputSchema.parse(input);
|
|
184
|
+
const { project_path, current_file, recent_commands, error_message, installed_skills, limit, session_id, } = validated;
|
|
185
|
+
// Check rate limit
|
|
186
|
+
const limiter = getRateLimiter();
|
|
187
|
+
const rateLimitResult = await limiter.checkLimit(session_id);
|
|
188
|
+
if (!rateLimitResult.allowed) {
|
|
189
|
+
return {
|
|
190
|
+
suggestions: [],
|
|
191
|
+
context_score: 0,
|
|
192
|
+
rate_limited: true,
|
|
193
|
+
next_suggestion_at: rateLimitResult.resetAt,
|
|
194
|
+
triggers_fired: [],
|
|
195
|
+
timing: {
|
|
196
|
+
totalMs: Math.round(performance.now() - startTime),
|
|
197
|
+
},
|
|
198
|
+
};
|
|
199
|
+
}
|
|
200
|
+
const analysisStart = performance.now();
|
|
201
|
+
// Analyze codebase (with timeout and caching)
|
|
202
|
+
let codebaseContext = null;
|
|
203
|
+
try {
|
|
204
|
+
const analyzer = new CodebaseAnalyzer();
|
|
205
|
+
codebaseContext = await analyzer.analyze(project_path, {
|
|
206
|
+
maxFiles: 500,
|
|
207
|
+
includeDevDeps: true,
|
|
208
|
+
});
|
|
209
|
+
}
|
|
210
|
+
catch (error) {
|
|
211
|
+
// Log error but continue with trigger detection
|
|
212
|
+
console.warn('CodebaseAnalyzer failed:', error);
|
|
213
|
+
}
|
|
214
|
+
const analysisMs = Math.round(performance.now() - analysisStart);
|
|
215
|
+
// Detect triggers
|
|
216
|
+
const detector = new TriggerDetector();
|
|
217
|
+
const triggers = detector.detectTriggers(codebaseContext, {
|
|
218
|
+
currentFile: current_file,
|
|
219
|
+
recentCommands: recent_commands,
|
|
220
|
+
errorMessage: error_message,
|
|
221
|
+
minConfidence: 0.5,
|
|
222
|
+
});
|
|
223
|
+
// Score context
|
|
224
|
+
const scorer = new ContextScorer();
|
|
225
|
+
const contextScore = scorer.scoreContext(triggers, codebaseContext);
|
|
226
|
+
// Check if we should suggest
|
|
227
|
+
if (!scorer.shouldSuggest(contextScore)) {
|
|
228
|
+
return {
|
|
229
|
+
suggestions: [],
|
|
230
|
+
context_score: contextScore.score,
|
|
231
|
+
rate_limited: false,
|
|
232
|
+
triggers_fired: contextScore.triggers,
|
|
233
|
+
timing: {
|
|
234
|
+
totalMs: Math.round(performance.now() - startTime),
|
|
235
|
+
analysisMs,
|
|
236
|
+
},
|
|
237
|
+
};
|
|
238
|
+
}
|
|
239
|
+
const matchingStart = performance.now();
|
|
240
|
+
// Load skills from database
|
|
241
|
+
const skillDatabase = await loadSkillsFromDatabase(context, 500);
|
|
242
|
+
// Filter skills by detected categories
|
|
243
|
+
const relevantCategories = new Set(contextScore.recommendedCategories);
|
|
244
|
+
const candidateSkills = skillDatabase.filter((skill) => {
|
|
245
|
+
// Skip already installed skills
|
|
246
|
+
if (installed_skills.some((id) => id.toLowerCase() === skill.id.toLowerCase())) {
|
|
247
|
+
return false;
|
|
248
|
+
}
|
|
249
|
+
// Check if skill matches any detected category
|
|
250
|
+
return skill.categories.some((cat) => relevantCategories.has(cat));
|
|
251
|
+
});
|
|
252
|
+
// Use SkillMatcher for semantic ranking
|
|
253
|
+
const matcher = new SkillMatcher({
|
|
254
|
+
useFallback: true,
|
|
255
|
+
minSimilarity: 0.3,
|
|
256
|
+
qualityWeight: 0.3,
|
|
257
|
+
});
|
|
258
|
+
// Build query from triggered categories
|
|
259
|
+
const query = contextScore.recommendedCategories.join(' ');
|
|
260
|
+
const matchResults = await matcher.findSimilarSkills(query, candidateSkills, limit);
|
|
261
|
+
const matchingMs = Math.round(performance.now() - matchingStart);
|
|
262
|
+
// Transform to response format
|
|
263
|
+
const suggestions = matchResults.map((result) => {
|
|
264
|
+
const skill = result.skill;
|
|
265
|
+
return {
|
|
266
|
+
skill_id: skill.id,
|
|
267
|
+
name: skill.name,
|
|
268
|
+
reason: result.matchReason,
|
|
269
|
+
confidence: contextScore.confidence,
|
|
270
|
+
trigger_types: contextScore.triggers,
|
|
271
|
+
trust_tier: skill.trustTier,
|
|
272
|
+
quality_score: skill.qualityScore,
|
|
273
|
+
};
|
|
274
|
+
});
|
|
275
|
+
matcher.close();
|
|
276
|
+
const totalMs = Math.round(performance.now() - startTime);
|
|
277
|
+
return {
|
|
278
|
+
suggestions,
|
|
279
|
+
context_score: contextScore.score,
|
|
280
|
+
rate_limited: false,
|
|
281
|
+
triggers_fired: contextScore.triggers,
|
|
282
|
+
timing: {
|
|
283
|
+
totalMs,
|
|
284
|
+
analysisMs,
|
|
285
|
+
matchingMs,
|
|
286
|
+
},
|
|
287
|
+
};
|
|
288
|
+
}
|
|
289
|
+
/**
|
|
290
|
+
* Format suggestions for terminal display
|
|
291
|
+
*/
|
|
292
|
+
export function formatSuggestions(response) {
|
|
293
|
+
const lines = [];
|
|
294
|
+
lines.push('\n=== Skill Suggestions ===\n');
|
|
295
|
+
if (response.rate_limited) {
|
|
296
|
+
lines.push('Rate limited. Please wait before requesting more suggestions.');
|
|
297
|
+
if (response.next_suggestion_at) {
|
|
298
|
+
lines.push(`Next suggestion available at: ${response.next_suggestion_at}`);
|
|
299
|
+
}
|
|
300
|
+
return lines.join('\n');
|
|
301
|
+
}
|
|
302
|
+
if (response.suggestions.length === 0) {
|
|
303
|
+
lines.push('No relevant suggestions at this time.');
|
|
304
|
+
lines.push('');
|
|
305
|
+
lines.push(`Context score: ${Math.round(response.context_score * 100)}%`);
|
|
306
|
+
lines.push(`Triggers: ${response.triggers_fired.join(', ') || 'none'}`);
|
|
307
|
+
return lines.join('\n');
|
|
308
|
+
}
|
|
309
|
+
lines.push(`Found ${response.suggestions.length} suggestion(s):\n`);
|
|
310
|
+
response.suggestions.forEach((sug, index) => {
|
|
311
|
+
const trustBadge = getTrustBadge(sug.trust_tier);
|
|
312
|
+
lines.push(`${index + 1}. ${sug.name} ${trustBadge}`);
|
|
313
|
+
lines.push(` Confidence: ${Math.round(sug.confidence * 100)}%`);
|
|
314
|
+
lines.push(` ${sug.reason}`);
|
|
315
|
+
lines.push(` Triggers: ${sug.trigger_types.join(', ')}`);
|
|
316
|
+
lines.push(` ID: ${sug.skill_id}`);
|
|
317
|
+
lines.push('');
|
|
318
|
+
});
|
|
319
|
+
lines.push('---');
|
|
320
|
+
lines.push(`Context score: ${Math.round(response.context_score * 100)}%`);
|
|
321
|
+
lines.push(`Triggers fired: ${response.triggers_fired.join(', ')}`);
|
|
322
|
+
lines.push(`Completed in ${response.timing.totalMs}ms`);
|
|
323
|
+
return lines.join('\n');
|
|
324
|
+
}
|
|
325
|
+
/**
|
|
326
|
+
* Get trust badge for display
|
|
327
|
+
*/
|
|
328
|
+
function getTrustBadge(tier) {
|
|
329
|
+
switch (tier) {
|
|
330
|
+
case 'verified':
|
|
331
|
+
return '[VERIFIED]';
|
|
332
|
+
case 'community':
|
|
333
|
+
return '[COMMUNITY]';
|
|
334
|
+
case 'standard':
|
|
335
|
+
return '[STANDARD]';
|
|
336
|
+
case 'unverified':
|
|
337
|
+
return '[UNVERIFIED]';
|
|
338
|
+
default:
|
|
339
|
+
return '[UNKNOWN]';
|
|
340
|
+
}
|
|
341
|
+
}
|
|
342
|
+
//# sourceMappingURL=suggest.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"suggest.js","sourceRoot":"","sources":["../../../src/tools/suggest.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;GAyBG;AAEH,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAA;AACvB,OAAO,EAAE,eAAe,EAAE,aAAa,EAAE,MAAM,kBAAkB,CAAA;AACjE,OAAO,EAAE,gBAAgB,EAAE,MAAM,kBAAkB,CAAA;AACnD,OAAO,EAAE,YAAY,EAAE,MAAM,kBAAkB,CAAA;AAC/C,OAAO,EAAE,WAAW,EAAsB,MAAM,kBAAkB,CAAA;AAIlE;;GAEG;AACH,MAAM,CAAC,MAAM,kBAAkB,GAAG,CAAC,CAAC,MAAM,CAAC;IACzC,+BAA+B;IAC/B,YAAY,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,GAAG,CAAC,CAAC,CAAC;IAC/B,2CAA2C;IAC3C,YAAY,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,EAAE;IACnC,wCAAwC;IACxC,eAAe,EAAE,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,MAAM,EAAE,CAAC,CAAC,GAAG,CAAC,EAAE,CAAC,CAAC,OAAO,CAAC,EAAE,CAAC;IACxD,kCAAkC;IAClC,aAAa,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,EAAE;IACpC,oCAAoC;IACpC,gBAAgB,EAAE,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,MAAM,EAAE,CAAC,CAAC,OAAO,CAAC,EAAE,CAAC;IACjD,gDAAgD;IAChD,KAAK,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,EAAE,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC;IAC3C,mCAAmC;IACnC,UAAU,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,OAAO,CAAC,SAAS,CAAC;CAC1C,CAAC,CAAA;AAiDF;;GAEG;AACH,MAAM,CAAC,MAAM,iBAAiB,GAAG;IAC/B,IAAI,EAAE,eAAe;IACrB,WAAW,EACT,6JAA6J;IAC/J,WAAW,EAAE;QACX,IAAI,EAAE,QAAiB;QACvB,UAAU,EAAE;YACV,YAAY,EAAE;gBACZ,IAAI,EAAE,QAAQ;gBACd,WAAW,EAAE,qCAAqC;aACnD;YACD,YAAY,EAAE;gBACZ,IAAI,EAAE,QAAQ;gBACd,WAAW,EAAE,sDAAsD;aACpE;YACD,eAAe,EAAE;gBACf,IAAI,EAAE,OAAO;gBACb,KAAK,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE;gBACzB,WAAW,EAAE,qEAAqE;aACnF;YACD,aAAa,EAAE;gBACb,IAAI,EAAE,QAAQ;gBACd,WAAW,EAAE,6BAA6B;aAC3C;YACD,gBAAgB,EAAE;gBAChB,IAAI,EAAE,OAAO;gBACb,KAAK,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE;gBACzB,WAAW,EAAE,+CAA+C;aAC7D;YACD,KAAK,EAAE;gBACL,IAAI,EAAE,QAAQ;gBACd,WAAW,EAAE,mDAAmD;gBAChE,OAAO,EAAE,CAAC;gBACV,OAAO,EAAE,EAAE;gBACX,OAAO,EAAE,CAAC;aACX;YACD,UAAU,EAAE;gBACV,IAAI,EAAE,QAAQ;gBACd,WAAW,EAAE,mDAAmD;gBAChE,OAAO,EAAE,SAAS;aACnB;SACF;QACD,QAAQ,EAAE,CAAC,cAAc,CAAC;KAC3B;CACF,CAAA;AAyBD;;GAEG;AACH,SAAS,kBAAkB,CAAC,MAAc;IACxC,QAAQ,MAAM,EAAE,CAAC;QACf,KAAK,UAAU;YACb,OAAO,UAAU,CAAA;QACnB,KAAK,WAAW;YACd,OAAO,WAAW,CAAA;QACpB,KAAK,cAAc;YACjB,OAAO,UAAU,CAAA;QACnB,KAAK,SAAS,CAAC;QACf;YACE,OAAO,YAAY,CAAA;IACvB,CAAC;AACH,CAAC;AAED;;GAEG;AACH,SAAS,yBAAyB,CAAC,KAOlC;IACC,wDAAwD;IACxD,MAAM,cAAc,GAAG;QACrB,KAAK,CAAC,IAAI;QACV,OAAO,KAAK,CAAC,IAAI,EAAE;QACnB,GAAG,KAAK,CAAC,IAAI,OAAO;QACpB,GAAG,KAAK,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,GAAG,EAAE,EAAE,CAAC,GAAG,GAAG,IAAI,KAAK,CAAC,IAAI,EAAE,CAAC;KAC/D,CAAA;IAED,OAAO;QACL,EAAE,EAAE,KAAK,CAAC,EAAE;QACZ,IAAI,EAAE,KAAK,CAAC,IAAI;QAChB,WAAW,EAAE,KAAK,CAAC,WAAW,IAAI,EAAE;QACpC,cAAc;QACd,QAAQ,EAAE,KAAK,CAAC,IAAI;QACpB,YAAY,EAAE,IAAI,CAAC,KAAK,CAAC,CAAC,KAAK,CAAC,YAAY,IAAI,GAAG,CAAC,GAAG,GAAG,CAAC;QAC3D,SAAS,EAAE,kBAAkB,CAAC,KAAK,CAAC,SAAS,CAAC;QAC9C,uCAAuC;QACvC,UAAU,EAAE,KAAK,CAAC,IAAI;KACvB,CAAA;AACH,CAAC;AAED;;;GAGG;AACH,KAAK,UAAU,sBAAsB,CACnC,OAAoB,EACpB,QAAgB,GAAG;IAEnB,MAAM,MAAM,GAAG,OAAO,CAAC,eAAe,CAAC,OAAO,CAAC,KAAK,EAAE,CAAC,CAAC,CAAA;IACxD,OAAO,MAAM,CAAC,KAAK,CAAC,GAAG,CAAC,yBAAyB,CAAC,CAAA;AACpD,CAAC;AAED,oCAAoC;AACpC,IAAI,WAAW,GAAuB,IAAI,CAAA;AAE1C;;GAEG;AACH,SAAS,cAAc;IACrB,IAAI,CAAC,WAAW,EAAE,CAAC;QACjB,+DAA+D;QAC/D,2EAA2E;QAC3E,WAAW,GAAG,IAAI,WAAW,CAAC;YAC5B,SAAS,EAAE,CAAC,EAAE,8BAA8B;YAC5C,UAAU,EAAE,CAAC,GAAG,GAAG,EAAE,sCAAsC;YAC3D,QAAQ,EAAE,MAAM,EAAE,kBAAkB;YACpC,SAAS,EAAE,SAAS;YACpB,QAAQ,EAAE,MAAM,EAAE,yCAAyC;SAC5D,CAAC,CAAA;IACJ,CAAC;IACD,OAAO,WAAW,CAAA;AACpB,CAAC;AAED;;;;;;;;;;;;;;;GAeG;AACH,MAAM,CAAC,KAAK,UAAU,cAAc,CAClC,KAAmB,EACnB,OAAoB;IAEpB,MAAM,SAAS,GAAG,WAAW,CAAC,GAAG,EAAE,CAAA;IAEnC,iBAAiB;IACjB,MAAM,SAAS,GAAG,kBAAkB,CAAC,KAAK,CAAC,KAAK,CAAC,CAAA;IACjD,MAAM,EACJ,YAAY,EACZ,YAAY,EACZ,eAAe,EACf,aAAa,EACb,gBAAgB,EAChB,KAAK,EACL,UAAU,GACX,GAAG,SAAS,CAAA;IAEb,mBAAmB;IACnB,MAAM,OAAO,GAAG,cAAc,EAAE,CAAA;IAChC,MAAM,eAAe,GAAG,MAAM,OAAO,CAAC,UAAU,CAAC,UAAU,CAAC,CAAA;IAE5D,IAAI,CAAC,eAAe,CAAC,OAAO,EAAE,CAAC;QAC7B,OAAO;YACL,WAAW,EAAE,EAAE;YACf,aAAa,EAAE,CAAC;YAChB,YAAY,EAAE,IAAI;YAClB,kBAAkB,EAAE,eAAe,CAAC,OAAO;YAC3C,cAAc,EAAE,EAAE;YAClB,MAAM,EAAE;gBACN,OAAO,EAAE,IAAI,CAAC,KAAK,CAAC,WAAW,CAAC,GAAG,EAAE,GAAG,SAAS,CAAC;aACnD;SACF,CAAA;IACH,CAAC;IAED,MAAM,aAAa,GAAG,WAAW,CAAC,GAAG,EAAE,CAAA;IAEvC,8CAA8C;IAC9C,IAAI,eAAe,GAAG,IAAI,CAAA;IAC1B,IAAI,CAAC;QACH,MAAM,QAAQ,GAAG,IAAI,gBAAgB,EAAE,CAAA;QACvC,eAAe,GAAG,MAAM,QAAQ,CAAC,OAAO,CAAC,YAAY,EAAE;YACrD,QAAQ,EAAE,GAAG;YACb,cAAc,EAAE,IAAI;SACrB,CAAC,CAAA;IACJ,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QACf,gDAAgD;QAChD,OAAO,CAAC,IAAI,CAAC,0BAA0B,EAAE,KAAK,CAAC,CAAA;IACjD,CAAC;IAED,MAAM,UAAU,GAAG,IAAI,CAAC,KAAK,CAAC,WAAW,CAAC,GAAG,EAAE,GAAG,aAAa,CAAC,CAAA;IAEhE,kBAAkB;IAClB,MAAM,QAAQ,GAAG,IAAI,eAAe,EAAE,CAAA;IACtC,MAAM,QAAQ,GAAG,QAAQ,CAAC,cAAc,CAAC,eAAe,EAAE;QACxD,WAAW,EAAE,YAAY;QACzB,cAAc,EAAE,eAAe;QAC/B,YAAY,EAAE,aAAa;QAC3B,aAAa,EAAE,GAAG;KACnB,CAAC,CAAA;IAEF,gBAAgB;IAChB,MAAM,MAAM,GAAG,IAAI,aAAa,EAAE,CAAA;IAClC,MAAM,YAAY,GAAG,MAAM,CAAC,YAAY,CAAC,QAAQ,EAAE,eAAe,CAAC,CAAA;IAEnE,6BAA6B;IAC7B,IAAI,CAAC,MAAM,CAAC,aAAa,CAAC,YAAY,CAAC,EAAE,CAAC;QACxC,OAAO;YACL,WAAW,EAAE,EAAE;YACf,aAAa,EAAE,YAAY,CAAC,KAAK;YACjC,YAAY,EAAE,KAAK;YACnB,cAAc,EAAE,YAAY,CAAC,QAAQ;YACrC,MAAM,EAAE;gBACN,OAAO,EAAE,IAAI,CAAC,KAAK,CAAC,WAAW,CAAC,GAAG,EAAE,GAAG,SAAS,CAAC;gBAClD,UAAU;aACX;SACF,CAAA;IACH,CAAC;IAED,MAAM,aAAa,GAAG,WAAW,CAAC,GAAG,EAAE,CAAA;IAEvC,4BAA4B;IAC5B,MAAM,aAAa,GAAG,MAAM,sBAAsB,CAAC,OAAO,EAAE,GAAG,CAAC,CAAA;IAEhE,uCAAuC;IACvC,MAAM,kBAAkB,GAAG,IAAI,GAAG,CAAC,YAAY,CAAC,qBAAqB,CAAC,CAAA;IACtE,MAAM,eAAe,GAAG,aAAa,CAAC,MAAM,CAAC,CAAC,KAAK,EAAE,EAAE;QACrD,gCAAgC;QAChC,IAAI,gBAAgB,CAAC,IAAI,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,EAAE,CAAC,WAAW,EAAE,KAAK,KAAK,CAAC,EAAE,CAAC,WAAW,EAAE,CAAC,EAAE,CAAC;YAC/E,OAAO,KAAK,CAAA;QACd,CAAC;QAED,+CAA+C;QAC/C,OAAO,KAAK,CAAC,UAAU,CAAC,IAAI,CAAC,CAAC,GAAG,EAAE,EAAE,CAAC,kBAAkB,CAAC,GAAG,CAAC,GAAG,CAAC,CAAC,CAAA;IACpE,CAAC,CAAC,CAAA;IAEF,wCAAwC;IACxC,MAAM,OAAO,GAAG,IAAI,YAAY,CAAC;QAC/B,WAAW,EAAE,IAAI;QACjB,aAAa,EAAE,GAAG;QAClB,aAAa,EAAE,GAAG;KACnB,CAAC,CAAA;IAEF,wCAAwC;IACxC,MAAM,KAAK,GAAG,YAAY,CAAC,qBAAqB,CAAC,IAAI,CAAC,GAAG,CAAC,CAAA;IAC1D,MAAM,YAAY,GAAG,MAAM,OAAO,CAAC,iBAAiB,CAAC,KAAK,EAAE,eAAe,EAAE,KAAK,CAAC,CAAA;IAEnF,MAAM,UAAU,GAAG,IAAI,CAAC,KAAK,CAAC,WAAW,CAAC,GAAG,EAAE,GAAG,aAAa,CAAC,CAAA;IAEhE,+BAA+B;IAC/B,MAAM,WAAW,GAAsB,YAAY,CAAC,GAAG,CAAC,CAAC,MAAM,EAAE,EAAE;QACjE,MAAM,KAAK,GAAG,MAAM,CAAC,KAAkB,CAAA;QACvC,OAAO;YACL,QAAQ,EAAE,KAAK,CAAC,EAAE;YAClB,IAAI,EAAE,KAAK,CAAC,IAAI;YAChB,MAAM,EAAE,MAAM,CAAC,WAAW;YAC1B,UAAU,EAAE,YAAY,CAAC,UAAU;YACnC,aAAa,EAAE,YAAY,CAAC,QAAQ;YACpC,UAAU,EAAE,KAAK,CAAC,SAAS;YAC3B,aAAa,EAAE,KAAK,CAAC,YAAY;SAClC,CAAA;IACH,CAAC,CAAC,CAAA;IAEF,OAAO,CAAC,KAAK,EAAE,CAAA;IAEf,MAAM,OAAO,GAAG,IAAI,CAAC,KAAK,CAAC,WAAW,CAAC,GAAG,EAAE,GAAG,SAAS,CAAC,CAAA;IAEzD,OAAO;QACL,WAAW;QACX,aAAa,EAAE,YAAY,CAAC,KAAK;QACjC,YAAY,EAAE,KAAK;QACnB,cAAc,EAAE,YAAY,CAAC,QAAQ;QACrC,MAAM,EAAE;YACN,OAAO;YACP,UAAU;YACV,UAAU;SACX;KACF,CAAA;AACH,CAAC;AAED;;GAEG;AACH,MAAM,UAAU,iBAAiB,CAAC,QAAyB;IACzD,MAAM,KAAK,GAAa,EAAE,CAAA;IAE1B,KAAK,CAAC,IAAI,CAAC,+BAA+B,CAAC,CAAA;IAE3C,IAAI,QAAQ,CAAC,YAAY,EAAE,CAAC;QAC1B,KAAK,CAAC,IAAI,CAAC,+DAA+D,CAAC,CAAA;QAC3E,IAAI,QAAQ,CAAC,kBAAkB,EAAE,CAAC;YAChC,KAAK,CAAC,IAAI,CAAC,iCAAiC,QAAQ,CAAC,kBAAkB,EAAE,CAAC,CAAA;QAC5E,CAAC;QACD,OAAO,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,CAAA;IACzB,CAAC;IAED,IAAI,QAAQ,CAAC,WAAW,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;QACtC,KAAK,CAAC,IAAI,CAAC,uCAAuC,CAAC,CAAA;QACnD,KAAK,CAAC,IAAI,CAAC,EAAE,CAAC,CAAA;QACd,KAAK,CAAC,IAAI,CAAC,kBAAkB,IAAI,CAAC,KAAK,CAAC,QAAQ,CAAC,aAAa,GAAG,GAAG,CAAC,GAAG,CAAC,CAAA;QACzE,KAAK,CAAC,IAAI,CAAC,aAAa,QAAQ,CAAC,cAAc,CAAC,IAAI,CAAC,IAAI,CAAC,IAAI,MAAM,EAAE,CAAC,CAAA;QACvE,OAAO,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,CAAA;IACzB,CAAC;IAED,KAAK,CAAC,IAAI,CAAC,SAAS,QAAQ,CAAC,WAAW,CAAC,MAAM,mBAAmB,CAAC,CAAA;IAEnE,QAAQ,CAAC,WAAW,CAAC,OAAO,CAAC,CAAC,GAAG,EAAE,KAAK,EAAE,EAAE;QAC1C,MAAM,UAAU,GAAG,aAAa,CAAC,GAAG,CAAC,UAAU,CAAC,CAAA;QAChD,KAAK,CAAC,IAAI,CAAC,GAAG,KAAK,GAAG,CAAC,KAAK,GAAG,CAAC,IAAI,IAAI,UAAU,EAAE,CAAC,CAAA;QACrD,KAAK,CAAC,IAAI,CAAC,kBAAkB,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,UAAU,GAAG,GAAG,CAAC,GAAG,CAAC,CAAA;QACjE,KAAK,CAAC,IAAI,CAAC,MAAM,GAAG,CAAC,MAAM,EAAE,CAAC,CAAA;QAC9B,KAAK,CAAC,IAAI,CAAC,gBAAgB,GAAG,CAAC,aAAa,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,CAAA;QAC1D,KAAK,CAAC,IAAI,CAAC,UAAU,GAAG,CAAC,QAAQ,EAAE,CAAC,CAAA;QACpC,KAAK,CAAC,IAAI,CAAC,EAAE,CAAC,CAAA;IAChB,CAAC,CAAC,CAAA;IAEF,KAAK,CAAC,IAAI,CAAC,KAAK,CAAC,CAAA;IACjB,KAAK,CAAC,IAAI,CAAC,kBAAkB,IAAI,CAAC,KAAK,CAAC,QAAQ,CAAC,aAAa,GAAG,GAAG,CAAC,GAAG,CAAC,CAAA;IACzE,KAAK,CAAC,IAAI,CAAC,mBAAmB,QAAQ,CAAC,cAAc,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,CAAA;IACnE,KAAK,CAAC,IAAI,CAAC,gBAAgB,QAAQ,CAAC,MAAM,CAAC,OAAO,IAAI,CAAC,CAAA;IAEvD,OAAO,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,CAAA;AACzB,CAAC;AAED;;GAEG;AACH,SAAS,aAAa,CAAC,IAAe;IACpC,QAAQ,IAAI,EAAE,CAAC;QACb,KAAK,UAAU;YACb,OAAO,YAAY,CAAA;QACrB,KAAK,WAAW;YACd,OAAO,aAAa,CAAA;QACtB,KAAK,UAAU;YACb,OAAO,YAAY,CAAA;QACrB,KAAK,YAAY;YACf,OAAO,cAAc,CAAA;QACvB;YACE,OAAO,WAAW,CAAA;IACtB,CAAC;AACH,CAAC"}
|
|
@@ -0,0 +1,123 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @fileoverview MCP Uninstall Skill Tool for safely removing installed skills
|
|
3
|
+
* @module @skillsmith/mcp-server/tools/uninstall
|
|
4
|
+
* @see {@link https://github.com/wrsmith108/skillsmith|Skillsmith Repository}
|
|
5
|
+
*
|
|
6
|
+
* Provides skill uninstallation functionality with:
|
|
7
|
+
* - Manifest-based tracking of installed skills
|
|
8
|
+
* - Modification detection (warns if files changed since install)
|
|
9
|
+
* - Force removal option for modified or untracked skills
|
|
10
|
+
* - Clean removal from ~/.claude/skills/ directory
|
|
11
|
+
*
|
|
12
|
+
* @example
|
|
13
|
+
* // Uninstall a skill
|
|
14
|
+
* const result = await uninstallSkill({ skillName: 'commit' });
|
|
15
|
+
* if (result.success) {
|
|
16
|
+
* console.log(result.message);
|
|
17
|
+
* }
|
|
18
|
+
*
|
|
19
|
+
* @example
|
|
20
|
+
* // Force uninstall modified skill
|
|
21
|
+
* const result = await uninstallSkill({
|
|
22
|
+
* skillName: 'my-custom-skill',
|
|
23
|
+
* force: true
|
|
24
|
+
* });
|
|
25
|
+
*/
|
|
26
|
+
import { z } from 'zod';
|
|
27
|
+
import type { ToolContext } from '../context.js';
|
|
28
|
+
export declare const uninstallInputSchema: z.ZodObject<{
|
|
29
|
+
skillName: z.ZodString;
|
|
30
|
+
force: z.ZodDefault<z.ZodBoolean>;
|
|
31
|
+
}, "strip", z.ZodTypeAny, {
|
|
32
|
+
force: boolean;
|
|
33
|
+
skillName: string;
|
|
34
|
+
}, {
|
|
35
|
+
skillName: string;
|
|
36
|
+
force?: boolean | undefined;
|
|
37
|
+
}>;
|
|
38
|
+
export type UninstallInput = z.infer<typeof uninstallInputSchema>;
|
|
39
|
+
export interface UninstallResult {
|
|
40
|
+
success: boolean;
|
|
41
|
+
skillName: string;
|
|
42
|
+
message: string;
|
|
43
|
+
removedPath?: string;
|
|
44
|
+
warning?: string;
|
|
45
|
+
}
|
|
46
|
+
/**
|
|
47
|
+
* Uninstall a skill from the local Claude Code skills directory.
|
|
48
|
+
*
|
|
49
|
+
* This function:
|
|
50
|
+
* 1. Loads the manifest to find the skill
|
|
51
|
+
* 2. Checks for local modifications (warns unless force=true)
|
|
52
|
+
* 3. Removes the skill directory from ~/.claude/skills/
|
|
53
|
+
* 4. Updates the manifest to remove the skill entry
|
|
54
|
+
*
|
|
55
|
+
* If the skill exists on disk but not in manifest, force=true is required.
|
|
56
|
+
*
|
|
57
|
+
* @param input - Uninstall parameters
|
|
58
|
+
* @param input.skillName - Name of the skill to uninstall
|
|
59
|
+
* @param input.force - Force removal even if modified (default: false)
|
|
60
|
+
* @returns Promise resolving to uninstall result with success status
|
|
61
|
+
*
|
|
62
|
+
* @example
|
|
63
|
+
* // Standard uninstall
|
|
64
|
+
* const result = await uninstallSkill({ skillName: 'jest-helper' });
|
|
65
|
+
* if (result.success) {
|
|
66
|
+
* console.log(`Removed from ${result.removedPath}`);
|
|
67
|
+
* }
|
|
68
|
+
*
|
|
69
|
+
* @example
|
|
70
|
+
* // Handle modified skill
|
|
71
|
+
* const result = await uninstallSkill({ skillName: 'custom-skill' });
|
|
72
|
+
* if (!result.success && result.warning) {
|
|
73
|
+
* console.log(result.warning); // 'Local modifications will be lost...'
|
|
74
|
+
* // Ask user confirmation, then:
|
|
75
|
+
* await uninstallSkill({ skillName: 'custom-skill', force: true });
|
|
76
|
+
* }
|
|
77
|
+
*
|
|
78
|
+
* @example
|
|
79
|
+
* // Check if skill is installed first
|
|
80
|
+
* const installed = await listInstalledSkills();
|
|
81
|
+
* if (installed.includes('my-skill')) {
|
|
82
|
+
* await uninstallSkill({ skillName: 'my-skill' });
|
|
83
|
+
* }
|
|
84
|
+
*/
|
|
85
|
+
export declare function uninstallSkill(input: UninstallInput, _context?: ToolContext): Promise<UninstallResult>;
|
|
86
|
+
/**
|
|
87
|
+
* List all skills currently installed via Skillsmith.
|
|
88
|
+
*
|
|
89
|
+
* Reads the manifest file and returns an array of skill names.
|
|
90
|
+
* This only includes skills tracked in the manifest, not skills
|
|
91
|
+
* manually placed in ~/.claude/skills/.
|
|
92
|
+
*
|
|
93
|
+
* @returns Promise resolving to array of installed skill names
|
|
94
|
+
*
|
|
95
|
+
* @example
|
|
96
|
+
* const skills = await listInstalledSkills();
|
|
97
|
+
* console.log(`${skills.length} skills installed:`);
|
|
98
|
+
* skills.forEach(s => console.log(` - ${s}`));
|
|
99
|
+
*/
|
|
100
|
+
export declare function listInstalledSkills(): Promise<string[]>;
|
|
101
|
+
/**
|
|
102
|
+
* MCP tool definition
|
|
103
|
+
*/
|
|
104
|
+
export declare const uninstallTool: {
|
|
105
|
+
name: string;
|
|
106
|
+
description: string;
|
|
107
|
+
inputSchema: {
|
|
108
|
+
type: "object";
|
|
109
|
+
properties: {
|
|
110
|
+
skillName: {
|
|
111
|
+
type: string;
|
|
112
|
+
description: string;
|
|
113
|
+
};
|
|
114
|
+
force: {
|
|
115
|
+
type: string;
|
|
116
|
+
description: string;
|
|
117
|
+
};
|
|
118
|
+
};
|
|
119
|
+
required: string[];
|
|
120
|
+
};
|
|
121
|
+
};
|
|
122
|
+
export default uninstallTool;
|
|
123
|
+
//# sourceMappingURL=uninstall.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"uninstall.d.ts","sourceRoot":"","sources":["../../../src/tools/uninstall.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;GAwBG;AAEH,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAA;AAIvB,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,eAAe,CAAA;AAGhD,eAAO,MAAM,oBAAoB;;;;;;;;;EAG/B,CAAA;AAEF,MAAM,MAAM,cAAc,GAAG,CAAC,CAAC,KAAK,CAAC,OAAO,oBAAoB,CAAC,CAAA;AAGjE,MAAM,WAAW,eAAe;IAC9B,OAAO,EAAE,OAAO,CAAA;IAChB,SAAS,EAAE,MAAM,CAAA;IACjB,OAAO,EAAE,MAAM,CAAA;IACf,WAAW,CAAC,EAAE,MAAM,CAAA;IACpB,OAAO,CAAC,EAAE,MAAM,CAAA;CACjB;AAiFD;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAsCG;AACH,wBAAsB,cAAc,CAClC,KAAK,EAAE,cAAc,EACrB,QAAQ,CAAC,EAAE,WAAW,GACrB,OAAO,CAAC,eAAe,CAAC,CAuF1B;AAED;;;;;;;;;;;;;GAaG;AACH,wBAAsB,mBAAmB,IAAI,OAAO,CAAC,MAAM,EAAE,CAAC,CAG7D;AAED;;GAEG;AACH,eAAO,MAAM,aAAa;;;;;;;;;;;;;;;;;CAiBzB,CAAA;AAED,eAAe,aAAa,CAAA"}
|