@skillsmith/cli 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.
Files changed (110) hide show
  1. package/dist/.tsbuildinfo +1 -0
  2. package/dist/src/commands/author.d.ts +33 -0
  3. package/dist/src/commands/author.d.ts.map +1 -0
  4. package/dist/src/commands/author.js +337 -0
  5. package/dist/src/commands/author.js.map +1 -0
  6. package/dist/src/commands/index.d.ts +9 -0
  7. package/dist/src/commands/index.d.ts.map +1 -0
  8. package/dist/src/commands/index.js +12 -0
  9. package/dist/src/commands/index.js.map +1 -0
  10. package/dist/src/commands/manage.d.ts +37 -0
  11. package/dist/src/commands/manage.d.ts.map +1 -0
  12. package/dist/src/commands/manage.js +308 -0
  13. package/dist/src/commands/manage.js.map +1 -0
  14. package/dist/src/commands/search.d.ts +12 -0
  15. package/dist/src/commands/search.d.ts.map +1 -0
  16. package/dist/src/commands/search.js +316 -0
  17. package/dist/src/commands/search.js.map +1 -0
  18. package/dist/src/config.d.ts +19 -0
  19. package/dist/src/config.d.ts.map +1 -0
  20. package/dist/src/config.js +21 -0
  21. package/dist/src/config.js.map +1 -0
  22. package/dist/src/import.d.ts +29 -0
  23. package/dist/src/import.d.ts.map +1 -0
  24. package/dist/src/import.js +255 -0
  25. package/dist/src/import.js.map +1 -0
  26. package/dist/src/index.d.ts +16 -0
  27. package/dist/src/index.d.ts.map +1 -0
  28. package/dist/src/index.js +65 -0
  29. package/dist/src/index.js.map +1 -0
  30. package/dist/src/templates/index.d.ts +8 -0
  31. package/dist/src/templates/index.d.ts.map +1 -0
  32. package/dist/src/templates/index.js +8 -0
  33. package/dist/src/templates/index.js.map +1 -0
  34. package/dist/src/templates/readme.md.template.d.ts +8 -0
  35. package/dist/src/templates/readme.md.template.d.ts.map +1 -0
  36. package/dist/src/templates/readme.md.template.js +86 -0
  37. package/dist/src/templates/readme.md.template.js.map +1 -0
  38. package/dist/src/templates/skill.md.template.d.ts +8 -0
  39. package/dist/src/templates/skill.md.template.d.ts.map +1 -0
  40. package/dist/src/templates/skill.md.template.js +99 -0
  41. package/dist/src/templates/skill.md.template.js.map +1 -0
  42. package/dist/src/utils/license.d.ts +82 -0
  43. package/dist/src/utils/license.d.ts.map +1 -0
  44. package/dist/src/utils/license.js +282 -0
  45. package/dist/src/utils/license.js.map +1 -0
  46. package/dist/src/utils/license.test.d.ts +7 -0
  47. package/dist/src/utils/license.test.d.ts.map +1 -0
  48. package/dist/src/utils/license.test.js +303 -0
  49. package/dist/src/utils/license.test.js.map +1 -0
  50. package/dist/src/utils/sanitize.d.ts +30 -0
  51. package/dist/src/utils/sanitize.d.ts.map +1 -0
  52. package/dist/src/utils/sanitize.js +45 -0
  53. package/dist/src/utils/sanitize.js.map +1 -0
  54. package/dist/tests/author.test.d.ts +5 -0
  55. package/dist/tests/author.test.d.ts.map +1 -0
  56. package/dist/tests/author.test.js +149 -0
  57. package/dist/tests/author.test.js.map +1 -0
  58. package/dist/tests/e2e/author.e2e.test.d.ts +9 -0
  59. package/dist/tests/e2e/author.e2e.test.d.ts.map +1 -0
  60. package/dist/tests/e2e/author.e2e.test.js +346 -0
  61. package/dist/tests/e2e/author.e2e.test.js.map +1 -0
  62. package/dist/tests/e2e/import.e2e.test.d.ts +10 -0
  63. package/dist/tests/e2e/import.e2e.test.d.ts.map +1 -0
  64. package/dist/tests/e2e/import.e2e.test.js +213 -0
  65. package/dist/tests/e2e/import.e2e.test.js.map +1 -0
  66. package/dist/tests/e2e/manage.e2e.test.d.ts +9 -0
  67. package/dist/tests/e2e/manage.e2e.test.d.ts.map +1 -0
  68. package/dist/tests/e2e/manage.e2e.test.js +277 -0
  69. package/dist/tests/e2e/manage.e2e.test.js.map +1 -0
  70. package/dist/tests/e2e/search.e2e.test.d.ts +10 -0
  71. package/dist/tests/e2e/search.e2e.test.d.ts.map +1 -0
  72. package/dist/tests/e2e/search.e2e.test.js +267 -0
  73. package/dist/tests/e2e/search.e2e.test.js.map +1 -0
  74. package/dist/tests/e2e/test-config.d.ts +39 -0
  75. package/dist/tests/e2e/test-config.d.ts.map +1 -0
  76. package/dist/tests/e2e/test-config.js +44 -0
  77. package/dist/tests/e2e/test-config.js.map +1 -0
  78. package/dist/tests/e2e/utils/baseline-collector.d.ts +107 -0
  79. package/dist/tests/e2e/utils/baseline-collector.d.ts.map +1 -0
  80. package/dist/tests/e2e/utils/baseline-collector.js +211 -0
  81. package/dist/tests/e2e/utils/baseline-collector.js.map +1 -0
  82. package/dist/tests/e2e/utils/hardcoded-detector.d.ts +46 -0
  83. package/dist/tests/e2e/utils/hardcoded-detector.d.ts.map +1 -0
  84. package/dist/tests/e2e/utils/hardcoded-detector.js +197 -0
  85. package/dist/tests/e2e/utils/hardcoded-detector.js.map +1 -0
  86. package/dist/tests/e2e/utils/index.d.ts +8 -0
  87. package/dist/tests/e2e/utils/index.d.ts.map +1 -0
  88. package/dist/tests/e2e/utils/index.js +8 -0
  89. package/dist/tests/e2e/utils/index.js.map +1 -0
  90. package/dist/tests/e2e/utils/linear-reporter.d.ts +60 -0
  91. package/dist/tests/e2e/utils/linear-reporter.d.ts.map +1 -0
  92. package/dist/tests/e2e/utils/linear-reporter.js +223 -0
  93. package/dist/tests/e2e/utils/linear-reporter.js.map +1 -0
  94. package/dist/tests/import.test.d.ts +5 -0
  95. package/dist/tests/import.test.d.ts.map +1 -0
  96. package/dist/tests/import.test.js +11 -0
  97. package/dist/tests/import.test.js.map +1 -0
  98. package/dist/tests/manage.test.d.ts +5 -0
  99. package/dist/tests/manage.test.d.ts.map +1 -0
  100. package/dist/tests/manage.test.js +135 -0
  101. package/dist/tests/manage.test.js.map +1 -0
  102. package/dist/tests/search.test.d.ts +5 -0
  103. package/dist/tests/search.test.d.ts.map +1 -0
  104. package/dist/tests/search.test.js +91 -0
  105. package/dist/tests/search.test.js.map +1 -0
  106. package/dist/vitest.config.d.ts +3 -0
  107. package/dist/vitest.config.d.ts.map +1 -0
  108. package/dist/vitest.config.js +9 -0
  109. package/dist/vitest.config.js.map +1 -0
  110. package/package.json +62 -0
