@shapeshift-labs/frontier-lang-compiler 0.2.103 → 0.2.104
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +13 -0
- package/dist/declarations/bidirectional-target-change-source-edit.d.ts +30 -0
- package/dist/declarations/bidirectional-target-change.d.ts +10 -0
- package/dist/declarations/js-ts-safe-member-merge.d.ts +58 -0
- package/dist/declarations/js-ts-safe-merge.d.ts +120 -0
- package/dist/declarations/js-ts-semantic-conflict-sidecars.d.ts +235 -0
- package/dist/declarations/js-ts-semantic-merge-contracts.d.ts +287 -0
- package/dist/declarations/js-ts-semantic-merge.d.ts +4 -0
- package/dist/declarations/native-import-losses.d.ts +3 -0
- package/dist/declarations/semantic-edit-replay-diagnostics.d.ts +12 -0
- package/dist/declarations/semantic-edit-script.d.ts +7 -4
- package/dist/declarations/semantic-patch-bundle-index.d.ts +45 -0
- package/dist/declarations/semantic-patch-bundle.d.ts +6 -4
- package/dist/declarations/semantic-sidecar-example.d.ts +18 -0
- package/dist/declarations/semantic-transform-identity.d.ts +3 -0
- package/dist/declarations/source-preservation.d.ts +72 -0
- package/dist/declarations/universal-capability.d.ts +4 -0
- package/dist/declarations/universal-conversion-artifacts.d.ts +61 -1
- package/dist/declarations/universal-conversion-compact-counts.d.ts +51 -0
- package/dist/declarations/universal-conversion-plan.d.ts +6 -1
- package/dist/declarations/universal-representation-coverage.d.ts +90 -0
- package/dist/index.d.ts +4 -0
- package/dist/index.js +3 -0
- package/dist/internal/index-impl/bidirectionalExactSourceBackprojection.js +199 -0
- package/dist/internal/index-impl/bidirectionalSameLanguageSourceProjection.js +112 -0
- package/dist/internal/index-impl/bidirectionalSourceEditProjection.js +319 -0
- package/dist/internal/index-impl/bidirectionalSourceEditProjectionArtifacts.js +67 -0
- package/dist/internal/index-impl/bidirectionalTargetChangeRecordInternals.js +17 -5
- package/dist/internal/index-impl/bidirectionalTargetRoundtripEvidence.js +58 -20
- package/dist/internal/index-impl/createBidirectionalTargetChangeRecord.js +60 -7
- package/dist/internal/index-impl/createLightweightNativeImport.js +1 -0
- package/dist/internal/index-impl/createNativeSourcePreservation.js +28 -2
- package/dist/internal/index-impl/diffNativeSymbols.js +3 -3
- package/dist/internal/index-impl/nativeChangeProjectionSourceMapLinks.js +2 -0
- package/dist/internal/index-impl/projectSemanticEditScriptToSource.js +43 -8
- package/dist/internal/index-impl/replaySemanticEditLineEndings.js +34 -0
- package/dist/internal/index-impl/replaySemanticEditProjection.js +39 -19
- package/dist/internal/index-impl/semanticEditBundleAdmission.js +7 -3
- package/dist/internal/index-impl/semanticEditBundleIndex.js +47 -1
- package/dist/internal/index-impl/semanticEditExplicitSourceReplacement.js +40 -0
- package/dist/internal/index-impl/semanticEditOperationCoverage.js +33 -3
- package/dist/internal/index-impl/semanticEditProjectionRecord.js +29 -0
- package/dist/internal/index-impl/semanticEditReplayDiagnostics.js +39 -0
- package/dist/internal/index-impl/semanticEditReplaySourceReplacement.js +85 -0
- package/dist/internal/index-impl/semanticEditScripts.js +4 -0
- package/dist/internal/index-impl/semanticEditSourceRanges.js +27 -0
- package/dist/internal/index-impl/semanticIndexFromNativeDeclarations.js +1 -0
- package/dist/internal/index-impl/semanticPatchBundleAdmission.js +41 -7
- package/dist/internal/index-impl/semanticPatchBundleRecords.js +16 -0
- package/dist/internal/index-impl/semanticPatchBundleSourceRecords.js +2 -0
- package/dist/internal/index-impl/semanticSidecarQuality.js +111 -0
- package/dist/internal/index-impl/semanticSourceEditDedupe.js +69 -9
- package/dist/internal/index-impl/semanticTransformIdentityRecords.js +85 -9
- package/dist/js-ts-safe-member-merge-result.js +158 -0
- package/dist/js-ts-safe-member-merge.js +202 -0
- package/dist/js-ts-safe-merge-analyze.js +279 -0
- package/dist/js-ts-safe-merge-constants.js +50 -0
- package/dist/js-ts-safe-merge-context.js +118 -0
- package/dist/js-ts-safe-merge-ledger-validation.js +92 -0
- package/dist/js-ts-safe-merge-ledger.js +85 -0
- package/dist/js-ts-safe-merge-parse-declarations.js +210 -0
- package/dist/js-ts-safe-merge-parse-statements.js +155 -0
- package/dist/js-ts-safe-merge-plan.js +190 -0
- package/dist/js-ts-safe-merge.js +175 -0
- package/dist/js-ts-semantic-conflict-sidecar-constants.js +77 -0
- package/dist/js-ts-semantic-conflict-sidecar-detectors.js +195 -0
- package/dist/js-ts-semantic-conflict-sidecar-normalize.js +203 -0
- package/dist/js-ts-semantic-conflict-sidecar-utils.js +190 -0
- package/dist/js-ts-semantic-conflict-sidecars.js +81 -0
- package/dist/js-ts-semantic-merge-contract-helpers.js +128 -0
- package/dist/js-ts-semantic-merge-contracts.js +217 -0
- package/dist/js-ts-semantic-merge-member-containers.js +100 -0
- package/dist/js-ts-semantic-merge-member-keys.js +142 -0
- package/dist/js-ts-semantic-merge-member-segments.js +185 -0
- package/dist/js-ts-semantic-merge-member-source.js +64 -0
- package/dist/js-ts-semantic-merge-member-utils.js +18 -0
- package/dist/js-ts-semantic-merge-parse.js +15 -0
- package/dist/js-ts-semantic-merge.js +21 -0
- package/dist/lightweight-dependency-effects.js +51 -0
- package/dist/lightweight-dependency-language.js +12 -1
- package/dist/lightweight-dependency-relations.js +14 -27
- package/dist/native-region-scanner-core.js +33 -1
- package/dist/native-region-scanner-csharp.js +151 -0
- package/dist/native-region-scanner-dart.js +91 -0
- package/dist/native-region-scanner-dynamic.js +21 -151
- package/dist/native-region-scanner-functional.js +40 -13
- package/dist/native-region-scanner-java.js +97 -0
- package/dist/native-region-scanner-js-class.js +100 -0
- package/dist/native-region-scanner-js-helpers.js +28 -86
- package/dist/native-region-scanner-js-imports.js +121 -1
- package/dist/native-region-scanner-js-nested.js +96 -8
- package/dist/native-region-scanner-js-structure.js +27 -0
- package/dist/native-region-scanner-js-types.js +99 -0
- package/dist/native-region-scanner-js.js +70 -118
- package/dist/native-region-scanner-kotlin.js +94 -0
- package/dist/native-region-scanner-main.js +15 -181
- package/dist/native-region-scanner-php.js +80 -0
- package/dist/native-region-scanner-python.js +62 -0
- package/dist/native-region-scanner-ruby.js +72 -0
- package/dist/native-region-scanner-scala.js +91 -0
- package/dist/native-region-scanner-spans.js +74 -0
- package/dist/native-region-scanner-swift.js +155 -0
- package/dist/native-region-scanner.js +14 -10
- package/dist/native-source-ledger-helpers.js +195 -0
- package/dist/native-source-ledger.js +306 -0
- package/dist/native-source-preservation-scanner.js +4 -0
- package/dist/semantic-import-callsite-regions.js +136 -0
- package/dist/semantic-import-effect-regions.js +283 -0
- package/dist/semantic-import-regions.js +11 -2
- package/dist/semantic-import-sidecar-entry.js +16 -2
- package/dist/semantic-import-sidecar-types.d.ts +2 -0
- package/dist/semantic-sidecar-example.js +68 -0
- package/dist/universal-capability-matrix.js +23 -0
- package/dist/universal-conversion-artifact-query.js +79 -2
- package/dist/universal-conversion-artifact-semantic-edit.js +103 -0
- package/dist/universal-conversion-artifact-summary.js +33 -1
- package/dist/universal-conversion-artifacts.js +13 -48
- package/dist/universal-conversion-plan-scoring.js +21 -1
- package/dist/universal-conversion-plan-summary.js +30 -0
- package/dist/universal-conversion-plan.js +25 -9
- package/dist/universal-conversion-route-metadata.js +96 -0
- package/dist/universal-conversion-route-operations.js +7 -0
- package/dist/universal-representation-coverage.js +193 -0
- package/package.json +1 -1
|
@@ -6,6 +6,7 @@ import type {
|
|
|
6
6
|
import type { FrontierCompileTarget } from './compile.js';
|
|
7
7
|
import type { SemanticHistoryRecord } from './semantic-history.js';
|
|
8
8
|
import type { SemanticPatchBundleRecord } from './semantic-patch-bundle.js';
|
|
9
|
+
import type { UniversalConversionArtifactCompactCounts } from './universal-conversion-compact-counts.js';
|
|
9
10
|
import type {
|
|
10
11
|
UniversalConversionAdmissionAction,
|
|
11
12
|
UniversalConversionPlan,
|
|
@@ -17,6 +18,7 @@ import type {
|
|
|
17
18
|
UniversalConversionMergeScore,
|
|
18
19
|
UniversalConversionRisk
|
|
19
20
|
} from './universal-conversion-plan.js';
|
|
21
|
+
import type { UniversalRepresentationCoverageQuery } from './universal-representation-coverage.js';
|
|
20
22
|
|
|
21
23
|
export type UniversalConversionArtifactAdmissionStatus = 'queued' | 'needs-review' | 'blocked' | string;
|
|
22
24
|
export type UniversalConversionArtifactAdmissionBucket =
|
|
@@ -151,6 +153,27 @@ export interface UniversalConversionArtifactIndex {
|
|
|
151
153
|
readonly proofIds: readonly string[];
|
|
152
154
|
readonly semanticOperationIds: readonly string[];
|
|
153
155
|
readonly semanticOperationKinds: readonly string[];
|
|
156
|
+
readonly semanticEditStatuses: readonly string[];
|
|
157
|
+
readonly semanticEditScriptIds: readonly string[];
|
|
158
|
+
readonly semanticEditProjectionIds: readonly string[];
|
|
159
|
+
readonly semanticEditReplayIds: readonly string[];
|
|
160
|
+
readonly semanticEditReplayStatuses: readonly string[];
|
|
161
|
+
readonly semanticEditReplayActions: readonly string[];
|
|
162
|
+
readonly semanticEditAdmissionStatuses: readonly string[];
|
|
163
|
+
readonly semanticEditAdmissionActions: readonly string[];
|
|
164
|
+
readonly semanticEditAdmissionReadinesses: readonly string[];
|
|
165
|
+
readonly semanticEditReplayCurrentHashes: readonly string[];
|
|
166
|
+
readonly semanticEditReplayOutputHashes: readonly string[];
|
|
167
|
+
readonly semanticEditKeys: readonly string[];
|
|
168
|
+
readonly semanticEditHashes: readonly string[];
|
|
169
|
+
readonly semanticIdentityHashes: readonly string[];
|
|
170
|
+
readonly sourceIdentityHashes: readonly string[];
|
|
171
|
+
readonly operationContentHashes: readonly string[];
|
|
172
|
+
readonly editContentHashes: readonly string[];
|
|
173
|
+
readonly representationConstructKinds: readonly string[];
|
|
174
|
+
readonly runtimeCapabilities: readonly string[];
|
|
175
|
+
readonly sourceMapPrecisions: readonly string[];
|
|
176
|
+
readonly transformIdentityHashes: readonly string[];
|
|
154
177
|
}
|
|
155
178
|
|
|
156
179
|
export interface UniversalConversionArtifacts {
|
|
@@ -171,6 +194,7 @@ export interface UniversalConversionArtifacts {
|
|
|
171
194
|
readonly patchBundles: number;
|
|
172
195
|
readonly admissionRecords: number;
|
|
173
196
|
readonly semanticOperations: number;
|
|
197
|
+
readonly compactCounts: UniversalConversionArtifactCompactCounts;
|
|
174
198
|
readonly mergeReady: number;
|
|
175
199
|
readonly needsEvidence: number;
|
|
176
200
|
readonly needsAdapter: number;
|
|
@@ -217,7 +241,7 @@ export type CreateUniversalConversionArtifactsInput =
|
|
|
217
241
|
| UniversalConversionRoute
|
|
218
242
|
| UniversalConversionPlanOptions;
|
|
219
243
|
|
|
220
|
-
export interface UniversalConversionArtifactQuery {
|
|
244
|
+
export interface UniversalConversionArtifactQuery extends UniversalRepresentationCoverageQuery {
|
|
221
245
|
readonly routeId?: string | readonly string[];
|
|
222
246
|
readonly historyId?: string | readonly string[];
|
|
223
247
|
readonly patchBundleId?: string | readonly string[];
|
|
@@ -240,6 +264,42 @@ export interface UniversalConversionArtifactQuery {
|
|
|
240
264
|
readonly proofId?: string | readonly string[];
|
|
241
265
|
readonly semanticOperationId?: string | readonly string[];
|
|
242
266
|
readonly semanticOperationKind?: string | readonly string[];
|
|
267
|
+
readonly semanticEditStatus?: string | readonly string[];
|
|
268
|
+
readonly semanticEditStatuses?: readonly string[];
|
|
269
|
+
readonly semanticEditScriptId?: string | readonly string[];
|
|
270
|
+
readonly semanticEditScriptIds?: readonly string[];
|
|
271
|
+
readonly semanticEditProjectionId?: string | readonly string[];
|
|
272
|
+
readonly semanticEditProjectionIds?: readonly string[];
|
|
273
|
+
readonly semanticEditReplayId?: string | readonly string[];
|
|
274
|
+
readonly semanticEditReplayIds?: readonly string[];
|
|
275
|
+
readonly semanticEditReplayStatus?: string | readonly string[];
|
|
276
|
+
readonly semanticEditReplayStatuses?: readonly string[];
|
|
277
|
+
readonly semanticEditReplayAction?: string | readonly string[];
|
|
278
|
+
readonly semanticEditReplayActions?: readonly string[];
|
|
279
|
+
readonly semanticEditAdmission?: string | readonly string[];
|
|
280
|
+
readonly semanticEditAdmissionStatus?: string | readonly string[];
|
|
281
|
+
readonly semanticEditAdmissionStatuses?: readonly string[];
|
|
282
|
+
readonly semanticEditAdmissionAction?: string | readonly string[];
|
|
283
|
+
readonly semanticEditAdmissionActions?: readonly string[];
|
|
284
|
+
readonly semanticEditAdmissionReadiness?: string | readonly string[];
|
|
285
|
+
readonly semanticEditAdmissionReadinesses?: readonly string[];
|
|
286
|
+
readonly semanticEditReplayCurrentHash?: string | readonly string[];
|
|
287
|
+
readonly semanticEditReplayCurrentHashes?: readonly string[];
|
|
288
|
+
readonly semanticEditReplayOutputHash?: string | readonly string[];
|
|
289
|
+
readonly semanticEditReplayOutputHashes?: readonly string[];
|
|
290
|
+
readonly semanticEditKey?: string | readonly string[];
|
|
291
|
+
readonly semanticEditKeys?: readonly string[];
|
|
292
|
+
readonly semanticEditHash?: string | readonly string[];
|
|
293
|
+
readonly semanticEditHashes?: readonly string[];
|
|
294
|
+
readonly semanticIdentityHash?: string | readonly string[];
|
|
295
|
+
readonly semanticIdentityHashes?: readonly string[];
|
|
296
|
+
readonly sourceIdentityHash?: string | readonly string[];
|
|
297
|
+
readonly sourceIdentityHashes?: readonly string[];
|
|
298
|
+
readonly operationContentHash?: string | readonly string[];
|
|
299
|
+
readonly operationContentHashes?: readonly string[];
|
|
300
|
+
readonly editContentHash?: string | readonly string[];
|
|
301
|
+
readonly editContentHashes?: readonly string[];
|
|
302
|
+
readonly representationConstructKind?: string | readonly string[];
|
|
243
303
|
}
|
|
244
304
|
|
|
245
305
|
export declare function createUniversalConversionArtifacts(
|
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
export interface UniversalConversionRepresentationCompactCounts {
|
|
2
|
+
readonly total: number;
|
|
3
|
+
readonly byKind: Readonly<Record<string, number>>;
|
|
4
|
+
}
|
|
5
|
+
|
|
6
|
+
export interface UniversalConversionPlanRepresentationCompactCounts extends UniversalConversionRepresentationCompactCounts {
|
|
7
|
+
readonly represented: number;
|
|
8
|
+
readonly missing: number;
|
|
9
|
+
readonly review: number;
|
|
10
|
+
readonly blocked: number;
|
|
11
|
+
readonly byStatus: Readonly<Record<string, number>>;
|
|
12
|
+
}
|
|
13
|
+
|
|
14
|
+
export interface UniversalConversionArtifactRepresentationCompactCounts extends UniversalConversionRepresentationCompactCounts {
|
|
15
|
+
readonly routeArtifacts: number;
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
export interface UniversalConversionMissingConstructCompactCounts {
|
|
19
|
+
readonly total: number;
|
|
20
|
+
readonly byKind: Readonly<Record<string, number>>;
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
export interface UniversalConversionArtifactMissingConstructCompactCounts extends UniversalConversionMissingConstructCompactCounts {
|
|
24
|
+
readonly routeArtifacts: number;
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
export interface UniversalConversionPlanCompactCounts {
|
|
28
|
+
readonly representationConstructs: UniversalConversionPlanRepresentationCompactCounts;
|
|
29
|
+
readonly missingConstructs: UniversalConversionMissingConstructCompactCounts;
|
|
30
|
+
readonly semanticEditReadiness: { readonly routes: Readonly<Record<string, number>> };
|
|
31
|
+
readonly admissionStatuses: {
|
|
32
|
+
readonly byAction: Readonly<Record<string, number>>;
|
|
33
|
+
readonly byRouteStatus: Readonly<Record<string, number>>;
|
|
34
|
+
readonly byRisk: Readonly<Record<string, number>>;
|
|
35
|
+
};
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
export interface UniversalConversionArtifactCompactCounts {
|
|
39
|
+
readonly representationConstructs: UniversalConversionArtifactRepresentationCompactCounts;
|
|
40
|
+
readonly missingConstructs: UniversalConversionArtifactMissingConstructCompactCounts;
|
|
41
|
+
readonly semanticEditReadiness: {
|
|
42
|
+
readonly routeArtifacts: Readonly<Record<string, number>>;
|
|
43
|
+
readonly semanticOperations: Readonly<Record<string, number>>;
|
|
44
|
+
};
|
|
45
|
+
readonly admissionStatuses: {
|
|
46
|
+
readonly byStatus: Readonly<Record<string, number>>;
|
|
47
|
+
readonly byBucket: Readonly<Record<string, number>>;
|
|
48
|
+
readonly byAction: Readonly<Record<string, number>>;
|
|
49
|
+
readonly byRisk: Readonly<Record<string, number>>;
|
|
50
|
+
};
|
|
51
|
+
}
|
|
@@ -9,6 +9,8 @@ import type { NativeParserFeatureCategory } from './native-parser-features.js';
|
|
|
9
9
|
import type { ProjectionSourceProjectionCoverage, ProjectionTargetCoverageEntry } from './projection-coverage.js';
|
|
10
10
|
import type { ProjectionReadinessTargetCell } from './projection-readiness.js';
|
|
11
11
|
import type { UniversalCapabilityMatrix, UniversalCapabilityMatrixOptions } from './universal-capability.js';
|
|
12
|
+
import type { UniversalRepresentationCoverage, UniversalRepresentationCoverageQuery } from './universal-representation-coverage.js';
|
|
13
|
+
import type { UniversalConversionPlanCompactCounts } from './universal-conversion-compact-counts.js';
|
|
12
14
|
import type {
|
|
13
15
|
UniversalRuntimeAdapterRequirement,
|
|
14
16
|
UniversalRuntimeCapabilityKind,
|
|
@@ -40,6 +42,7 @@ export type UniversalConversionScoreComponentKey =
|
|
|
40
42
|
| 'importEvidence'
|
|
41
43
|
| 'parserEvidence'
|
|
42
44
|
| 'semanticIndex'
|
|
45
|
+
| 'representationCoverage'
|
|
43
46
|
| 'projectionPath'
|
|
44
47
|
| 'proofEvidence';
|
|
45
48
|
|
|
@@ -145,6 +148,7 @@ export interface UniversalConversionRoute {
|
|
|
145
148
|
readonly runtime: UniversalConversionRouteRuntime;
|
|
146
149
|
readonly runtimeAdapterRequirements: readonly UniversalRuntimeAdapterRequirement[];
|
|
147
150
|
readonly evidence: UniversalConversionRouteEvidence;
|
|
151
|
+
readonly representation: UniversalRepresentationCoverage;
|
|
148
152
|
readonly missingEvidence: readonly string[];
|
|
149
153
|
readonly blockers: readonly string[];
|
|
150
154
|
readonly review: readonly string[];
|
|
@@ -167,6 +171,7 @@ export interface UniversalConversionPlan {
|
|
|
167
171
|
readonly byMode: Readonly<Record<UniversalConversionRouteMode, number>>;
|
|
168
172
|
readonly byReadiness: Readonly<Record<SemanticMergeReadiness, number>>;
|
|
169
173
|
readonly byAdmissionAction: Readonly<Record<UniversalConversionAdmissionAction, number>>;
|
|
174
|
+
readonly compactCounts: UniversalConversionPlanCompactCounts;
|
|
170
175
|
readonly readyRoutes: number;
|
|
171
176
|
readonly reviewRoutes: number;
|
|
172
177
|
readonly blockedRoutes: number;
|
|
@@ -237,7 +242,7 @@ export interface UniversalConversionPlanOptions extends UniversalCapabilityMatri
|
|
|
237
242
|
readonly evidence?: readonly EvidenceRecord[];
|
|
238
243
|
}
|
|
239
244
|
|
|
240
|
-
export interface UniversalConversionPlanQuery {
|
|
245
|
+
export interface UniversalConversionPlanQuery extends UniversalRepresentationCoverageQuery {
|
|
241
246
|
readonly sourceLanguage?: FrontierSourceLanguage | string;
|
|
242
247
|
readonly language?: FrontierSourceLanguage | string;
|
|
243
248
|
readonly target?: FrontierCompileTarget | string;
|
|
@@ -0,0 +1,90 @@
|
|
|
1
|
+
import type { FrontierSourceLanguage } from '@shapeshift-labs/frontier-lang-kernel';
|
|
2
|
+
import type { FrontierCompileTarget } from './compile.js';
|
|
3
|
+
import type { UniversalRuntimeCapabilityKind } from './universal-runtime-capabilities.js';
|
|
4
|
+
|
|
5
|
+
export type UniversalRepresentationConstructKind =
|
|
6
|
+
| 'source-import'
|
|
7
|
+
| 'semantic-symbol'
|
|
8
|
+
| 'source-map'
|
|
9
|
+
| 'parser-feature'
|
|
10
|
+
| 'source-preservation'
|
|
11
|
+
| 'declaration-stub'
|
|
12
|
+
| 'target-adapter'
|
|
13
|
+
| 'runtime-capability'
|
|
14
|
+
| 'semantic-ownership'
|
|
15
|
+
| 'proof-evidence'
|
|
16
|
+
| string;
|
|
17
|
+
|
|
18
|
+
export type UniversalRepresentationConstructStatus = 'represented' | 'missing' | 'review' | 'blocked' | string;
|
|
19
|
+
|
|
20
|
+
export interface UniversalRepresentationConstructRecord {
|
|
21
|
+
readonly kind: UniversalRepresentationConstructKind;
|
|
22
|
+
readonly status: UniversalRepresentationConstructStatus;
|
|
23
|
+
readonly surface: string;
|
|
24
|
+
readonly count: number;
|
|
25
|
+
readonly autoMergeClaim: false;
|
|
26
|
+
readonly semanticEquivalenceClaim: false;
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
export interface UniversalRepresentationCoverage {
|
|
30
|
+
readonly kind: 'frontier.lang.universalRepresentationCoverage';
|
|
31
|
+
readonly version: 1;
|
|
32
|
+
readonly language?: FrontierSourceLanguage | string;
|
|
33
|
+
readonly target?: FrontierCompileTarget | string;
|
|
34
|
+
readonly constructKinds: readonly UniversalRepresentationConstructKind[];
|
|
35
|
+
readonly constructs: readonly UniversalRepresentationConstructRecord[];
|
|
36
|
+
readonly surfaces: {
|
|
37
|
+
readonly sourceImport: { readonly total: number; readonly readiness?: string };
|
|
38
|
+
readonly semanticIndex: { readonly symbols: number; readonly sourceMapMappings: number };
|
|
39
|
+
readonly sourceMaps: { readonly mappings: number; readonly precisions: readonly string[] };
|
|
40
|
+
readonly parser: { readonly rows: number; readonly mergeReadyParsers: readonly string[] };
|
|
41
|
+
readonly projection: {
|
|
42
|
+
readonly targetEntries: number;
|
|
43
|
+
readonly missingTargets: readonly string[];
|
|
44
|
+
readonly unsupportedTargets: readonly string[];
|
|
45
|
+
};
|
|
46
|
+
readonly runtime: {
|
|
47
|
+
readonly requiredCapabilities: readonly UniversalRuntimeCapabilityKind[];
|
|
48
|
+
readonly satisfiedCapabilities: readonly UniversalRuntimeCapabilityKind[];
|
|
49
|
+
readonly missingCapabilities: readonly UniversalRuntimeCapabilityKind[];
|
|
50
|
+
readonly adapterRequirements: readonly string[];
|
|
51
|
+
};
|
|
52
|
+
readonly mergeRefs: {
|
|
53
|
+
readonly ownershipKeys: readonly string[];
|
|
54
|
+
readonly conflictKeys: readonly string[];
|
|
55
|
+
readonly sourceMapIds: readonly string[];
|
|
56
|
+
readonly sourceMapMappingIds: readonly string[];
|
|
57
|
+
readonly transformIdentityHashes: readonly string[];
|
|
58
|
+
};
|
|
59
|
+
readonly evidence: { readonly records: number; readonly proofRecords: number };
|
|
60
|
+
};
|
|
61
|
+
readonly missing: readonly string[];
|
|
62
|
+
readonly blockers: readonly string[];
|
|
63
|
+
readonly review: readonly string[];
|
|
64
|
+
readonly summary: {
|
|
65
|
+
readonly constructs: number;
|
|
66
|
+
readonly representedConstructs: number;
|
|
67
|
+
readonly reviewConstructs: number;
|
|
68
|
+
readonly blockedConstructs: number;
|
|
69
|
+
readonly missing: number;
|
|
70
|
+
readonly blockers: number;
|
|
71
|
+
readonly review: number;
|
|
72
|
+
};
|
|
73
|
+
readonly autoMergeClaim: false;
|
|
74
|
+
readonly semanticEquivalenceClaim: false;
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
export interface UniversalRepresentationCoverageQuery {
|
|
78
|
+
readonly constructKind?: UniversalRepresentationConstructKind | readonly UniversalRepresentationConstructKind[];
|
|
79
|
+
readonly construct?: UniversalRepresentationConstructKind | readonly UniversalRepresentationConstructKind[];
|
|
80
|
+
readonly runtimeCapability?: UniversalRuntimeCapabilityKind | readonly UniversalRuntimeCapabilityKind[];
|
|
81
|
+
readonly sourceMapPrecision?: string | readonly string[];
|
|
82
|
+
readonly transformIdentityHash?: string | readonly string[];
|
|
83
|
+
}
|
|
84
|
+
|
|
85
|
+
export declare const UniversalRepresentationConstructKinds: readonly UniversalRepresentationConstructKind[];
|
|
86
|
+
export declare function createUniversalRepresentationCoverage(input?: Record<string, unknown>): UniversalRepresentationCoverage;
|
|
87
|
+
export declare function representationCoverageMatches(
|
|
88
|
+
coverage?: UniversalRepresentationCoverage,
|
|
89
|
+
query?: UniversalRepresentationCoverageQuery
|
|
90
|
+
): boolean;
|
package/dist/index.d.ts
CHANGED
|
@@ -6,6 +6,7 @@ export * from './declarations/native-import-coverage.js';
|
|
|
6
6
|
export * from './declarations/projection-coverage.js';
|
|
7
7
|
export * from './declarations/projection-readiness.js';
|
|
8
8
|
export * from './declarations/universal-capability.js';
|
|
9
|
+
export * from './declarations/universal-representation-coverage.js';
|
|
9
10
|
export * from './declarations/universal-conversion-artifacts.js';
|
|
10
11
|
export * from './declarations/universal-conversion-plan.js';
|
|
11
12
|
export * from './declarations/universal-runtime-capabilities.js';
|
|
@@ -25,8 +26,11 @@ export * from './declarations/semantic-patch-bundle.js';
|
|
|
25
26
|
export * from './declarations/semantic-patch-bundle-overlaps.js';
|
|
26
27
|
export * from './declarations/semantic-transform-identity.js';
|
|
27
28
|
export * from './declarations/bidirectional-target-change.js';
|
|
29
|
+
export * from './declarations/bidirectional-target-change-source-edit.js';
|
|
28
30
|
export * from './declarations/semantic-impact.js';
|
|
29
31
|
export * from './declarations/semantic-sidecar.js';
|
|
32
|
+
export * from './declarations/semantic-sidecar-example.js';
|
|
33
|
+
export * from './declarations/js-ts-semantic-merge.js';
|
|
30
34
|
export * from './declarations/native-diff.js';
|
|
31
35
|
export * from './declarations/semantic-slice.js';
|
|
32
36
|
export * from './declarations/semantic-slice-admission.js';
|
package/dist/index.js
CHANGED
|
@@ -23,6 +23,8 @@ export { createProjectionTargetLossMatrix } from './internal/index-impl/createPr
|
|
|
23
23
|
export { createPythonAstNativeImporterAdapter } from './internal/index-impl/createPythonAstNativeImporterAdapter.js';
|
|
24
24
|
export { createRustSynNativeImporterAdapter } from './internal/index-impl/createRustSynNativeImporterAdapter.js';
|
|
25
25
|
export { createSemanticImportSidecar } from './internal/index-impl/createSemanticImportSidecar.js';
|
|
26
|
+
export { compactSemanticSidecarExample } from './semantic-sidecar-example.js';
|
|
27
|
+
export * from './js-ts-semantic-merge.js';
|
|
26
28
|
export { createSemanticSlice } from './internal/index-impl/createSemanticSlice.js';
|
|
27
29
|
export { createSemanticSliceAdmissionRecord } from './internal/index-impl/createSemanticSliceAdmissionRecord.js';
|
|
28
30
|
export { createSwiftSyntaxNativeImporterAdapter } from './internal/index-impl/createSwiftSyntaxNativeImporterAdapter.js';
|
|
@@ -30,6 +32,7 @@ export { createTreeSitterNativeImporterAdapter } from './internal/index-impl/cre
|
|
|
30
32
|
export { createTypeScriptCompilerNativeImporterAdapter } from './internal/index-impl/createTypeScriptCompilerNativeImporterAdapter.js';
|
|
31
33
|
export { createUniversalAstFromDocument } from './internal/index-impl/createUniversalAstFromDocument.js';
|
|
32
34
|
export { createUniversalCapabilityMatrix } from './internal/index-impl/createUniversalCapabilityMatrix.js';
|
|
35
|
+
export { createUniversalRepresentationCoverage, representationCoverageMatches, UniversalRepresentationConstructKinds } from './universal-representation-coverage.js';
|
|
33
36
|
export { createUniversalConversionArtifacts } from './internal/index-impl/createUniversalConversionArtifacts.js';
|
|
34
37
|
export { queryUniversalConversionArtifacts } from './universal-conversion-artifacts.js';
|
|
35
38
|
export { createUniversalConversionPlan } from './internal/index-impl/createUniversalConversionPlan.js';
|
|
@@ -0,0 +1,199 @@
|
|
|
1
|
+
import { hashSemanticValue } from '@shapeshift-labs/frontier-lang-kernel';
|
|
2
|
+
import { normalizeNativeLanguageId } from '../../native-import-utils.js';
|
|
3
|
+
import { nativeImportSourceText } from './nativeImportSourceText.js';
|
|
4
|
+
import { spanOffsets } from './semanticEditSourceRanges.js';
|
|
5
|
+
|
|
6
|
+
export function exactSourceBackprojectionForMatch(match, context) {
|
|
7
|
+
if (!sameLanguage(context.source?.language, context.targetChangeSet?.language)) {
|
|
8
|
+
return explicitSourceReplacementBackprojection(match, context);
|
|
9
|
+
}
|
|
10
|
+
const anchor = match.sourceAnchors[0];
|
|
11
|
+
const link = match.sourceMapLinks.find((entry) => entry.precision === 'exact');
|
|
12
|
+
const region = targetRegionForMatch(match, context);
|
|
13
|
+
if (!anchor || !link || !['added', 'modified', 'removed'].includes(region?.changeKind)) return undefined;
|
|
14
|
+
const sourceText = nativeImportSourceText(context.source);
|
|
15
|
+
const targetBeforeText = nativeImportSourceText(context.targetChangeSet.before);
|
|
16
|
+
const targetAfterText = nativeImportSourceText(context.targetChangeSet.after);
|
|
17
|
+
const beforeSpan = region.metadata?.changedRegionProjection?.before?.sourceSpan ?? region.sourceSpan;
|
|
18
|
+
const afterSpan = region.metadata?.changedRegionProjection?.after?.sourceSpan;
|
|
19
|
+
const ranges = {
|
|
20
|
+
source: spanOffsets(sourceText, link.sourceSpan ?? anchor.sourceSpan),
|
|
21
|
+
generated: spanOffsets(targetBeforeText, link.generatedSpan),
|
|
22
|
+
before: spanOffsets(targetBeforeText, beforeSpan),
|
|
23
|
+
after: spanOffsets(targetAfterText, afterSpan)
|
|
24
|
+
};
|
|
25
|
+
if (region.changeKind === 'added') return addedSourceBackprojection({ anchor, link, region, sourceText, targetAfterText, ranges, context });
|
|
26
|
+
if (!validRanges(ranges, region.changeKind)) return undefined;
|
|
27
|
+
const sourceMappedText = sourceText.slice(ranges.source.start, ranges.source.end);
|
|
28
|
+
const targetBeforeMappedText = targetBeforeText.slice(ranges.generated.start, ranges.generated.end);
|
|
29
|
+
const targetBeforeEditText = targetBeforeText.slice(ranges.before.start, ranges.before.end);
|
|
30
|
+
const targetAfterEditText = region.changeKind === 'removed'
|
|
31
|
+
? ''
|
|
32
|
+
: targetAfterText.slice(ranges.after.start, ranges.after.end);
|
|
33
|
+
const targetAfterMappedText = afterMappedText(targetBeforeMappedText, targetAfterEditText, ranges);
|
|
34
|
+
const matchesBefore = sourceMappedText === targetBeforeMappedText;
|
|
35
|
+
const matchesAfter = sourceMappedText === targetAfterMappedText;
|
|
36
|
+
const lineEndingStableBefore = !matchesBefore && sameLineEndingStable(sourceMappedText, targetBeforeMappedText);
|
|
37
|
+
const lineEndingStableAfter = !matchesBefore && sameLineEndingStable(sourceMappedText, targetAfterMappedText);
|
|
38
|
+
if (!matchesBefore && !matchesAfter && !lineEndingStableBefore && !lineEndingStableAfter) return undefined;
|
|
39
|
+
const alreadyApplied = matchesAfter && !matchesBefore;
|
|
40
|
+
const lineEndingStable = lineEndingStableBefore || lineEndingStableAfter;
|
|
41
|
+
const sourceEditRange = lineEndingStable
|
|
42
|
+
? lineEndingStableSourceEditRange(sourceMappedText, lineEndingStableAfter ? targetAfterMappedText : targetBeforeMappedText, ranges, lineEndingStableAfter ? targetAfterEditText : targetBeforeEditText)
|
|
43
|
+
: sourceEditRangeForMatch(ranges, alreadyApplied ? targetAfterEditText : targetBeforeEditText);
|
|
44
|
+
if (!sourceEditRange) return undefined;
|
|
45
|
+
const sourceEditText = sourceText.slice(sourceEditRange.start, sourceEditRange.end);
|
|
46
|
+
const expectedSourceEditText = alreadyApplied || lineEndingStableAfter ? targetAfterEditText : targetBeforeEditText;
|
|
47
|
+
if (sourceEditText !== expectedSourceEditText && !sameLineEndingStable(sourceEditText, expectedSourceEditText)) return undefined;
|
|
48
|
+
return compactRecord({
|
|
49
|
+
mode: 'same-language-exact-source-map',
|
|
50
|
+
alreadyApplied: alreadyApplied || lineEndingStableAfter,
|
|
51
|
+
lineEndingStable,
|
|
52
|
+
sourceMapLinkId: link.id,
|
|
53
|
+
sourceMapMappingId: link.sourceMapMappingId,
|
|
54
|
+
sourceEditSpan: { start: sourceEditRange.start, end: sourceEditRange.end, path: anchor.sourcePath },
|
|
55
|
+
targetBeforeEditSpan: { start: ranges.before.start, end: ranges.before.end, path: region.sourcePath },
|
|
56
|
+
targetAfterEditSpan: ranges.after ? { start: ranges.after.start, end: ranges.after.end, path: region.sourcePath } : undefined,
|
|
57
|
+
sourceEditTextHash: hashSemanticValue(sourceEditText),
|
|
58
|
+
targetBeforeEditTextHash: hashSemanticValue(targetBeforeEditText),
|
|
59
|
+
targetAfterEditTextHash: hashSemanticValue(targetAfterEditText),
|
|
60
|
+
targetAfterSourceHash: context.targetChangeSet.afterHash
|
|
61
|
+
});
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
function explicitSourceReplacementBackprojection(match, context) {
|
|
65
|
+
const anchor = match.sourceAnchors[0];
|
|
66
|
+
const link = match.sourceMapLinks.find((entry) => typeof sourceReplacementText(entry) === 'string');
|
|
67
|
+
const replacement = sourceReplacementText(link);
|
|
68
|
+
const sourceText = nativeImportSourceText(context.source);
|
|
69
|
+
const targetAfterText = nativeImportSourceText(context.targetChangeSet?.after);
|
|
70
|
+
const region = targetRegionForMatch(match, context);
|
|
71
|
+
const ranges = {
|
|
72
|
+
source: spanOffsets(sourceText, link?.sourceSpan ?? anchor?.sourceSpan),
|
|
73
|
+
after: spanOffsets(targetAfterText, region?.metadata?.changedRegionProjection?.after?.sourceSpan ?? region?.sourceSpan)
|
|
74
|
+
};
|
|
75
|
+
if (!anchor || !link || link.precision !== 'exact' || typeof replacement !== 'string' || !ranges.source) return undefined;
|
|
76
|
+
const sourceEditText = sourceText.slice(ranges.source.start, ranges.source.end);
|
|
77
|
+
const replacementHash = sourceReplacementHash(link) ?? hashSemanticValue(replacement);
|
|
78
|
+
if (replacementHash !== hashSemanticValue(replacement)) return undefined;
|
|
79
|
+
const targetAfterEditText = ranges.after ? targetAfterText.slice(ranges.after.start, ranges.after.end) : undefined;
|
|
80
|
+
return compactRecord({
|
|
81
|
+
mode: 'cross-language-explicit-source-replacement',
|
|
82
|
+
alreadyApplied: sourceEditText === replacement,
|
|
83
|
+
sourceMapLinkId: link.id,
|
|
84
|
+
sourceMapMappingId: link.sourceMapMappingId,
|
|
85
|
+
sourceEditSpan: { start: ranges.source.start, end: ranges.source.end, path: anchor.sourcePath },
|
|
86
|
+
targetAfterEditSpan: ranges.after ? { start: ranges.after.start, end: ranges.after.end, path: region.sourcePath } : undefined,
|
|
87
|
+
sourceEditTextHash: hashSemanticValue(sourceEditText),
|
|
88
|
+
sourceReplacementText: replacement,
|
|
89
|
+
sourceReplacementTextHash: replacementHash,
|
|
90
|
+
targetAfterEditTextHash: targetAfterEditText === undefined ? undefined : hashSemanticValue(targetAfterEditText),
|
|
91
|
+
targetAfterSourceHash: context.targetChangeSet.afterHash
|
|
92
|
+
});
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
function addedSourceBackprojection(input) {
|
|
96
|
+
const { anchor, link, region, sourceText, targetAfterText, ranges, context } = input;
|
|
97
|
+
const generated = spanOffsets(targetAfterText, link.generatedSpan);
|
|
98
|
+
if (!ranges.source || !ranges.after || !generated) return undefined;
|
|
99
|
+
const sourceMappedText = sourceText.slice(ranges.source.start, ranges.source.end);
|
|
100
|
+
const targetAfterMappedText = targetAfterText.slice(generated.start, generated.end);
|
|
101
|
+
const targetAfterEditText = targetAfterText.slice(ranges.after.start, ranges.after.end);
|
|
102
|
+
const exact = sourceMappedText === targetAfterMappedText && sourceMappedText === targetAfterEditText;
|
|
103
|
+
const lineEndingStable = !exact && sameLineEndingStable(sourceMappedText, targetAfterMappedText) && sameLineEndingStable(sourceMappedText, targetAfterEditText);
|
|
104
|
+
if (!exact && !lineEndingStable) return undefined;
|
|
105
|
+
const sourceEditRange = lineEndingStable
|
|
106
|
+
? lineEndingStableSourceEditRange(sourceMappedText, targetAfterMappedText, { ...ranges, before: generated, generated }, targetAfterEditText)
|
|
107
|
+
: { start: ranges.source.start, end: ranges.source.start + targetAfterEditText.length };
|
|
108
|
+
if (!sourceEditRange) return undefined;
|
|
109
|
+
return compactRecord({
|
|
110
|
+
mode: 'same-language-exact-source-map',
|
|
111
|
+
alreadyApplied: true,
|
|
112
|
+
lineEndingStable,
|
|
113
|
+
sourceMapLinkId: link.id,
|
|
114
|
+
sourceMapMappingId: link.sourceMapMappingId,
|
|
115
|
+
sourceEditSpan: { start: sourceEditRange.start, end: sourceEditRange.end, path: anchor.sourcePath },
|
|
116
|
+
targetAfterEditSpan: { start: ranges.after.start, end: ranges.after.end, path: region.sourcePath },
|
|
117
|
+
sourceEditTextHash: hashSemanticValue(sourceText.slice(sourceEditRange.start, sourceEditRange.end)),
|
|
118
|
+
targetBeforeEditTextHash: hashSemanticValue(''),
|
|
119
|
+
targetAfterEditTextHash: hashSemanticValue(targetAfterEditText),
|
|
120
|
+
targetAfterSourceHash: context.targetChangeSet.afterHash
|
|
121
|
+
});
|
|
122
|
+
}
|
|
123
|
+
|
|
124
|
+
function validRanges(ranges, changeKind) {
|
|
125
|
+
const hasAfter = changeKind === 'removed' || ranges.after;
|
|
126
|
+
return ranges.source && ranges.generated && ranges.before && hasAfter && containedRange(ranges.before, ranges.generated);
|
|
127
|
+
}
|
|
128
|
+
|
|
129
|
+
function afterMappedText(targetBeforeMappedText, targetAfterEditText, ranges) {
|
|
130
|
+
const start = ranges.before.start - ranges.generated.start;
|
|
131
|
+
const end = ranges.before.end - ranges.generated.start;
|
|
132
|
+
return targetBeforeMappedText.slice(0, start) + targetAfterEditText + targetBeforeMappedText.slice(end);
|
|
133
|
+
}
|
|
134
|
+
|
|
135
|
+
function sourceEditRangeForMatch(ranges, editText) {
|
|
136
|
+
const start = ranges.source.start + ranges.before.start - ranges.generated.start;
|
|
137
|
+
return { start, end: start + editText.length };
|
|
138
|
+
}
|
|
139
|
+
|
|
140
|
+
function lineEndingStableSourceEditRange(sourceMappedText, targetAfterMappedText, ranges, targetAfterEditText) {
|
|
141
|
+
const targetStart = ranges.before.start - ranges.generated.start;
|
|
142
|
+
const targetEnd = targetStart + targetAfterEditText.length;
|
|
143
|
+
const normalizedStart = normalizedPrefixLength(targetAfterMappedText, targetStart);
|
|
144
|
+
const normalizedEnd = normalizedPrefixLength(targetAfterMappedText, targetEnd);
|
|
145
|
+
const sourceStart = rawOffsetForNormalizedPrefix(sourceMappedText, normalizedStart);
|
|
146
|
+
const sourceEnd = rawOffsetForNormalizedPrefix(sourceMappedText, normalizedEnd);
|
|
147
|
+
if (sourceStart < 0 || sourceEnd < sourceStart) return undefined;
|
|
148
|
+
return {
|
|
149
|
+
start: ranges.source.start + sourceStart,
|
|
150
|
+
end: ranges.source.start + sourceEnd
|
|
151
|
+
};
|
|
152
|
+
}
|
|
153
|
+
|
|
154
|
+
function targetRegionForMatch(match, context) {
|
|
155
|
+
return context.targetChangeSet.changedRegions.find((region) => region.id === match.targetRegion?.id)
|
|
156
|
+
?? match.targetRegion;
|
|
157
|
+
}
|
|
158
|
+
|
|
159
|
+
function sameLanguage(left, right) {
|
|
160
|
+
return normalizeNativeLanguageId(left) && normalizeNativeLanguageId(left) === normalizeNativeLanguageId(right);
|
|
161
|
+
}
|
|
162
|
+
|
|
163
|
+
function sourceReplacementText(link) {
|
|
164
|
+
return link?.sourceReplacementText ?? link?.sourceEditText ?? link?.metadata?.sourceReplacementText;
|
|
165
|
+
}
|
|
166
|
+
|
|
167
|
+
function sourceReplacementHash(link) {
|
|
168
|
+
return link?.sourceReplacementTextHash ?? link?.sourceReplacementHash ?? link?.metadata?.sourceReplacementTextHash;
|
|
169
|
+
}
|
|
170
|
+
|
|
171
|
+
function containedRange(inner, outer) {
|
|
172
|
+
return Boolean(inner && outer && outer.start <= inner.start && inner.end <= outer.end);
|
|
173
|
+
}
|
|
174
|
+
|
|
175
|
+
function sameLineEndingStable(left, right) {
|
|
176
|
+
return normalizeLineEndings(left) === normalizeLineEndings(right);
|
|
177
|
+
}
|
|
178
|
+
|
|
179
|
+
function normalizeLineEndings(value) {
|
|
180
|
+
return String(value ?? '').replace(/\r\n/g, '\n').replace(/\r/g, '\n');
|
|
181
|
+
}
|
|
182
|
+
|
|
183
|
+
function normalizedPrefixLength(value, rawOffset) {
|
|
184
|
+
return normalizeLineEndings(String(value ?? '').slice(0, rawOffset)).length;
|
|
185
|
+
}
|
|
186
|
+
|
|
187
|
+
function rawOffsetForNormalizedPrefix(value, normalizedOffset) {
|
|
188
|
+
let normalized = 0;
|
|
189
|
+
for (let index = 0; index < value.length; index += 1) {
|
|
190
|
+
if (normalized === normalizedOffset) return index;
|
|
191
|
+
if (value[index] === '\r' && value[index + 1] === '\n') index += 1;
|
|
192
|
+
normalized += 1;
|
|
193
|
+
}
|
|
194
|
+
return normalized === normalizedOffset ? value.length : -1;
|
|
195
|
+
}
|
|
196
|
+
|
|
197
|
+
function compactRecord(value) {
|
|
198
|
+
return Object.fromEntries(Object.entries(value ?? {}).filter(([, entry]) => entry !== undefined && (!Array.isArray(entry) || entry.length > 0)));
|
|
199
|
+
}
|
|
@@ -0,0 +1,112 @@
|
|
|
1
|
+
import { idFragment, normalizeNativeLanguageId } from '../../native-import-utils.js';
|
|
2
|
+
import { nativeImportSourceText } from './nativeImportSourceText.js';
|
|
3
|
+
import { createSemanticEditScript } from './semanticEditScripts.js';
|
|
4
|
+
import { projectSemanticEditScriptToSource } from './projectSemanticEditScriptToSource.js';
|
|
5
|
+
import { replaySemanticEditProjection } from './replaySemanticEditProjection.js';
|
|
6
|
+
|
|
7
|
+
const backprojectionMode = 'same-language-target-source-edit';
|
|
8
|
+
|
|
9
|
+
export function createSameLanguageTargetSourceProjection(context = {}) {
|
|
10
|
+
if (!sameLanguageSamePath(context.source, context.targetChangeSet)) return {};
|
|
11
|
+
const sourceText = nativeImportSourceText(context.source);
|
|
12
|
+
const workerSourceText = nativeImportSourceText(context.targetChangeSet?.after);
|
|
13
|
+
if (typeof sourceText !== 'string' || typeof workerSourceText !== 'string') return {};
|
|
14
|
+
const script = createSemanticEditScript({
|
|
15
|
+
id: `semantic_edit_script_${idFragment(context.id)}_same_language_target`,
|
|
16
|
+
language: context.source.language,
|
|
17
|
+
sourcePath: context.source.sourcePath,
|
|
18
|
+
base: context.targetChangeSet.before,
|
|
19
|
+
worker: context.targetChangeSet.after,
|
|
20
|
+
head: context.source,
|
|
21
|
+
generatedAt: context.generatedAt,
|
|
22
|
+
metadata: {
|
|
23
|
+
sourceBackprojectionMode: backprojectionMode,
|
|
24
|
+
bidirectionalTargetChangeId: context.id,
|
|
25
|
+
targetChangeSetId: context.targetChangeSet.id
|
|
26
|
+
}
|
|
27
|
+
});
|
|
28
|
+
const projection = projectSemanticEditScriptToSource({
|
|
29
|
+
id: `semantic_edit_projection_${idFragment(context.id)}_same_language_target`,
|
|
30
|
+
script,
|
|
31
|
+
workerSourceText,
|
|
32
|
+
headSourceText: sourceText,
|
|
33
|
+
headSourcePath: context.source.sourcePath,
|
|
34
|
+
metadata: { sourceBackprojectionMode: backprojectionMode }
|
|
35
|
+
});
|
|
36
|
+
const replay = projection.status === 'projected'
|
|
37
|
+
? replaySemanticEditProjection({
|
|
38
|
+
id: `semantic_edit_replay_${idFragment(context.id)}_same_language_target`,
|
|
39
|
+
projection,
|
|
40
|
+
currentSourceText: sourceText
|
|
41
|
+
})
|
|
42
|
+
: undefined;
|
|
43
|
+
const sourceProjectionHint = projectionHint(context, script, projection, replay);
|
|
44
|
+
return {
|
|
45
|
+
sourceEditScript: script,
|
|
46
|
+
sourceProjectionHint,
|
|
47
|
+
sourceEditProjection: projection,
|
|
48
|
+
sourceEditReplay: replay,
|
|
49
|
+
evidence: [sameLanguageEvidence(context, script, projection, replay)]
|
|
50
|
+
};
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
function projectionHint(context, script, projection, replay) {
|
|
54
|
+
const replayReady = ['accepted-clean', 'already-applied'].includes(replay?.status);
|
|
55
|
+
const ready = script.admission?.status === 'auto-merge-candidate' && projection?.status === 'projected' && replayReady;
|
|
56
|
+
return {
|
|
57
|
+
schema: 'frontier.lang.bidirectionalTargetChangeSourceEditProjectionHint.v1',
|
|
58
|
+
version: 1,
|
|
59
|
+
id: `source_projection_hint_${idFragment(context.id)}_same_language_target`,
|
|
60
|
+
scriptId: script.id,
|
|
61
|
+
status: ready ? 'auto-merge-candidate' : script.admission?.status ?? 'needs-port',
|
|
62
|
+
action: ready ? sourceAction(replay) : 'reanchor-or-human-port',
|
|
63
|
+
readiness: ready ? 'ready' : script.admission?.readiness ?? 'needs-review',
|
|
64
|
+
sourcePath: context.source.sourcePath,
|
|
65
|
+
sourceHash: script.headHash,
|
|
66
|
+
targetPath: context.targetChangeSet.sourcePath,
|
|
67
|
+
targetHash: context.targetChangeSet.afterHash,
|
|
68
|
+
targetChangeSetId: context.targetChangeSet.id,
|
|
69
|
+
targetPatchId: context.targetChangeSet.patch?.id,
|
|
70
|
+
targetMergeCandidateId: context.targetChangeSet.mergeCandidate?.id,
|
|
71
|
+
operationIds: (script.operations ?? []).map((operation) => operation.id),
|
|
72
|
+
reviewRequired: !ready,
|
|
73
|
+
autoMergeClaim: false,
|
|
74
|
+
semanticEquivalenceClaim: false,
|
|
75
|
+
reasonCodes: ready ? ['same-language-target-source-edit-replayed'] : script.admission?.reasonCodes,
|
|
76
|
+
sourceBackprojectionMode: backprojectionMode
|
|
77
|
+
};
|
|
78
|
+
}
|
|
79
|
+
|
|
80
|
+
function sameLanguageEvidence(context, script, projection, replay) {
|
|
81
|
+
const passed = projection?.status === 'projected' && ['accepted-clean', 'already-applied'].includes(replay?.status);
|
|
82
|
+
return {
|
|
83
|
+
id: `evidence_${idFragment(context.id)}_same_language_target_replay`,
|
|
84
|
+
kind: 'verification',
|
|
85
|
+
status: passed ? 'passed' : 'failed',
|
|
86
|
+
path: script.sourcePath,
|
|
87
|
+
summary: passed
|
|
88
|
+
? 'Verified same-language target change by projecting and replaying it onto the source file.'
|
|
89
|
+
: 'Same-language target change did not project and replay cleanly onto the source file.',
|
|
90
|
+
metadata: {
|
|
91
|
+
schema: 'frontier.lang.bidirectionalSameLanguageTargetSourceEvidence.v1',
|
|
92
|
+
bidirectionalTargetChangeId: context.id,
|
|
93
|
+
sourceEditScriptId: script.id,
|
|
94
|
+
sourceEditProjectionId: projection?.id,
|
|
95
|
+
sourceEditReplayId: replay?.id,
|
|
96
|
+
projectionStatus: projection?.status,
|
|
97
|
+
replayStatus: replay?.status,
|
|
98
|
+
autoMergeClaim: false,
|
|
99
|
+
semanticEquivalenceClaim: false
|
|
100
|
+
}
|
|
101
|
+
};
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
function sameLanguageSamePath(source, targetChangeSet) {
|
|
105
|
+
const sourceLanguage = normalizeNativeLanguageId(source?.language);
|
|
106
|
+
const targetLanguage = normalizeNativeLanguageId(targetChangeSet?.language);
|
|
107
|
+
return Boolean(sourceLanguage && sourceLanguage === targetLanguage && source?.sourcePath && source.sourcePath === targetChangeSet?.sourcePath);
|
|
108
|
+
}
|
|
109
|
+
|
|
110
|
+
function sourceAction(replay) {
|
|
111
|
+
return replay?.status === 'already-applied' ? 'skip-source-backprojection' : 'admit-source-backprojection';
|
|
112
|
+
}
|