@likec4/leanix-bridge 1.55.1 → 1.57.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/index.mjs +38 -4
- package/package.json +5 -5
package/dist/index.mjs
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import { readFileSync } from "node:fs";
|
|
2
2
|
import { dirname, join } from "node:path";
|
|
3
3
|
import { fileURLToPath } from "node:url";
|
|
4
|
+
//#region src/contracts.ts
|
|
4
5
|
/**
|
|
5
6
|
* Canonical bridge contracts for LikeC4 ↔ LeanIX interoperability.
|
|
6
7
|
* LikeC4 remains the semantic source of truth; external IDs are provider-scoped.
|
|
@@ -31,6 +32,8 @@ const BRIDGE_VERSION = readVersion();
|
|
|
31
32
|
const BRIDGE_MANIFEST_VERSION = "1.0";
|
|
32
33
|
/** Provider identifier for LeanIX (single source of truth for external.leanix). */
|
|
33
34
|
const LEANIX_PROVIDER = "leanix";
|
|
35
|
+
//#endregion
|
|
36
|
+
//#region src/mapping.ts
|
|
34
37
|
/** Fallback when element kind is unknown (G25: named constant). */
|
|
35
38
|
const FALLBACK_FACT_SHEET_TYPE = "Application";
|
|
36
39
|
/** Fallback when relation kind is unknown (G25: named constant). */
|
|
@@ -106,7 +109,7 @@ function mergeWithDefault(partial) {
|
|
|
106
109
|
* Uses mapping.factSheetTypes[kind], then 'default', then FALLBACK_FACT_SHEET_TYPE.
|
|
107
110
|
*/
|
|
108
111
|
function getFactSheetType(likec4Kind, mapping) {
|
|
109
|
-
return mapping.factSheetTypes[likec4Kind] ?? mapping.factSheetTypes["default"] ??
|
|
112
|
+
return mapping.factSheetTypes[likec4Kind] ?? mapping.factSheetTypes["default"] ?? "Application";
|
|
110
113
|
}
|
|
111
114
|
/**
|
|
112
115
|
* Returns LeanIX relation type for a LikeC4 relationship kind.
|
|
@@ -114,10 +117,12 @@ function getFactSheetType(likec4Kind, mapping) {
|
|
|
114
117
|
*/
|
|
115
118
|
function getRelationType(likec4Kind, mapping) {
|
|
116
119
|
const kind = likec4Kind ?? "default";
|
|
117
|
-
return mapping.relationTypes[kind] ?? mapping.relationTypes["default"] ??
|
|
120
|
+
return mapping.relationTypes[kind] ?? mapping.relationTypes["default"] ?? "depends on";
|
|
118
121
|
}
|
|
122
|
+
//#endregion
|
|
123
|
+
//#region src/to-bridge-manifest.ts
|
|
119
124
|
const defaultOptions = {
|
|
120
|
-
manifestVersion:
|
|
125
|
+
manifestVersion: "1.0",
|
|
121
126
|
bridgeVersion: BRIDGE_VERSION,
|
|
122
127
|
mappingProfile: "default"
|
|
123
128
|
};
|
|
@@ -172,6 +177,8 @@ function toBridgeManifest(model, options = {}) {
|
|
|
172
177
|
relations: buildManifestRelations(model)
|
|
173
178
|
};
|
|
174
179
|
}
|
|
180
|
+
//#endregion
|
|
181
|
+
//#region src/to-leanix-inventory-dry-run.ts
|
|
175
182
|
/** Builds LeanIX fact sheet dry-run list from model elements and mapping. */
|
|
176
183
|
function buildFactSheetsFromModel(model, mapping) {
|
|
177
184
|
const factSheets = [];
|
|
@@ -225,6 +232,8 @@ function toLeanixInventoryDryRun(model, options = {}) {
|
|
|
225
232
|
relations: buildRelationsFromModel(model, mapping)
|
|
226
233
|
};
|
|
227
234
|
}
|
|
235
|
+
//#endregion
|
|
236
|
+
//#region src/report.ts
|
|
228
237
|
/** Builds error message listing which coherence fields mismatched (projectId, mappingProfile). */
|
|
229
238
|
function buildCoherenceErrorMessage(manifest, leanixDryRun) {
|
|
230
239
|
const mismatches = [];
|
|
@@ -256,10 +265,14 @@ function buildBridgeReport(manifest, leanixDryRun) {
|
|
|
256
265
|
}
|
|
257
266
|
};
|
|
258
267
|
}
|
|
268
|
+
//#endregion
|
|
269
|
+
//#region src/leanix-api-client.ts
|
|
259
270
|
const DEFAULT_BASE_URL = "https://app.leanix.net";
|
|
260
271
|
const DEFAULT_DELAY_MS = 200;
|
|
261
272
|
/** Thrown when the LeanIX API returns errors or non-OK HTTP. */
|
|
262
273
|
var LeanixApiError = class extends Error {
|
|
274
|
+
statusCode;
|
|
275
|
+
graphqlErrors;
|
|
263
276
|
constructor(message, statusCode, graphqlErrors) {
|
|
264
277
|
super(message);
|
|
265
278
|
this.statusCode = statusCode;
|
|
@@ -338,6 +351,8 @@ var LeanixApiClient = class {
|
|
|
338
351
|
}
|
|
339
352
|
}
|
|
340
353
|
};
|
|
354
|
+
//#endregion
|
|
355
|
+
//#region src/leanix-graphql-operations.ts
|
|
341
356
|
/** Search fact sheets by name and type (for idempotency). Returns null when not found; throws on API/network error. */
|
|
342
357
|
async function findFactSheetByNameAndType(client, name, type) {
|
|
343
358
|
const edges = (await client.graphql(`
|
|
@@ -448,6 +463,8 @@ async function createRelation(client, sourceFactSheetId, targetFactSheetId, rela
|
|
|
448
463
|
}
|
|
449
464
|
return id;
|
|
450
465
|
}
|
|
466
|
+
//#endregion
|
|
467
|
+
//#region src/sync-to-leanix.ts
|
|
451
468
|
/**
|
|
452
469
|
* Sync bridge manifest + LeanIX dry-run inventory to the LeanIX API.
|
|
453
470
|
* Creates or updates fact sheets and relations; returns manifest with external LeanIX IDs.
|
|
@@ -635,6 +652,8 @@ async function syncToLeanix(manifest, leanixDryRun, client, options = {}) {
|
|
|
635
652
|
errors: [...fsResult.errors, ...relResult.errors]
|
|
636
653
|
};
|
|
637
654
|
}
|
|
655
|
+
//#endregion
|
|
656
|
+
//#region src/drawio-leanix-roundtrip.ts
|
|
638
657
|
/**
|
|
639
658
|
* Draw.io ↔ LeanIX round-trip: mapping between bridge manifest (with LeanIX external IDs)
|
|
640
659
|
* and diagram identity (likec4Id, likec4RelationId).
|
|
@@ -647,7 +666,7 @@ async function syncToLeanix(manifest, leanixDryRun, client, options = {}) {
|
|
|
647
666
|
function collectLikec4IdToLeanixId(manifest) {
|
|
648
667
|
const out = {};
|
|
649
668
|
for (const [canonicalId, entity] of Object.entries(manifest.entities)) {
|
|
650
|
-
const leanixId = entity.external?.[
|
|
669
|
+
const leanixId = entity.external?.["leanix"]?.factSheetId ?? entity.external?.["leanix"]?.externalId;
|
|
651
670
|
if (leanixId) out[canonicalId] = leanixId;
|
|
652
671
|
}
|
|
653
672
|
return out;
|
|
@@ -674,6 +693,8 @@ function manifestToDrawioLeanixMapping(manifest) {
|
|
|
674
693
|
relationKeyToLeanixRelationId: collectRelationKeyToLeanixRelationId(manifest)
|
|
675
694
|
};
|
|
676
695
|
}
|
|
696
|
+
//#endregion
|
|
697
|
+
//#region src/leanix-inventory-snapshot.ts
|
|
677
698
|
const DEFAULT_PAGE_SIZE = 100;
|
|
678
699
|
const DEFAULT_MAX_FACT_SHEETS = 1e3;
|
|
679
700
|
const MAX_GRAPHQL_RETRIES = 3;
|
|
@@ -819,6 +840,8 @@ async function fetchAllRelations(client, factSheetIds) {
|
|
|
819
840
|
}
|
|
820
841
|
return relations;
|
|
821
842
|
}
|
|
843
|
+
//#endregion
|
|
844
|
+
//#region src/reconcile.ts
|
|
822
845
|
/**
|
|
823
846
|
* Reconciliation of LeanIX inventory snapshot with LikeC4 manifest.
|
|
824
847
|
* Produces matched, unmatched (in LikeC4 only / in LeanIX only), and ambiguous pairs.
|
|
@@ -937,6 +960,8 @@ function reconcileInventoryWithManifest(snapshot, manifest, options = {}) {
|
|
|
937
960
|
}
|
|
938
961
|
};
|
|
939
962
|
}
|
|
963
|
+
//#endregion
|
|
964
|
+
//#region src/impact-report.ts
|
|
940
965
|
/**
|
|
941
966
|
* Builds an impact report from a sync plan (read-only).
|
|
942
967
|
* Use before applying sync to understand what would be created/updated.
|
|
@@ -957,6 +982,8 @@ function impactReportFromSyncPlan(plan) {
|
|
|
957
982
|
hasErrors: errors.length > 0
|
|
958
983
|
};
|
|
959
984
|
}
|
|
985
|
+
//#endregion
|
|
986
|
+
//#region src/drift-report.ts
|
|
960
987
|
/**
|
|
961
988
|
* Builds a drift report from a reconciliation result.
|
|
962
989
|
* In_sync: all matched, no unmatched, no ambiguous. Likec4_ahead: only unmatched in LikeC4. Leanix_ahead: only unmatched in LeanIX. Diverged: mixed or ambiguous.
|
|
@@ -994,6 +1021,8 @@ function buildDriftReport(reconciliation) {
|
|
|
994
1021
|
description
|
|
995
1022
|
};
|
|
996
1023
|
}
|
|
1024
|
+
//#endregion
|
|
1025
|
+
//#region src/adr-generation.ts
|
|
997
1026
|
/** Returns date part YYYY-MM-DD from ISO timestamp (G25, G5). Handles short strings defensively. */
|
|
998
1027
|
function formatIsoDateString(iso) {
|
|
999
1028
|
if (typeof iso !== "string" || iso.length < 10) return iso;
|
|
@@ -1058,6 +1087,8 @@ function generateAdrFromDriftReport(drift, options = {}) {
|
|
|
1058
1087
|
""
|
|
1059
1088
|
].join("\n");
|
|
1060
1089
|
}
|
|
1090
|
+
//#endregion
|
|
1091
|
+
//#region src/governance-checks.ts
|
|
1061
1092
|
const DEFAULT_OPTIONS = {
|
|
1062
1093
|
noAmbiguous: true,
|
|
1063
1094
|
allLikec4Matched: false,
|
|
@@ -1093,6 +1124,8 @@ function runGovernanceChecks(reconciliation, options = {}) {
|
|
|
1093
1124
|
checks
|
|
1094
1125
|
};
|
|
1095
1126
|
}
|
|
1127
|
+
//#endregion
|
|
1128
|
+
//#region src/validate.ts
|
|
1096
1129
|
function isRecord(value) {
|
|
1097
1130
|
return typeof value === "object" && value !== null;
|
|
1098
1131
|
}
|
|
@@ -1148,4 +1181,5 @@ function isLeanixInventorySnapshot(obj) {
|
|
|
1148
1181
|
for (const rel of obj["relations"]) if (!isLeanixRelationSnapshotItem(rel)) return false;
|
|
1149
1182
|
return true;
|
|
1150
1183
|
}
|
|
1184
|
+
//#endregion
|
|
1151
1185
|
export { BRIDGE_MANIFEST_VERSION, BRIDGE_VERSION, DEFAULT_LEANIX_MAPPING, FALLBACK_FACT_SHEET_TYPE, FALLBACK_RELATION_TYPE, LEANIX_PROVIDER, LeanixApiClient, LeanixApiError, buildBridgeReport, buildDriftReport, fetchLeanixInventorySnapshot, generateAdrFromDriftReport, generateAdrFromReconciliation, getFactSheetType, getRelationType, impactReportFromSyncPlan, isBridgeManifest, isLeanixInventorySnapshot, manifestToDrawioLeanixMapping, mergeWithDefault, parseLeanixMappingInput, planSyncToLeanix, reconcileInventoryWithManifest, runGovernanceChecks, syncToLeanix, toBridgeManifest, toLeanixInventoryDryRun };
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@likec4/leanix-bridge",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.57.0",
|
|
4
4
|
"license": "MIT",
|
|
5
5
|
"bugs": "https://github.com/likec4/likec4/issues",
|
|
6
6
|
"homepage": "https://likec4.dev",
|
|
@@ -38,15 +38,15 @@
|
|
|
38
38
|
},
|
|
39
39
|
"dependencies": {
|
|
40
40
|
"remeda": "^2.33.7",
|
|
41
|
-
"@likec4/core": "1.
|
|
41
|
+
"@likec4/core": "1.57.0"
|
|
42
42
|
},
|
|
43
43
|
"devDependencies": {
|
|
44
|
-
"@types/node": "~22.19.
|
|
44
|
+
"@types/node": "~22.19.19",
|
|
45
45
|
"typescript": "5.9.3",
|
|
46
46
|
"obuild": "0.4.31",
|
|
47
47
|
"vitest": "4.1.3",
|
|
48
|
-
"@likec4/tsconfig": "1.
|
|
49
|
-
"@likec4/devops": "1.
|
|
48
|
+
"@likec4/tsconfig": "1.57.0",
|
|
49
|
+
"@likec4/devops": "1.57.0"
|
|
50
50
|
},
|
|
51
51
|
"scripts": {
|
|
52
52
|
"typecheck": "tsc -b --verbose",
|