@@ -0,0 +1,44 @@
1
+ /**
2
+ * E2E Test Configuration
3
+ *
4
+ * Centralizes configurable values for E2E tests to avoid hardcoded URLs
5
+ * and make tests adaptable to different environments.
6
+ */
7
+ /**
8
+ * Base URL for test repository references.
9
+ * Used to construct mock skill repository URLs in seed data.
10
+ *
11
+ * Can be overridden via TEST_REPO_URL_BASE environment variable.
12
+ *
13
+ * @default 'https://github.com/skillsmith-community'
14
+ */
15
+ export const TEST_REPO_URL_BASE = process.env['TEST_REPO_URL_BASE'] || 'https://github.com/skillsmith-community';
16
+ /**
17
+ * Anthropic official skills repository base URL.
18
+ * Used for verified/official skill references.
19
+ *
20
+ * Can be overridden via TEST_ANTHROPIC_REPO_URL environment variable.
21
+ *
22
+ * @default 'https://github.com/anthropics/claude-code/tree/main/skills'
23
+ */
24
+ export const TEST_ANTHROPIC_REPO_URL = process.env['TEST_ANTHROPIC_REPO_URL'] ||
25
+ 'https://github.com/anthropics/claude-code/tree/main/skills';
26
+ /**
27
+ * Build a skill repository URL using the configured base.
28
+ *
29
+ * @param skillName - Name of the skill (e.g., 'jest-helper')
30
+ * @returns Full repository URL
31
+ */
32
+ export function buildRepoUrl(skillName) {
33
+ return `${TEST_REPO_URL_BASE}/${skillName}`;
34
+ }
35
+ /**
36
+ * Build an Anthropic official skill repository URL.
37
+ *
38
+ * @param skillName - Name of the skill (e.g., 'commit')
39
+ * @returns Full repository URL
40
+ */
41
+ export function buildAnthropicRepoUrl(skillName) {
42
+ return `${TEST_ANTHROPIC_REPO_URL}/${skillName}`;
43
+ }
44
+ //# sourceMappingURL=test-config.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"test-config.js","sourceRoot":"","sources":["../../../tests/e2e/test-config.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH;;;;;;;GAOG;AACH,MAAM,CAAC,MAAM,kBAAkB,GAC7B,OAAO,CAAC,GAAG,CAAC,oBAAoB,CAAC,IAAI,yCAAyC,CAAA;AAEhF;;;;;;;GAOG;AACH,MAAM,CAAC,MAAM,uBAAuB,GAClC,OAAO,CAAC,GAAG,CAAC,yBAAyB,CAAC;IACtC,4DAA4D,CAAA;AAE9D;;;;;GAKG;AACH,MAAM,UAAU,YAAY,CAAC,SAAiB;IAC5C,OAAO,GAAG,kBAAkB,IAAI,SAAS,EAAE,CAAA;AAC7C,CAAC;AAED;;;;;GAKG;AACH,MAAM,UAAU,qBAAqB,CAAC,SAAiB;IACrD,OAAO,GAAG,uBAAuB,IAAI,SAAS,EAAE,CAAA;AAClD,CAAC"}
@@ -0,0 +1,107 @@
1
+ /**
2
+ * Performance Baseline Collector
3
+ *
4
+ * Captures timing and resource metrics during E2E tests
5
+ * to establish baselines for future performance tracking.
6
+ *
7
+ * @see docs/testing/e2e-testing-plan.md
8
+ */
9
+ export interface TimingMetric {
10
+ name: string;
11
+ command: string;
12
+ durationMs: number;
13
+ timestamp: string;
14
+ }
15
+ export interface MemoryMetric {
16
+ name: string;
17
+ command: string;
18
+ heapUsedMB: number;
19
+ heapTotalMB: number;
20
+ externalMB: number;
21
+ timestamp: string;
22
+ }
23
+ export interface PercentileStats {
24
+ min: number;
25
+ max: number;
26
+ median: number;
27
+ mean: number;
28
+ p95: number;
29
+ p99: number;
30
+ count: number;
31
+ }
32
+ export interface BaselineReport {
33
+ timestamp: string;
34
+ environment: {
35
+ type: string;
36
+ nodeVersion: string;
37
+ platform: string;
38
+ arch: string;
39
+ };
40
+ baselines: {
41
+ [category: string]: {
42
+ [metric: string]: PercentileStats | number;
43
+ };
44
+ };
45
+ rawMetrics: {
46
+ timing: TimingMetric[];
47
+ memory: MemoryMetric[];
48
+ };
49
+ }
50
+ /**
51
+ * Record timing for a command execution
52
+ */
53
+ export declare function recordTiming(name: string, command: string, durationMs: number): void;
54
+ /**
55
+ * Record memory usage for a command execution
56
+ */
57
+ export declare function recordMemory(name: string, command: string): void;
58
+ /**
59
+ * Measure async function execution time
60
+ */
61
+ export declare function measureAsync<T>(name: string, command: string, fn: () => Promise<T>): Promise<{
62
+ result: T;
63
+ durationMs: number;
64
+ }>;
65
+ /**
66
+ * Measure sync function execution time
67
+ */
68
+ export declare function measureSync<T>(name: string, command: string, fn: () => T): {
69
+ result: T;
70
+ durationMs: number;
71
+ };
72
+ /**
73
+ * Generate baseline report from collected metrics
74
+ */
75
+ export declare function generateBaselineReport(): BaselineReport;
76
+ /**
77
+ * Export baseline report as JSON
78
+ */
79
+ export declare function exportBaselineJSON(): string;
80
+ /**
81
+ * Export baseline report as Markdown
82
+ */
83
+ export declare function exportBaselineMarkdown(): string;
84
+ /**
85
+ * Clear all collected metrics (for test isolation)
86
+ */
87
+ export declare function clearMetrics(): void;
88
+ /**
89
+ * Get current metrics count
90
+ */
91
+ export declare function getMetricsCount(): {
92
+ timing: number;
93
+ memory: number;
94
+ };
95
+ declare const _default: {
96
+ recordTiming: typeof recordTiming;
97
+ recordMemory: typeof recordMemory;
98
+ measureAsync: typeof measureAsync;
99
+ measureSync: typeof measureSync;
100
+ generateBaselineReport: typeof generateBaselineReport;
101
+ exportBaselineJSON: typeof exportBaselineJSON;
102
+ exportBaselineMarkdown: typeof exportBaselineMarkdown;
103
+ clearMetrics: typeof clearMetrics;
104
+ getMetricsCount: typeof getMetricsCount;
105
+ };
106
+ export default _default;
107
+ //# sourceMappingURL=baseline-collector.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"baseline-collector.d.ts","sourceRoot":"","sources":["../../../../tests/e2e/utils/baseline-collector.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAEH,MAAM,WAAW,YAAY;IAC3B,IAAI,EAAE,MAAM,CAAA;IACZ,OAAO,EAAE,MAAM,CAAA;IACf,UAAU,EAAE,MAAM,CAAA;IAClB,SAAS,EAAE,MAAM,CAAA;CAClB;AAED,MAAM,WAAW,YAAY;IAC3B,IAAI,EAAE,MAAM,CAAA;IACZ,OAAO,EAAE,MAAM,CAAA;IACf,UAAU,EAAE,MAAM,CAAA;IAClB,WAAW,EAAE,MAAM,CAAA;IACnB,UAAU,EAAE,MAAM,CAAA;IAClB,SAAS,EAAE,MAAM,CAAA;CAClB;AAED,MAAM,WAAW,eAAe;IAC9B,GAAG,EAAE,MAAM,CAAA;IACX,GAAG,EAAE,MAAM,CAAA;IACX,MAAM,EAAE,MAAM,CAAA;IACd,IAAI,EAAE,MAAM,CAAA;IACZ,GAAG,EAAE,MAAM,CAAA;IACX,GAAG,EAAE,MAAM,CAAA;IACX,KAAK,EAAE,MAAM,CAAA;CACd;AAED,MAAM,WAAW,cAAc;IAC7B,SAAS,EAAE,MAAM,CAAA;IACjB,WAAW,EAAE;QACX,IAAI,EAAE,MAAM,CAAA;QACZ,WAAW,EAAE,MAAM,CAAA;QACnB,QAAQ,EAAE,MAAM,CAAA;QAChB,IAAI,EAAE,MAAM,CAAA;KACb,CAAA;IACD,SAAS,EAAE;QACT,CAAC,QAAQ,EAAE,MAAM,GAAG;YAClB,CAAC,MAAM,EAAE,MAAM,GAAG,eAAe,GAAG,MAAM,CAAA;SAC3C,CAAA;KACF,CAAA;IACD,UAAU,EAAE;QACV,MAAM,EAAE,YAAY,EAAE,CAAA;QACtB,MAAM,EAAE,YAAY,EAAE,CAAA;KACvB,CAAA;CACF;AAMD;;GAEG;AACH,wBAAgB,YAAY,CAAC,IAAI,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,EAAE,UAAU,EAAE,MAAM,GAAG,IAAI,CAOpF;AAED;;GAEG;AACH,wBAAgB,YAAY,CAAC,IAAI,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,GAAG,IAAI,CAUhE;AAED;;GAEG;AACH,wBAAsB,YAAY,CAAC,CAAC,EAClC,IAAI,EAAE,MAAM,EACZ,OAAO,EAAE,MAAM,EACf,EAAE,EAAE,MAAM,OAAO,CAAC,CAAC,CAAC,GACnB,OAAO,CAAC;IAAE,MAAM,EAAE,CAAC,CAAC;IAAC,UAAU,EAAE,MAAM,CAAA;CAAE,CAAC,CAS5C;AAED;;GAEG;AACH,wBAAgB,WAAW,CAAC,CAAC,EAC3B,IAAI,EAAE,MAAM,EACZ,OAAO,EAAE,MAAM,EACf,EAAE,EAAE,MAAM,CAAC,GACV;IAAE,MAAM,EAAE,CAAC,CAAC;IAAC,UAAU,EAAE,MAAM,CAAA;CAAE,CASnC;AAiDD;;GAEG;AACH,wBAAgB,sBAAsB,IAAI,cAAc,CAmCvD;AAED;;GAEG;AACH,wBAAgB,kBAAkB,IAAI,MAAM,CAE3C;AAED;;GAEG;AACH,wBAAgB,sBAAsB,IAAI,MAAM,CA+C/C;AAED;;GAEG;AACH,wBAAgB,YAAY,IAAI,IAAI,CAGnC;AAED;;GAEG;AACH,wBAAgB,eAAe,IAAI;IAAE,MAAM,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,MAAM,CAAA;CAAE,CAKpE;;;;;;;;;;;;AAED,wBAUC"}
@@ -0,0 +1,211 @@
1
+ /**
2
+ * Performance Baseline Collector
3
+ *
4
+ * Captures timing and resource metrics during E2E tests
5
+ * to establish baselines for future performance tracking.
6
+ *
7
+ * @see docs/testing/e2e-testing-plan.md
8
+ */
9
+ // Collected metrics during test run
10
+ const timingMetrics = [];
11
+ const memoryMetrics = [];
12
+ /**
13
+ * Record timing for a command execution
14
+ */
15
+ export function recordTiming(name, command, durationMs) {
16
+ timingMetrics.push({
17
+ name,
18
+ command,
19
+ durationMs,
20
+ timestamp: new Date().toISOString(),
21
+ });
22
+ }
23
+ /**
24
+ * Record memory usage for a command execution
25
+ */
26
+ export function recordMemory(name, command) {
27
+ const usage = process.memoryUsage();
28
+ memoryMetrics.push({
29
+ name,
30
+ command,
31
+ heapUsedMB: Math.round((usage.heapUsed / 1024 / 1024) * 100) / 100,
32
+ heapTotalMB: Math.round((usage.heapTotal / 1024 / 1024) * 100) / 100,
33
+ externalMB: Math.round((usage.external / 1024 / 1024) * 100) / 100,
34
+ timestamp: new Date().toISOString(),
35
+ });
36
+ }
37
+ /**
38
+ * Measure async function execution time
39
+ */
40
+ export async function measureAsync(name, command, fn) {
41
+ const start = performance.now();
42
+ const result = await fn();
43
+ const durationMs = performance.now() - start;
44
+ recordTiming(name, command, durationMs);
45
+ recordMemory(name, command);
46
+ return { result, durationMs };
47
+ }
48
+ /**
49
+ * Measure sync function execution time
50
+ */
51
+ export function measureSync(name, command, fn) {
52
+ const start = performance.now();
53
+ const result = fn();
54
+ const durationMs = performance.now() - start;
55
+ recordTiming(name, command, durationMs);
56
+ recordMemory(name, command);
57
+ return { result, durationMs };
58
+ }
59
+ /**
60
+ * Calculate percentile statistics for an array of numbers
61
+ */
62
+ function calculateStats(values) {
63
+ if (values.length === 0) {
64
+ return { min: 0, max: 0, median: 0, mean: 0, p95: 0, p99: 0, count: 0 };
65
+ }
66
+ const sorted = [...values].sort((a, b) => a - b);
67
+ const sum = sorted.reduce((a, b) => a + b, 0);
68
+ const percentile = (p) => {
69
+ const index = Math.ceil((p / 100) * sorted.length) - 1;
70
+ return sorted[Math.max(0, index)] ?? 0;
71
+ };
72
+ return {
73
+ min: sorted[0] ?? 0,
74
+ max: sorted[sorted.length - 1] ?? 0,
75
+ median: percentile(50),
76
+ mean: Math.round((sum / sorted.length) * 100) / 100,
77
+ p95: percentile(95),
78
+ p99: percentile(99),
79
+ count: sorted.length,
80
+ };
81
+ }
82
+ /**
83
+ * Group metrics by command category
84
+ */
85
+ function groupByCategory(metrics) {
86
+ const groups = {};
87
+ for (const metric of metrics) {
88
+ // Extract category from command (e.g., "skillsmith search" -> "search")
89
+ const parts = metric.command.split(' ');
90
+ const category = (parts.length > 1 ? parts[1] : parts[0]) ?? 'unknown';
91
+ if (!groups[category]) {
92
+ groups[category] = [];
93
+ }
94
+ groups[category].push(metric);
95
+ }
96
+ return groups;
97
+ }
98
+ /**
99
+ * Generate baseline report from collected metrics
100
+ */
101
+ export function generateBaselineReport() {
102
+ const timingGroups = groupByCategory(timingMetrics);
103
+ const baselines = {};
104
+ // Calculate timing baselines per category
105
+ for (const [category, metrics] of Object.entries(timingGroups)) {
106
+ const durations = metrics.map((m) => m.durationMs);
107
+ baselines[category] = {
108
+ timing: calculateStats(durations),
109
+ };
110
+ }
111
+ // Calculate overall memory baseline
112
+ if (memoryMetrics.length > 0) {
113
+ const heapUsed = memoryMetrics.map((m) => m.heapUsedMB);
114
+ baselines['memory'] = {
115
+ heapUsedMB: calculateStats(heapUsed),
116
+ peakHeapMB: Math.max(...heapUsed),
117
+ };
118
+ }
119
+ return {
120
+ timestamp: new Date().toISOString(),
121
+ environment: {
122
+ type: process.env['SKILLSMITH_E2E'] ? 'codespace' : 'local',
123
+ nodeVersion: process.version,
124
+ platform: process.platform,
125
+ arch: process.arch,
126
+ },
127
+ baselines,
128
+ rawMetrics: {
129
+ timing: timingMetrics,
130
+ memory: memoryMetrics,
131
+ },
132
+ };
133
+ }
134
+ /**
135
+ * Export baseline report as JSON
136
+ */
137
+ export function exportBaselineJSON() {
138
+ return JSON.stringify(generateBaselineReport(), null, 2);
139
+ }
140
+ /**
141
+ * Export baseline report as Markdown
142
+ */
143
+ export function exportBaselineMarkdown() {
144
+ const report = generateBaselineReport();
145
+ const lines = [];
146
+ lines.push('# Performance Baseline Report');
147
+ lines.push('');
148
+ lines.push(`**Generated**: ${report.timestamp}`);
149
+ lines.push('');
150
+ lines.push('## Environment');
151
+ lines.push('');
152
+ lines.push(`- **Type**: ${report.environment.type}`);
153
+ lines.push(`- **Node Version**: ${report.environment.nodeVersion}`);
154
+ lines.push(`- **Platform**: ${report.environment.platform}-${report.environment.arch}`);
155
+ lines.push('');
156
+ lines.push('## Timing Baselines');
157
+ lines.push('');
158
+ lines.push('| Command | Median (ms) | P95 (ms) | P99 (ms) | Count |');
159
+ lines.push('|---------|-------------|----------|----------|-------|');
160
+ for (const [category, metrics] of Object.entries(report.baselines)) {
161
+ if (category === 'memory')
162
+ continue;
163
+ const timing = metrics.timing;
164
+ lines.push(`| ${category} | ${timing.median.toFixed(1)} | ${timing.p95.toFixed(1)} | ${timing.p99.toFixed(1)} | ${timing.count} |`);
165
+ }
166
+ lines.push('');
167
+ if (report.baselines['memory']) {
168
+ lines.push('## Memory Baselines');
169
+ lines.push('');
170
+ const mem = report.baselines['memory'];
171
+ const heapStats = mem.heapUsedMB;
172
+ lines.push(`- **Median Heap Used**: ${heapStats.median.toFixed(1)} MB`);
173
+ lines.push(`- **P95 Heap Used**: ${heapStats.p95.toFixed(1)} MB`);
174
+ lines.push(`- **Peak Heap**: ${mem.peakHeapMB} MB`);
175
+ lines.push('');
176
+ }
177
+ lines.push('## Raw Metrics');
178
+ lines.push('');
179
+ lines.push(`Total timing samples: ${report.rawMetrics.timing.length}`);
180
+ lines.push(`Total memory samples: ${report.rawMetrics.memory.length}`);
181
+ lines.push('');
182
+ return lines.join('\n');
183
+ }
184
+ /**
185
+ * Clear all collected metrics (for test isolation)
186
+ */
187
+ export function clearMetrics() {
188
+ timingMetrics.length = 0;
189
+ memoryMetrics.length = 0;
190
+ }
191
+ /**
192
+ * Get current metrics count
193
+ */
194
+ export function getMetricsCount() {
195
+ return {
196
+ timing: timingMetrics.length,
197
+ memory: memoryMetrics.length,
198
+ };
199
+ }
200
+ export default {
201
+ recordTiming,
202
+ recordMemory,
203
+ measureAsync,
204
+ measureSync,
205
+ generateBaselineReport,
206
+ exportBaselineJSON,
207
+ exportBaselineMarkdown,
208
+ clearMetrics,
209
+ getMetricsCount,
210
+ };
211
+ //# sourceMappingURL=baseline-collector.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"baseline-collector.js","sourceRoot":"","sources":["../../../../tests/e2e/utils/baseline-collector.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,46 @@
1
+ /**
2
+ * Hardcoded Value Detection Utility
3
+ *
4
+ * Scans command output and file contents for hardcoded values that
5
+ * would fail in clean environments (Codespaces).
6
+ *
7
+ * @see docs/testing/e2e-testing-plan.md
8
+ */
9
+ export interface HardcodedIssue {
10
+ type: 'path' | 'url' | 'credential' | 'env_assumption';
11
+ pattern: string;
12
+ value: string;
13
+ location: {
14
+ source: 'stdout' | 'stderr' | 'file' | 'database';
15
+ context?: string | undefined;
16
+ line?: number | undefined;
17
+ };
18
+ command: string;
19
+ timestamp: string;
20
+ severity: 'error' | 'warning';
21
+ }
22
+ export interface DetectionResult {
23
+ passed: boolean;
24
+ issues: HardcodedIssue[];
25
+ scannedBytes: number;
26
+ scanDurationMs: number;
27
+ }
28
+ /**
29
+ * Scan text content for hardcoded values
30
+ */
31
+ export declare function scanForHardcoded(content: string, command: string, source: 'stdout' | 'stderr' | 'file' | 'database', context?: string): HardcodedIssue[];
32
+ /**
33
+ * Scan command execution result for hardcoded values
34
+ */
35
+ export declare function scanCommandOutput(stdout: string, stderr: string, command: string): DetectionResult;
36
+ /**
37
+ * Create a summary report of detected issues
38
+ */
39
+ export declare function createDetectionReport(results: DetectionResult[]): string;
40
+ declare const _default: {
41
+ scanForHardcoded: typeof scanForHardcoded;
42
+ scanCommandOutput: typeof scanCommandOutput;
43
+ createDetectionReport: typeof createDetectionReport;
44
+ };
45
+ export default _default;
46
+ //# sourceMappingURL=hardcoded-detector.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"hardcoded-detector.d.ts","sourceRoot":"","sources":["../../../../tests/e2e/utils/hardcoded-detector.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAEH,MAAM,WAAW,cAAc;IAC7B,IAAI,EAAE,MAAM,GAAG,KAAK,GAAG,YAAY,GAAG,gBAAgB,CAAA;IACtD,OAAO,EAAE,MAAM,CAAA;IACf,KAAK,EAAE,MAAM,CAAA;IACb,QAAQ,EAAE;QACR,MAAM,EAAE,QAAQ,GAAG,QAAQ,GAAG,MAAM,GAAG,UAAU,CAAA;QACjD,OAAO,CAAC,EAAE,MAAM,GAAG,SAAS,CAAA;QAC5B,IAAI,CAAC,EAAE,MAAM,GAAG,SAAS,CAAA;KAC1B,CAAA;IACD,OAAO,EAAE,MAAM,CAAA;IACf,SAAS,EAAE,MAAM,CAAA;IACjB,QAAQ,EAAE,OAAO,GAAG,SAAS,CAAA;CAC9B;AAED,MAAM,WAAW,eAAe;IAC9B,MAAM,EAAE,OAAO,CAAA;IACf,MAAM,EAAE,cAAc,EAAE,CAAA;IACxB,YAAY,EAAE,MAAM,CAAA;IACpB,cAAc,EAAE,MAAM,CAAA;CACvB;AAuDD;;GAEG;AACH,wBAAgB,gBAAgB,CAC9B,OAAO,EAAE,MAAM,EACf,OAAO,EAAE,MAAM,EACf,MAAM,EAAE,QAAQ,GAAG,QAAQ,GAAG,MAAM,GAAG,UAAU,EACjD,OAAO,CAAC,EAAE,MAAM,GACf,cAAc,EAAE,CA0ElB;AAUD;;GAEG;AACH,wBAAgB,iBAAiB,CAC/B,MAAM,EAAE,MAAM,EACd,MAAM,EAAE,MAAM,EACd,OAAO,EAAE,MAAM,GACd,eAAe,CAajB;AAED;;GAEG;AACH,wBAAgB,qBAAqB,CAAC,OAAO,EAAE,eAAe,EAAE,GAAG,MAAM,CA4CxE;;;;;;AAED,wBAIC"}
@@ -0,0 +1,197 @@
1
+ /**
2
+ * Hardcoded Value Detection Utility
3
+ *
4
+ * Scans command output and file contents for hardcoded values that
5
+ * would fail in clean environments (Codespaces).
6
+ *
7
+ * @see docs/testing/e2e-testing-plan.md
8
+ */
9
+ /**
10
+ * Patterns for detecting hardcoded values
11
+ */
12
+ const DETECTION_PATTERNS = {
13
+ // User-specific paths (high severity)
14
+ userPaths: [
15
+ { pattern: /\/Users\/[a-zA-Z0-9_-]+\//g, name: 'macOS user path' },
16
+ { pattern: /\/home\/[a-zA-Z0-9_-]+\//g, name: 'Linux user path' },
17
+ { pattern: /C:\\Users\\[a-zA-Z0-9_-]+\\/g, name: 'Windows user path' },
18
+ { pattern: /~\/(?!\.claude)/g, name: 'Home directory shorthand' },
19
+ ],
20
+ // Localhost/dev URLs (medium severity)
21
+ devUrls: [
22
+ { pattern: /localhost:\d+/g, name: 'localhost with port' },
23
+ { pattern: /127\.0\.0\.1(:\d+)?/g, name: 'IPv4 loopback' },
24
+ { pattern: /0\.0\.0\.0(:\d+)?/g, name: 'All interfaces bind' },
25
+ { pattern: /\[::1\](:\d+)?/g, name: 'IPv6 loopback' },
26
+ ],
27
+ // Hardcoded credentials (critical severity)
28
+ credentials: [
29
+ { pattern: /sk-[a-zA-Z0-9]{32,}/g, name: 'OpenAI API key' },
30
+ { pattern: /ghp_[a-zA-Z0-9]{36}/g, name: 'GitHub personal token' },
31
+ { pattern: /gho_[a-zA-Z0-9]{36}/g, name: 'GitHub OAuth token' },
32
+ { pattern: /lin_api_[a-zA-Z0-9]+/g, name: 'Linear API key' },
33
+ { pattern: /sk-ant-[a-zA-Z0-9-]+/g, name: 'Anthropic API key' },
34
+ { pattern: /xoxb-[a-zA-Z0-9-]+/g, name: 'Slack bot token' },
35
+ ],
36
+ // Environment assumptions (medium severity)
37
+ envAssumptions: [
38
+ { pattern: /\.skillsmith\/skills\.db(?!['"])/g, name: 'Hardcoded DB path' },
39
+ { pattern: /\/tmp\/skillsmith(?!-e2e)/g, name: 'Hardcoded temp path' },
40
+ ],
41
+ };
42
+ // Allowlist for known safe patterns (e.g., in security tests)
43
+ const ALLOWLIST_CONTEXTS = [
44
+ 'security.test',
45
+ 'validation.test',
46
+ '.security.test',
47
+ 'RawUrlSourceAdapter',
48
+ ];
49
+ /**
50
+ * Check if a match should be allowed based on context
51
+ */
52
+ function isAllowlisted(context) {
53
+ if (!context)
54
+ return false;
55
+ return ALLOWLIST_CONTEXTS.some((allowed) => context.includes(allowed));
56
+ }
57
+ /**
58
+ * Scan text content for hardcoded values
59
+ */
60
+ export function scanForHardcoded(content, command, source, context) {
61
+ const issues = [];
62
+ const timestamp = new Date().toISOString();
63
+ // Skip allowlisted contexts
64
+ if (isAllowlisted(context)) {
65
+ return issues;
66
+ }
67
+ // Scan for user paths
68
+ for (const { pattern, name } of DETECTION_PATTERNS.userPaths) {
69
+ const matches = content.matchAll(pattern);
70
+ for (const match of matches) {
71
+ issues.push({
72
+ type: 'path',
73
+ pattern: name,
74
+ value: match[0],
75
+ location: { source, context },
76
+ command,
77
+ timestamp,
78
+ severity: 'error',
79
+ });
80
+ }
81
+ }
82
+ // Scan for dev URLs
83
+ for (const { pattern, name } of DETECTION_PATTERNS.devUrls) {
84
+ const matches = content.matchAll(pattern);
85
+ for (const match of matches) {
86
+ issues.push({
87
+ type: 'url',
88
+ pattern: name,
89
+ value: match[0],
90
+ location: { source, context },
91
+ command,
92
+ timestamp,
93
+ severity: 'warning',
94
+ });
95
+ }
96
+ }
97
+ // Scan for credentials
98
+ for (const { pattern, name } of DETECTION_PATTERNS.credentials) {
99
+ const matches = content.matchAll(pattern);
100
+ for (const match of matches) {
101
+ issues.push({
102
+ type: 'credential',
103
+ pattern: name,
104
+ value: maskCredential(match[0]),
105
+ location: { source, context },
106
+ command,
107
+ timestamp,
108
+ severity: 'error',
109
+ });
110
+ }
111
+ }
112
+ // Scan for environment assumptions
113
+ for (const { pattern, name } of DETECTION_PATTERNS.envAssumptions) {
114
+ const matches = content.matchAll(pattern);
115
+ for (const match of matches) {
116
+ issues.push({
117
+ type: 'env_assumption',
118
+ pattern: name,
119
+ value: match[0],
120
+ location: { source, context },
121
+ command,
122
+ timestamp,
123
+ severity: 'warning',
124
+ });
125
+ }
126
+ }
127
+ return issues;
128
+ }
129
+ /**
130
+ * Mask sensitive credential values for safe logging
131
+ */
132
+ function maskCredential(value) {
133
+ if (value.length <= 8)
134
+ return '***';
135
+ return value.substring(0, 4) + '***' + value.substring(value.length - 4);
136
+ }
137
+ /**
138
+ * Scan command execution result for hardcoded values
139
+ */
140
+ export function scanCommandOutput(stdout, stderr, command) {
141
+ const startTime = Date.now();
142
+ const issues = [];
143
+ issues.push(...scanForHardcoded(stdout, command, 'stdout'));
144
+ issues.push(...scanForHardcoded(stderr, command, 'stderr'));
145
+ return {
146
+ passed: issues.filter((i) => i.severity === 'error').length === 0,
147
+ issues,
148
+ scannedBytes: stdout.length + stderr.length,
149
+ scanDurationMs: Date.now() - startTime,
150
+ };
151
+ }
152
+ /**
153
+ * Create a summary report of detected issues
154
+ */
155
+ export function createDetectionReport(results) {
156
+ const allIssues = results.flatMap((r) => r.issues);
157
+ const errors = allIssues.filter((i) => i.severity === 'error');
158
+ const warnings = allIssues.filter((i) => i.severity === 'warning');
159
+ const lines = [
160
+ '# Hardcoded Value Detection Report',
161
+ '',
162
+ `**Scan Time**: ${new Date().toISOString()}`,
163
+ `**Total Scanned**: ${results.reduce((sum, r) => sum + r.scannedBytes, 0)} bytes`,
164
+ '',
165
+ '## Summary',
166
+ '',
167
+ `- **Errors**: ${errors.length}`,
168
+ `- **Warnings**: ${warnings.length}`,
169
+ `- **Status**: ${errors.length === 0 ? 'PASSED' : 'FAILED'}`,
170
+ '',
171
+ ];
172
+ if (errors.length > 0) {
173
+ lines.push('## Errors (Must Fix)', '');
174
+ lines.push('| Type | Pattern | Value | Command | Source |');
175
+ lines.push('|------|---------|-------|---------|--------|');
176
+ for (const issue of errors) {
177
+ lines.push(`| ${issue.type} | ${issue.pattern} | \`${issue.value}\` | ${issue.command} | ${issue.location.source} |`);
178
+ }
179
+ lines.push('');
180
+ }
181
+ if (warnings.length > 0) {
182
+ lines.push('## Warnings (Review Required)', '');
183
+ lines.push('| Type | Pattern | Value | Command | Source |');
184
+ lines.push('|------|---------|-------|---------|--------|');
185
+ for (const issue of warnings) {
186
+ lines.push(`| ${issue.type} | ${issue.pattern} | \`${issue.value}\` | ${issue.command} | ${issue.location.source} |`);
187
+ }
188
+ lines.push('');
189
+ }
190
+ return lines.join('\n');
191
+ }
192
+ export default {
193
+ scanForHardcoded,
194
+ scanCommandOutput,
195
+ createDetectionReport,
196
+ };
197
+ //# sourceMappingURL=hardcoded-detector.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"hardcoded-detector.js","sourceRoot":"","sources":["../../../../tests/e2e/utils/hardcoded-detector.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,8 @@
1
+ /**
2
+ * E2E Test Utilities Index
3
+ */
4
+ export * from './hardcoded-detector.js';
5
+ export * from './linear-reporter.js';
6
+ export * from './baseline-collector.js';
7
+ export * from '../test-config.js';
8
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../../tests/e2e/utils/index.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,cAAc,yBAAyB,CAAA;AACvC,cAAc,sBAAsB,CAAA;AACpC,cAAc,yBAAyB,CAAA;AACvC,cAAc,mBAAmB,CAAA"}
@@ -0,0 +1,8 @@
1
+ /**
2
+ * E2E Test Utilities Index
3
+ */
4
+ export * from './hardcoded-detector.js';
5
+ export * from './linear-reporter.js';
6
+ export * from './baseline-collector.js';
7
+ export * from '../test-config.js';
8
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../tests/e2e/utils/index.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,cAAc,yBAAyB,CAAA;AACvC,cAAc,sBAAsB,CAAA;AACpC,cAAc,yBAAyB,CAAA;AACvC,cAAc,mBAAmB,CAAA"}