@itwin/imodel-transformer 2.0.0-dev.7 → 2.0.0-dev.70
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 -27
- package/lib/cjs/Algo.d.ts +0 -4
- package/lib/cjs/Algo.d.ts.map +1 -1
- package/lib/cjs/Algo.js +0 -11
- package/lib/cjs/Algo.js.map +1 -1
- package/lib/cjs/BigMap.d.ts.map +1 -1
- package/lib/cjs/BigMap.js.map +1 -1
- package/lib/cjs/BranchProvenanceInitializer.d.ts.map +1 -1
- package/lib/cjs/BranchProvenanceInitializer.js +26 -26
- package/lib/cjs/BranchProvenanceInitializer.js.map +1 -1
- package/lib/cjs/ChangedElementForest.d.ts +14 -0
- package/lib/cjs/ChangedElementForest.d.ts.map +1 -0
- package/lib/cjs/ChangedElementForest.js +86 -0
- package/lib/cjs/ChangedElementForest.js.map +1 -0
- package/lib/cjs/ChangesetScanner.d.ts +141 -0
- package/lib/cjs/ChangesetScanner.d.ts.map +1 -0
- package/lib/cjs/ChangesetScanner.js +187 -0
- package/lib/cjs/ChangesetScanner.js.map +1 -0
- package/lib/cjs/ECReferenceTypesCache.d.ts +0 -4
- package/lib/cjs/ECReferenceTypesCache.d.ts.map +1 -1
- package/lib/cjs/ECReferenceTypesCache.js +61 -111
- package/lib/cjs/ECReferenceTypesCache.js.map +1 -1
- package/lib/cjs/ECSqlReaderAsyncIterableIteratorAdapter.d.ts.map +1 -1
- package/lib/cjs/ECSqlReaderAsyncIterableIteratorAdapter.js.map +1 -1
- package/lib/cjs/ElementAspectCleanup.d.ts +16 -0
- package/lib/cjs/ElementAspectCleanup.d.ts.map +1 -0
- package/lib/cjs/ElementAspectCleanup.js +87 -0
- package/lib/cjs/ElementAspectCleanup.js.map +1 -0
- package/lib/cjs/ElementAspectExportCoordinator.d.ts +44 -0
- package/lib/cjs/ElementAspectExportCoordinator.d.ts.map +1 -0
- package/lib/cjs/ElementAspectExportCoordinator.js +148 -0
- package/lib/cjs/ElementAspectExportCoordinator.js.map +1 -0
- package/lib/cjs/ElementAspectExportProcessor.d.ts +44 -0
- package/lib/cjs/ElementAspectExportProcessor.d.ts.map +1 -0
- package/lib/cjs/ElementAspectExportProcessor.js +152 -0
- package/lib/cjs/ElementAspectExportProcessor.js.map +1 -0
- package/lib/cjs/ElementBulkDelete.d.ts +30 -0
- package/lib/cjs/ElementBulkDelete.d.ts.map +1 -0
- package/lib/cjs/ElementBulkDelete.js +358 -0
- package/lib/cjs/ElementBulkDelete.js.map +1 -0
- package/lib/cjs/EntityExistenceCache.d.ts +43 -0
- package/lib/cjs/EntityExistenceCache.d.ts.map +1 -0
- package/lib/cjs/EntityExistenceCache.js +91 -0
- package/lib/cjs/EntityExistenceCache.js.map +1 -0
- package/lib/cjs/EntityUnifier.d.ts +7 -7
- package/lib/cjs/EntityUnifier.d.ts.map +1 -1
- package/lib/cjs/EntityUnifier.js +55 -24
- package/lib/cjs/EntityUnifier.js.map +1 -1
- package/lib/cjs/IModelCloneContext.d.ts +9 -3
- package/lib/cjs/IModelCloneContext.d.ts.map +1 -1
- package/lib/cjs/IModelCloneContext.js +56 -22
- package/lib/cjs/IModelCloneContext.js.map +1 -1
- package/lib/cjs/IModelExporter.d.ts +171 -43
- package/lib/cjs/IModelExporter.d.ts.map +1 -1
- package/lib/cjs/IModelExporter.js +946 -247
- package/lib/cjs/IModelExporter.js.map +1 -1
- package/lib/cjs/IModelImporter.d.ts +75 -30
- package/lib/cjs/IModelImporter.d.ts.map +1 -1
- package/lib/cjs/IModelImporter.js +292 -132
- package/lib/cjs/IModelImporter.js.map +1 -1
- package/lib/cjs/IModelTransformContext.d.ts +54 -0
- package/lib/cjs/IModelTransformContext.d.ts.map +1 -0
- package/lib/cjs/IModelTransformContext.js +3 -0
- package/lib/cjs/IModelTransformContext.js.map +1 -0
- package/lib/cjs/IModelTransformer.d.ts +180 -206
- package/lib/cjs/IModelTransformer.d.ts.map +1 -1
- package/lib/cjs/IModelTransformer.js +811 -1278
- package/lib/cjs/IModelTransformer.js.map +1 -1
- package/lib/cjs/IModelTransformerError.d.ts +84 -0
- package/lib/cjs/IModelTransformerError.d.ts.map +1 -0
- package/lib/cjs/IModelTransformerError.js +93 -0
- package/lib/cjs/IModelTransformerError.js.map +1 -0
- package/lib/cjs/ProvenanceManager.d.ts +177 -0
- package/lib/cjs/ProvenanceManager.d.ts.map +1 -0
- package/lib/cjs/ProvenanceManager.js +719 -0
- package/lib/cjs/ProvenanceManager.js.map +1 -0
- package/lib/cjs/SourceClassKinds.d.ts +22 -0
- package/lib/cjs/SourceClassKinds.d.ts.map +1 -0
- package/lib/cjs/SourceClassKinds.js +60 -0
- package/lib/cjs/SourceClassKinds.js.map +1 -0
- package/lib/cjs/SyncTypeResolver.d.ts +32 -0
- package/lib/cjs/SyncTypeResolver.d.ts.map +1 -0
- package/lib/cjs/SyncTypeResolver.js +92 -0
- package/lib/cjs/SyncTypeResolver.js.map +1 -0
- package/lib/cjs/TransformerLoggerCategory.d.ts +1 -1
- package/lib/cjs/TransformerLoggerCategory.js +1 -1
- package/lib/cjs/TransformerLoggerCategory.js.map +1 -1
- package/lib/cjs/TransformerPackageMetadata.d.ts +8 -0
- package/lib/cjs/TransformerPackageMetadata.d.ts.map +1 -0
- package/lib/cjs/TransformerPackageMetadata.js +47 -0
- package/lib/cjs/TransformerPackageMetadata.js.map +1 -0
- package/lib/cjs/imodel-transformer.d.ts +28 -0
- package/lib/cjs/imodel-transformer.d.ts.map +1 -1
- package/lib/cjs/imodel-transformer.js +61 -34
- package/lib/cjs/imodel-transformer.js.map +1 -1
- package/lib/cjs/schema-processing/DynamicSchemaUnionStrategy.d.ts +29 -0
- package/lib/cjs/schema-processing/DynamicSchemaUnionStrategy.d.ts.map +1 -0
- package/lib/cjs/schema-processing/DynamicSchemaUnionStrategy.js +212 -0
- package/lib/cjs/schema-processing/DynamicSchemaUnionStrategy.js.map +1 -0
- package/lib/cjs/schema-processing/SchemaProcessingCoordinator.d.ts +25 -0
- package/lib/cjs/schema-processing/SchemaProcessingCoordinator.d.ts.map +1 -0
- package/lib/cjs/schema-processing/SchemaProcessingCoordinator.js +196 -0
- package/lib/cjs/schema-processing/SchemaProcessingCoordinator.js.map +1 -0
- package/lib/cjs/schema-processing/SchemaProcessingStrategy.d.ts +59 -0
- package/lib/cjs/schema-processing/SchemaProcessingStrategy.d.ts.map +1 -0
- package/lib/cjs/schema-processing/SchemaProcessingStrategy.js +28 -0
- package/lib/cjs/schema-processing/SchemaProcessingStrategy.js.map +1 -0
- package/lib/cjs/schema-processing.d.ts +7 -0
- package/lib/cjs/schema-processing.d.ts.map +1 -0
- package/lib/cjs/schema-processing.js +27 -0
- package/lib/cjs/schema-processing.js.map +1 -0
- package/package.json +70 -57
- package/lib/cjs/DetachedExportElementAspectsStrategy.d.ts +0 -16
- package/lib/cjs/DetachedExportElementAspectsStrategy.d.ts.map +0 -1
- package/lib/cjs/DetachedExportElementAspectsStrategy.js +0 -106
- package/lib/cjs/DetachedExportElementAspectsStrategy.js.map +0 -1
- package/lib/cjs/ElementCascadingDeleter.d.ts +0 -22
- package/lib/cjs/ElementCascadingDeleter.d.ts.map +0 -1
- package/lib/cjs/ElementCascadingDeleter.js +0 -57
- package/lib/cjs/ElementCascadingDeleter.js.map +0 -1
- package/lib/cjs/EntityMap.d.ts +0 -26
- package/lib/cjs/EntityMap.d.ts.map +0 -1
- package/lib/cjs/EntityMap.js +0 -54
- package/lib/cjs/EntityMap.js.map +0 -1
- package/lib/cjs/ExportElementAspectsStrategy.d.ts +0 -35
- package/lib/cjs/ExportElementAspectsStrategy.d.ts.map +0 -1
- package/lib/cjs/ExportElementAspectsStrategy.js +0 -52
- package/lib/cjs/ExportElementAspectsStrategy.js.map +0 -1
- package/lib/cjs/ExportElementAspectsWithElementsStrategy.d.ts +0 -12
- package/lib/cjs/ExportElementAspectsWithElementsStrategy.d.ts.map +0 -1
- package/lib/cjs/ExportElementAspectsWithElementsStrategy.js +0 -47
- package/lib/cjs/ExportElementAspectsWithElementsStrategy.js.map +0 -1
package/README.md
CHANGED
|
@@ -4,47 +4,33 @@ Copyright © Bentley Systems, Incorporated. All rights reserved. See LICENSE.md
|
|
|
4
4
|
|
|
5
5
|
## Description
|
|
6
6
|
|
|
7
|
-
The
|
|
7
|
+
The **@itwin/imodel-transformer** package contains classes that handle traversing iModels for exporting and importing their parts.
|
|
8
8
|
|
|
9
9
|
## Documentation
|
|
10
10
|
|
|
11
11
|
See the [iTwin.js](https://www.itwinjs.org) documentation for more information.
|
|
12
12
|
|
|
13
|
+
### Transformation context
|
|
14
|
+
|
|
15
|
+
Retrieve the supported transformation context from an `IModelTransformer`. Depend on `IModelTransformContext` when passing the context to helpers or creating test doubles; `IModelCloneContext` is an implementation detail.
|
|
16
|
+
|
|
17
|
+
```ts
|
|
18
|
+
import type { IModelTransformContext } from "@itwin/imodel-transformer";
|
|
19
|
+
|
|
20
|
+
const context: IModelTransformContext = transformer.context;
|
|
21
|
+
```
|
|
22
|
+
|
|
13
23
|
## Versioning
|
|
14
24
|
|
|
15
25
|
This package, for the time being, relies on @internal APIs in iTwin.js, and therefore has very strict peerDependencies versions.
|
|
16
26
|
We perform a version check at runtime to ensure this. Every new iTwin.js version must be validated, and fixes are rarely ported
|
|
17
27
|
to old versions currently, you must request this in an issue. Removing Dependencies on internal APIs is ongoing.
|
|
18
|
-
You can find the latest @itwin/imodel-transformer version for your iTwin.js version by copy and pasting this into a bash shell
|
|
19
|
-
|
|
20
|
-
(use git bash on windows).
|
|
21
|
-
|
|
22
|
-
```sh
|
|
23
|
-
MY_ITWINJS_VERSION="3.6.0" # edit me
|
|
24
|
-
pnpm -s --package=semver -c dlx node <<EOF
|
|
25
|
-
json=""
|
|
26
|
-
require("https").get("https://registry.npmjs.org/@itwin/imodel-transformer", r=>r.setEncoding("utf8").on("data", d=>json+=d).on("end", ()=>{
|
|
27
|
-
semver=require(process.env.PATH.split(":").find(x=>x.includes(".bin"))+"/../semver")
|
|
28
|
-
console.log(Object.entries(JSON.parse(json).versions)
|
|
29
|
-
.filter(([,v])=>semver.satisfies("$MY_ITWINJS_VERSION", v.peerDependencies["@itwin/core-backend"]))
|
|
30
|
-
.map(([k,v])=>k).reverse())
|
|
31
|
-
}))
|
|
32
|
-
EOF
|
|
33
|
-
```
|
|
34
|
-
|
|
35
28
|
## Environment Variables
|
|
36
29
|
|
|
37
30
|
### TRANSFORMER_NO_STRICT_DEP_CHECK
|
|
38
31
|
|
|
39
|
-
Set this variable to `1` to disable strict dependency checks in `packages/transformer/src/transformer.ts`. The strict dependency check validates that the version of
|
|
40
|
-
|
|
41
|
-
### SUGGEST_TRANSFORMER_VERSIONS
|
|
42
|
-
|
|
43
|
-
Set this variable to `1` to enable `packages/transformer/src/transformer.ts` to suggest compatible versions if dependencies are not in the specified peer dependency range of this package.
|
|
32
|
+
Set this variable to `1` to disable strict dependency checks in `packages/transformer/src/imodel-transformer.ts`. The strict dependency check validates that the version of `@itwin/core-backend` provided falls in the range defined by the peer dependencies of the transformer package.
|
|
44
33
|
|
|
45
34
|
```dotenv
|
|
46
|
-
# Disable strict dependency checks in transformer.ts
|
|
47
35
|
TRANSFORMER_NO_STRICT_DEP_CHECK=1
|
|
48
|
-
|
|
49
|
-
# Enable version suggestions in transformer.ts
|
|
50
|
-
SUGGEST_TRANSFORMER_VERSIONS=1
|
|
36
|
+
```
|
package/lib/cjs/Algo.d.ts
CHANGED
|
@@ -7,8 +7,4 @@
|
|
|
7
7
|
* @internal
|
|
8
8
|
*/
|
|
9
9
|
export declare function rangesFromRangeAndSkipped(start: number, end: number, skipped: number[]): [number, number][];
|
|
10
|
-
/**
|
|
11
|
-
* @internal
|
|
12
|
-
*/
|
|
13
|
-
export declare function renderRanges(ranges: [number, number][]): number[];
|
|
14
10
|
//# sourceMappingURL=Algo.d.ts.map
|
package/lib/cjs/Algo.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"Algo.d.ts","sourceRoot":"","sources":["../../src/Algo.ts"],"names":[],"mappings":"AAIA;;GAEG;AAEH;;;;GAIG;AACH,wBAAgB,yBAAyB,CACvC,KAAK,EAAE,MAAM,EACb,GAAG,EAAE,MAAM,EACX,OAAO,EAAE,MAAM,EAAE,GAChB,CAAC,MAAM,EAAE,MAAM,CAAC,EAAE,CA2BpB
|
|
1
|
+
{"version":3,"file":"Algo.d.ts","sourceRoot":"","sources":["../../src/Algo.ts"],"names":[],"mappings":"AAIA;;GAEG;AAEH;;;;GAIG;AACH,wBAAgB,yBAAyB,CACvC,KAAK,EAAE,MAAM,EACb,GAAG,EAAE,MAAM,EACX,OAAO,EAAE,MAAM,EAAE,GAChB,CAAC,MAAM,EAAE,MAAM,CAAC,EAAE,CA2BpB"}
|
package/lib/cjs/Algo.js
CHANGED
|
@@ -8,7 +8,6 @@
|
|
|
8
8
|
*/
|
|
9
9
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
10
10
|
exports.rangesFromRangeAndSkipped = rangesFromRangeAndSkipped;
|
|
11
|
-
exports.renderRanges = renderRanges;
|
|
12
11
|
/** given a discrete inclusive range [start, end] e.g. [-10, 12] and several "skipped" values", e.g.
|
|
13
12
|
* (-10, 1, -3, 5, 15), return the ordered set of subranges of the original range that exclude
|
|
14
13
|
* those values
|
|
@@ -58,14 +57,4 @@ function findRangeContaining(pt, inRanges) {
|
|
|
58
57
|
}
|
|
59
58
|
return -1;
|
|
60
59
|
}
|
|
61
|
-
/**
|
|
62
|
-
* @internal
|
|
63
|
-
*/
|
|
64
|
-
function renderRanges(ranges) {
|
|
65
|
-
const result = [];
|
|
66
|
-
for (const range of ranges)
|
|
67
|
-
for (let i = range[0]; i <= range[1]; ++i)
|
|
68
|
-
result.push(i);
|
|
69
|
-
return result;
|
|
70
|
-
}
|
|
71
60
|
//# sourceMappingURL=Algo.js.map
|
package/lib/cjs/Algo.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"Algo.js","sourceRoot":"","sources":["../../src/Algo.ts"],"names":[],"mappings":";AAAA;;;gGAGgG;AAChG;;GAEG
|
|
1
|
+
{"version":3,"file":"Algo.js","sourceRoot":"","sources":["../../src/Algo.ts"],"names":[],"mappings":";AAAA;;;gGAGgG;AAChG;;GAEG;;;AAEH;;;;GAIG;AACH,mCACE,KAAa,EACb,GAAW,EACX,OAAiB;IAEjB,SAAS,UAAU,CAAC,KAAuB;QACzC,OAAO,KAAK,CAAC,CAAC,CAAC,IAAI,KAAK,CAAC,CAAC,CAAC,CAAC;IAC9B,CAAC;IAED,MAAM,UAAU,GAAG,CAAC,KAAK,EAAE,GAAG,CAAqB,CAAC;IAEpD,IAAI,CAAC,UAAU,CAAC,UAAU,CAAC;QACzB,MAAM,UAAU,CAAC,mBAAmB,KAAK,KAAK,GAAG,GAAG,CAAC,CAAC;IAExD,MAAM,MAAM,GAAG,CAAC,UAAU,CAAC,CAAC;IAC5B,KAAK,MAAM,IAAI,IAAI,OAAO,EAAE,CAAC;QAC3B,MAAM,UAAU,GAAG,mBAAmB,CAAC,IAAI,EAAE,MAAM,CAAC,CAAC;QACrD,IAAI,UAAU,KAAK,CAAC,CAAC;YAAE,SAAS;QAChC,MAAM,KAAK,GAAG,MAAM,CAAC,UAAU,CAAC,CAAC;QACjC,oIAAoI;QACpI,IAAI,KAAK,CAAC,CAAC,CAAC,KAAK,KAAK,CAAC,CAAC,CAAC,IAAI,IAAI,KAAK,KAAK,CAAC,CAAC,CAAC;YAC5C,MAAM,CAAC,MAAM,CAAC,UAAU,EAAE,CAAC,CAAC,CAAC;QAC/B,MAAM,SAAS,GAAG,CAAC,KAAK,CAAC,CAAC,CAAC,EAAE,IAAI,GAAG,CAAC,CAAqB,CAAC;QAC3D,MAAM,UAAU,GAAG,CAAC,IAAI,GAAG,CAAC,EAAE,KAAK,CAAC,CAAC,CAAC,CAAqB,CAAC;QAC5D,IAAI,UAAU,CAAC,SAAS,CAAC,IAAI,UAAU,CAAC,UAAU,CAAC;YACjD,MAAM,CAAC,MAAM,CAAC,UAAU,EAAE,CAAC,EAAE,SAAS,EAAE,UAAU,CAAC,CAAC;aACjD,IAAI,UAAU,CAAC,SAAS,CAAC;YAAE,MAAM,CAAC,MAAM,CAAC,UAAU,EAAE,CAAC,EAAE,SAAS,CAAC,CAAC;aACnE,IAAI,UAAU,CAAC,UAAU,CAAC;YAAE,MAAM,CAAC,MAAM,CAAC,UAAU,EAAE,CAAC,EAAE,UAAU,CAAC,CAAC;IAC5E,CAAC;IAED,OAAO,MAAM,CAAC;AAChB,CAAC;AAED,SAAS,mBAAmB,CAAC,EAAU,EAAE,QAA4B;IACnE,IAAI,KAAK,GAAG,CAAC,CAAC;IACd,IAAI,GAAG,GAAG,QAAQ,CAAC,MAAM,GAAG,CAAC,CAAC;IAC9B,OAAO,GAAG,IAAI,KAAK,EAAE,CAAC;QACpB,MAAM,GAAG,GAAG,KAAK,GAAG,IAAI,CAAC,KAAK,CAAC,CAAC,GAAG,GAAG,KAAK,CAAC,GAAG,CAAC,CAAC,CAAC;QAClD,MAAM,KAAK,GAAG,QAAQ,CAAC,GAAG,CAAC,CAAC;QAE5B,IAAI,EAAE,IAAI,KAAK,CAAC,CAAC,CAAC,IAAI,EAAE,IAAI,KAAK,CAAC,CAAC,CAAC;YAAE,OAAO,GAAG,CAAC;QAEjD,IAAI,EAAE,GAAG,KAAK,CAAC,CAAC,CAAC,EAAE,CAAC;YAClB,GAAG,GAAG,GAAG,GAAG,CAAC,CAAC;QAChB,CAAC;aAAM,CAAC;YACN,KAAK,GAAG,GAAG,GAAG,CAAC,CAAC;QAClB,CAAC;IACH,CAAC;IACD,OAAO,CAAC,CAAC,CAAC;AACZ,CAAC","sourcesContent":["/*---------------------------------------------------------------------------------------------\n * Copyright (c) Bentley Systems, Incorporated. All rights reserved.\n * See LICENSE.md in the project root for license terms and full copyright notice.\n *--------------------------------------------------------------------------------------------*/\n/** @packageDocumentation\n * @module Utils\n */\n\n/** given a discrete inclusive range [start, end] e.g. [-10, 12] and several \"skipped\" values\", e.g.\n * (-10, 1, -3, 5, 15), return the ordered set of subranges of the original range that exclude\n * those values\n * @internal\n */\nexport function rangesFromRangeAndSkipped(\n start: number,\n end: number,\n skipped: number[]\n): [number, number][] {\n function validRange(range: [number, number]): boolean {\n return range[0] <= range[1];\n }\n\n const firstRange = [start, end] as [number, number];\n\n if (!validRange(firstRange))\n throw RangeError(`invalid range: [${start}, ${end}]`);\n\n const ranges = [firstRange];\n for (const skip of skipped) {\n const rangeIndex = findRangeContaining(skip, ranges);\n if (rangeIndex === -1) continue;\n const range = ranges[rangeIndex];\n // If the range we find ourselves in is just a single point (range[0] === range[1]) then we need to remove it if (range[0] === skip)\n if (range[0] === range[1] && skip === range[0])\n ranges.splice(rangeIndex, 1);\n const leftRange = [range[0], skip - 1] as [number, number];\n const rightRange = [skip + 1, range[1]] as [number, number];\n if (validRange(leftRange) && validRange(rightRange))\n ranges.splice(rangeIndex, 1, leftRange, rightRange);\n else if (validRange(leftRange)) ranges.splice(rangeIndex, 1, leftRange);\n else if (validRange(rightRange)) ranges.splice(rangeIndex, 1, rightRange);\n }\n\n return ranges;\n}\n\nfunction findRangeContaining(pt: number, inRanges: [number, number][]): number {\n let begin = 0;\n let end = inRanges.length - 1;\n while (end >= begin) {\n const mid = begin + Math.floor((end - begin) / 2);\n const range = inRanges[mid];\n\n if (pt >= range[0] && pt <= range[1]) return mid;\n\n if (pt < range[0]) {\n end = mid - 1;\n } else {\n begin = mid + 1;\n }\n }\n return -1;\n}\n"]}
|
package/lib/cjs/BigMap.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"BigMap.d.ts","sourceRoot":"","sources":["../../src/BigMap.ts"],"names":[],"mappings":"AAIA;;GAEG;AACH,OAAO,EAAE,UAAU,EAAE,MAAM,qBAAqB,CAAC;AAEjD;;;;;;GAMG;AACH,qBAAa,MAAM,CAAC,CAAC,CAAE,YAAW,GAAG,CAAC,UAAU,EAAE,CAAC,CAAC;IAClD,OAAO,CAAC,KAAK,CAAiC;IAC9C,OAAO,CAAC,KAAK,CAAS;IAEtB,IAAW,IAAI,IAAI,MAAM,CAExB
|
|
1
|
+
{"version":3,"file":"BigMap.d.ts","sourceRoot":"","sources":["../../src/BigMap.ts"],"names":[],"mappings":"AAIA;;GAEG;AACH,OAAO,EAAE,UAAU,EAAE,MAAM,qBAAqB,CAAC;AAEjD;;;;;;GAMG;AACH,qBAAa,MAAM,CAAC,CAAC,CAAE,YAAW,GAAG,CAAC,UAAU,EAAE,CAAC,CAAC;IAClD,OAAO,CAAC,KAAK,CAAiC;IAC9C,OAAO,CAAC,KAAK,CAAS;IAEtB,IAAW,IAAI,IAAI,MAAM,CAExB;IAED,cAoBC;IAEM,KAAK,IAAI,IAAI,CAGnB;IAEM,MAAM,CAAC,GAAG,EAAE,UAAU,GAAG,OAAO,CAOtC;IAEM,OAAO,CACZ,UAAU,EAAE,CAAC,KAAK,EAAE,CAAC,EAAE,GAAG,EAAE,UAAU,EAAE,GAAG,EAAE,GAAG,CAAC,UAAU,EAAE,CAAC,CAAC,KAAK,IAAI,EACxE,OAAO,CAAC,EAAE,GAAG,GACZ,IAAI,CAIN;IAEM,GAAG,CAAC,GAAG,EAAE,UAAU,GAAG,CAAC,GAAG,SAAS,CAEzC;IAEM,GAAG,CAAC,GAAG,EAAE,UAAU,GAAG,OAAO,CAEnC;IAEM,GAAG,CAAC,GAAG,EAAE,UAAU,EAAE,KAAK,EAAE,CAAC,GAAG,IAAI,CAS1C;IAEM,CAAC,MAAM,CAAC,QAAQ,CAAC,IAAI,WAAW,CAAC,CAAC,UAAU,EAAE,CAAC,CAAC,CAAC,CAEvD;IAED,IAAW,CAAC,MAAM,CAAC,WAAW,CAAC,WAE9B;IAEO,OAAO,IAAI,WAAW,CAAC,CAAC,UAAU,EAAE,CAAC,CAAC,CAAC,CAK9C;IAEO,IAAI,IAAI,WAAW,CAAC,UAAU,CAAC,CAKtC;IAEO,MAAM,IAAI,WAAW,CAAC,CAAC,CAAC,CAK/B;CACF"}
|
package/lib/cjs/BigMap.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"BigMap.js","sourceRoot":"","sources":["../../src/BigMap.ts"],"names":[],"mappings":";;;AASA;;;;;;GAMG;AACH
|
|
1
|
+
{"version":3,"file":"BigMap.js","sourceRoot":"","sources":["../../src/BigMap.ts"],"names":[],"mappings":"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","sourcesContent":["/*---------------------------------------------------------------------------------------------\n * Copyright (c) Bentley Systems, Incorporated. All rights reserved.\n * See LICENSE.md in the project root for license terms and full copyright notice.\n *--------------------------------------------------------------------------------------------*/\n/** @packageDocumentation\n * @module Utils\n */\nimport { Id64String } from \"@itwin/core-bentley\";\n\n/**\n * This class serves as a temporary solution to address the issue of the V8 JavaScript engine's Map implementation,\n * which is limited to approximately 16.7 million elements. Currently, only Id64 string representations are\n * supported by this Map; any other type will lead to errors. It's worth noting that our future plan is to\n * replace this stopgap with a more robust solution, utilizing a temporary SQLite database (https://github.com/iTwin/imodel-transformer/issues/83).\n * @internal\n */\nexport class BigMap<V> implements Map<Id64String, V> {\n private _maps: Record<string, Map<string, V>>;\n private _size: number;\n\n public get size(): number {\n return this._size;\n }\n\n public constructor() {\n this._maps = {\n 0: new Map(),\n 1: new Map(),\n 2: new Map(),\n 3: new Map(),\n 4: new Map(),\n 5: new Map(),\n 6: new Map(),\n 7: new Map(),\n 8: new Map(),\n 9: new Map(),\n a: new Map(),\n b: new Map(),\n c: new Map(),\n d: new Map(),\n e: new Map(),\n f: new Map(),\n };\n this._size = 0;\n }\n\n public clear(): void {\n Object.values(this._maps).forEach((m) => m.clear());\n this._size = 0;\n }\n\n public delete(key: Id64String): boolean {\n const wasDeleted = this._maps[key[key.length - 1]].delete(key);\n if (wasDeleted) {\n this._size--;\n }\n\n return wasDeleted;\n }\n\n public forEach(\n callbackfn: (value: V, key: Id64String, map: Map<Id64String, V>) => void,\n thisArg?: any\n ): void {\n Object.values(this._maps).forEach((m) => {\n m.forEach(callbackfn, thisArg);\n });\n }\n\n public get(key: Id64String): V | undefined {\n return this._maps[key[key.length - 1]].get(key);\n }\n\n public has(key: Id64String): boolean {\n return this._maps[key[key.length - 1]].has(key);\n }\n\n public set(key: Id64String, value: V): this {\n const mapForKey = this._maps[key[key.length - 1]];\n if (mapForKey === undefined)\n throw Error(`Tried to set ${key}, but that key has no submap`);\n const beforeSize = mapForKey.size;\n mapForKey.set(key, value);\n const afterSize = mapForKey.size;\n this._size += afterSize - beforeSize;\n return this;\n }\n\n public [Symbol.iterator](): MapIterator<[Id64String, V]> {\n return this.entries();\n }\n\n public get [Symbol.toStringTag]() {\n return \"BigMap\";\n }\n\n public *entries(): MapIterator<[Id64String, V]> {\n const maps = Object.values(this._maps);\n for (const map of maps) {\n for (const [key, value] of map.entries()) yield [key, value];\n }\n }\n\n public *keys(): MapIterator<Id64String> {\n const maps = Object.values(this._maps);\n for (const map of maps) {\n for (const key of map.keys()) yield key;\n }\n }\n\n public *values(): MapIterator<V> {\n const maps = Object.values(this._maps);\n for (const map of maps) {\n for (const value of map.values()) yield value;\n }\n }\n}\n"]}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"BranchProvenanceInitializer.d.ts","sourceRoot":"","sources":["../../src/BranchProvenanceInitializer.ts"],"names":[],"mappings":"AAIA,OAAO,
|
|
1
|
+
{"version":3,"file":"BranchProvenanceInitializer.d.ts","sourceRoot":"","sources":["../../src/BranchProvenanceInitializer.ts"],"names":[],"mappings":"AAIA,OAAO,EAKL,QAAQ,EAGT,MAAM,qBAAqB,CAAC;AAC7B,OAAO,EAAY,UAAU,EAAoB,MAAM,qBAAqB,CAAC;AAW7E;;GAEG;AACH,MAAM,WAAW,kBAAkB;IACjC,8DAA8D;IAC9D,MAAM,EAAE,QAAQ,CAAC;IACjB,6CAA6C;IAC7C,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,2CAA2C;IAC3C,iBAAiB,CAAC,EAAE,MAAM,CAAC;IAC3B;;;OAGG;IACH,MAAM,EAAE,QAAQ,CAAC;IACjB;;;;;;;OAOG;IACH,uBAAuB,CAAC,EAAE,IAAI,GAAG,KAAK,GAAG,kBAAkB,CAAC;CAC7D;AAED;;GAEG;AACH,MAAM,WAAW,oBAAoB;IACnC,oBAAoB,EAAE,UAAU,CAAC;IACjC,sBAAsB,EAAE,UAAU,CAAC;IACnC,sBAAsB,EAAE,UAAU,CAAC;CACpC;AAED;;GAEG;AACH,wBAAsB,0BAA0B,CAC9C,IAAI,EAAE,kBAAkB,GACvB,OAAO,CAAC,oBAAoB,CAAC,CAqJ/B"}
|
|
@@ -8,13 +8,16 @@ exports.initializeBranchProvenance = initializeBranchProvenance;
|
|
|
8
8
|
const core_backend_1 = require("@itwin/core-backend");
|
|
9
9
|
const core_bentley_1 = require("@itwin/core-bentley");
|
|
10
10
|
const core_common_1 = require("@itwin/core-common");
|
|
11
|
-
const
|
|
12
|
-
const
|
|
13
|
-
const
|
|
11
|
+
const node_assert_1 = require("node:assert");
|
|
12
|
+
const ProvenanceManager_1 = require("./ProvenanceManager");
|
|
13
|
+
const node_url_1 = require("node:url");
|
|
14
|
+
const TransformerPackageMetadata_1 = require("./TransformerPackageMetadata");
|
|
14
15
|
/**
|
|
15
16
|
* @alpha
|
|
16
17
|
*/
|
|
17
18
|
async function initializeBranchProvenance(args) {
|
|
19
|
+
let editTxn = new core_backend_1.EditTxn(args.branch, "initializeBranchProvenance");
|
|
20
|
+
editTxn.start();
|
|
18
21
|
if (args.createFedGuidsForMaster) {
|
|
19
22
|
// FIXME<LOW>: Consider enforcing that the master and branch dbs passed as part of ProvenanceInitArgs to this function
|
|
20
23
|
// are identical. https://github.com/iTwin/imodel-transformer/issues/138
|
|
@@ -22,33 +25,27 @@ async function initializeBranchProvenance(args) {
|
|
|
22
25
|
UPDATE bis_Element
|
|
23
26
|
SET FederationGuid=randomblob(16)
|
|
24
27
|
WHERE FederationGuid IS NULL
|
|
25
|
-
`,
|
|
26
|
-
// eslint-disable-next-line @itwin/no-internal
|
|
27
|
-
(s) => assert(s.step() === core_bentley_1.DbResult.BE_SQLITE_DONE, args.branch.getLastError()));
|
|
28
|
+
`, (s) => (0, node_assert_1.strict)(s.step() === core_bentley_1.DbResult.BE_SQLITE_DONE, args.master.getLastError()));
|
|
28
29
|
const masterPath = args.master.pathName;
|
|
29
30
|
const reopenMaster = makeDbReopener(args.master);
|
|
30
31
|
args.master.close(); // prevent busy
|
|
31
|
-
args.branch.withSqliteStatement(`ATTACH DATABASE '${(0,
|
|
32
|
-
// eslint-disable-next-line @itwin/no-internal
|
|
33
|
-
(s) => assert(s.step() === core_bentley_1.DbResult.BE_SQLITE_DONE, args.branch.getLastError()));
|
|
32
|
+
args.branch.withSqliteStatement(`ATTACH DATABASE '${(0, node_url_1.pathToFileURL)(`${masterPath}`)}?mode=ro' AS master`, (s) => (0, node_assert_1.strict)(s.step() === core_bentley_1.DbResult.BE_SQLITE_DONE, args.branch.getLastError()));
|
|
34
33
|
args.branch.withSqliteStatement(`
|
|
35
34
|
UPDATE main.bis_Element
|
|
36
35
|
SET FederationGuid = (
|
|
37
36
|
SELECT m.FederationGuid
|
|
38
37
|
FROM master.bis_Element m
|
|
39
38
|
WHERE m.Id=main.bis_Element.Id
|
|
40
|
-
)`,
|
|
41
|
-
// eslint-disable-next-line @itwin/no-internal
|
|
42
|
-
(s) => assert(s.step() === core_bentley_1.DbResult.BE_SQLITE_DONE, args.branch.getLastError()));
|
|
39
|
+
)`, (s) => (0, node_assert_1.strict)(s.step() === core_bentley_1.DbResult.BE_SQLITE_DONE, args.branch.getLastError()));
|
|
43
40
|
args.branch.clearCaches(); // statements write lock attached db (clearing statement cache does not fix this)
|
|
44
|
-
|
|
41
|
+
editTxn.saveChanges();
|
|
42
|
+
editTxn.end();
|
|
45
43
|
args.branch.withSqliteStatement("DETACH DATABASE master", (s) => {
|
|
46
44
|
const res = s.step();
|
|
47
45
|
if (res !== core_bentley_1.DbResult.BE_SQLITE_DONE)
|
|
48
46
|
core_bentley_1.Logger.logTrace("initializeBranchProvenance", `Error detaching db (we will close anyway): ${args.branch.getLastError()}`);
|
|
49
47
|
// this is the case until native side changes
|
|
50
|
-
|
|
51
|
-
assert(res === core_bentley_1.DbResult.BE_SQLITE_ERROR, args.branch.getLastError());
|
|
48
|
+
(0, node_assert_1.strict)(res === core_bentley_1.DbResult.BE_SQLITE_ERROR, args.branch.getLastError());
|
|
52
49
|
});
|
|
53
50
|
args.branch.performCheckpoint();
|
|
54
51
|
const reopenBranch = makeDbReopener(args.branch);
|
|
@@ -58,9 +55,12 @@ async function initializeBranchProvenance(args) {
|
|
|
58
55
|
reopenMaster(),
|
|
59
56
|
reopenBranch(),
|
|
60
57
|
]);
|
|
58
|
+
// Recreate editTxn on the reopened branch db
|
|
59
|
+
editTxn = new core_backend_1.EditTxn(args.branch, "initializeBranchProvenance");
|
|
60
|
+
editTxn.start();
|
|
61
61
|
}
|
|
62
62
|
// create an external source and owning repository link to use as our *Target Scope Element* for future synchronizations
|
|
63
|
-
const masterRepoLinkId =
|
|
63
|
+
const masterRepoLinkId = editTxn.insertElement({
|
|
64
64
|
classFullName: core_backend_1.RepositoryLink.classFullName,
|
|
65
65
|
code: core_backend_1.RepositoryLink.createCode(args.branch, core_backend_1.IModelDb.repositoryModelId, "example-code-value"),
|
|
66
66
|
model: core_backend_1.IModelDb.repositoryModelId,
|
|
@@ -69,15 +69,13 @@ async function initializeBranchProvenance(args) {
|
|
|
69
69
|
repositoryGuid: args.master.iModelId,
|
|
70
70
|
description: args.masterDescription,
|
|
71
71
|
});
|
|
72
|
-
const masterExternalSourceId =
|
|
72
|
+
const masterExternalSourceId = editTxn.insertElement({
|
|
73
73
|
classFullName: core_backend_1.ExternalSource.classFullName,
|
|
74
74
|
model: core_backend_1.IModelDb.rootSubjectId,
|
|
75
75
|
code: core_common_1.Code.createEmpty(),
|
|
76
76
|
repository: new core_backend_1.ExternalSourceIsInRepository(masterRepoLinkId),
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
connectorVersion: require("../../package.json").version,
|
|
80
|
-
/* eslint-enable @typescript-eslint/no-require-imports */
|
|
77
|
+
connectorName: TransformerPackageMetadata_1.transformerPackageMetadata.name,
|
|
78
|
+
connectorVersion: TransformerPackageMetadata_1.transformerPackageMetadata.version,
|
|
81
79
|
});
|
|
82
80
|
const fedGuidlessElemsSql = `
|
|
83
81
|
SELECT ECInstanceId AS id
|
|
@@ -88,13 +86,13 @@ async function initializeBranchProvenance(args) {
|
|
|
88
86
|
const elemReader = args.branch.createQueryReader(fedGuidlessElemsSql, undefined, { usePrimaryConn: true });
|
|
89
87
|
for await (const row of elemReader) {
|
|
90
88
|
const id = row.id;
|
|
91
|
-
const aspectProps =
|
|
89
|
+
const aspectProps = ProvenanceManager_1.ProvenanceManager.initElementProvenanceOptions(id, id, {
|
|
92
90
|
isReverseSynchronization: false,
|
|
93
91
|
targetScopeElementId: masterExternalSourceId,
|
|
94
92
|
sourceDb: args.master,
|
|
95
93
|
targetDb: args.branch,
|
|
96
94
|
});
|
|
97
|
-
|
|
95
|
+
editTxn.insertAspect(aspectProps);
|
|
98
96
|
}
|
|
99
97
|
const fedGuidlessRelsSql = `
|
|
100
98
|
SELECT erte.ECInstanceId as id
|
|
@@ -108,15 +106,17 @@ async function initializeBranchProvenance(args) {
|
|
|
108
106
|
const relReader = args.branch.createQueryReader(fedGuidlessRelsSql, undefined, { usePrimaryConn: true });
|
|
109
107
|
for await (const row of relReader) {
|
|
110
108
|
const id = row.id;
|
|
111
|
-
const aspectProps = await
|
|
109
|
+
const aspectProps = await ProvenanceManager_1.ProvenanceManager.initRelationshipProvenanceOptions(id, id, {
|
|
112
110
|
isReverseSynchronization: false,
|
|
113
111
|
targetScopeElementId: masterExternalSourceId,
|
|
114
112
|
sourceDb: args.master,
|
|
115
113
|
targetDb: args.branch,
|
|
116
114
|
forceOldRelationshipProvenanceMethod: false,
|
|
117
115
|
});
|
|
118
|
-
|
|
116
|
+
editTxn.insertAspect(aspectProps);
|
|
119
117
|
}
|
|
118
|
+
editTxn.saveChanges();
|
|
119
|
+
editTxn.end();
|
|
120
120
|
if (args.createFedGuidsForMaster === true) {
|
|
121
121
|
args.master.close();
|
|
122
122
|
args.branch.close();
|
|
@@ -139,7 +139,7 @@ function makeDbReopener(db) {
|
|
|
139
139
|
else if (db instanceof core_backend_1.StandaloneDb)
|
|
140
140
|
reopenDb = (mode = originalMode) => core_backend_1.StandaloneDb.openFile(dbPath, mode);
|
|
141
141
|
else
|
|
142
|
-
|
|
142
|
+
(0, node_assert_1.strict)(false, `db type '${db.constructor.name}' not supported`);
|
|
143
143
|
return reopenDb;
|
|
144
144
|
}
|
|
145
145
|
//# sourceMappingURL=BranchProvenanceInitializer.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"BranchProvenanceInitializer.js","sourceRoot":"","sources":["../../src/BranchProvenanceInitializer.ts"],"names":[],"mappings":"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","sourcesContent":["/*---------------------------------------------------------------------------------------------\n * Copyright (c) Bentley Systems, Incorporated. All rights reserved.\n * See LICENSE.md in the project root for license terms and full copyright notice.\n *--------------------------------------------------------------------------------------------*/\nimport {\n BriefcaseDb,\n ExternalSource,\n ExternalSourceIsInRepository,\n IModelDb,\n RepositoryLink,\n StandaloneDb,\n} from \"@itwin/core-backend\";\nimport { DbResult, Id64String, Logger, OpenMode } from \"@itwin/core-bentley\";\nimport {\n Code,\n ExternalSourceProps,\n RepositoryLinkProps,\n} from \"@itwin/core-common\";\nimport * as assert from \"assert\";\nimport { IModelTransformer } from \"./IModelTransformer\";\nimport { pathToFileURL } from \"url\";\n/**\n * @alpha\n */\nexport interface ProvenanceInitArgs {\n /** the master iModel which is the source of the provenance */\n master: IModelDb;\n /** the canonical url of the master iModel */\n masterUrl?: string;\n /** the description of the master iModel */\n masterDescription?: string;\n /**\n * @param {IModelDb} branchDb - the branch iModel which is the container of the provenance\n * Must be opened Read/Write\n */\n branch: IModelDb;\n /**\n * insert Federation Guids in all lacking elements in the master database, which will prevent\n * needing to insert External Source Aspects for provenance tracking\n * @note requires a read/write master\n * @note closes both the master and branch iModels to reset caches, so you must reopen them.\n * If you pass `\"keep-reopened-db\"`, this object's `master` and `branch` properties will\n * be set to new, open databases.\n */\n createFedGuidsForMaster?: true | false | \"keep-reopened-db\";\n}\n\n/**\n * @alpha\n */\nexport interface ProvenanceInitResult {\n targetScopeElementId: Id64String;\n masterExternalSourceId: Id64String;\n masterRepositoryLinkId: Id64String;\n}\n\n/**\n * @alpha\n */\nexport async function initializeBranchProvenance(\n args: ProvenanceInitArgs\n): Promise<ProvenanceInitResult> {\n if (args.createFedGuidsForMaster) {\n // FIXME<LOW>: Consider enforcing that the master and branch dbs passed as part of ProvenanceInitArgs to this function\n // are identical. https://github.com/iTwin/imodel-transformer/issues/138\n args.master.withSqliteStatement(\n `\n UPDATE bis_Element\n SET FederationGuid=randomblob(16)\n WHERE FederationGuid IS NULL\n `,\n // eslint-disable-next-line @itwin/no-internal\n (s) =>\n assert(s.step() === DbResult.BE_SQLITE_DONE, args.branch.getLastError())\n );\n const masterPath = args.master.pathName;\n const reopenMaster = makeDbReopener(args.master);\n args.master.close(); // prevent busy\n args.branch.withSqliteStatement(\n `ATTACH DATABASE '${pathToFileURL(`${masterPath}`)}?mode=ro' AS master`,\n // eslint-disable-next-line @itwin/no-internal\n (s) =>\n assert(s.step() === DbResult.BE_SQLITE_DONE, args.branch.getLastError())\n );\n args.branch.withSqliteStatement(\n `\n UPDATE main.bis_Element\n SET FederationGuid = (\n SELECT m.FederationGuid\n FROM master.bis_Element m\n WHERE m.Id=main.bis_Element.Id\n )`,\n\n // eslint-disable-next-line @itwin/no-internal\n (s) =>\n assert(s.step() === DbResult.BE_SQLITE_DONE, args.branch.getLastError())\n );\n args.branch.clearCaches(); // statements write lock attached db (clearing statement cache does not fix this)\n args.branch.saveChanges();\n args.branch.withSqliteStatement(\"DETACH DATABASE master\", (s) => {\n const res = s.step();\n if (res !== DbResult.BE_SQLITE_DONE)\n Logger.logTrace(\n \"initializeBranchProvenance\",\n `Error detaching db (we will close anyway): ${args.branch.getLastError()}`\n );\n // this is the case until native side changes\n // eslint-disable-next-line @itwin/no-internal\n assert(res === DbResult.BE_SQLITE_ERROR, args.branch.getLastError());\n });\n args.branch.performCheckpoint();\n\n const reopenBranch = makeDbReopener(args.branch);\n // close dbs because element cache could be invalid\n args.branch.close();\n [args.master, args.branch] = await Promise.all([\n reopenMaster(),\n reopenBranch(),\n ]);\n }\n\n // create an external source and owning repository link to use as our *Target Scope Element* for future synchronizations\n const masterRepoLinkId = args.branch.elements.insertElement({\n classFullName: RepositoryLink.classFullName,\n code: RepositoryLink.createCode(\n args.branch,\n IModelDb.repositoryModelId,\n \"example-code-value\"\n ),\n model: IModelDb.repositoryModelId,\n url: args.masterUrl,\n format: \"iModel\",\n repositoryGuid: args.master.iModelId,\n description: args.masterDescription,\n } as RepositoryLinkProps);\n\n const masterExternalSourceId = args.branch.elements.insertElement({\n classFullName: ExternalSource.classFullName,\n model: IModelDb.rootSubjectId,\n code: Code.createEmpty(),\n repository: new ExternalSourceIsInRepository(masterRepoLinkId),\n /* eslint-disable @typescript-eslint/no-require-imports */\n connectorName: require(\"../../package.json\").name,\n connectorVersion: require(\"../../package.json\").version,\n /* eslint-enable @typescript-eslint/no-require-imports */\n } as ExternalSourceProps);\n\n const fedGuidlessElemsSql = `\n SELECT ECInstanceId AS id\n FROM Bis.Element\n WHERE FederationGuid IS NULL\n AND ECInstanceId NOT IN (0x1, 0xe, 0x10) /* ignore special elems */\n `;\n const elemReader = args.branch.createQueryReader(\n fedGuidlessElemsSql,\n undefined,\n { usePrimaryConn: true }\n );\n for await (const row of elemReader) {\n const id: string = row.id;\n const aspectProps = IModelTransformer.initElementProvenanceOptions(id, id, {\n isReverseSynchronization: false,\n targetScopeElementId: masterExternalSourceId,\n sourceDb: args.master,\n targetDb: args.branch,\n });\n args.branch.elements.insertAspect(aspectProps);\n }\n\n const fedGuidlessRelsSql = `\n SELECT erte.ECInstanceId as id\n FROM Bis.ElementRefersToElements erte\n JOIN bis.Element se\n ON se.ECInstanceId=erte.SourceECInstanceId\n JOIN bis.Element te\n ON te.ECInstanceId=erte.TargetECInstanceId\n WHERE se.FederationGuid IS NULL\n OR te.FederationGuid IS NULL`;\n const relReader = args.branch.createQueryReader(\n fedGuidlessRelsSql,\n undefined,\n { usePrimaryConn: true }\n );\n for await (const row of relReader) {\n const id: string = row.id;\n const aspectProps =\n await IModelTransformer.initRelationshipProvenanceOptions(id, id, {\n isReverseSynchronization: false,\n targetScopeElementId: masterExternalSourceId,\n sourceDb: args.master,\n targetDb: args.branch,\n forceOldRelationshipProvenanceMethod: false,\n });\n args.branch.elements.insertAspect(aspectProps);\n }\n\n if (args.createFedGuidsForMaster === true) {\n args.master.close();\n args.branch.close();\n }\n\n return {\n targetScopeElementId: masterExternalSourceId,\n masterExternalSourceId,\n masterRepositoryLinkId: masterRepoLinkId,\n };\n}\n\nfunction makeDbReopener(db: IModelDb) {\n const originalMode = db.isReadonly ? OpenMode.Readonly : OpenMode.ReadWrite;\n const dbPath = db.pathName;\n let reopenDb: (mode?: OpenMode) => IModelDb | Promise<IModelDb>;\n if (db instanceof BriefcaseDb)\n reopenDb = async (mode = originalMode) =>\n BriefcaseDb.open({\n fileName: dbPath,\n readonly: mode === OpenMode.Readonly,\n });\n else if (db instanceof StandaloneDb)\n reopenDb = (mode = originalMode) => StandaloneDb.openFile(dbPath, mode);\n else assert(false, `db type '${db.constructor.name}' not supported`);\n return reopenDb;\n}\n"]}
|
|
1
|
+
{"version":3,"file":"BranchProvenanceInitializer.js","sourceRoot":"","sources":["../../src/BranchProvenanceInitializer.ts"],"names":[],"mappings":"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","sourcesContent":["/*---------------------------------------------------------------------------------------------\n * Copyright (c) Bentley Systems, Incorporated. All rights reserved.\n * See LICENSE.md in the project root for license terms and full copyright notice.\n *--------------------------------------------------------------------------------------------*/\nimport {\n BriefcaseDb,\n EditTxn,\n ExternalSource,\n ExternalSourceIsInRepository,\n IModelDb,\n RepositoryLink,\n StandaloneDb,\n} from \"@itwin/core-backend\";\nimport { DbResult, Id64String, Logger, OpenMode } from \"@itwin/core-bentley\";\nimport {\n Code,\n ExternalSourceProps,\n RepositoryLinkProps,\n} from \"@itwin/core-common\";\nimport { strict as assert } from \"node:assert\";\nimport { ProvenanceManager } from \"./ProvenanceManager\";\nimport { pathToFileURL } from \"node:url\";\nimport { transformerPackageMetadata } from \"./TransformerPackageMetadata\";\n\n/**\n * @alpha\n */\nexport interface ProvenanceInitArgs {\n /** the master iModel which is the source of the provenance */\n master: IModelDb;\n /** the canonical url of the master iModel */\n masterUrl?: string;\n /** the description of the master iModel */\n masterDescription?: string;\n /**\n * @param {IModelDb} branchDb - the branch iModel which is the container of the provenance\n * Must be opened Read/Write\n */\n branch: IModelDb;\n /**\n * insert Federation Guids in all lacking elements in the master database, which will prevent\n * needing to insert External Source Aspects for provenance tracking\n * @note requires a read/write master\n * @note closes both the master and branch iModels to reset caches, so you must reopen them.\n * If you pass `\"keep-reopened-db\"`, this object's `master` and `branch` properties will\n * be set to new, open databases.\n */\n createFedGuidsForMaster?: true | false | \"keep-reopened-db\";\n}\n\n/**\n * @alpha\n */\nexport interface ProvenanceInitResult {\n targetScopeElementId: Id64String;\n masterExternalSourceId: Id64String;\n masterRepositoryLinkId: Id64String;\n}\n\n/**\n * @alpha\n */\nexport async function initializeBranchProvenance(\n args: ProvenanceInitArgs\n): Promise<ProvenanceInitResult> {\n let editTxn = new EditTxn(args.branch, \"initializeBranchProvenance\");\n editTxn.start();\n\n if (args.createFedGuidsForMaster) {\n // FIXME<LOW>: Consider enforcing that the master and branch dbs passed as part of ProvenanceInitArgs to this function\n // are identical. https://github.com/iTwin/imodel-transformer/issues/138\n args.master.withSqliteStatement(\n `\n UPDATE bis_Element\n SET FederationGuid=randomblob(16)\n WHERE FederationGuid IS NULL\n `,\n (s) =>\n assert(s.step() === DbResult.BE_SQLITE_DONE, args.master.getLastError())\n );\n const masterPath = args.master.pathName;\n const reopenMaster = makeDbReopener(args.master);\n args.master.close(); // prevent busy\n args.branch.withSqliteStatement(\n `ATTACH DATABASE '${pathToFileURL(`${masterPath}`)}?mode=ro' AS master`,\n (s) =>\n assert(s.step() === DbResult.BE_SQLITE_DONE, args.branch.getLastError())\n );\n args.branch.withSqliteStatement(\n `\n UPDATE main.bis_Element\n SET FederationGuid = (\n SELECT m.FederationGuid\n FROM master.bis_Element m\n WHERE m.Id=main.bis_Element.Id\n )`,\n\n (s) =>\n assert(s.step() === DbResult.BE_SQLITE_DONE, args.branch.getLastError())\n );\n args.branch.clearCaches(); // statements write lock attached db (clearing statement cache does not fix this)\n editTxn.saveChanges();\n editTxn.end();\n args.branch.withSqliteStatement(\"DETACH DATABASE master\", (s) => {\n const res = s.step();\n if (res !== DbResult.BE_SQLITE_DONE)\n Logger.logTrace(\n \"initializeBranchProvenance\",\n `Error detaching db (we will close anyway): ${args.branch.getLastError()}`\n );\n // this is the case until native side changes\n assert(res === DbResult.BE_SQLITE_ERROR, args.branch.getLastError());\n });\n args.branch.performCheckpoint();\n\n const reopenBranch = makeDbReopener(args.branch);\n // close dbs because element cache could be invalid\n args.branch.close();\n [args.master, args.branch] = await Promise.all([\n reopenMaster(),\n reopenBranch(),\n ]);\n // Recreate editTxn on the reopened branch db\n editTxn = new EditTxn(args.branch, \"initializeBranchProvenance\");\n editTxn.start();\n }\n\n // create an external source and owning repository link to use as our *Target Scope Element* for future synchronizations\n const masterRepoLinkId = editTxn.insertElement({\n classFullName: RepositoryLink.classFullName,\n code: RepositoryLink.createCode(\n args.branch,\n IModelDb.repositoryModelId,\n \"example-code-value\"\n ),\n model: IModelDb.repositoryModelId,\n url: args.masterUrl,\n format: \"iModel\",\n repositoryGuid: args.master.iModelId,\n description: args.masterDescription,\n } as RepositoryLinkProps);\n\n const masterExternalSourceId = editTxn.insertElement({\n classFullName: ExternalSource.classFullName,\n model: IModelDb.rootSubjectId,\n code: Code.createEmpty(),\n repository: new ExternalSourceIsInRepository(masterRepoLinkId),\n connectorName: transformerPackageMetadata.name,\n connectorVersion: transformerPackageMetadata.version,\n } as ExternalSourceProps);\n\n const fedGuidlessElemsSql = `\n SELECT ECInstanceId AS id\n FROM Bis.Element\n WHERE FederationGuid IS NULL\n AND ECInstanceId NOT IN (0x1, 0xe, 0x10) /* ignore special elems */\n `;\n const elemReader = args.branch.createQueryReader(\n fedGuidlessElemsSql,\n undefined,\n { usePrimaryConn: true }\n );\n for await (const row of elemReader) {\n const id: string = row.id;\n const aspectProps = ProvenanceManager.initElementProvenanceOptions(id, id, {\n isReverseSynchronization: false,\n targetScopeElementId: masterExternalSourceId,\n sourceDb: args.master,\n targetDb: args.branch,\n });\n editTxn.insertAspect(aspectProps);\n }\n\n const fedGuidlessRelsSql = `\n SELECT erte.ECInstanceId as id\n FROM Bis.ElementRefersToElements erte\n JOIN bis.Element se\n ON se.ECInstanceId=erte.SourceECInstanceId\n JOIN bis.Element te\n ON te.ECInstanceId=erte.TargetECInstanceId\n WHERE se.FederationGuid IS NULL\n OR te.FederationGuid IS NULL`;\n const relReader = args.branch.createQueryReader(\n fedGuidlessRelsSql,\n undefined,\n { usePrimaryConn: true }\n );\n for await (const row of relReader) {\n const id: string = row.id;\n const aspectProps =\n await ProvenanceManager.initRelationshipProvenanceOptions(id, id, {\n isReverseSynchronization: false,\n targetScopeElementId: masterExternalSourceId,\n sourceDb: args.master,\n targetDb: args.branch,\n forceOldRelationshipProvenanceMethod: false,\n });\n editTxn.insertAspect(aspectProps);\n }\n\n editTxn.saveChanges();\n editTxn.end();\n\n if (args.createFedGuidsForMaster === true) {\n args.master.close();\n args.branch.close();\n }\n\n return {\n targetScopeElementId: masterExternalSourceId,\n masterExternalSourceId,\n masterRepositoryLinkId: masterRepoLinkId,\n };\n}\n\nfunction makeDbReopener(db: IModelDb) {\n const originalMode = db.isReadonly ? OpenMode.Readonly : OpenMode.ReadWrite;\n const dbPath = db.pathName;\n let reopenDb: (mode?: OpenMode) => IModelDb | Promise<IModelDb>;\n if (db instanceof BriefcaseDb)\n reopenDb = async (mode = originalMode) =>\n BriefcaseDb.open({\n fileName: dbPath,\n readonly: mode === OpenMode.Readonly,\n });\n else if (db instanceof StandaloneDb)\n reopenDb = (mode = originalMode) => StandaloneDb.openFile(dbPath, mode);\n else assert(false, `db type '${db.constructor.name}' not supported`);\n return reopenDb;\n}\n"]}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import { IModelDb } from "@itwin/core-backend";
|
|
2
|
+
import { Id64String } from "@itwin/core-bentley";
|
|
3
|
+
/** The minimal parent-child forest containing changed or excluded elements and their ancestors. */
|
|
4
|
+
export declare class ChangedElementForest {
|
|
5
|
+
private readonly _rootsByModel;
|
|
6
|
+
private readonly _childrenByParent;
|
|
7
|
+
private constructor();
|
|
8
|
+
static create(sourceDb: IModelDb, ownedCandidateIds: Id64String[], maximumElementCount: number): Promise<ChangedElementForest | undefined>;
|
|
9
|
+
/** Gets the indexed root element IDs for a model. */
|
|
10
|
+
getModelRoots(modelId: Id64String): readonly Id64String[];
|
|
11
|
+
/** Gets the indexed child element IDs for a parent element. */
|
|
12
|
+
getChildren(parentId: Id64String): readonly Id64String[];
|
|
13
|
+
}
|
|
14
|
+
//# sourceMappingURL=ChangedElementForest.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"ChangedElementForest.d.ts","sourceRoot":"","sources":["../../src/ChangedElementForest.ts"],"names":[],"mappings":"AAKA,OAAO,EAGL,QAAQ,EACT,MAAM,qBAAqB,CAAC;AAC7B,OAAO,EAAE,UAAU,EAAuB,MAAM,qBAAqB,CAAC;AAGtE,mGAAmG;AACnG,qBAAa,oBAAoB;IAE7B,OAAO,CAAC,QAAQ,CAAC,aAAa;IAI9B,OAAO,CAAC,QAAQ,CAAC,iBAAiB;IALpC,OAAO,eASH;IAEJ,OAAoB,MAAM,CACxB,QAAQ,EAAE,QAAQ,EAClB,iBAAiB,EAAE,UAAU,EAAE,EAC/B,mBAAmB,EAAE,MAAM,GAC1B,OAAO,CAAC,oBAAoB,GAAG,SAAS,CAAC,CAwD3C;IAED,qDAAqD;IAC9C,aAAa,CAAC,OAAO,EAAE,UAAU,GAAG,SAAS,UAAU,EAAE,CAE/D;IAED,+DAA+D;IACxD,WAAW,CAAC,QAAQ,EAAE,UAAU,GAAG,SAAS,UAAU,EAAE,CAE9D;CACF"}
|
|
@@ -0,0 +1,86 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
/*---------------------------------------------------------------------------------------------
|
|
3
|
+
* Copyright (c) Bentley Systems, Incorporated. All rights reserved.
|
|
4
|
+
* See LICENSE.md in the project root for license terms and full copyright notice.
|
|
5
|
+
*--------------------------------------------------------------------------------------------*/
|
|
6
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
7
|
+
exports.ChangedElementForest = void 0;
|
|
8
|
+
const core_backend_1 = require("@itwin/core-backend");
|
|
9
|
+
const core_bentley_1 = require("@itwin/core-bentley");
|
|
10
|
+
const core_common_1 = require("@itwin/core-common");
|
|
11
|
+
/** The minimal parent-child forest containing changed or excluded elements and their ancestors. */
|
|
12
|
+
class ChangedElementForest {
|
|
13
|
+
_rootsByModel;
|
|
14
|
+
_childrenByParent;
|
|
15
|
+
constructor(_rootsByModel, _childrenByParent) {
|
|
16
|
+
this._rootsByModel = _rootsByModel;
|
|
17
|
+
this._childrenByParent = _childrenByParent;
|
|
18
|
+
}
|
|
19
|
+
static async create(sourceDb, ownedCandidateIds, maximumElementCount) {
|
|
20
|
+
if (ownedCandidateIds.length === 0) {
|
|
21
|
+
return new ChangedElementForest(new Map(), new Map());
|
|
22
|
+
}
|
|
23
|
+
const sql = `
|
|
24
|
+
WITH RECURSIVE ChangedElementHierarchy (ECInstanceId, ParentId, ModelId) AS (
|
|
25
|
+
SELECT e.ECInstanceId, e.Parent.Id, e.Model.Id
|
|
26
|
+
FROM ${core_backend_1.Element.classFullName} e
|
|
27
|
+
INNER JOIN IdSet(:candidateIds) ids ON ids.id = e.ECInstanceId
|
|
28
|
+
UNION
|
|
29
|
+
SELECT p.ECInstanceId, p.Parent.Id, p.Model.Id
|
|
30
|
+
FROM ${core_backend_1.Element.classFullName} p
|
|
31
|
+
INNER JOIN ChangedElementHierarchy c ON p.ECInstanceId = c.ParentId
|
|
32
|
+
)
|
|
33
|
+
SELECT ECInstanceId, ParentId, ModelId FROM ChangedElementHierarchy
|
|
34
|
+
LIMIT :resultLimit
|
|
35
|
+
`;
|
|
36
|
+
core_bentley_1.OrderedId64Iterable.sortArray(ownedCandidateIds);
|
|
37
|
+
const params = new core_common_1.QueryBinder()
|
|
38
|
+
.bindIdSet("candidateIds", ownedCandidateIds)
|
|
39
|
+
.bindInt("resultLimit", maximumElementCount + 1);
|
|
40
|
+
// QueryBinder serializes the IdSet synchronously, so release this temporary copy before retaining the hierarchy.
|
|
41
|
+
ownedCandidateIds.length = 0;
|
|
42
|
+
const rootsByModel = new Map();
|
|
43
|
+
const childrenByParent = new Map();
|
|
44
|
+
let elementCount = 0;
|
|
45
|
+
let elementLimitExceeded = false;
|
|
46
|
+
for await (const row of sourceDb.createQueryReader(sql, params, {
|
|
47
|
+
usePrimaryConn: true,
|
|
48
|
+
})) {
|
|
49
|
+
if (elementCount >= maximumElementCount) {
|
|
50
|
+
// Consume the single overflow row so the ECSqlReader reaches done; it has no disposal API.
|
|
51
|
+
elementLimitExceeded = true;
|
|
52
|
+
continue;
|
|
53
|
+
}
|
|
54
|
+
elementCount++;
|
|
55
|
+
const elementId = row[0];
|
|
56
|
+
const parentId = row[1] ?? undefined;
|
|
57
|
+
const modelId = row[2];
|
|
58
|
+
const index = parentId === undefined ? rootsByModel : childrenByParent;
|
|
59
|
+
const key = parentId ?? modelId;
|
|
60
|
+
const siblings = index.get(key);
|
|
61
|
+
if (siblings === undefined)
|
|
62
|
+
index.set(key, [elementId]);
|
|
63
|
+
else
|
|
64
|
+
siblings.push(elementId);
|
|
65
|
+
}
|
|
66
|
+
if (elementLimitExceeded)
|
|
67
|
+
return undefined;
|
|
68
|
+
for (const siblings of rootsByModel.values()) {
|
|
69
|
+
core_bentley_1.OrderedId64Iterable.sortArray(siblings);
|
|
70
|
+
}
|
|
71
|
+
for (const siblings of childrenByParent.values()) {
|
|
72
|
+
core_bentley_1.OrderedId64Iterable.sortArray(siblings);
|
|
73
|
+
}
|
|
74
|
+
return new ChangedElementForest(rootsByModel, childrenByParent);
|
|
75
|
+
}
|
|
76
|
+
/** Gets the indexed root element IDs for a model. */
|
|
77
|
+
getModelRoots(modelId) {
|
|
78
|
+
return this._rootsByModel.get(modelId) ?? [];
|
|
79
|
+
}
|
|
80
|
+
/** Gets the indexed child element IDs for a parent element. */
|
|
81
|
+
getChildren(parentId) {
|
|
82
|
+
return this._childrenByParent.get(parentId) ?? [];
|
|
83
|
+
}
|
|
84
|
+
}
|
|
85
|
+
exports.ChangedElementForest = ChangedElementForest;
|
|
86
|
+
//# sourceMappingURL=ChangedElementForest.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"ChangedElementForest.js","sourceRoot":"","sources":["../../src/ChangedElementForest.ts"],"names":[],"mappings":"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","sourcesContent":["/*---------------------------------------------------------------------------------------------\n * Copyright (c) Bentley Systems, Incorporated. All rights reserved.\n * See LICENSE.md in the project root for license terms and full copyright notice.\n *--------------------------------------------------------------------------------------------*/\n\nimport {\n // eslint-disable-next-line @typescript-eslint/no-redeclare\n Element,\n IModelDb,\n} from \"@itwin/core-backend\";\nimport { Id64String, OrderedId64Iterable } from \"@itwin/core-bentley\";\nimport { QueryBinder } from \"@itwin/core-common\";\n\n/** The minimal parent-child forest containing changed or excluded elements and their ancestors. */\nexport class ChangedElementForest {\n private constructor(\n private readonly _rootsByModel: ReadonlyMap<\n Id64String,\n readonly Id64String[]\n >,\n private readonly _childrenByParent: ReadonlyMap<\n Id64String,\n readonly Id64String[]\n >\n ) {}\n\n public static async create(\n sourceDb: IModelDb,\n ownedCandidateIds: Id64String[],\n maximumElementCount: number\n ): Promise<ChangedElementForest | undefined> {\n if (ownedCandidateIds.length === 0) {\n return new ChangedElementForest(new Map(), new Map());\n }\n\n const sql = `\n WITH RECURSIVE ChangedElementHierarchy (ECInstanceId, ParentId, ModelId) AS (\n SELECT e.ECInstanceId, e.Parent.Id, e.Model.Id\n FROM ${Element.classFullName} e\n INNER JOIN IdSet(:candidateIds) ids ON ids.id = e.ECInstanceId\n UNION\n SELECT p.ECInstanceId, p.Parent.Id, p.Model.Id\n FROM ${Element.classFullName} p\n INNER JOIN ChangedElementHierarchy c ON p.ECInstanceId = c.ParentId\n )\n SELECT ECInstanceId, ParentId, ModelId FROM ChangedElementHierarchy\n LIMIT :resultLimit\n `;\n OrderedId64Iterable.sortArray(ownedCandidateIds);\n const params = new QueryBinder()\n .bindIdSet(\"candidateIds\", ownedCandidateIds)\n .bindInt(\"resultLimit\", maximumElementCount + 1);\n // QueryBinder serializes the IdSet synchronously, so release this temporary copy before retaining the hierarchy.\n ownedCandidateIds.length = 0;\n const rootsByModel = new Map<Id64String, Id64String[]>();\n const childrenByParent = new Map<Id64String, Id64String[]>();\n let elementCount = 0;\n let elementLimitExceeded = false;\n for await (const row of sourceDb.createQueryReader(sql, params, {\n usePrimaryConn: true,\n })) {\n if (elementCount >= maximumElementCount) {\n // Consume the single overflow row so the ECSqlReader reaches done; it has no disposal API.\n elementLimitExceeded = true;\n continue;\n }\n elementCount++;\n const elementId: Id64String = row[0];\n const parentId: Id64String | undefined = row[1] ?? undefined;\n const modelId: Id64String = row[2];\n const index = parentId === undefined ? rootsByModel : childrenByParent;\n const key = parentId ?? modelId;\n const siblings = index.get(key);\n if (siblings === undefined) index.set(key, [elementId]);\n else siblings.push(elementId);\n }\n\n if (elementLimitExceeded) return undefined;\n\n for (const siblings of rootsByModel.values()) {\n OrderedId64Iterable.sortArray(siblings);\n }\n for (const siblings of childrenByParent.values()) {\n OrderedId64Iterable.sortArray(siblings);\n }\n return new ChangedElementForest(rootsByModel, childrenByParent);\n }\n\n /** Gets the indexed root element IDs for a model. */\n public getModelRoots(modelId: Id64String): readonly Id64String[] {\n return this._rootsByModel.get(modelId) ?? [];\n }\n\n /** Gets the indexed child element IDs for a parent element. */\n public getChildren(parentId: Id64String): readonly Id64String[] {\n return this._childrenByParent.get(parentId) ?? [];\n }\n}\n"]}
|