semantic-change-tracker 0.3.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 (42) hide show
  1. package/README.md +122 -0
  2. package/dist/analyzer/functionDiff.d.ts +14 -0
  3. package/dist/analyzer/functionDiff.d.ts.map +1 -0
  4. package/dist/analyzer/functionDiff.js +173 -0
  5. package/dist/analyzer/functionDiff.js.map +1 -0
  6. package/dist/analyzer/reasonAggregator.d.ts +8 -0
  7. package/dist/analyzer/reasonAggregator.d.ts.map +1 -0
  8. package/dist/analyzer/reasonAggregator.js +269 -0
  9. package/dist/analyzer/reasonAggregator.js.map +1 -0
  10. package/dist/analyzer/ruleEngine.d.ts +5 -0
  11. package/dist/analyzer/ruleEngine.d.ts.map +1 -0
  12. package/dist/analyzer/ruleEngine.js +129 -0
  13. package/dist/analyzer/ruleEngine.js.map +1 -0
  14. package/dist/cli/index.d.ts +3 -0
  15. package/dist/cli/index.d.ts.map +1 -0
  16. package/dist/cli/index.js +124 -0
  17. package/dist/cli/index.js.map +1 -0
  18. package/dist/config/default.d.ts +18 -0
  19. package/dist/config/default.d.ts.map +1 -0
  20. package/dist/config/default.js +20 -0
  21. package/dist/config/default.js.map +1 -0
  22. package/dist/config/loader.d.ts +3 -0
  23. package/dist/config/loader.d.ts.map +1 -0
  24. package/dist/config/loader.js +63 -0
  25. package/dist/config/loader.js.map +1 -0
  26. package/dist/git/diff.d.ts +10 -0
  27. package/dist/git/diff.d.ts.map +1 -0
  28. package/dist/git/diff.js +58 -0
  29. package/dist/git/diff.js.map +1 -0
  30. package/dist/index.d.ts +8 -0
  31. package/dist/index.d.ts.map +1 -0
  32. package/dist/index.js +24 -0
  33. package/dist/index.js.map +1 -0
  34. package/dist/model/semanticChange.d.ts +12 -0
  35. package/dist/model/semanticChange.d.ts.map +1 -0
  36. package/dist/model/semanticChange.js +3 -0
  37. package/dist/model/semanticChange.js.map +1 -0
  38. package/dist/parser/tsParser.d.ts +15 -0
  39. package/dist/parser/tsParser.d.ts.map +1 -0
  40. package/dist/parser/tsParser.js +158 -0
  41. package/dist/parser/tsParser.js.map +1 -0
  42. package/package.json +45 -0
