@gitwand/core 1.6.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/LICENSE +21 -0
- package/README.md +52 -0
- package/dist/__tests__/bench.bench.d.ts +14 -0
- package/dist/__tests__/bench.bench.d.ts.map +1 -0
- package/dist/__tests__/bench.bench.js +137 -0
- package/dist/__tests__/bench.bench.js.map +1 -0
- package/dist/__tests__/confidence-v14.test.d.ts +13 -0
- package/dist/__tests__/confidence-v14.test.d.ts.map +1 -0
- package/dist/__tests__/confidence-v14.test.js +284 -0
- package/dist/__tests__/confidence-v14.test.js.map +1 -0
- package/dist/__tests__/config.test.d.ts +2 -0
- package/dist/__tests__/config.test.d.ts.map +1 -0
- package/dist/__tests__/config.test.js +317 -0
- package/dist/__tests__/config.test.js.map +1 -0
- package/dist/__tests__/corpus.d.ts +36 -0
- package/dist/__tests__/corpus.d.ts.map +1 -0
- package/dist/__tests__/corpus.js +541 -0
- package/dist/__tests__/corpus.js.map +1 -0
- package/dist/__tests__/corpus.test.d.ts +17 -0
- package/dist/__tests__/corpus.test.d.ts.map +1 -0
- package/dist/__tests__/corpus.test.js +179 -0
- package/dist/__tests__/corpus.test.js.map +1 -0
- package/dist/__tests__/diff.test.d.ts +10 -0
- package/dist/__tests__/diff.test.d.ts.map +1 -0
- package/dist/__tests__/diff.test.js +178 -0
- package/dist/__tests__/diff.test.js.map +1 -0
- package/dist/__tests__/format-resolvers.test.d.ts +2 -0
- package/dist/__tests__/format-resolvers.test.d.ts.map +1 -0
- package/dist/__tests__/format-resolvers.test.js +577 -0
- package/dist/__tests__/format-resolvers.test.js.map +1 -0
- package/dist/__tests__/imports-extended.test.d.ts +2 -0
- package/dist/__tests__/imports-extended.test.d.ts.map +1 -0
- package/dist/__tests__/imports-extended.test.js +94 -0
- package/dist/__tests__/imports-extended.test.js.map +1 -0
- package/dist/__tests__/lockfile-resolvers.test.d.ts +2 -0
- package/dist/__tests__/lockfile-resolvers.test.d.ts.map +1 -0
- package/dist/__tests__/lockfile-resolvers.test.js +200 -0
- package/dist/__tests__/lockfile-resolvers.test.js.map +1 -0
- package/dist/__tests__/patterns/insertion-at-boundary.test.d.ts +10 -0
- package/dist/__tests__/patterns/insertion-at-boundary.test.d.ts.map +1 -0
- package/dist/__tests__/patterns/insertion-at-boundary.test.js +185 -0
- package/dist/__tests__/patterns/insertion-at-boundary.test.js.map +1 -0
- package/dist/__tests__/patterns/reorder-only.test.d.ts +10 -0
- package/dist/__tests__/patterns/reorder-only.test.d.ts.map +1 -0
- package/dist/__tests__/patterns/reorder-only.test.js +181 -0
- package/dist/__tests__/patterns/reorder-only.test.js.map +1 -0
- package/dist/__tests__/phase-7-2-3b.test.d.ts +6 -0
- package/dist/__tests__/phase-7-2-3b.test.d.ts.map +1 -0
- package/dist/__tests__/phase-7-2-3b.test.js +730 -0
- package/dist/__tests__/phase-7-2-3b.test.js.map +1 -0
- package/dist/__tests__/resolver.test.d.ts +2 -0
- package/dist/__tests__/resolver.test.d.ts.map +1 -0
- package/dist/__tests__/resolver.test.js +927 -0
- package/dist/__tests__/resolver.test.js.map +1 -0
- package/dist/__tests__/resolvers/cargo.test.d.ts +10 -0
- package/dist/__tests__/resolvers/cargo.test.d.ts.map +1 -0
- package/dist/__tests__/resolvers/cargo.test.js +158 -0
- package/dist/__tests__/resolvers/cargo.test.js.map +1 -0
- package/dist/__tests__/resolvers/dockerfile.test.d.ts +8 -0
- package/dist/__tests__/resolvers/dockerfile.test.d.ts.map +1 -0
- package/dist/__tests__/resolvers/dockerfile.test.js +120 -0
- package/dist/__tests__/resolvers/dockerfile.test.js.map +1 -0
- package/dist/__tests__/resolvers/dotenv.test.d.ts +9 -0
- package/dist/__tests__/resolvers/dotenv.test.d.ts.map +1 -0
- package/dist/__tests__/resolvers/dotenv.test.js +113 -0
- package/dist/__tests__/resolvers/dotenv.test.js.map +1 -0
- package/dist/__tests__/resolvers/improvements-v14.test.d.ts +8 -0
- package/dist/__tests__/resolvers/improvements-v14.test.d.ts.map +1 -0
- package/dist/__tests__/resolvers/improvements-v14.test.js +306 -0
- package/dist/__tests__/resolvers/improvements-v14.test.js.map +1 -0
- package/dist/__tests__/validation.test.d.ts +12 -0
- package/dist/__tests__/validation.test.d.ts.map +1 -0
- package/dist/__tests__/validation.test.js +136 -0
- package/dist/__tests__/validation.test.js.map +1 -0
- package/dist/classifier.d.ts +21 -0
- package/dist/classifier.d.ts.map +1 -0
- package/dist/classifier.js +127 -0
- package/dist/classifier.js.map +1 -0
- package/dist/config.d.ts +108 -0
- package/dist/config.d.ts.map +1 -0
- package/dist/config.js +200 -0
- package/dist/config.js.map +1 -0
- package/dist/diff.d.ts +69 -0
- package/dist/diff.d.ts.map +1 -0
- package/dist/diff.js +328 -0
- package/dist/diff.js.map +1 -0
- package/dist/index.d.ts +47 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +38 -0
- package/dist/index.js.map +1 -0
- package/dist/parser.d.ts +39 -0
- package/dist/parser.d.ts.map +1 -0
- package/dist/parser.js +164 -0
- package/dist/parser.js.map +1 -0
- package/dist/patterns/complex.d.ts +5 -0
- package/dist/patterns/complex.d.ts.map +1 -0
- package/dist/patterns/complex.js +27 -0
- package/dist/patterns/complex.js.map +1 -0
- package/dist/patterns/delete-no-change.d.ts +4 -0
- package/dist/patterns/delete-no-change.d.ts.map +1 -0
- package/dist/patterns/delete-no-change.js +75 -0
- package/dist/patterns/delete-no-change.js.map +1 -0
- package/dist/patterns/insertion-at-boundary.d.ts +22 -0
- package/dist/patterns/insertion-at-boundary.d.ts.map +1 -0
- package/dist/patterns/insertion-at-boundary.js +164 -0
- package/dist/patterns/insertion-at-boundary.js.map +1 -0
- package/dist/patterns/non-overlapping.d.ts +4 -0
- package/dist/patterns/non-overlapping.d.ts.map +1 -0
- package/dist/patterns/non-overlapping.js +28 -0
- package/dist/patterns/non-overlapping.js.map +1 -0
- package/dist/patterns/one-side-change.d.ts +4 -0
- package/dist/patterns/one-side-change.d.ts.map +1 -0
- package/dist/patterns/one-side-change.js +45 -0
- package/dist/patterns/one-side-change.js.map +1 -0
- package/dist/patterns/reorder-only.d.ts +14 -0
- package/dist/patterns/reorder-only.d.ts.map +1 -0
- package/dist/patterns/reorder-only.js +81 -0
- package/dist/patterns/reorder-only.js.map +1 -0
- package/dist/patterns/same-change.d.ts +4 -0
- package/dist/patterns/same-change.d.ts.map +1 -0
- package/dist/patterns/same-change.js +25 -0
- package/dist/patterns/same-change.js.map +1 -0
- package/dist/patterns/utils.d.ts +70 -0
- package/dist/patterns/utils.d.ts.map +1 -0
- package/dist/patterns/utils.js +206 -0
- package/dist/patterns/utils.js.map +1 -0
- package/dist/patterns/value-only-change.d.ts +4 -0
- package/dist/patterns/value-only-change.d.ts.map +1 -0
- package/dist/patterns/value-only-change.js +34 -0
- package/dist/patterns/value-only-change.js.map +1 -0
- package/dist/patterns/whitespace-only.d.ts +4 -0
- package/dist/patterns/whitespace-only.d.ts.map +1 -0
- package/dist/patterns/whitespace-only.js +32 -0
- package/dist/patterns/whitespace-only.js.map +1 -0
- package/dist/resolver/assemble.d.ts +25 -0
- package/dist/resolver/assemble.d.ts.map +1 -0
- package/dist/resolver/assemble.js +170 -0
- package/dist/resolver/assemble.js.map +1 -0
- package/dist/resolver/format-dispatch.d.ts +40 -0
- package/dist/resolver/format-dispatch.d.ts.map +1 -0
- package/dist/resolver/format-dispatch.js +51 -0
- package/dist/resolver/format-dispatch.js.map +1 -0
- package/dist/resolver/generated-detection.d.ts +48 -0
- package/dist/resolver/generated-detection.d.ts.map +1 -0
- package/dist/resolver/generated-detection.js +123 -0
- package/dist/resolver/generated-detection.js.map +1 -0
- package/dist/resolver/index.d.ts +26 -0
- package/dist/resolver/index.d.ts.map +1 -0
- package/dist/resolver/index.js +147 -0
- package/dist/resolver/index.js.map +1 -0
- package/dist/resolver/policy.d.ts +53 -0
- package/dist/resolver/policy.d.ts.map +1 -0
- package/dist/resolver/policy.js +99 -0
- package/dist/resolver/policy.js.map +1 -0
- package/dist/resolver/validation.d.ts +28 -0
- package/dist/resolver/validation.d.ts.map +1 -0
- package/dist/resolver/validation.js +96 -0
- package/dist/resolver/validation.js.map +1 -0
- package/dist/resolver.d.ts +18 -0
- package/dist/resolver.d.ts.map +1 -0
- package/dist/resolver.js +18 -0
- package/dist/resolver.js.map +1 -0
- package/dist/resolvers/cargo.d.ts +34 -0
- package/dist/resolvers/cargo.d.ts.map +1 -0
- package/dist/resolvers/cargo.js +262 -0
- package/dist/resolvers/cargo.js.map +1 -0
- package/dist/resolvers/css.d.ts +60 -0
- package/dist/resolvers/css.d.ts.map +1 -0
- package/dist/resolvers/css.js +531 -0
- package/dist/resolvers/css.js.map +1 -0
- package/dist/resolvers/dispatcher.d.ts +78 -0
- package/dist/resolvers/dispatcher.d.ts.map +1 -0
- package/dist/resolvers/dispatcher.js +290 -0
- package/dist/resolvers/dispatcher.js.map +1 -0
- package/dist/resolvers/dockerfile.d.ts +24 -0
- package/dist/resolvers/dockerfile.d.ts.map +1 -0
- package/dist/resolvers/dockerfile.js +221 -0
- package/dist/resolvers/dockerfile.js.map +1 -0
- package/dist/resolvers/dotenv.d.ts +27 -0
- package/dist/resolvers/dotenv.d.ts.map +1 -0
- package/dist/resolvers/dotenv.js +114 -0
- package/dist/resolvers/dotenv.js.map +1 -0
- package/dist/resolvers/imports.d.ts +63 -0
- package/dist/resolvers/imports.d.ts.map +1 -0
- package/dist/resolvers/imports.js +513 -0
- package/dist/resolvers/imports.js.map +1 -0
- package/dist/resolvers/json.d.ts +48 -0
- package/dist/resolvers/json.d.ts.map +1 -0
- package/dist/resolvers/json.js +363 -0
- package/dist/resolvers/json.js.map +1 -0
- package/dist/resolvers/lockfile-npm.d.ts +38 -0
- package/dist/resolvers/lockfile-npm.d.ts.map +1 -0
- package/dist/resolvers/lockfile-npm.js +267 -0
- package/dist/resolvers/lockfile-npm.js.map +1 -0
- package/dist/resolvers/lockfile-pnpm.d.ts +44 -0
- package/dist/resolvers/lockfile-pnpm.d.ts.map +1 -0
- package/dist/resolvers/lockfile-pnpm.js +277 -0
- package/dist/resolvers/lockfile-pnpm.js.map +1 -0
- package/dist/resolvers/lockfile-yarn.d.ts +40 -0
- package/dist/resolvers/lockfile-yarn.d.ts.map +1 -0
- package/dist/resolvers/lockfile-yarn.js +184 -0
- package/dist/resolvers/lockfile-yarn.js.map +1 -0
- package/dist/resolvers/markdown.d.ts +64 -0
- package/dist/resolvers/markdown.d.ts.map +1 -0
- package/dist/resolvers/markdown.js +335 -0
- package/dist/resolvers/markdown.js.map +1 -0
- package/dist/resolvers/vue.d.ts +65 -0
- package/dist/resolvers/vue.d.ts.map +1 -0
- package/dist/resolvers/vue.js +258 -0
- package/dist/resolvers/vue.js.map +1 -0
- package/dist/resolvers/yaml.d.ts +65 -0
- package/dist/resolvers/yaml.d.ts.map +1 -0
- package/dist/resolvers/yaml.js +405 -0
- package/dist/resolvers/yaml.js.map +1 -0
- package/dist/types.d.ts +256 -0
- package/dist/types.d.ts.map +1 -0
- package/dist/types.js +8 -0
- package/dist/types.js.map +1 -0
- package/package.json +57 -0
|
@@ -0,0 +1,70 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* GitWand — Utilitaires partagés entre les patterns
|
|
3
|
+
*
|
|
4
|
+
* Contient les fonctions de scoring, de normalisation et de détection
|
|
5
|
+
* de valeurs volatiles utilisées par plusieurs PatternPlugin.
|
|
6
|
+
*/
|
|
7
|
+
import type { Confidence, ConfidenceScore } from "../types.js";
|
|
8
|
+
/**
|
|
9
|
+
* Calcule le scopeImpact à partir du nombre total de lignes concernées.
|
|
10
|
+
* 1–2 lignes → 0, 3–10 → 15, 11–30 → 35, >30 → 55
|
|
11
|
+
*/
|
|
12
|
+
export declare function scopeImpact(lines: number): number;
|
|
13
|
+
/**
|
|
14
|
+
* Dérive le label Confidence depuis un score numérique 0–100.
|
|
15
|
+
* - score ≥ 92 → "certain"
|
|
16
|
+
* - score ≥ 68 → "high"
|
|
17
|
+
* - score ≥ 44 → "medium"
|
|
18
|
+
* - score < 44 → "low"
|
|
19
|
+
*/
|
|
20
|
+
export declare function labelFromScore(score: number): Confidence;
|
|
21
|
+
/**
|
|
22
|
+
* Construit un ConfidenceScore à partir des dimensions et des justifications.
|
|
23
|
+
*
|
|
24
|
+
* Formule v1.4 :
|
|
25
|
+
* `score = typeClassification
|
|
26
|
+
* − dataRisk × 0.40
|
|
27
|
+
* − scopeImpact × 0.15
|
|
28
|
+
* − fileFrequency × 0.10
|
|
29
|
+
* + baseAvailability × 0.05`
|
|
30
|
+
*
|
|
31
|
+
* `fileFrequency` et `baseAvailability` sont optionnels (défaut 0) pour
|
|
32
|
+
* la compatibilité ascendante avec les patterns existants.
|
|
33
|
+
*/
|
|
34
|
+
export declare function makeScore(typeClassification: number, dataRisk: number, si: number, boosters: string[], penalties: string[], fileFrequency?: number, baseAvailability?: number): ConfidenceScore;
|
|
35
|
+
/**
|
|
36
|
+
* Normalise les lignes d'un bloc pour la comparaison whitespace-only.
|
|
37
|
+
*
|
|
38
|
+
* Étapes :
|
|
39
|
+
* 1. Tabs → 2 espaces
|
|
40
|
+
* 2. Trim leading/trailing sur chaque ligne
|
|
41
|
+
* 3. Strip des lignes vides en tête et queue du bloc
|
|
42
|
+
* 4. Collapse des espaces internes multiples → un seul espace
|
|
43
|
+
*/
|
|
44
|
+
export declare function normalizeForWhitespaceCheck(lines: string[]): string;
|
|
45
|
+
/**
|
|
46
|
+
* Normalise une ligne individuelle pour les comparaisons de patterns
|
|
47
|
+
* (reorder_only, insertion_at_boundary).
|
|
48
|
+
* Tabs → espaces, trim, collapse.
|
|
49
|
+
*/
|
|
50
|
+
export declare function normalizeLine(line: string): string;
|
|
51
|
+
/** Regex qui matche les tokens "volatiles" : hashes, UUIDs, semver, timestamps, URLs */
|
|
52
|
+
export declare const VOLATILE_PATTERNS: RegExp[];
|
|
53
|
+
/**
|
|
54
|
+
* Vérifie si deux tokens diffèrent uniquement par une sous-chaîne "hash-like".
|
|
55
|
+
*/
|
|
56
|
+
export declare function isPairwiseVolatile(a: string, b: string): boolean;
|
|
57
|
+
/**
|
|
58
|
+
* Tokenize une ligne en parties structurelles et valeurs.
|
|
59
|
+
*/
|
|
60
|
+
export declare function tokenizeLine(line: string): string[];
|
|
61
|
+
/**
|
|
62
|
+
* Détecte si deux ensembles de lignes ne diffèrent que par des valeurs atomiques.
|
|
63
|
+
* Retourne un résultat de classification ou null si non applicable.
|
|
64
|
+
*/
|
|
65
|
+
export declare function detectValueOnlyChange(oursLines: string[], theirsLines: string[]): {
|
|
66
|
+
confidenceScore: ConfidenceScore;
|
|
67
|
+
explanation: string;
|
|
68
|
+
traceReason: string;
|
|
69
|
+
} | null;
|
|
70
|
+
//# sourceMappingURL=utils.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"utils.d.ts","sourceRoot":"","sources":["../../src/patterns/utils.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH,OAAO,KAAK,EAAE,UAAU,EAAE,eAAe,EAAE,MAAM,aAAa,CAAC;AAI/D;;;GAGG;AACH,wBAAgB,WAAW,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM,CAKjD;AAED;;;;;;GAMG;AACH,wBAAgB,cAAc,CAAC,KAAK,EAAE,MAAM,GAAG,UAAU,CAKxD;AAED;;;;;;;;;;;;GAYG;AACH,wBAAgB,SAAS,CACvB,kBAAkB,EAAE,MAAM,EAC1B,QAAQ,EAAE,MAAM,EAChB,EAAE,EAAE,MAAM,EACV,QAAQ,EAAE,MAAM,EAAE,EAClB,SAAS,EAAE,MAAM,EAAE,EACnB,aAAa,SAAI,EACjB,gBAAgB,SAAI,GACnB,eAAe,CAejB;AAID;;;;;;;;GAQG;AACH,wBAAgB,2BAA2B,CAAC,KAAK,EAAE,MAAM,EAAE,GAAG,MAAM,CAOnE;AAED;;;;GAIG;AACH,wBAAgB,aAAa,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CAElD;AAID,wFAAwF;AACxF,eAAO,MAAM,iBAAiB,UAQ7B,CAAC;AAEF;;GAEG;AACH,wBAAgB,kBAAkB,CAAC,CAAC,EAAE,MAAM,EAAE,CAAC,EAAE,MAAM,GAAG,OAAO,CAqChE;AAED;;GAEG;AACH,wBAAgB,YAAY,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,EAAE,CAEnD;AAED;;;GAGG;AACH,wBAAgB,qBAAqB,CACnC,SAAS,EAAE,MAAM,EAAE,EACnB,WAAW,EAAE,MAAM,EAAE,GACpB;IAAE,eAAe,EAAE,eAAe,CAAC;IAAC,WAAW,EAAE,MAAM,CAAC;IAAC,WAAW,EAAE,MAAM,CAAA;CAAE,GAAG,IAAI,CAiEvF"}
|
|
@@ -0,0 +1,206 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* GitWand — Utilitaires partagés entre les patterns
|
|
3
|
+
*
|
|
4
|
+
* Contient les fonctions de scoring, de normalisation et de détection
|
|
5
|
+
* de valeurs volatiles utilisées par plusieurs PatternPlugin.
|
|
6
|
+
*/
|
|
7
|
+
// ─── Scoring ─────────────────────────────────────────────────
|
|
8
|
+
/**
|
|
9
|
+
* Calcule le scopeImpact à partir du nombre total de lignes concernées.
|
|
10
|
+
* 1–2 lignes → 0, 3–10 → 15, 11–30 → 35, >30 → 55
|
|
11
|
+
*/
|
|
12
|
+
export function scopeImpact(lines) {
|
|
13
|
+
if (lines <= 2)
|
|
14
|
+
return 0;
|
|
15
|
+
if (lines <= 10)
|
|
16
|
+
return 15;
|
|
17
|
+
if (lines <= 30)
|
|
18
|
+
return 35;
|
|
19
|
+
return 55;
|
|
20
|
+
}
|
|
21
|
+
/**
|
|
22
|
+
* Dérive le label Confidence depuis un score numérique 0–100.
|
|
23
|
+
* - score ≥ 92 → "certain"
|
|
24
|
+
* - score ≥ 68 → "high"
|
|
25
|
+
* - score ≥ 44 → "medium"
|
|
26
|
+
* - score < 44 → "low"
|
|
27
|
+
*/
|
|
28
|
+
export function labelFromScore(score) {
|
|
29
|
+
if (score >= 92)
|
|
30
|
+
return "certain";
|
|
31
|
+
if (score >= 68)
|
|
32
|
+
return "high";
|
|
33
|
+
if (score >= 44)
|
|
34
|
+
return "medium";
|
|
35
|
+
return "low";
|
|
36
|
+
}
|
|
37
|
+
/**
|
|
38
|
+
* Construit un ConfidenceScore à partir des dimensions et des justifications.
|
|
39
|
+
*
|
|
40
|
+
* Formule v1.4 :
|
|
41
|
+
* `score = typeClassification
|
|
42
|
+
* − dataRisk × 0.40
|
|
43
|
+
* − scopeImpact × 0.15
|
|
44
|
+
* − fileFrequency × 0.10
|
|
45
|
+
* + baseAvailability × 0.05`
|
|
46
|
+
*
|
|
47
|
+
* `fileFrequency` et `baseAvailability` sont optionnels (défaut 0) pour
|
|
48
|
+
* la compatibilité ascendante avec les patterns existants.
|
|
49
|
+
*/
|
|
50
|
+
export function makeScore(typeClassification, dataRisk, si, boosters, penalties, fileFrequency = 0, baseAvailability = 0) {
|
|
51
|
+
const raw = typeClassification
|
|
52
|
+
- dataRisk * 0.40
|
|
53
|
+
- si * 0.15
|
|
54
|
+
- fileFrequency * 0.10
|
|
55
|
+
+ baseAvailability * 0.05;
|
|
56
|
+
const score = Math.round(Math.max(0, Math.min(100, raw)));
|
|
57
|
+
return {
|
|
58
|
+
score,
|
|
59
|
+
label: labelFromScore(score),
|
|
60
|
+
dimensions: { typeClassification, dataRisk, scopeImpact: si, fileFrequency, baseAvailability },
|
|
61
|
+
boosters,
|
|
62
|
+
penalties,
|
|
63
|
+
};
|
|
64
|
+
}
|
|
65
|
+
// ─── Normalisation whitespace ─────────────────────────────────
|
|
66
|
+
/**
|
|
67
|
+
* Normalise les lignes d'un bloc pour la comparaison whitespace-only.
|
|
68
|
+
*
|
|
69
|
+
* Étapes :
|
|
70
|
+
* 1. Tabs → 2 espaces
|
|
71
|
+
* 2. Trim leading/trailing sur chaque ligne
|
|
72
|
+
* 3. Strip des lignes vides en tête et queue du bloc
|
|
73
|
+
* 4. Collapse des espaces internes multiples → un seul espace
|
|
74
|
+
*/
|
|
75
|
+
export function normalizeForWhitespaceCheck(lines) {
|
|
76
|
+
let normalized = lines.map((l) => l.replace(/\t/g, " "));
|
|
77
|
+
normalized = normalized.map((l) => l.trim());
|
|
78
|
+
while (normalized.length > 0 && normalized[0] === "")
|
|
79
|
+
normalized.shift();
|
|
80
|
+
while (normalized.length > 0 && normalized[normalized.length - 1] === "")
|
|
81
|
+
normalized.pop();
|
|
82
|
+
normalized = normalized.map((l) => l.replace(/ +/g, " "));
|
|
83
|
+
return normalized.join("\n");
|
|
84
|
+
}
|
|
85
|
+
/**
|
|
86
|
+
* Normalise une ligne individuelle pour les comparaisons de patterns
|
|
87
|
+
* (reorder_only, insertion_at_boundary).
|
|
88
|
+
* Tabs → espaces, trim, collapse.
|
|
89
|
+
*/
|
|
90
|
+
export function normalizeLine(line) {
|
|
91
|
+
return line.replace(/\t/g, " ").trim().replace(/ +/g, " ");
|
|
92
|
+
}
|
|
93
|
+
// ─── Détection de valeurs volatiles ──────────────────────────
|
|
94
|
+
/** Regex qui matche les tokens "volatiles" : hashes, UUIDs, semver, timestamps, URLs */
|
|
95
|
+
export const VOLATILE_PATTERNS = [
|
|
96
|
+
/^[a-f0-9]{7,64}$/,
|
|
97
|
+
/^[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}$/,
|
|
98
|
+
/^(?=.*[A-Z])(?=.*[a-z])(?=.*\d)[A-Za-z\d]{6,20}$/,
|
|
99
|
+
/^[~^>=<]*\d+\.\d+\.\d+(-[\w.]+)?(\+[\w.]+)?$/,
|
|
100
|
+
/^\d{4}-\d{2}-\d{2}[T\s]\d{2}:\d{2}(:\d{2})?([Z+\-]\S*)?$/,
|
|
101
|
+
/^(https?:)?\/\/\S+$/,
|
|
102
|
+
/^[a-z][a-z0-9]{1,9}-[A-Za-z0-9+/=]{8,}$/,
|
|
103
|
+
];
|
|
104
|
+
/**
|
|
105
|
+
* Vérifie si deux tokens diffèrent uniquement par une sous-chaîne "hash-like".
|
|
106
|
+
*/
|
|
107
|
+
export function isPairwiseVolatile(a, b) {
|
|
108
|
+
if (a === b)
|
|
109
|
+
return false;
|
|
110
|
+
let prefixLen = 0;
|
|
111
|
+
while (prefixLen < a.length && prefixLen < b.length && a[prefixLen] === b[prefixLen]) {
|
|
112
|
+
prefixLen++;
|
|
113
|
+
}
|
|
114
|
+
let suffixLen = 0;
|
|
115
|
+
const aRem = a.length - prefixLen;
|
|
116
|
+
const bRem = b.length - prefixLen;
|
|
117
|
+
while (suffixLen < aRem &&
|
|
118
|
+
suffixLen < bRem &&
|
|
119
|
+
a[a.length - 1 - suffixLen] === b[b.length - 1 - suffixLen]) {
|
|
120
|
+
suffixLen++;
|
|
121
|
+
}
|
|
122
|
+
if (prefixLen + suffixLen === 0)
|
|
123
|
+
return false;
|
|
124
|
+
const aMid = a.slice(prefixLen, suffixLen > 0 ? a.length - suffixLen : undefined);
|
|
125
|
+
const bMid = b.slice(prefixLen, suffixLen > 0 ? b.length - suffixLen : undefined);
|
|
126
|
+
if (aMid.length === 0 || bMid.length === 0)
|
|
127
|
+
return false;
|
|
128
|
+
const isHashLikeMid = (s) => {
|
|
129
|
+
if (VOLATILE_PATTERNS.some((p) => p.test(s)))
|
|
130
|
+
return true;
|
|
131
|
+
if (s.length >= 7 && /^[A-Za-z\d]+$/.test(s)) {
|
|
132
|
+
const upper = (s.match(/[A-Z]/g) ?? []).length;
|
|
133
|
+
const lower = (s.match(/[a-z]/g) ?? []).length;
|
|
134
|
+
if (upper >= 2 && lower >= 2)
|
|
135
|
+
return true;
|
|
136
|
+
}
|
|
137
|
+
return false;
|
|
138
|
+
};
|
|
139
|
+
return isHashLikeMid(aMid) && isHashLikeMid(bMid);
|
|
140
|
+
}
|
|
141
|
+
/**
|
|
142
|
+
* Tokenize une ligne en parties structurelles et valeurs.
|
|
143
|
+
*/
|
|
144
|
+
export function tokenizeLine(line) {
|
|
145
|
+
return line.split(/(\s+|[{}[\](),:;"'`=<>])/);
|
|
146
|
+
}
|
|
147
|
+
/**
|
|
148
|
+
* Détecte si deux ensembles de lignes ne diffèrent que par des valeurs atomiques.
|
|
149
|
+
* Retourne un résultat de classification ou null si non applicable.
|
|
150
|
+
*/
|
|
151
|
+
export function detectValueOnlyChange(oursLines, theirsLines) {
|
|
152
|
+
if (oursLines.length !== theirsLines.length)
|
|
153
|
+
return null;
|
|
154
|
+
if (oursLines.length === 0)
|
|
155
|
+
return null;
|
|
156
|
+
let diffCount = 0;
|
|
157
|
+
let totalTokens = 0;
|
|
158
|
+
let allDiffsAreVolatile = true;
|
|
159
|
+
for (let i = 0; i < oursLines.length; i++) {
|
|
160
|
+
const oursTokens = tokenizeLine(oursLines[i]);
|
|
161
|
+
const theirsTokens = tokenizeLine(theirsLines[i]);
|
|
162
|
+
if (oursTokens.length !== theirsTokens.length) {
|
|
163
|
+
allDiffsAreVolatile = false;
|
|
164
|
+
break;
|
|
165
|
+
}
|
|
166
|
+
totalTokens += oursTokens.length;
|
|
167
|
+
for (let j = 0; j < oursTokens.length; j++) {
|
|
168
|
+
if (oursTokens[j] !== theirsTokens[j]) {
|
|
169
|
+
diffCount++;
|
|
170
|
+
const isOursVolatile = VOLATILE_PATTERNS.some((p) => p.test(oursTokens[j]));
|
|
171
|
+
const isTheirsVolatile = VOLATILE_PATTERNS.some((p) => p.test(theirsTokens[j]));
|
|
172
|
+
if (!isOursVolatile && !isTheirsVolatile) {
|
|
173
|
+
if (!isPairwiseVolatile(oursTokens[j], theirsTokens[j])) {
|
|
174
|
+
allDiffsAreVolatile = false;
|
|
175
|
+
break;
|
|
176
|
+
}
|
|
177
|
+
}
|
|
178
|
+
}
|
|
179
|
+
}
|
|
180
|
+
if (!allDiffsAreVolatile)
|
|
181
|
+
break;
|
|
182
|
+
}
|
|
183
|
+
if (!allDiffsAreVolatile || diffCount === 0)
|
|
184
|
+
return null;
|
|
185
|
+
const diffRatio = diffCount / Math.max(totalTokens, 1);
|
|
186
|
+
const typeClassification = diffRatio <= 0.10 ? 88
|
|
187
|
+
: diffRatio <= 0.20 ? 72
|
|
188
|
+
: diffRatio <= 0.30 ? 55
|
|
189
|
+
: 0;
|
|
190
|
+
if (typeClassification < 55)
|
|
191
|
+
return null;
|
|
192
|
+
const si = scopeImpact(oursLines.length);
|
|
193
|
+
const confidenceScore = makeScore(typeClassification, 25, si, [
|
|
194
|
+
`${diffCount} token${diffCount > 1 ? "s" : ""} identifié${diffCount > 1 ? "s" : ""} comme volatile${diffCount > 1 ? "s" : ""} (hash, version, timestamp…)`,
|
|
195
|
+
"Même structure de lignes",
|
|
196
|
+
], [
|
|
197
|
+
`Ratio de différences : ${(diffRatio * 100).toFixed(1)}%`,
|
|
198
|
+
"Sans base (diff2) — heuristique basée sur les patterns volatils",
|
|
199
|
+
]);
|
|
200
|
+
if (confidenceScore.label === "low")
|
|
201
|
+
return null;
|
|
202
|
+
const explanation = `Même structure avec ${diffCount} valeur${diffCount > 1 ? "s" : ""} volatile${diffCount > 1 ? "s" : ""} différente${diffCount > 1 ? "s" : ""} (hash, version, timestamp…). Résolution proposée : accepter la version la plus récente (theirs).`;
|
|
203
|
+
const traceReason = `${diffCount} token${diffCount > 1 ? "s" : ""} différent${diffCount > 1 ? "s" : ""} sur ${totalTokens} — tous identifiés comme volatiles (hash, version, timestamp…). Ratio : ${(diffRatio * 100).toFixed(1)}% → score ${confidenceScore.score} (${confidenceScore.label}).`;
|
|
204
|
+
return { confidenceScore, explanation, traceReason };
|
|
205
|
+
}
|
|
206
|
+
//# sourceMappingURL=utils.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"utils.js","sourceRoot":"","sources":["../../src/patterns/utils.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"value-only-change.d.ts","sourceRoot":"","sources":["../../src/patterns/value-only-change.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAkC,aAAa,EAAE,MAAM,aAAa,CAAC;AAGjF,QAAA,MAAM,eAAe,EAAE,aAiCtB,CAAC;AAEF,eAAe,eAAe,CAAC"}
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
import { makeScore, detectValueOnlyChange } from "./utils.js";
|
|
2
|
+
const valueOnlyChange = {
|
|
3
|
+
type: "value_only_change",
|
|
4
|
+
priority: 60,
|
|
5
|
+
requires: "diff2",
|
|
6
|
+
detect(h) {
|
|
7
|
+
if (h.oursLines.length !== h.theirsLines.length)
|
|
8
|
+
return false;
|
|
9
|
+
return detectValueOnlyChange(h.oursLines, h.theirsLines) !== null;
|
|
10
|
+
},
|
|
11
|
+
confidence(h) {
|
|
12
|
+
const result = detectValueOnlyChange(h.oursLines, h.theirsLines);
|
|
13
|
+
if (result)
|
|
14
|
+
return result.confidenceScore;
|
|
15
|
+
// Fallback (ne devrait pas être appelé si detect() retourne false)
|
|
16
|
+
return makeScore(0, 100, 0, [], ["Erreur interne : confidence() appelé sans match"]);
|
|
17
|
+
},
|
|
18
|
+
explanation(h) {
|
|
19
|
+
const result = detectValueOnlyChange(h.oursLines, h.theirsLines);
|
|
20
|
+
return result?.explanation ?? "Valeurs volatiles différentes.";
|
|
21
|
+
},
|
|
22
|
+
passReason(h) {
|
|
23
|
+
const result = detectValueOnlyChange(h.oursLines, h.theirsLines);
|
|
24
|
+
return result?.traceReason ?? "Valeurs atomiques identifiées comme volatiles.";
|
|
25
|
+
},
|
|
26
|
+
failReason(h) {
|
|
27
|
+
if (h.oursLines.length !== h.theirsLines.length) {
|
|
28
|
+
return "Ours et theirs n'ont pas le même nombre de lignes — structure différente.";
|
|
29
|
+
}
|
|
30
|
+
return "Les différences entre ours et theirs ne se limitent pas à des valeurs volatiles (hash, version, timestamp…).";
|
|
31
|
+
},
|
|
32
|
+
};
|
|
33
|
+
export default valueOnlyChange;
|
|
34
|
+
//# sourceMappingURL=value-only-change.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"value-only-change.js","sourceRoot":"","sources":["../../src/patterns/value-only-change.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,SAAS,EAAE,qBAAqB,EAAE,MAAM,YAAY,CAAC;AAE9D,MAAM,eAAe,GAAkB;IACrC,IAAI,EAAE,mBAAmB;IACzB,QAAQ,EAAE,EAAE;IACZ,QAAQ,EAAE,OAAO;IAEjB,MAAM,CAAC,CAAgB;QACrB,IAAI,CAAC,CAAC,SAAS,CAAC,MAAM,KAAK,CAAC,CAAC,WAAW,CAAC,MAAM;YAAE,OAAO,KAAK,CAAC;QAC9D,OAAO,qBAAqB,CAAC,CAAC,CAAC,SAAS,EAAE,CAAC,CAAC,WAAW,CAAC,KAAK,IAAI,CAAC;IACpE,CAAC;IAED,UAAU,CAAC,CAAgB;QACzB,MAAM,MAAM,GAAG,qBAAqB,CAAC,CAAC,CAAC,SAAS,EAAE,CAAC,CAAC,WAAW,CAAC,CAAC;QACjE,IAAI,MAAM;YAAE,OAAO,MAAM,CAAC,eAAe,CAAC;QAC1C,mEAAmE;QACnE,OAAO,SAAS,CAAC,CAAC,EAAE,GAAG,EAAE,CAAC,EAAE,EAAE,EAAE,CAAC,iDAAiD,CAAC,CAAC,CAAC;IACvF,CAAC;IAED,WAAW,CAAC,CAAgB;QAC1B,MAAM,MAAM,GAAG,qBAAqB,CAAC,CAAC,CAAC,SAAS,EAAE,CAAC,CAAC,WAAW,CAAC,CAAC;QACjE,OAAO,MAAM,EAAE,WAAW,IAAI,gCAAgC,CAAC;IACjE,CAAC;IAED,UAAU,CAAC,CAAgB;QACzB,MAAM,MAAM,GAAG,qBAAqB,CAAC,CAAC,CAAC,SAAS,EAAE,CAAC,CAAC,WAAW,CAAC,CAAC;QACjE,OAAO,MAAM,EAAE,WAAW,IAAI,gDAAgD,CAAC;IACjF,CAAC;IAED,UAAU,CAAC,CAAgB;QACzB,IAAI,CAAC,CAAC,SAAS,CAAC,MAAM,KAAK,CAAC,CAAC,WAAW,CAAC,MAAM,EAAE,CAAC;YAChD,OAAO,2EAA2E,CAAC;QACrF,CAAC;QACD,OAAO,8GAA8G,CAAC;IACxH,CAAC;CACF,CAAC;AAEF,eAAe,eAAe,CAAC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"whitespace-only.d.ts","sourceRoot":"","sources":["../../src/patterns/whitespace-only.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAkC,aAAa,EAAE,MAAM,aAAa,CAAC;AAGjF,QAAA,MAAM,cAAc,EAAE,aAuCrB,CAAC;AAEF,eAAe,cAAc,CAAC"}
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
import { scopeImpact, makeScore, normalizeForWhitespaceCheck } from "./utils.js";
|
|
2
|
+
const whitespaceOnly = {
|
|
3
|
+
type: "whitespace_only",
|
|
4
|
+
priority: 50,
|
|
5
|
+
requires: "both",
|
|
6
|
+
detect(h) {
|
|
7
|
+
const oursNorm = normalizeForWhitespaceCheck(h.oursLines);
|
|
8
|
+
const theirsNorm = normalizeForWhitespaceCheck(h.theirsLines);
|
|
9
|
+
return oursNorm === theirsNorm;
|
|
10
|
+
},
|
|
11
|
+
confidence(h) {
|
|
12
|
+
const hasBase = h.baseLines.length > 0;
|
|
13
|
+
const lines = Math.max(h.oursLines.length, h.theirsLines.length);
|
|
14
|
+
return makeScore(hasBase ? 95 : 80, 10, scopeImpact(lines), hasBase
|
|
15
|
+
? [
|
|
16
|
+
"Base disponible — whitespace confirmé par rapport à l'ancêtre",
|
|
17
|
+
"Seul le whitespace diffère après normalisation",
|
|
18
|
+
]
|
|
19
|
+
: ["Seul le whitespace diffère après normalisation (trim)"], hasBase ? [] : ["Sans base (diff2) — hypothèse basée sur la normalisation uniquement"]);
|
|
20
|
+
},
|
|
21
|
+
explanation(_h) {
|
|
22
|
+
return "Les deux branches contiennent le même code avec des différences de whitespace uniquement.";
|
|
23
|
+
},
|
|
24
|
+
passReason(_h) {
|
|
25
|
+
return "Après normalisation (trim), les deux versions sont identiques — seul le whitespace diffère.";
|
|
26
|
+
},
|
|
27
|
+
failReason(_h) {
|
|
28
|
+
return "Après normalisation (trim), les deux versions restent différentes — pas seulement du whitespace.";
|
|
29
|
+
},
|
|
30
|
+
};
|
|
31
|
+
export default whitespaceOnly;
|
|
32
|
+
//# sourceMappingURL=whitespace-only.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"whitespace-only.js","sourceRoot":"","sources":["../../src/patterns/whitespace-only.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,WAAW,EAAE,SAAS,EAAE,2BAA2B,EAAE,MAAM,YAAY,CAAC;AAEjF,MAAM,cAAc,GAAkB;IACpC,IAAI,EAAE,iBAAiB;IACvB,QAAQ,EAAE,EAAE;IACZ,QAAQ,EAAE,MAAM;IAEhB,MAAM,CAAC,CAAgB;QACrB,MAAM,QAAQ,GAAG,2BAA2B,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC;QAC1D,MAAM,UAAU,GAAG,2BAA2B,CAAC,CAAC,CAAC,WAAW,CAAC,CAAC;QAC9D,OAAO,QAAQ,KAAK,UAAU,CAAC;IACjC,CAAC;IAED,UAAU,CAAC,CAAgB;QACzB,MAAM,OAAO,GAAG,CAAC,CAAC,SAAS,CAAC,MAAM,GAAG,CAAC,CAAC;QACvC,MAAM,KAAK,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,SAAS,CAAC,MAAM,EAAE,CAAC,CAAC,WAAW,CAAC,MAAM,CAAC,CAAC;QACjE,OAAO,SAAS,CACd,OAAO,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,EACjB,EAAE,EACF,WAAW,CAAC,KAAK,CAAC,EAClB,OAAO;YACL,CAAC,CAAC;gBACE,+DAA+D;gBAC/D,gDAAgD;aACjD;YACH,CAAC,CAAC,CAAC,uDAAuD,CAAC,EAC7D,OAAO,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,qEAAqE,CAAC,CACvF,CAAC;IACJ,CAAC;IAED,WAAW,CAAC,EAAiB;QAC3B,OAAO,2FAA2F,CAAC;IACrG,CAAC;IAED,UAAU,CAAC,EAAiB;QAC1B,OAAO,6FAA6F,CAAC;IACvG,CAAC;IAED,UAAU,CAAC,EAAiB;QAC1B,OAAO,kGAAkG,CAAC;IAC5G,CAAC;CACF,CAAC;AAEF,eAAe,cAAc,CAAC"}
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Moteur textuel d'assemblage — switch par type de conflit.
|
|
3
|
+
*
|
|
4
|
+
* Appelé par `resolveHunk` après que :
|
|
5
|
+
* 1. le mode `explainOnly` ait été écarté,
|
|
6
|
+
* 2. le dispatch format-aware ait échoué (ou ne s'applique pas),
|
|
7
|
+
* 3. le seuil de confiance effectif ait été validé.
|
|
8
|
+
*
|
|
9
|
+
* Chaque `case` produit soit un tableau de lignes résolues, soit `null` avec
|
|
10
|
+
* une raison de refus. La stratégie par type est documentée individuellement.
|
|
11
|
+
*
|
|
12
|
+
* Extrait de `resolver.ts` lors du split P1.1.
|
|
13
|
+
*/
|
|
14
|
+
import type { ConflictHunk, GitWandOptions } from "../types.js";
|
|
15
|
+
import type { MergePolicy, PolicyConfig } from "../config.js";
|
|
16
|
+
/**
|
|
17
|
+
* Applique la stratégie textuelle correspondant au type de hunk.
|
|
18
|
+
* Les vérifications amont (explainOnly, format-dispatch, minConfidence)
|
|
19
|
+
* sont supposées déjà faites par l'appelant.
|
|
20
|
+
*/
|
|
21
|
+
export declare function assembleResolution(hunk: ConflictHunk, options: Required<GitWandOptions>, effectivePolicy: MergePolicy, policyCfg: PolicyConfig): {
|
|
22
|
+
lines: string[] | null;
|
|
23
|
+
reason: string;
|
|
24
|
+
};
|
|
25
|
+
//# sourceMappingURL=assemble.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"assemble.d.ts","sourceRoot":"","sources":["../../src/resolver/assemble.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;AAEH,OAAO,KAAK,EAAE,YAAY,EAAE,cAAc,EAAE,MAAM,aAAa,CAAC;AAChE,OAAO,KAAK,EAAE,WAAW,EAAE,YAAY,EAAE,MAAM,cAAc,CAAC;AAI9D;;;;GAIG;AACH,wBAAgB,kBAAkB,CAChC,IAAI,EAAE,YAAY,EAClB,OAAO,EAAE,QAAQ,CAAC,cAAc,CAAC,EACjC,eAAe,EAAE,WAAW,EAC5B,SAAS,EAAE,YAAY,GACtB;IAAE,KAAK,EAAE,MAAM,EAAE,GAAG,IAAI,CAAC;IAAC,MAAM,EAAE,MAAM,CAAA;CAAE,CAiK5C"}
|
|
@@ -0,0 +1,170 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Moteur textuel d'assemblage — switch par type de conflit.
|
|
3
|
+
*
|
|
4
|
+
* Appelé par `resolveHunk` après que :
|
|
5
|
+
* 1. le mode `explainOnly` ait été écarté,
|
|
6
|
+
* 2. le dispatch format-aware ait échoué (ou ne s'applique pas),
|
|
7
|
+
* 3. le seuil de confiance effectif ait été validé.
|
|
8
|
+
*
|
|
9
|
+
* Chaque `case` produit soit un tableau de lignes résolues, soit `null` avec
|
|
10
|
+
* une raison de refus. La stratégie par type est documentée individuellement.
|
|
11
|
+
*
|
|
12
|
+
* Extrait de `resolver.ts` lors du split P1.1.
|
|
13
|
+
*/
|
|
14
|
+
import { mergeNonOverlapping } from "../diff.js";
|
|
15
|
+
import { stripVolatileValues } from "./generated-detection.js";
|
|
16
|
+
/**
|
|
17
|
+
* Applique la stratégie textuelle correspondant au type de hunk.
|
|
18
|
+
* Les vérifications amont (explainOnly, format-dispatch, minConfidence)
|
|
19
|
+
* sont supposées déjà faites par l'appelant.
|
|
20
|
+
*/
|
|
21
|
+
export function assembleResolution(hunk, options, effectivePolicy, policyCfg) {
|
|
22
|
+
switch (hunk.type) {
|
|
23
|
+
case "same_change":
|
|
24
|
+
return {
|
|
25
|
+
lines: [...hunk.oursLines],
|
|
26
|
+
reason: "Même modification des deux côtés — résolution triviale (ours = theirs).",
|
|
27
|
+
};
|
|
28
|
+
case "one_side_change": {
|
|
29
|
+
const baseText = hunk.baseLines.join("\n");
|
|
30
|
+
const oursText = hunk.oursLines.join("\n");
|
|
31
|
+
if (oursText === baseText) {
|
|
32
|
+
return {
|
|
33
|
+
lines: [...hunk.theirsLines],
|
|
34
|
+
reason: "Ours = base → seul theirs a changé. Résolution : accepter theirs.",
|
|
35
|
+
};
|
|
36
|
+
}
|
|
37
|
+
else {
|
|
38
|
+
return {
|
|
39
|
+
lines: [...hunk.oursLines],
|
|
40
|
+
reason: "Theirs = base → seul ours a changé. Résolution : accepter ours.",
|
|
41
|
+
};
|
|
42
|
+
}
|
|
43
|
+
}
|
|
44
|
+
case "delete_no_change":
|
|
45
|
+
return {
|
|
46
|
+
lines: [],
|
|
47
|
+
reason: "Un côté a supprimé le bloc, l'autre n'a pas touché. Résolution : supprimer (0 lignes).",
|
|
48
|
+
};
|
|
49
|
+
case "reorder_only": {
|
|
50
|
+
// Résolution : accepter theirs (intent de réordonnancement le plus récent).
|
|
51
|
+
// Exception : si la base est disponible et que son ordre correspond à theirs,
|
|
52
|
+
// c'est ours qui a réordonné → accepter ours.
|
|
53
|
+
const hasBase = hunk.baseLines.length > 0;
|
|
54
|
+
let preferred;
|
|
55
|
+
let side;
|
|
56
|
+
if (hasBase && hunk.baseLines.join("\n") === hunk.theirsLines.join("\n")) {
|
|
57
|
+
preferred = [...hunk.oursLines];
|
|
58
|
+
side = "ours";
|
|
59
|
+
}
|
|
60
|
+
else {
|
|
61
|
+
preferred = [...hunk.theirsLines];
|
|
62
|
+
side = "theirs";
|
|
63
|
+
}
|
|
64
|
+
return {
|
|
65
|
+
lines: preferred,
|
|
66
|
+
reason: `Permutation pure — mêmes lignes, ordre différent. Résolution : accepter ${side}.`,
|
|
67
|
+
};
|
|
68
|
+
}
|
|
69
|
+
case "insertion_at_boundary": {
|
|
70
|
+
// Résolution : base + insertions ours + insertions theirs (diff3)
|
|
71
|
+
// ou ours + lignes de theirs absentes de ours (diff2)
|
|
72
|
+
const hasBase = hunk.baseLines.length > 0;
|
|
73
|
+
let merged;
|
|
74
|
+
if (hasBase) {
|
|
75
|
+
// Trouver les lignes ajoutées par chaque côté via inclusion dans l'ensemble de base
|
|
76
|
+
const baseSet = new Set(hunk.baseLines);
|
|
77
|
+
const oursInsertions = hunk.oursLines.filter((l) => !baseSet.has(l));
|
|
78
|
+
const theirsInsertions = hunk.theirsLines.filter((l) => !baseSet.has(l));
|
|
79
|
+
merged = [...hunk.baseLines, ...oursInsertions, ...theirsInsertions];
|
|
80
|
+
}
|
|
81
|
+
else {
|
|
82
|
+
// Heuristique diff2 : union (ours ordre préservé, on ajoute ce qui manque de theirs)
|
|
83
|
+
const oursSet = new Set(hunk.oursLines);
|
|
84
|
+
const theirsOnly = hunk.theirsLines.filter((l) => !oursSet.has(l));
|
|
85
|
+
merged = [...hunk.oursLines, ...theirsOnly];
|
|
86
|
+
}
|
|
87
|
+
return {
|
|
88
|
+
lines: merged,
|
|
89
|
+
reason: `Insertions pures — union des ${hasBase ? "insertions (base + ours + theirs)" : "lignes (heuristique diff2)"}. ${merged.length} lignes dans le résultat.`,
|
|
90
|
+
};
|
|
91
|
+
}
|
|
92
|
+
case "whitespace_only": {
|
|
93
|
+
if (!options.resolveWhitespace || !policyCfg.allowWhitespace) {
|
|
94
|
+
return {
|
|
95
|
+
lines: null,
|
|
96
|
+
reason: !policyCfg.allowWhitespace
|
|
97
|
+
? `Résolution whitespace désactivée par la politique "${effectivePolicy}".`
|
|
98
|
+
: "Résolution whitespace désactivée par options (resolveWhitespace: false).",
|
|
99
|
+
};
|
|
100
|
+
}
|
|
101
|
+
const wsSide = policyCfg.preferOurs ? "ours" : "theirs";
|
|
102
|
+
return {
|
|
103
|
+
lines: policyCfg.preferOurs ? [...hunk.oursLines] : [...hunk.theirsLines],
|
|
104
|
+
reason: `Seul le whitespace diffère. Résolution : préférer ${wsSide} (politique : ${effectivePolicy}).`,
|
|
105
|
+
};
|
|
106
|
+
}
|
|
107
|
+
case "non_overlapping": {
|
|
108
|
+
if (!options.resolveNonOverlapping || !policyCfg.allowNonOverlapping) {
|
|
109
|
+
return {
|
|
110
|
+
lines: null,
|
|
111
|
+
reason: !policyCfg.allowNonOverlapping
|
|
112
|
+
? `Résolution non-overlapping désactivée par la politique "${effectivePolicy}".`
|
|
113
|
+
: "Résolution non-overlapping désactivée par options (resolveNonOverlapping: false).",
|
|
114
|
+
};
|
|
115
|
+
}
|
|
116
|
+
const merged = mergeNonOverlapping(hunk.baseLines, hunk.oursLines, hunk.theirsLines);
|
|
117
|
+
if (merged !== null) {
|
|
118
|
+
return {
|
|
119
|
+
lines: merged,
|
|
120
|
+
reason: `Merge LCS 3-way réussi — ${merged.length} lignes dans le résultat fusionné.`,
|
|
121
|
+
};
|
|
122
|
+
}
|
|
123
|
+
return {
|
|
124
|
+
lines: null,
|
|
125
|
+
reason: "Le merge LCS 3-way a échoué (chevauchement détecté au moment de la résolution).",
|
|
126
|
+
};
|
|
127
|
+
}
|
|
128
|
+
case "value_only_change": {
|
|
129
|
+
if (!policyCfg.allowValueOnly) {
|
|
130
|
+
return {
|
|
131
|
+
lines: null,
|
|
132
|
+
reason: `Résolution value_only_change désactivée par la politique "${effectivePolicy}".`,
|
|
133
|
+
};
|
|
134
|
+
}
|
|
135
|
+
const preferred = policyCfg.preferOurs ? hunk.oursLines : hunk.theirsLines;
|
|
136
|
+
const side = policyCfg.preferOurs ? "ours" : "theirs";
|
|
137
|
+
return {
|
|
138
|
+
lines: [...preferred],
|
|
139
|
+
reason: `Même structure, valeur(s) volatile(s) différente(s). Résolution : accepter ${side} (politique : ${effectivePolicy}).`,
|
|
140
|
+
};
|
|
141
|
+
}
|
|
142
|
+
case "generated_file": {
|
|
143
|
+
// Smart resolution : si les deux côtés sont identiques après suppression
|
|
144
|
+
// des valeurs volatiles (hashes, timestamps), le conflit est cosmétique
|
|
145
|
+
const oursStripped = stripVolatileValues(hunk.oursLines);
|
|
146
|
+
const theirsStripped = stripVolatileValues(hunk.theirsLines);
|
|
147
|
+
if (oursStripped === theirsStripped) {
|
|
148
|
+
return {
|
|
149
|
+
lines: [...hunk.theirsLines],
|
|
150
|
+
reason: "Fichier auto-généré — contenu structurel identique (seules les valeurs volatiles diffèrent). Résolution : accepter theirs. Suggestion : relancer le build/install.",
|
|
151
|
+
};
|
|
152
|
+
}
|
|
153
|
+
return {
|
|
154
|
+
lines: [...hunk.theirsLines],
|
|
155
|
+
reason: "Fichier auto-généré — le fichier sera régénéré après merge. Résolution : accepter theirs. Suggestion : relancer le build/install.",
|
|
156
|
+
};
|
|
157
|
+
}
|
|
158
|
+
case "complex":
|
|
159
|
+
return {
|
|
160
|
+
lines: null,
|
|
161
|
+
reason: "Conflit complexe — aucune heuristique automatique applicable. Résolution manuelle requise.",
|
|
162
|
+
};
|
|
163
|
+
default:
|
|
164
|
+
return {
|
|
165
|
+
lines: null,
|
|
166
|
+
reason: `Type de conflit inconnu : ${hunk.type}.`,
|
|
167
|
+
};
|
|
168
|
+
}
|
|
169
|
+
}
|
|
170
|
+
//# sourceMappingURL=assemble.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"assemble.js","sourceRoot":"","sources":["../../src/resolver/assemble.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Dispatch vers les résolveurs format-aware (Phase 7.3).
|
|
3
|
+
*
|
|
4
|
+
* Avant de passer au moteur textuel, on tente un résolveur spécialisé par
|
|
5
|
+
* format (JSON/JSONC, Markdown, YAML, Vue, CSS, Dockerfile, Dotenv, Cargo,
|
|
6
|
+
* imports…). Ces résolveurs effectuent une validation sémantique, ce qui
|
|
7
|
+
* justifie de bypasser le filtre de confiance textuel.
|
|
8
|
+
*
|
|
9
|
+
* Exception : le résolveur `imports` est sémantiquement équivalent à
|
|
10
|
+
* `non_overlapping` — il doit respecter la politique `allowNonOverlapping`
|
|
11
|
+
* ainsi que l'option globale `resolveNonOverlapping`.
|
|
12
|
+
*
|
|
13
|
+
* Ce module encapsule à la fois l'appel au dispatcher et la politique
|
|
14
|
+
* appliquée aux imports, et retourne un résultat tagué (`status`) que le
|
|
15
|
+
* moteur principal sait consommer.
|
|
16
|
+
*/
|
|
17
|
+
import type { ConflictHunk, GitWandOptions } from "../types.js";
|
|
18
|
+
export type FormatDispatchResult =
|
|
19
|
+
/** Le résolveur format-aware a produit une résolution. */
|
|
20
|
+
{
|
|
21
|
+
status: "resolved";
|
|
22
|
+
lines: string[];
|
|
23
|
+
reason: string;
|
|
24
|
+
}
|
|
25
|
+
/** Le résolveur a résolu mais la politique rejette le résultat (ex: imports/non_overlapping off). */
|
|
26
|
+
| {
|
|
27
|
+
status: "rejected-policy";
|
|
28
|
+
reason: string;
|
|
29
|
+
}
|
|
30
|
+
/** Aucun résolveur format-aware n'a traité ce hunk — continuer vers le moteur textuel. */
|
|
31
|
+
| {
|
|
32
|
+
status: "not-applicable";
|
|
33
|
+
note: string;
|
|
34
|
+
};
|
|
35
|
+
/**
|
|
36
|
+
* Essaie les résolveurs format-aware pour ce hunk. Retourne le résultat
|
|
37
|
+
* tagué que le moteur principal sait router.
|
|
38
|
+
*/
|
|
39
|
+
export declare function dispatchFormatAware(hunk: ConflictHunk, filePath: string, options: Required<GitWandOptions>): FormatDispatchResult;
|
|
40
|
+
//# sourceMappingURL=format-dispatch.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"format-dispatch.d.ts","sourceRoot":"","sources":["../../src/resolver/format-dispatch.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;GAeG;AAEH,OAAO,KAAK,EAAE,YAAY,EAAE,cAAc,EAAE,MAAM,aAAa,CAAC;AAIhE,MAAM,MAAM,oBAAoB;AAC9B,0DAA0D;AACxD;IAAE,MAAM,EAAE,UAAU,CAAC;IAAC,KAAK,EAAE,MAAM,EAAE,CAAC;IAAC,MAAM,EAAE,MAAM,CAAA;CAAE;AACzD,qGAAqG;GACnG;IAAE,MAAM,EAAE,iBAAiB,CAAC;IAAC,MAAM,EAAE,MAAM,CAAA;CAAE;AAC/C,0FAA0F;GACxF;IAAE,MAAM,EAAE,gBAAgB,CAAC;IAAC,IAAI,EAAE,MAAM,CAAA;CAAE,CAAC;AAE/C;;;GAGG;AACH,wBAAgB,mBAAmB,CACjC,IAAI,EAAE,YAAY,EAClB,QAAQ,EAAE,MAAM,EAChB,OAAO,EAAE,QAAQ,CAAC,cAAc,CAAC,GAChC,oBAAoB,CA8BtB"}
|