import type { MEMOConfig } from '../model/config.js'; import type { MemoElement } from '../model/semantic.js'; import type { ProviderRegistry } from '../toolchain/registry.js'; import { type Corpus, type CorpusProvenance } from './corpus.js'; /** * How a single difference is classified. * * missing-declared the source declares it, the reference has it, MEMO does * not. A lowering gap — MEMO did not read the source. * missing-implied only the reference's *implied* pass produced it. A * derived-semantics gap: MEMO read the source but does not * compute what the source entails. * extra MEMO has an element neither XMI does. Something was * invented, or named differently than upstream names it. * differing-derived both have it; a derived value differs (today: metaclass * against MEMO's construct). * qualified-name the leaf name exists on both sides under different * containment paths. Reported apart from `missing`/`extra` * because it is one defect, not two, and it is a naming * gap rather than a missing element. */ export type DifferenceClass = 'missing-declared' | 'missing-implied' | 'extra' | 'differing-derived' | 'qualified-name'; export declare const DIFFERENCE_CLASSES: readonly DifferenceClass[]; export type DifferenceCounts = Record; export declare function emptyDifferenceCounts(): DifferenceCounts; export interface Difference { class: DifferenceClass; qualifiedName: string; /** Reference metaclass, where the reference has the element. */ metatype?: string; /** MEMO's construct, where MEMO has it. */ construct?: string; /** Free-text only for `differing-derived` and `qualified-name`. */ detail?: string; } export interface LibraryDiff { /** Source file, corpus-relative. */ source: string; /** The two XMI counterparts, corpus-relative; absent when upstream has none. */ declaredXmi?: string; impliedXmi?: string; /** Named elements each side computed. */ referenceDeclared: number; referenceImplied: number; memo: number; /** * Unnamed elements in the reference serialization. * * Not compared — see the module header — but reported, because "we compared * 19 of 336 elements" is a materially different claim from "we compared the * file", and only one of them is true. */ referenceAnonymous: number; counts: DifferenceCounts; /** Capped sample, sorted, so a baseline stays reviewable. */ differences: Difference[]; /** Set when the library could not be compared at all. */ failure?: string; } export interface DiffXmiReport { reportVersion: string; memoVersion: string; corpus: CorpusProvenance & { root: string; }; toolchain: { lowering: string; }; totals: { libraries: number; counts: DifferenceCounts; }; libraries: LibraryDiff[]; } export declare const DIFF_REPORT_VERSION = "1.0.0"; /** * MEMO's qualified name for an element. * * MEMO's model is flat: an element carries the package it was declared in, and * nesting is not part of its identity. The reference's is a containment path. * Joining package and id with `::` is the closest honest translation, and where * it does not line up the difference lands in `qualified-name` rather than * being hidden — which is the point of having that class. */ export declare function memoQualifiedName(element: MemoElement): string; /** * Whether a reference metaclass and a MEMO construct describe the same thing. * * MEMO's `construct` is the SysML keyword (`part`, `action`, `requirement`); * the reference's metatype is the metaclass (`PartUsage`, `PartDefinition`, * `ActionUsage`). Comparing them exactly would report every element as * differing, which is noise. The test is containment of the keyword in the * metaclass name, case-folded — deliberately loose, because this is the first * derived value compared and a strict mapping table belongs with the canonical * IR (Session 3), not here. */ export declare function derivedValuesAgree(metatype: string, construct: string | undefined): boolean; export interface DiffXmiOptions { config: MEMOConfig; projectDir: string; corpusDir?: string; /** * Library sources to compare, as corpus-relative paths or bare filenames. * Empty compares every library source that has an XMI counterpart. */ libraries?: readonly string[]; registry?: ProviderRegistry; memoVersion: string; verify?: boolean; onLibrary?: (source: string, index: number, total: number) => void; } /** Compare one library source against its two XMI counterparts. */ export declare function diffLibrary(source: string, corpus: Corpus, options: DiffXmiOptions): Promise; /** Library sources named by `--library`, or every one with an XMI counterpart. */ export declare function selectLibraries(corpus: Corpus, selectors: readonly string[]): string[]; export declare function runDiffXmi(options: DiffXmiOptions): Promise; export declare function formatDiffXmiReport(report: DiffXmiReport): string; //# sourceMappingURL=diff-xmi.d.ts.map