@@ -0,0 +1,129 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.analyzeChanges = analyzeChanges;
4
+ const reasonAggregator_1 = require("./reasonAggregator");
5
+ function analyzeChanges(diffs, config, changedFiles, testFilesChanged) {
6
+ const affectedDomains = detectAffectedDomains(changedFiles, config);
7
+ const behaviorChanged = diffs.some((d) => d.behaviorChanged);
8
+ const touchedFunctions = diffs.map((d) => d.functionName);
9
+ // Use aggregation for reasons
10
+ const aggregatedReasons = (0, reasonAggregator_1.aggregateReasons)(diffs);
11
+ const reasons = buildFinalReasons(aggregatedReasons, affectedDomains, testFilesChanged, diffs);
12
+ const changeType = determineOverallChangeType(diffs);
13
+ const riskScore = calculateRiskScore(behaviorChanged, affectedDomains.length > 0, !testFilesChanged, config);
14
+ const riskLevel = determineRiskLevel(riskScore, config);
15
+ const suggestedTests = generateTestSuggestion(aggregatedReasons, testFilesChanged);
16
+ return {
17
+ changeType,
18
+ affectedDomains,
19
+ behaviorChanged,
20
+ riskScore,
21
+ riskLevel,
22
+ reasons,
23
+ touchedFunctions,
24
+ suggestedTests,
25
+ };
26
+ }
27
+ function detectAffectedDomains(files, config) {
28
+ const domains = [];
29
+ if (!config.domains)
30
+ return domains;
31
+ for (const [domain, keywords] of Object.entries(config.domains)) {
32
+ for (const file of files) {
33
+ if (keywords.some((keyword) => file.toLowerCase().includes(keyword.toLowerCase()))) {
34
+ if (!domains.includes(domain)) {
35
+ domains.push(domain);
36
+ }
37
+ }
38
+ }
39
+ }
40
+ return domains;
41
+ }
42
+ function buildFinalReasons(aggregated, affectedDomains, testFilesChanged, diffs) {
43
+ const reasons = [];
44
+ // Sort by priority (1 = highest)
45
+ aggregated.sort((a, b) => a.priority - b.priority);
46
+ // Add aggregated reasons
47
+ aggregated.forEach(ar => reasons.push(ar.reason));
48
+ // Add domain context if relevant
49
+ if (affectedDomains.length > 0) {
50
+ const domainList = affectedDomains.join(", ");
51
+ reasons.push(`Changes detected in business domain files: ${domainList}`);
52
+ }
53
+ // Add test coverage gap only if behavior changed
54
+ if (!testFilesChanged && diffs.some(d => d.behaviorChanged)) {
55
+ const exportedChanges = diffs.filter(d => d.isExported && d.behaviorChanged);
56
+ if (exportedChanges.length > 0) {
57
+ const funcNames = exportedChanges
58
+ .map(d => `'${d.functionName}'`)
59
+ .slice(0, 3)
60
+ .join(", ");
61
+ const more = exportedChanges.length > 3 ? ` and ${exportedChanges.length - 3} more` : "";
62
+ reasons.push(`No test changes detected for ${funcNames}${more}`);
63
+ }
64
+ }
65
+ return reasons;
66
+ }
67
+ function determineOverallChangeType(diffs) {
68
+ const types = diffs.map((d) => d.changeType);
69
+ const hasExportedApiChange = diffs.some(d => d.changeType === "ApiChange" && d.isExported);
70
+ const hasBehaviorChange = types.includes("BehaviorChange");
71
+ if (hasExportedApiChange)
72
+ return "ApiChange";
73
+ if (hasBehaviorChange)
74
+ return "BehaviorChange";
75
+ if (types.includes("ApiChange"))
76
+ return "BehaviorChange";
77
+ if (types.includes("Rename"))
78
+ return "Rename";
79
+ return "Refactor";
80
+ }
81
+ function calculateRiskScore(behaviorChanged, affectedBusinessDomain, noTestChange, config) {
82
+ let score = 0;
83
+ const rules = config.riskRules;
84
+ if (behaviorChanged) {
85
+ score += rules.behaviorChange || 3;
86
+ }
87
+ if (affectedBusinessDomain) {
88
+ score += rules.businessDomain || 2;
89
+ }
90
+ if (noTestChange) {
91
+ score += rules.noTestChange || 2;
92
+ }
93
+ return score;
94
+ }
95
+ function determineRiskLevel(score, config) {
96
+ const thresholds = config.riskThresholds;
97
+ if (score >= (thresholds.high || 5))
98
+ return "High";
99
+ if (score >= (thresholds.medium || 3))
100
+ return "Medium";
101
+ return "Low";
102
+ }
103
+ function generateTestSuggestion(aggregated, testFilesChanged) {
104
+ if (testFilesChanged || aggregated.length === 0) {
105
+ return [];
106
+ }
107
+ // Find highest priority reason with behavior/API change
108
+ const highestPriority = aggregated.find(ar => ar.priority <= 2);
109
+ if (!highestPriority) {
110
+ return [];
111
+ }
112
+ const funcs = highestPriority.affectedFunctions
113
+ .slice(0, 3)
114
+ .map(f => `'${f}'`)
115
+ .join(", ");
116
+ const more = highestPriority.affectedFunctions.length > 3
117
+ ? ` and ${highestPriority.affectedFunctions.length - 3} more`
118
+ : "";
119
+ if (highestPriority.priority === 1) {
120
+ // API surface changes
121
+ return [`No test updates detected for API surface changes (${funcs}${more})`];
122
+ }
123
+ if (highestPriority.priority === 2) {
124
+ // Behavioral changes
125
+ return [`No test updates detected for behavior changes (${funcs}${more})`];
126
+ }
127
+ return [];
128
+ }
129
+ //# sourceMappingURL=ruleEngine.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ruleEngine.js","sourceRoot":"","sources":["../../src/analyzer/ruleEngine.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,3 @@
1
+ #!/usr/bin/env node
2
+ export {};
3
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/cli/index.ts"],"names":[],"mappings":""}
@@ -0,0 +1,124 @@
1
+ #!/usr/bin/env node
2
+ "use strict";
3
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
4
+ if (k2 === undefined) k2 = k;
5
+ var desc = Object.getOwnPropertyDescriptor(m, k);
6
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
7
+ desc = { enumerable: true, get: function() { return m[k]; } };
8
+ }
9
+ Object.defineProperty(o, k2, desc);
10
+ }) : (function(o, m, k, k2) {
11
+ if (k2 === undefined) k2 = k;
12
+ o[k2] = m[k];
13
+ }));
14
+ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
15
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
16
+ }) : function(o, v) {
17
+ o["default"] = v;
18
+ });
19
+ var __importStar = (this && this.__importStar) || (function () {
20
+ var ownKeys = function(o) {
21
+ ownKeys = Object.getOwnPropertyNames || function (o) {
22
+ var ar = [];
23
+ for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
24
+ return ar;
25
+ };
26
+ return ownKeys(o);
27
+ };
28
+ return function (mod) {
29
+ if (mod && mod.__esModule) return mod;
30
+ var result = {};
31
+ if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
32
+ __setModuleDefault(result, mod);
33
+ return result;
34
+ };
35
+ })();
36
+ Object.defineProperty(exports, "__esModule", { value: true });
37
+ const commander_1 = require("commander");
38
+ const fs = __importStar(require("fs"));
39
+ const path = __importStar(require("path"));
40
+ const loader_1 = require("../config/loader");
41
+ const default_1 = require("../config/default");
42
+ const diff_1 = require("../git/diff");
43
+ const tsParser_1 = require("../parser/tsParser");
44
+ const functionDiff_1 = require("../analyzer/functionDiff");
45
+ const ruleEngine_1 = require("../analyzer/ruleEngine");
46
+ const program = new commander_1.Command();
47
+ program
48
+ .name("sct")
49
+ .description("Semantic Change Tracker - Analyze Git code changes semantically")
50
+ .version("0.1.0");
51
+ program
52
+ .command("init")
53
+ .description("Generate default sct.config.json")
54
+ .action(() => {
55
+ const configPath = path.join(process.cwd(), "sct.config.json");
56
+ if (fs.existsSync(configPath)) {
57
+ console.error("sct.config.json already exists");
58
+ process.exit(1);
59
+ }
60
+ const config = {
61
+ languages: default_1.defaultConfig.languages,
62
+ include: default_1.defaultConfig.include,
63
+ exclude: default_1.defaultConfig.exclude,
64
+ domains: {
65
+ Order: ["order", "checkout"],
66
+ Discount: ["discount", "promotion", "coupon"],
67
+ },
68
+ riskRules: default_1.defaultConfig.riskRules,
69
+ riskThresholds: default_1.defaultConfig.riskThresholds,
70
+ };
71
+ fs.writeFileSync(configPath, JSON.stringify(config, null, 2));
72
+ console.log("Created sct.config.json");
73
+ });
74
+ program
75
+ .command("analyze")
76
+ .description("Run full analysis on git changes")
77
+ .option("-c, --config <path>", "Path to config file")
78
+ .action(async (options) => {
79
+ try {
80
+ const config = (0, loader_1.loadConfig)(options.config);
81
+ const changedFiles = (0, diff_1.getChangedFiles)();
82
+ if (changedFiles.length === 0) {
83
+ console.log(JSON.stringify({
84
+ message: "No changes detected",
85
+ }, null, 2));
86
+ return;
87
+ }
88
+ const filteredFiles = changedFiles.filter((file) => {
89
+ const ext = path.extname(file).slice(1);
90
+ return config.languages.includes(ext);
91
+ });
92
+ if (filteredFiles.length === 0) {
93
+ console.log(JSON.stringify({
94
+ message: "No relevant files changed",
95
+ }, null, 2));
96
+ return;
97
+ }
98
+ const allDiffs = [];
99
+ for (const file of filteredFiles) {
100
+ const diff = (0, diff_1.getDiffForFile)(file);
101
+ if (diff.status === "deleted")
102
+ continue;
103
+ const oldFunctions = diff.oldContent ? (0, tsParser_1.parseTypeScriptFile)(diff.oldContent) : [];
104
+ const newFunctions = diff.newContent ? (0, tsParser_1.parseTypeScriptFile)(diff.newContent) : [];
105
+ const functionDiffs = (0, functionDiff_1.compareFunctions)(oldFunctions, newFunctions, file);
106
+ allDiffs.push(...functionDiffs);
107
+ }
108
+ if (allDiffs.length === 0) {
109
+ console.log(JSON.stringify({
110
+ message: "No function-level changes detected",
111
+ }, null, 2));
112
+ return;
113
+ }
114
+ const testFilesChanged = (0, diff_1.getChangedTestFiles)().length > 0;
115
+ const result = (0, ruleEngine_1.analyzeChanges)(allDiffs, config, filteredFiles, testFilesChanged);
116
+ console.log(JSON.stringify(result, null, 2));
117
+ }
118
+ catch (error) {
119
+ console.error("Error:", error.message);
120
+ process.exit(1);
121
+ }
122
+ });
123
+ program.parse();
124
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/cli/index.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,18 @@
1
+ export interface SctConfig {
2
+ languages: string[];
3
+ include?: string[];
4
+ exclude?: string[];
5
+ domains?: Record<string, string[]>;
6
+ riskRules?: {
7
+ behaviorChange?: number;
8
+ businessDomain?: number;
9
+ noTestChange?: number;
10
+ manyCallSites?: number;
11
+ };
12
+ riskThresholds?: {
13
+ high?: number;
14
+ medium?: number;
15
+ };
16
+ }
17
+ export declare const defaultConfig: SctConfig;
18
+ //# sourceMappingURL=default.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"default.d.ts","sourceRoot":"","sources":["../../src/config/default.ts"],"names":[],"mappings":"AAAA,MAAM,WAAW,SAAS;IACxB,SAAS,EAAE,MAAM,EAAE,CAAC;IACpB,OAAO,CAAC,EAAE,MAAM,EAAE,CAAC;IACnB,OAAO,CAAC,EAAE,MAAM,EAAE,CAAC;IACnB,OAAO,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,EAAE,CAAC,CAAC;IACnC,SAAS,CAAC,EAAE;QACV,cAAc,CAAC,EAAE,MAAM,CAAC;QACxB,cAAc,CAAC,EAAE,MAAM,CAAC;QACxB,YAAY,CAAC,EAAE,MAAM,CAAC;QACtB,aAAa,CAAC,EAAE,MAAM,CAAC;KACxB,CAAC;IACF,cAAc,CAAC,EAAE;QACf,IAAI,CAAC,EAAE,MAAM,CAAC;QACd,MAAM,CAAC,EAAE,MAAM,CAAC;KACjB,CAAC;CACH;AAED,eAAO,MAAM,aAAa,EAAE,SAe3B,CAAC"}
@@ -0,0 +1,20 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.defaultConfig = void 0;
4
+ exports.defaultConfig = {
5
+ languages: ["ts", "js"],
6
+ include: ["**/*.ts", "**/*.js"],
7
+ exclude: ["node_modules/**", "dist/**", "**/*.spec.ts", "**/*.test.ts"],
8
+ domains: {},
9
+ riskRules: {
10
+ behaviorChange: 3,
11
+ businessDomain: 2,
12
+ noTestChange: 2,
13
+ manyCallSites: 1,
14
+ },
15
+ riskThresholds: {
16
+ high: 5,
17
+ medium: 3,
18
+ },
19
+ };
20
+ //# sourceMappingURL=default.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"default.js","sourceRoot":"","sources":["../../src/config/default.ts"],"names":[],"mappings":";;;AAiBa,QAAA,aAAa,GAAc;IACtC,SAAS,EAAE,CAAC,IAAI,EAAE,IAAI,CAAC;IACvB,OAAO,EAAE,CAAC,SAAS,EAAE,SAAS,CAAC;IAC/B,OAAO,EAAE,CAAC,iBAAiB,EAAE,SAAS,EAAE,cAAc,EAAE,cAAc,CAAC;IACvE,OAAO,EAAE,EAAE;IACX,SAAS,EAAE;QACT,cAAc,EAAE,CAAC;QACjB,cAAc,EAAE,CAAC;QACjB,YAAY,EAAE,CAAC;QACf,aAAa,EAAE,CAAC;KACjB;IACD,cAAc,EAAE;QACd,IAAI,EAAE,CAAC;QACP,MAAM,EAAE,CAAC;KACV;CACF,CAAC"}
@@ -0,0 +1,3 @@
1
+ import { SctConfig } from "./default";
2
+ export declare function loadConfig(configPath?: string): SctConfig;
3
+ //# sourceMappingURL=loader.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"loader.d.ts","sourceRoot":"","sources":["../../src/config/loader.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,SAAS,EAAiB,MAAM,WAAW,CAAC;AAErD,wBAAgB,UAAU,CAAC,UAAU,CAAC,EAAE,MAAM,GAAG,SAAS,CAczD"}
@@ -0,0 +1,63 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ var desc = Object.getOwnPropertyDescriptor(m, k);
5
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
+ desc = { enumerable: true, get: function() { return m[k]; } };
7
+ }
8
+ Object.defineProperty(o, k2, desc);
9
+ }) : (function(o, m, k, k2) {
10
+ if (k2 === undefined) k2 = k;
11
+ o[k2] = m[k];
12
+ }));
13
+ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
14
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
15
+ }) : function(o, v) {
16
+ o["default"] = v;
17
+ });
18
+ var __importStar = (this && this.__importStar) || (function () {
19
+ var ownKeys = function(o) {
20
+ ownKeys = Object.getOwnPropertyNames || function (o) {
21
+ var ar = [];
22
+ for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
23
+ return ar;
24
+ };
25
+ return ownKeys(o);
26
+ };
27
+ return function (mod) {
28
+ if (mod && mod.__esModule) return mod;
29
+ var result = {};
30
+ if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
31
+ __setModuleDefault(result, mod);
32
+ return result;
33
+ };
34
+ })();
35
+ Object.defineProperty(exports, "__esModule", { value: true });
36
+ exports.loadConfig = loadConfig;
37
+ const fs = __importStar(require("fs"));
38
+ const path = __importStar(require("path"));
39
+ const default_1 = require("./default");
40
+ function loadConfig(configPath) {
41
+ const resolvedPath = configPath || path.join(process.cwd(), "sct.config.json");
42
+ if (!fs.existsSync(resolvedPath)) {
43
+ return default_1.defaultConfig;
44
+ }
45
+ try {
46
+ const userConfig = JSON.parse(fs.readFileSync(resolvedPath, "utf-8"));
47
+ return mergeConfig(default_1.defaultConfig, userConfig);
48
+ }
49
+ catch (error) {
50
+ console.error(`Error loading config from ${resolvedPath}:`, error);
51
+ return default_1.defaultConfig;
52
+ }
53
+ }
54
+ function mergeConfig(defaults, user) {
55
+ return {
56
+ ...defaults,
57
+ ...user,
58
+ riskRules: { ...defaults.riskRules, ...user.riskRules },
59
+ riskThresholds: { ...defaults.riskThresholds, ...user.riskThresholds },
60
+ domains: { ...defaults.domains, ...user.domains },
61
+ };
62
+ }
63
+ //# sourceMappingURL=loader.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"loader.js","sourceRoot":"","sources":["../../src/config/loader.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAIA,gCAcC;AAlBD,uCAAyB;AACzB,2CAA6B;AAC7B,uCAAqD;AAErD,SAAgB,UAAU,CAAC,UAAmB;IAC5C,MAAM,YAAY,GAAG,UAAU,IAAI,IAAI,CAAC,IAAI,CAAC,OAAO,CAAC,GAAG,EAAE,EAAE,iBAAiB,CAAC,CAAC;IAE/E,IAAI,CAAC,EAAE,CAAC,UAAU,CAAC,YAAY,CAAC,EAAE,CAAC;QACjC,OAAO,uBAAa,CAAC;IACvB,CAAC;IAED,IAAI,CAAC;QACH,MAAM,UAAU,GAAG,IAAI,CAAC,KAAK,CAAC,EAAE,CAAC,YAAY,CAAC,YAAY,EAAE,OAAO,CAAC,CAAC,CAAC;QACtE,OAAO,WAAW,CAAC,uBAAa,EAAE,UAAU,CAAC,CAAC;IAChD,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QACf,OAAO,CAAC,KAAK,CAAC,6BAA6B,YAAY,GAAG,EAAE,KAAK,CAAC,CAAC;QACnE,OAAO,uBAAa,CAAC;IACvB,CAAC;AACH,CAAC;AAED,SAAS,WAAW,CAAC,QAAmB,EAAE,IAAwB;IAChE,OAAO;QACL,GAAG,QAAQ;QACX,GAAG,IAAI;QACP,SAAS,EAAE,EAAE,GAAG,QAAQ,CAAC,SAAS,EAAE,GAAG,IAAI,CAAC,SAAS,EAAE;QACvD,cAAc,EAAE,EAAE,GAAG,QAAQ,CAAC,cAAc,EAAE,GAAG,IAAI,CAAC,cAAc,EAAE;QACtE,OAAO,EAAE,EAAE,GAAG,QAAQ,CAAC,OAAO,EAAE,GAAG,IAAI,CAAC,OAAO,EAAE;KAClD,CAAC;AACJ,CAAC"}
@@ -0,0 +1,10 @@
1
+ export interface DiffFile {
2
+ path: string;
3
+ oldContent: string | null;
4
+ newContent: string | null;
5
+ status: "added" | "modified" | "deleted";
6
+ }
7
+ export declare function getChangedFiles(): string[];
8
+ export declare function getDiffForFile(filePath: string): DiffFile;
9
+ export declare function getChangedTestFiles(): string[];
10
+ //# sourceMappingURL=diff.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"diff.d.ts","sourceRoot":"","sources":["../../src/git/diff.ts"],"names":[],"mappings":"AAEA,MAAM,WAAW,QAAQ;IACvB,IAAI,EAAE,MAAM,CAAC;IACb,UAAU,EAAE,MAAM,GAAG,IAAI,CAAC;IAC1B,UAAU,EAAE,MAAM,GAAG,IAAI,CAAC;IAC1B,MAAM,EAAE,OAAO,GAAG,UAAU,GAAG,SAAS,CAAC;CAC1C;AAED,wBAAgB,eAAe,IAAI,MAAM,EAAE,CAU1C;AAED,wBAAgB,cAAc,CAAC,QAAQ,EAAE,MAAM,GAAG,QAAQ,CAkCzD;AAED,wBAAgB,mBAAmB,IAAI,MAAM,EAAE,CAK9C"}
@@ -0,0 +1,58 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.getChangedFiles = getChangedFiles;
4
+ exports.getDiffForFile = getDiffForFile;
5
+ exports.getChangedTestFiles = getChangedTestFiles;
6
+ const child_process_1 = require("child_process");
7
+ function getChangedFiles() {
8
+ try {
9
+ const output = (0, child_process_1.execSync)("git diff --name-only HEAD", {
10
+ encoding: "utf-8",
11
+ cwd: process.cwd(),
12
+ });
13
+ return output.trim().split("\n").filter(Boolean);
14
+ }
15
+ catch (error) {
16
+ throw new Error("Failed to get changed files from git. Are you in a git repository?");
17
+ }
18
+ }
19
+ function getDiffForFile(filePath) {
20
+ try {
21
+ let oldContent = null;
22
+ let newContent = null;
23
+ let status = "modified";
24
+ try {
25
+ oldContent = (0, child_process_1.execSync)(`git show HEAD:${filePath}`, {
26
+ encoding: "utf-8",
27
+ cwd: process.cwd(),
28
+ });
29
+ }
30
+ catch {
31
+ status = "added";
32
+ }
33
+ try {
34
+ newContent = (0, child_process_1.execSync)(`cat ${filePath}`, {
35
+ encoding: "utf-8",
36
+ cwd: process.cwd(),
37
+ });
38
+ }
39
+ catch {
40
+ status = "deleted";
41
+ newContent = null;
42
+ }
43
+ return {
44
+ path: filePath,
45
+ oldContent,
46
+ newContent,
47
+ status,
48
+ };
49
+ }
50
+ catch (error) {
51
+ throw new Error(`Failed to get diff for file: ${filePath}`);
52
+ }
53
+ }
54
+ function getChangedTestFiles() {
55
+ const changedFiles = getChangedFiles();
56
+ return changedFiles.filter((file) => file.includes(".test.") || file.includes(".spec."));
57
+ }
58
+ //# sourceMappingURL=diff.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"diff.js","sourceRoot":"","sources":["../../src/git/diff.ts"],"names":[],"mappings":";;AASA,0CAUC;AAED,wCAkCC;AAED,kDAKC;AA9DD,iDAAyC;AASzC,SAAgB,eAAe;IAC7B,IAAI,CAAC;QACH,MAAM,MAAM,GAAG,IAAA,wBAAQ,EAAC,2BAA2B,EAAE;YACnD,QAAQ,EAAE,OAAO;YACjB,GAAG,EAAE,OAAO,CAAC,GAAG,EAAE;SACnB,CAAC,CAAC;QACH,OAAO,MAAM,CAAC,IAAI,EAAE,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC,MAAM,CAAC,OAAO,CAAC,CAAC;IACnD,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QACf,MAAM,IAAI,KAAK,CAAC,oEAAoE,CAAC,CAAC;IACxF,CAAC;AACH,CAAC;AAED,SAAgB,cAAc,CAAC,QAAgB;IAC7C,IAAI,CAAC;QACH,IAAI,UAAU,GAAkB,IAAI,CAAC;QACrC,IAAI,UAAU,GAAkB,IAAI,CAAC;QACrC,IAAI,MAAM,GAAqC,UAAU,CAAC;QAE1D,IAAI,CAAC;YACH,UAAU,GAAG,IAAA,wBAAQ,EAAC,iBAAiB,QAAQ,EAAE,EAAE;gBACjD,QAAQ,EAAE,OAAO;gBACjB,GAAG,EAAE,OAAO,CAAC,GAAG,EAAE;aACnB,CAAC,CAAC;QACL,CAAC;QAAC,MAAM,CAAC;YACP,MAAM,GAAG,OAAO,CAAC;QACnB,CAAC;QAED,IAAI,CAAC;YACH,UAAU,GAAG,IAAA,wBAAQ,EAAC,OAAO,QAAQ,EAAE,EAAE;gBACvC,QAAQ,EAAE,OAAO;gBACjB,GAAG,EAAE,OAAO,CAAC,GAAG,EAAE;aACnB,CAAC,CAAC;QACL,CAAC;QAAC,MAAM,CAAC;YACP,MAAM,GAAG,SAAS,CAAC;YACnB,UAAU,GAAG,IAAI,CAAC;QACpB,CAAC;QAED,OAAO;YACL,IAAI,EAAE,QAAQ;YACd,UAAU;YACV,UAAU;YACV,MAAM;SACP,CAAC;IACJ,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QACf,MAAM,IAAI,KAAK,CAAC,gCAAgC,QAAQ,EAAE,CAAC,CAAC;IAC9D,CAAC;AACH,CAAC;AAED,SAAgB,mBAAmB;IACjC,MAAM,YAAY,GAAG,eAAe,EAAE,CAAC;IACvC,OAAO,YAAY,CAAC,MAAM,CACxB,CAAC,IAAI,EAAE,EAAE,CAAC,IAAI,CAAC,QAAQ,CAAC,QAAQ,CAAC,IAAI,IAAI,CAAC,QAAQ,CAAC,QAAQ,CAAC,CAC7D,CAAC;AACJ,CAAC"}
@@ -0,0 +1,8 @@
1
+ export * from "./model/semanticChange";
2
+ export * from "./config/default";
3
+ export * from "./config/loader";
4
+ export * from "./git/diff";
5
+ export * from "./parser/tsParser";
6
+ export * from "./analyzer/functionDiff";
7
+ export * from "./analyzer/ruleEngine";
8
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,cAAc,wBAAwB,CAAC;AACvC,cAAc,kBAAkB,CAAC;AACjC,cAAc,iBAAiB,CAAC;AAChC,cAAc,YAAY,CAAC;AAC3B,cAAc,mBAAmB,CAAC;AAClC,cAAc,yBAAyB,CAAC;AACxC,cAAc,uBAAuB,CAAC"}
package/dist/index.js ADDED
@@ -0,0 +1,24 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ var desc = Object.getOwnPropertyDescriptor(m, k);
5
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
+ desc = { enumerable: true, get: function() { return m[k]; } };
7
+ }
8
+ Object.defineProperty(o, k2, desc);
9
+ }) : (function(o, m, k, k2) {
10
+ if (k2 === undefined) k2 = k;
11
+ o[k2] = m[k];
12
+ }));
13
+ var __exportStar = (this && this.__exportStar) || function(m, exports) {
14
+ for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
15
+ };
16
+ Object.defineProperty(exports, "__esModule", { value: true });
17
+ __exportStar(require("./model/semanticChange"), exports);
18
+ __exportStar(require("./config/default"), exports);
19
+ __exportStar(require("./config/loader"), exports);
20
+ __exportStar(require("./git/diff"), exports);
21
+ __exportStar(require("./parser/tsParser"), exports);
22
+ __exportStar(require("./analyzer/functionDiff"), exports);
23
+ __exportStar(require("./analyzer/ruleEngine"), exports);
24
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;AAAA,yDAAuC;AACvC,mDAAiC;AACjC,kDAAgC;AAChC,6CAA2B;AAC3B,oDAAkC;AAClC,0DAAwC;AACxC,wDAAsC"}
@@ -0,0 +1,12 @@
1
+ export type ChangeType = "Refactor" | "BehaviorChange" | "ApiChange" | "Rename";
2
+ export interface SemanticChange {
3
+ changeType: ChangeType;
4
+ affectedDomains: string[];
5
+ behaviorChanged: boolean;
6
+ riskScore: number;
7
+ riskLevel: "Low" | "Medium" | "High";
8
+ reasons: string[];
9
+ touchedFunctions: string[];
10
+ suggestedTests: string[];
11
+ }
12
+ //# sourceMappingURL=semanticChange.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"semanticChange.d.ts","sourceRoot":"","sources":["../../src/model/semanticChange.ts"],"names":[],"mappings":"AAAA,MAAM,MAAM,UAAU,GAClB,UAAU,GACV,gBAAgB,GAChB,WAAW,GACX,QAAQ,CAAC;AAEb,MAAM,WAAW,cAAc;IAC7B,UAAU,EAAE,UAAU,CAAC;IACvB,eAAe,EAAE,MAAM,EAAE,CAAC;IAC1B,eAAe,EAAE,OAAO,CAAC;IACzB,SAAS,EAAE,MAAM,CAAC;IAClB,SAAS,EAAE,KAAK,GAAG,QAAQ,GAAG,MAAM,CAAC;IACrC,OAAO,EAAE,MAAM,EAAE,CAAC;IAClB,gBAAgB,EAAE,MAAM,EAAE,CAAC;IAC3B,cAAc,EAAE,MAAM,EAAE,CAAC;CAC1B"}
@@ -0,0 +1,3 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ //# sourceMappingURL=semanticChange.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"semanticChange.js","sourceRoot":"","sources":["../../src/model/semanticChange.ts"],"names":[],"mappings":""}
@@ -0,0 +1,15 @@
1
+ export interface FunctionInfo {
2
+ name: string;
3
+ parameters: string[];
4
+ returnType: string;
5
+ hasConditionals: boolean;
6
+ hasEarlyReturn: boolean;
7
+ returnExpressions: string[];
8
+ bodyHash: string;
9
+ isExported: boolean;
10
+ isAsync: boolean;
11
+ visibility: "public" | "private" | "protected" | "implicit-public";
12
+ isMethodDeclaration: boolean;
13
+ }
14
+ export declare function parseTypeScriptFile(content: string): FunctionInfo[];
15
+ //# sourceMappingURL=tsParser.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"tsParser.d.ts","sourceRoot":"","sources":["../../src/parser/tsParser.ts"],"names":[],"mappings":"AAEA,MAAM,WAAW,YAAY;IAC3B,IAAI,EAAE,MAAM,CAAC;IACb,UAAU,EAAE,MAAM,EAAE,CAAC;IACrB,UAAU,EAAE,MAAM,CAAC;IACnB,eAAe,EAAE,OAAO,CAAC;IACzB,cAAc,EAAE,OAAO,CAAC;IACxB,iBAAiB,EAAE,MAAM,EAAE,CAAC;IAC5B,QAAQ,EAAE,MAAM,CAAC;IACjB,UAAU,EAAE,OAAO,CAAC;IACpB,OAAO,EAAE,OAAO,CAAC;IACjB,UAAU,EAAE,QAAQ,GAAG,SAAS,GAAG,WAAW,GAAG,iBAAiB,CAAC;IACnE,mBAAmB,EAAE,OAAO,CAAC;CAC9B;AAED,wBAAgB,mBAAmB,CAAC,OAAO,EAAE,MAAM,GAAG,YAAY,EAAE,CA2BnE"}