@sigloch/contracts 6.1.0 → 9.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/se/ao-rules.js +44 -29
- package/dist/se/conformance-rules.d.ts +29 -0
- package/dist/se/conformance-rules.js +107 -17
- package/dist/se/fchain-quality-rules.js +57 -53
- package/dist/se/flat-graph.d.ts +3 -0
- package/dist/se/flat-graph.js +52 -0
- package/dist/se/format-e-parser.d.ts +14 -2
- package/dist/se/format-e-parser.js +33 -9
- package/dist/se/grammar-snapshot.d.ts +7 -6
- package/dist/se/grammar-snapshot.js +17 -16
- package/dist/se/graph-index.d.ts +56 -0
- package/dist/se/graph-index.js +60 -0
- package/dist/se/index.d.ts +5 -3
- package/dist/se/index.js +5 -3
- package/dist/se/meta-model.d.ts +52 -7
- package/dist/se/meta-model.js +108 -14
- package/dist/se/metric-rules.d.ts +8 -0
- package/dist/se/metric-rules.js +95 -23
- package/dist/se/ontology.d.ts +32 -25
- package/dist/se/ontology.js +56 -11
- package/dist/se/quality-rules.js +19 -5
- package/dist/se/readiness.d.ts +4 -2
- package/dist/se/readiness.js +23 -1
- package/dist/se/rules.d.ts +12 -7
- package/dist/se/rules.js +215 -103
- package/dist/se/uc-quality-rules.js +67 -25
- package/package.json +1 -1
package/dist/se/ontology.js
CHANGED
|
@@ -13,7 +13,7 @@ import { z } from 'zod/v4';
|
|
|
13
13
|
export const ElementType = z.enum([
|
|
14
14
|
'SYS', 'UC', 'ACTOR', 'FCHAIN',
|
|
15
15
|
'FUNC', 'FLOW', 'REQ', 'TEST',
|
|
16
|
-
'MOD', 'SCHEMA', '
|
|
16
|
+
'MOD', 'SCHEMA', 'CR',
|
|
17
17
|
'MS',
|
|
18
18
|
]);
|
|
19
19
|
/**
|
|
@@ -22,13 +22,49 @@ export const ElementType = z.enum([
|
|
|
22
22
|
* verify=test coverage, allocate=function-to-module, relation=generic link.
|
|
23
23
|
*/
|
|
24
24
|
export const TraceType = z.enum([
|
|
25
|
-
'compose', 'io', 'satisfy', 'verify', 'allocate', 'relation',
|
|
25
|
+
'compose', 'io', 'satisfy', 'verify', 'allocate', 'relation',
|
|
26
26
|
]);
|
|
27
|
-
/**
|
|
27
|
+
/**
|
|
28
|
+
* REQ kind — 6 values aligned with SysML 2.0 + FMEA (CR-180).
|
|
29
|
+
*
|
|
30
|
+
* CR-SM-266 B: `negative` ENTFAELLT. Ein Verbots-REQ ("das System tut X nie") ist auch eine
|
|
31
|
+
* Anforderung — die Implementierung muss Regeln abfragen oder Sicherungen einbauen, und das
|
|
32
|
+
* ist `functional`. Der Wert hatte NULL Leser (kein Regel-, Gate- oder View-Konsument; anders
|
|
33
|
+
* als risk/mitigation → FM-01..03, pre/postcondition → UC-05/06, non-functional → NFR-01) und
|
|
34
|
+
* haette durch die where-Praedikate am satisfy-Pattern per AUSLASSUNG erstmals Wirkung
|
|
35
|
+
* bekommen: er stand in keiner der vier Listen und waere damit nur noch per FCHAIN erfuellbar
|
|
36
|
+
* gewesen. Die sechs verbleibenden Werte partitionieren die where-Listen VOLLSTAENDIG — kein
|
|
37
|
+
* Wert ohne Zuordnung, keine Kante, die durch ein Loch in der Aufzaehlung faellt.
|
|
38
|
+
*/
|
|
28
39
|
export const ReqKind = z.enum([
|
|
29
|
-
'functional', 'non-functional', 'risk',
|
|
40
|
+
'functional', 'non-functional', 'risk',
|
|
30
41
|
'mitigation', 'precondition', 'postcondition',
|
|
31
42
|
]);
|
|
43
|
+
/**
|
|
44
|
+
* `kinds` in der Form, die WIRKLICH auf Platte liegt — als Liste.
|
|
45
|
+
*
|
|
46
|
+
* Gefunden beim Migrations-Audit zu CR-SM-266 (2026-08-25), nicht von Hand: drei Graphen der
|
|
47
|
+
* Familie tragen `kinds` als blossen STRING statt als Liste (`graph-view-edit`
|
|
48
|
+
* `REQ-edit-genesis: 'functional'`, dazu gc_test-graphview und graphify), einer davon mit dem
|
|
49
|
+
* Wert `'security'`, den das Enum gar nicht kennt. Ursache ist der Format-E-Weg: dort reist
|
|
50
|
+
* das Feld als `@kinds a,b` und wird erst vom Konsumenten gehoben (graph-api-core, CR-195d).
|
|
51
|
+
*
|
|
52
|
+
* Seit die where-Praedikate `kinds` LESEN (CR-SM-266 B), ist diese Drift tragend: ein
|
|
53
|
+
* `kinds.every(...)` auf einem String wirft, und eine geworfene Exception in `isValidTrace`
|
|
54
|
+
* reisst den ganzen Regellauf statt einen Befund zu melden. Die SSOT muss auch bei kaputten
|
|
55
|
+
* Daten ein URTEIL liefern, keinen Absturz.
|
|
56
|
+
*
|
|
57
|
+
* Normalisieren heisst hier ausdruecklich NICHT raten: `'a,b'` wird zu `['a','b']`, weil genau
|
|
58
|
+
* das die Schreibform ist — ein unbekannter Wert wie `'security'` ueberlebt die Normalisierung
|
|
59
|
+
* und faellt danach am Enum-Vergleich durch. Die Drift wird sichtbar, nicht geheilt.
|
|
60
|
+
*/
|
|
61
|
+
export function normalizeReqKinds(raw) {
|
|
62
|
+
if (raw == null)
|
|
63
|
+
return [];
|
|
64
|
+
if (Array.isArray(raw))
|
|
65
|
+
return raw.map(k => String(k).trim()).filter(Boolean);
|
|
66
|
+
return String(raw).split(',').map(k => k.trim()).filter(Boolean);
|
|
67
|
+
}
|
|
32
68
|
export const AsilLevel = z.enum(['QM', 'A', 'B', 'C', 'D']);
|
|
33
69
|
/** INCOSE TIAD verification method (only relevant for type=TEST). */
|
|
34
70
|
export const VerificationMethod = z.enum(['test', 'inspection', 'analysis', 'demonstration']);
|
|
@@ -175,14 +211,24 @@ export const OntologyElement = z.object({
|
|
|
175
211
|
* A trace (edge) in the SE ontology graph.
|
|
176
212
|
* `label` provides semantic context for 'relation' edges (e.g. 'derives', 'depends-on').
|
|
177
213
|
*/
|
|
178
|
-
|
|
179
|
-
|
|
214
|
+
/*
|
|
215
|
+
* CR-SM-266 D5: `TraceCategory` und `Trace.category` ENTFALLEN ersatzlos.
|
|
216
|
+
*
|
|
217
|
+
* Die Unterscheidung modeling/audit trug genau EIN Pattern (`SESSION -produces-> *`), und das
|
|
218
|
+
* ist mit D5 weg. Was blieb, waere ein SCHLUPFLOCH gewesen, kein Vertrag: R-08 und R-18 haben
|
|
219
|
+
* `category === 'audit'` uebersprungen (`filter(t => t.category !== 'audit')`), also haette
|
|
220
|
+
* JEDE Kante mit diesem Attribut die komplette Pattern-Matrix umgangen — die
|
|
221
|
+
* Referenzintegritaet gleich mit. Ein selbstgesetztes Attribut, das eine Strukturpruefung
|
|
222
|
+
* abschaltet, ist genau die Klasse, die CR-SM-263 und CR-SM-257 abgelehnt haben, und hier
|
|
223
|
+
* zusaetzlich der billige Zweitweg aus CR-GC-366: die Kante gaebe es weiterhin, nur ungeprueft.
|
|
224
|
+
* Gemessen: 0 Kanten in allen 9 aktiven Familie-Graphen tragen `category` ueberhaupt — die
|
|
225
|
+
* Entfernung nimmt niemandem etwas weg. Provenance lebt seit CR-GC-347 in
|
|
226
|
+
* `.graphcode/audit.jsonl`, ausserhalb des Graphen.
|
|
227
|
+
*/
|
|
180
228
|
export const Trace = z.object({
|
|
181
229
|
source: z.string(),
|
|
182
230
|
target: z.string(),
|
|
183
231
|
type: TraceType,
|
|
184
|
-
/** 'modeling' (default, user-visible) or 'audit' (internal, e.g. produces traces). Absent = modeling. */
|
|
185
|
-
category: TraceCategory.optional(),
|
|
186
232
|
label: z.string().optional(),
|
|
187
233
|
weight: z.number().default(1),
|
|
188
234
|
attributes: z.record(z.string(), z.unknown()).optional(),
|
|
@@ -208,12 +254,11 @@ export const ELEMENT_DESCRIPTIONS = {
|
|
|
208
254
|
TEST: 'Testfall',
|
|
209
255
|
MOD: 'Modul (SW-Paket oder HW-Baugruppe)',
|
|
210
256
|
SCHEMA: 'Datenschema (Zod)',
|
|
211
|
-
SESSION: 'Audit-Session',
|
|
212
257
|
CR: 'Change Request',
|
|
213
258
|
MS: 'Meilenstein',
|
|
214
259
|
};
|
|
215
|
-
/** Element types used in modeling (user-visible). Excludes
|
|
216
|
-
export const MODELING_ELEMENT_TYPES = ElementType.options.filter(t => t !== '
|
|
260
|
+
/** Element types used in modeling (user-visible). Excludes the planning type CR. */
|
|
261
|
+
export const MODELING_ELEMENT_TYPES = ElementType.options.filter(t => t !== 'CR');
|
|
217
262
|
/**
|
|
218
263
|
* Documented attributes per ElementType.
|
|
219
264
|
* `attributes` is Record<string,unknown> on the schema level, but these are
|
package/dist/se/quality-rules.js
CHANGED
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import { normalizeReqKinds } from './ontology.js';
|
|
1
2
|
// ---------------------------------------------------------------------------
|
|
2
3
|
// Weasel words list (BQ-01)
|
|
3
4
|
// ---------------------------------------------------------------------------
|
|
@@ -162,12 +163,22 @@ export function bq06Conforming(graph) {
|
|
|
162
163
|
const placeholderPattern = /\b(TBD|TBR|TODO|placeholder|to be determined)\b|needs\s.*review/i;
|
|
163
164
|
const BQ07_MIN_DESC_LENGTH = 20;
|
|
164
165
|
export function bq07Complete(graph) {
|
|
166
|
+
// CR-SM-266 REQ-X06: `kinds` ist Pflicht am REQ — hier als DRITTER Grund derselben Regel,
|
|
167
|
+
// bewusst ohne neue Regel-ID (Gate 6 des Grammatik-Reviews: eine ID kostet dauerhaft einen
|
|
168
|
+
// Nenner-Anteil, eine Katalogzeile, eine readiness-Zuordnung und einen Golden-File-Eintrag).
|
|
169
|
+
// BQ-07 heisst "Complete" und sammelt bereits mehrere Unvollstaendigkeits-Gruende in EINEN
|
|
170
|
+
// Befund; ein REQ ohne Klassifikation ist genau das — unvollstaendig, nicht falsch.
|
|
171
|
+
//
|
|
172
|
+
// Die DURCHSETZENDE Haelfte liegt woanders: `satisfiesPredicate` (meta-model.ts) lehnt jede
|
|
173
|
+
// satisfy-Kante auf ein REQ ohne `kinds` ab, weil dort nicht entscheidbar ist, ob sie
|
|
174
|
+
// zulaessig ist. Das ist die Fehlmessung und deshalb R-18/error; das blosse Fehlen der
|
|
175
|
+
// Angabe ist ein Vollstaendigkeitssignal und deshalb hier/warning — dieselbe Trennung, die
|
|
176
|
+
// CR-SM-262 fuer RC-06 begruendet hat.
|
|
177
|
+
const isIncomplete = (req) => req.description.trim().length < BQ07_MIN_DESC_LENGTH ||
|
|
178
|
+
placeholderPattern.test(req.description) ||
|
|
179
|
+
normalizeReqKinds(req.kinds).length === 0;
|
|
165
180
|
return reqElements(graph)
|
|
166
|
-
.filter(
|
|
167
|
-
const tooShort = req.description.trim().length < BQ07_MIN_DESC_LENGTH;
|
|
168
|
-
const hasPlaceholder = placeholderPattern.test(req.description);
|
|
169
|
-
return tooShort || hasPlaceholder;
|
|
170
|
-
})
|
|
181
|
+
.filter(isIncomplete)
|
|
171
182
|
.map(req => {
|
|
172
183
|
const reasons = [];
|
|
173
184
|
if (req.description.trim().length < BQ07_MIN_DESC_LENGTH) {
|
|
@@ -176,6 +187,9 @@ export function bq07Complete(graph) {
|
|
|
176
187
|
if (placeholderPattern.test(req.description)) {
|
|
177
188
|
reasons.push('contains placeholder');
|
|
178
189
|
}
|
|
190
|
+
if (normalizeReqKinds(req.kinds).length === 0) {
|
|
191
|
+
reasons.push('no kinds declared');
|
|
192
|
+
}
|
|
179
193
|
return {
|
|
180
194
|
rule_id: 'BQ-07',
|
|
181
195
|
severity: 'warning',
|
package/dist/se/readiness.d.ts
CHANGED
|
@@ -30,9 +30,10 @@ export declare const ReadinessScore: z.ZodObject<{
|
|
|
30
30
|
cr: "cr";
|
|
31
31
|
ms: "ms";
|
|
32
32
|
}>;
|
|
33
|
-
score: z.ZodNumber
|
|
33
|
+
score: z.ZodNullable<z.ZodNumber>;
|
|
34
34
|
violations: z.ZodNumber;
|
|
35
35
|
applicable: z.ZodNumber;
|
|
36
|
+
coreApplicable: z.ZodNumber;
|
|
36
37
|
ready: z.ZodBoolean;
|
|
37
38
|
}, z.core.$strip>;
|
|
38
39
|
export type ReadinessScoreType = z.infer<typeof ReadinessScore>;
|
|
@@ -57,9 +58,10 @@ export declare const ReadinessReport: z.ZodObject<{
|
|
|
57
58
|
cr: "cr";
|
|
58
59
|
ms: "ms";
|
|
59
60
|
}>;
|
|
60
|
-
score: z.ZodNumber
|
|
61
|
+
score: z.ZodNullable<z.ZodNumber>;
|
|
61
62
|
violations: z.ZodNumber;
|
|
62
63
|
applicable: z.ZodNumber;
|
|
64
|
+
coreApplicable: z.ZodNumber;
|
|
63
65
|
ready: z.ZodBoolean;
|
|
64
66
|
}, z.core.$strip>>;
|
|
65
67
|
timestamp: z.ZodISODateTime;
|
package/dist/se/readiness.js
CHANGED
|
@@ -20,11 +20,33 @@ export const ReadinessDimension = z.enum([
|
|
|
20
20
|
]);
|
|
21
21
|
export const ReadinessScore = z.object({
|
|
22
22
|
dimension: ReadinessDimension,
|
|
23
|
-
|
|
23
|
+
/**
|
|
24
|
+
* `1 - (violations / applicable)` — oder **`null`**, wenn die Dimension nicht messbar ist
|
|
25
|
+
* (CR-SM-270).
|
|
26
|
+
*
|
|
27
|
+
* `null` heisst nie 0 %, so wie schon bei `graph_metrics` (CR-GC-326): "a value that is not
|
|
28
|
+
* measurable is not zero percent". Der Anlass war die Gegenrichtung — ein Modell ohne einen
|
|
29
|
+
* einzigen Use Case meldete `uc: 0,997, ready: true`, weil 306 FUNC ueber eine einzige
|
|
30
|
+
* Fremdtyp-Regel (FC-03) den Nenner fuellten, waehrend die dreizehn Regeln, die wirklich Use
|
|
31
|
+
* Cases pruefen, nichts zu pruefen hatten und ihr SCHWEIGEN sich als Erfolg las. Der Score
|
|
32
|
+
* zeigte damit in die falsche Richtung: je mehr importierte FUNCs ein Repo ohne Wozu-Ebene
|
|
33
|
+
* hat, desto reifer sah seine uc-Readiness aus.
|
|
34
|
+
*/
|
|
35
|
+
score: z.number().min(0).max(1).nullable(),
|
|
24
36
|
violations: z.number().int(),
|
|
25
37
|
applicable: z.number().int(),
|
|
38
|
+
/**
|
|
39
|
+
* CR-SM-270: die Kernmenge der Dimension — die Elemente der Typen, die die MEHRHEIT ihrer
|
|
40
|
+
* Regeln prueft (uc → UC/FCHAIN/ACTOR, arch → FUNC/MOD). Ist sie 0, ist `score` `null`.
|
|
41
|
+
*
|
|
42
|
+
* Sie steht im Bericht, weil sonst niemand das `null` erklaeren kann: `applicable` allein
|
|
43
|
+
* unterscheidet "nichts zu pruefen" (0) nicht von "nur Fremdtypen" (307). Genau die
|
|
44
|
+
* Unterscheidung, an der der dokumentierte Ausweg aus CR-SM-237 gescheitert ist.
|
|
45
|
+
*/
|
|
46
|
+
coreApplicable: z.number().int(),
|
|
26
47
|
// CR-SM-235: `score >= readyThreshold`. Die Schwelle steht bewusst NICHT hier — sie ist
|
|
27
48
|
// Eingabe von `computeReadiness`, und eine Zahl im Kommentar wäre die dritte Meinung dazu.
|
|
49
|
+
// CR-SM-270: bei `score === null` ist `ready` immer `false` — nicht messbar ist nicht bereit.
|
|
28
50
|
ready: z.boolean(),
|
|
29
51
|
});
|
|
30
52
|
/**
|
package/dist/se/rules.d.ts
CHANGED
|
@@ -26,7 +26,6 @@ export declare const ViolationCandidate: z.ZodObject<{
|
|
|
26
26
|
TEST: "TEST";
|
|
27
27
|
MOD: "MOD";
|
|
28
28
|
SCHEMA: "SCHEMA";
|
|
29
|
-
SESSION: "SESSION";
|
|
30
29
|
CR: "CR";
|
|
31
30
|
MS: "MS";
|
|
32
31
|
}>;
|
|
@@ -46,7 +45,6 @@ export declare const ViolationContext: z.ZodObject<{
|
|
|
46
45
|
TEST: "TEST";
|
|
47
46
|
MOD: "MOD";
|
|
48
47
|
SCHEMA: "SCHEMA";
|
|
49
|
-
SESSION: "SESSION";
|
|
50
48
|
CR: "CR";
|
|
51
49
|
MS: "MS";
|
|
52
50
|
}>>;
|
|
@@ -64,7 +62,6 @@ export declare const ViolationContext: z.ZodObject<{
|
|
|
64
62
|
TEST: "TEST";
|
|
65
63
|
MOD: "MOD";
|
|
66
64
|
SCHEMA: "SCHEMA";
|
|
67
|
-
SESSION: "SESSION";
|
|
68
65
|
CR: "CR";
|
|
69
66
|
MS: "MS";
|
|
70
67
|
}>;
|
|
@@ -79,7 +76,6 @@ export declare const ViolationContext: z.ZodObject<{
|
|
|
79
76
|
verify: "verify";
|
|
80
77
|
allocate: "allocate";
|
|
81
78
|
relation: "relation";
|
|
82
|
-
produces: "produces";
|
|
83
79
|
}>;
|
|
84
80
|
}, z.core.$strip>>>;
|
|
85
81
|
parent_module: z.ZodOptional<z.ZodString>;
|
|
@@ -108,7 +104,6 @@ export declare const RuleViolation: z.ZodObject<{
|
|
|
108
104
|
TEST: "TEST";
|
|
109
105
|
MOD: "MOD";
|
|
110
106
|
SCHEMA: "SCHEMA";
|
|
111
|
-
SESSION: "SESSION";
|
|
112
107
|
CR: "CR";
|
|
113
108
|
MS: "MS";
|
|
114
109
|
}>>;
|
|
@@ -126,7 +121,6 @@ export declare const RuleViolation: z.ZodObject<{
|
|
|
126
121
|
TEST: "TEST";
|
|
127
122
|
MOD: "MOD";
|
|
128
123
|
SCHEMA: "SCHEMA";
|
|
129
|
-
SESSION: "SESSION";
|
|
130
124
|
CR: "CR";
|
|
131
125
|
MS: "MS";
|
|
132
126
|
}>;
|
|
@@ -141,7 +135,6 @@ export declare const RuleViolation: z.ZodObject<{
|
|
|
141
135
|
verify: "verify";
|
|
142
136
|
allocate: "allocate";
|
|
143
137
|
relation: "relation";
|
|
144
|
-
produces: "produces";
|
|
145
138
|
}>;
|
|
146
139
|
}, z.core.$strip>>>;
|
|
147
140
|
parent_module: z.ZodOptional<z.ZodString>;
|
|
@@ -186,6 +179,18 @@ export interface RuleDefinition {
|
|
|
186
179
|
*/
|
|
187
180
|
domain: readonly string[];
|
|
188
181
|
}
|
|
182
|
+
/** Find the MOD a FUNC/SCHEMA is allocated to. */
|
|
183
|
+
/**
|
|
184
|
+
* CR-SM-256: die EINE Definition von "zerlegt". Ein FUNC mit FUNC-Kindern ist ein Rollup
|
|
185
|
+
* seiner Kinder — ein Blackbox-Block, durch den nichts fliesst und der keine Anforderung
|
|
186
|
+
* erfuellt, die nicht schon ein Blatt erfuellt. Die Pflichten liegen vollstaendig auf den
|
|
187
|
+
* Blaettern (so schon R-30 seit CR-SM-249, so R-20 seit CR-210).
|
|
188
|
+
*
|
|
189
|
+
* Bewusst EIN Helper statt drei Kopien: eine zweite Definition von "Blatt" waere ein
|
|
190
|
+
* zweiter Weg zu derselben Aussage, und der billigere gewinnt immer. CR-SM-263 haengt als
|
|
191
|
+
* vierter Nutzer daran (MT-02, `metric-rules.ts`) — deshalb exportiert.
|
|
192
|
+
*/
|
|
193
|
+
export declare function decomposedFuncs(graph: OntologyGraph): Set<string>;
|
|
189
194
|
export declare const V3_RULES: RuleDefinition[];
|
|
190
195
|
/** Run all rules against a graph. CR-SM-236: `policy` ist Pflicht — wie bei `evaluateAllRules`. */
|
|
191
196
|
export declare function evaluateRules(graph: OntologyGraph, policy: MetricPolicy): RuleViolation[];
|