UNPKG

@itwin/core-backend

Version:
377 lines • 24.7 kB
/*--------------------------------------------------------------------------------------------- * Copyright (c) Bentley Systems, Incorporated. All rights reserved. * See LICENSE.md in the project root for license terms and full copyright notice. *--------------------------------------------------------------------------------------------*/ import { Id64 } from "@itwin/core-bentley"; import { BisCodeSpec, CodeScopeSpec, CodeSpec, EditTxnError } from "@itwin/core-common"; import { EditTxn, withEditTxn } from "../../EditTxn"; import { SnapshotDb } from "../../IModelDb"; import { ExtensiveTestScenario, IModelTestUtils } from "../IModelTestUtils"; import { DocumentPartition, Sheet } from "../../Element"; import { expect } from "chai"; import { DocumentListModel, SheetIndexModel, SheetModel } from "../../Model"; import { ElementOwnsChildElements, SheetIndexFolderOwnsEntries, SheetIndexOwnsEntries, SheetIndexReferenceRefersToSheetIndex, SheetReferenceRefersToSheet } from "../../NavigationRelationship"; import { SheetIndex, SheetIndexFolder, SheetIndexReference, SheetReference } from "../../SheetIndex"; const getOrCreateDocumentList = (txn) => { const documentListName = "SheetList"; const ids = txn.iModel.queryEntityIds({ from: DocumentPartition.classFullName, where: `CodeValue = '${documentListName}'` }); if (ids.size === 1) return ids.values().next().value; const subjectId = txn.iModel.elements.getRootSubject().id; return DocumentListModel.insert(txn, subjectId, documentListName); }; const insertSheet = (txn, sheetName) => { const modelId = getOrCreateDocumentList(txn); const sheetElementProps = { height: 42, width: 42, scale: 42, classFullName: Sheet.classFullName, code: Sheet.createCode(txn.iModel, modelId, sheetName), model: modelId, }; const sheetElementId = txn.insertElement(sheetElementProps); return txn.insertModel({ classFullName: SheetModel.classFullName, modeledElement: { id: sheetElementId, relClassName: "BisCore:ModelModelsElement" }, }); }; const insertCodeSpec = (txn) => { const indexSpec = CodeSpec.create(txn.iModel, BisCodeSpec.sheetIndex, CodeScopeSpec.Type.Model); txn.iModel.codeSpecs.insert(txn, indexSpec); const entrySpec = CodeSpec.create(txn.iModel, BisCodeSpec.sheetIndexEntry, CodeScopeSpec.Type.ParentElement); txn.iModel.codeSpecs.insert(txn, entrySpec); }; describe("SheetIndex", () => { let iModel; beforeEach(async () => { const iModelFile = IModelTestUtils.prepareOutputFile("IModel", "TestSheetIndex.bim"); const iModelDb = SnapshotDb.createEmpty(iModelFile, { rootSubject: { name: "SheetIndex" } }); await ExtensiveTestScenario.prepareDb(iModelDb); await ExtensiveTestScenario.populateDb(iModelDb); iModel = iModelDb; withEditTxn(iModel, (txn) => insertCodeSpec(txn)); }); afterEach(() => { iModel.close(); }); it("SheetIndexModel Should insert", () => { withEditTxn(iModel, (txn) => { const subjectId = iModel.elements.getRootSubject().id; const modelId = SheetIndexModel.insert(txn, subjectId, "testSheetIndex"); expect(Id64.isValidId64(modelId)).to.be.true; }); }); it("SheetIndex Should insert", () => { withEditTxn(iModel, (txn) => { const subjectId = iModel.elements.getRootSubject().id; const modelId = SheetIndexModel.insert(txn, subjectId, "TestSheetIndexModel"); expect(Id64.isValidId64(modelId)).to.be.true; const sheetIndex = SheetIndex.insert(txn, modelId, "TestSheetIndex"); expect(Id64.isValidId64(sheetIndex)).to.be.true; }); }); describe("Update", () => { it("Priority", () => { withEditTxn(iModel, (txn) => { const subjectId = iModel.elements.getRootSubject().id; const modelId = SheetIndexModel.insert(txn, subjectId, "TestSheetIndexModel"); expect(Id64.isValidId64(modelId)).to.be.true; const sheetIndex1Id = SheetIndex.insert(txn, modelId, "TestSheetIndex"); expect(Id64.isValidId64(sheetIndex1Id)).to.be.true; const folderId = SheetIndexFolder.insert(txn, { sheetIndexModelId: modelId, parentId: sheetIndex1Id, name: "TestFolder", priority: 1 }); expect(Id64.isValidId64(folderId)).to.be.true; const folder = iModel.elements.tryGetElement(folderId); expect(folder).to.not.be.undefined; expect(folder?.entryPriority).equals(1); folder.entryPriority = 0; folder.update(txn); const folderPostUpdate = iModel.elements.tryGetElement(folderId); expect(folderPostUpdate?.entryPriority).equals(0); }); }); it("Parent", () => { withEditTxn(iModel, (txn) => { const subjectId = iModel.elements.getRootSubject().id; const modelId = SheetIndexModel.insert(txn, subjectId, "TestSheetIndexModel"); expect(Id64.isValidId64(modelId)).to.be.true; const sheetIndex1Id = SheetIndex.insert(txn, modelId, "TestSheetIndex-1"); expect(Id64.isValidId64(sheetIndex1Id)).to.be.true; const sheetIndex2Id = SheetIndex.insert(txn, modelId, "TestSheetIndex-2"); expect(Id64.isValidId64(sheetIndex2Id)).to.be.true; const folderId = SheetIndexFolder.insert(txn, { sheetIndexModelId: modelId, parentId: sheetIndex1Id, name: "TestFolder", priority: 1 }); expect(Id64.isValidId64(folderId)).to.be.true; const folder = iModel.elements.tryGetElement(folderId); expect(folder).to.not.be.undefined; const parentRel11 = iModel.relationships.tryGetInstanceProps(ElementOwnsChildElements.classFullName, { sourceId: sheetIndex1Id, targetId: folderId }); expect(parentRel11).to.not.be.undefined; folder.parent = new SheetIndexOwnsEntries(sheetIndex2Id); folder.update(txn); const parentRel12 = iModel.relationships.tryGetInstanceProps(ElementOwnsChildElements.classFullName, { sourceId: sheetIndex1Id, targetId: folderId }); expect(parentRel12).to.be.undefined; const parentRel22 = iModel.relationships.tryGetInstanceProps(ElementOwnsChildElements.classFullName, { sourceId: sheetIndex2Id, targetId: folderId }); expect(parentRel22).to.not.be.undefined; }); }); it("Sheet Reference", () => { withEditTxn(iModel, (txn) => { const sheet1Id = insertSheet(txn, "sheet-1"); const sheet2Id = insertSheet(txn, "sheet-2"); const subjectId = iModel.elements.getRootSubject().id; const modelId = SheetIndexModel.insert(txn, subjectId, "TestSheetIndexModel"); expect(Id64.isValidId64(modelId)).to.be.true; const sheetIndexId = SheetIndex.insert(txn, modelId, "TestSheetIndex"); expect(Id64.isValidId64(sheetIndexId)).to.be.true; const sheetRefId = SheetReference.insert(txn, { sheetIndexModelId: modelId, parentId: sheetIndexId, name: "TestSheetReference", priority: 1 }); expect(Id64.isValidId64(sheetRefId)).to.be.true; const sheetRef = iModel.elements.tryGetElement(sheetRefId); expect(sheetRef).to.not.be.undefined; expect(sheetRef.sheet).to.be.undefined; sheetRef.sheet = new SheetReferenceRefersToSheet(sheet1Id); sheetRef.update(txn); const refersRel11 = iModel.relationships.tryGetInstanceProps(SheetReferenceRefersToSheet.classFullName, { sourceId: sheetRefId, targetId: sheet1Id }); expect(refersRel11).to.not.be.undefined; const parentRel12 = iModel.relationships.tryGetInstanceProps(SheetReferenceRefersToSheet.classFullName, { sourceId: sheetRefId, targetId: sheet2Id }); expect(parentRel12).to.be.undefined; sheetRef.sheet = new SheetReferenceRefersToSheet(sheet2Id); sheetRef.update(txn); const refersRel21 = iModel.relationships.tryGetInstanceProps(SheetReferenceRefersToSheet.classFullName, { sourceId: sheetRefId, targetId: sheet1Id }); expect(refersRel21).to.be.undefined; const parentRel22 = iModel.relationships.tryGetInstanceProps(SheetReferenceRefersToSheet.classFullName, { sourceId: sheetRefId, targetId: sheet2Id }); expect(parentRel22).to.not.be.undefined; }); }); it("Sheet Index Reference", () => { withEditTxn(iModel, (txn) => { const subjectId = iModel.elements.getRootSubject().id; const modelId = SheetIndexModel.insert(txn, subjectId, "TestSheetIndexModel"); expect(Id64.isValidId64(modelId)).to.be.true; const sheetIndex1Id = SheetIndex.insert(txn, modelId, "TestSheetIndex-1"); expect(Id64.isValidId64(sheetIndex1Id)).to.be.true; const sheetIndex2Id = SheetIndex.insert(txn, modelId, "TestSheetIndex-2"); expect(Id64.isValidId64(sheetIndex2Id)).to.be.true; const sheetIndex3Id = SheetIndex.insert(txn, modelId, "TestSheetIndex-3"); expect(Id64.isValidId64(sheetIndex3Id)).to.be.true; const sheetIndexRefId = SheetIndexReference.insert(txn, { sheetIndexModelId: modelId, parentId: sheetIndex1Id, name: "TestSheetReference", priority: 1 }); expect(Id64.isValidId64(sheetIndexRefId)).to.be.true; const sheetIndexRef = iModel.elements.tryGetElement(sheetIndexRefId); expect(sheetIndexRef).to.not.be.undefined; expect(sheetIndexRef.sheetIndex).to.be.undefined; sheetIndexRef.sheetIndex = new SheetIndexReferenceRefersToSheetIndex(sheetIndex2Id); sheetIndexRef.update(txn); const parentRel11 = iModel.relationships.tryGetInstanceProps(SheetIndexReferenceRefersToSheetIndex.classFullName, { sourceId: sheetIndexRefId, targetId: sheetIndex2Id }); expect(parentRel11).to.not.be.undefined; sheetIndexRef.sheetIndex = new SheetIndexReferenceRefersToSheetIndex(sheetIndex3Id); sheetIndexRef.update(txn); const refersRel21 = iModel.relationships.tryGetInstanceProps(SheetIndexReferenceRefersToSheetIndex.classFullName, { sourceId: sheetIndexRefId, targetId: sheetIndex2Id }); expect(refersRel21).to.be.undefined; const parentRel22 = iModel.relationships.tryGetInstanceProps(SheetIndexReferenceRefersToSheetIndex.classFullName, { sourceId: sheetIndexRefId, targetId: sheetIndex3Id }); expect(parentRel22).to.not.be.undefined; }); }); }); describe("SheetIndexFolder", () => { it("Should insert", () => { withEditTxn(iModel, (txn) => { const subjectId = iModel.elements.getRootSubject().id; const modelId = SheetIndexModel.insert(txn, subjectId, "TestSheetIndexModel"); expect(Id64.isValidId64(modelId)).to.be.true; const sheetIndexId = SheetIndex.insert(txn, modelId, "TestSheetIndex"); expect(Id64.isValidId64(sheetIndexId)).to.be.true; const folderId = SheetIndexFolder.insert(txn, { sheetIndexModelId: modelId, parentId: sheetIndexId, name: "TestFolder-1", priority: 1 }); expect(Id64.isValidId64(folderId)).to.be.true; const folder = iModel.elements.tryGetElement(folderId); expect(folder).to.not.be.undefined; const relationship = iModel.relationships.tryGetInstanceProps(ElementOwnsChildElements.classFullName, { sourceId: sheetIndexId, targetId: folderId }); expect(relationship).to.not.be.undefined; expect(relationship?.classFullName).equals(SheetIndexOwnsEntries.classFullName); expect(folder?.parent?.id).equals(sheetIndexId); }); }); it("Should not insert SheetIndexFolder with the same name", () => { withEditTxn(iModel, (txn) => { const subjectId = iModel.elements.getRootSubject().id; const modelId = SheetIndexModel.insert(txn, subjectId, "TestSheetIndexModel"); expect(Id64.isValidId64(modelId)).to.be.true; const sheetIndex = SheetIndex.insert(txn, modelId, "TestSheetIndex"); expect(Id64.isValidId64(sheetIndex)).to.be.true; const folder = SheetIndexFolder.insert(txn, { sheetIndexModelId: modelId, parentId: sheetIndex, name: "TestFolder", priority: 1 }); expect(Id64.isValidId64(folder)).to.be.true; const failInsert = () => SheetIndexFolder.insert(txn, { sheetIndexModelId: modelId, parentId: sheetIndex, name: "TestFolder", priority: 0 }); expect(failInsert).throws(); }); }); it("Should have children", () => { withEditTxn(iModel, (txn) => { const subjectId = iModel.elements.getRootSubject().id; const modelId = SheetIndexModel.insert(txn, subjectId, "TestSheetIndexModel"); expect(Id64.isValidId64(modelId)).to.be.true; const sheetIndexId = SheetIndex.insert(txn, modelId, "TestSheetIndex"); expect(Id64.isValidId64(sheetIndexId)).to.be.true; const folder1Id = SheetIndexFolder.insert(txn, { sheetIndexModelId: modelId, parentId: sheetIndexId, name: "TestFolder-1", priority: 1 }); expect(Id64.isValidId64(folder1Id)).to.be.true; const folder2Id = SheetIndexFolder.insert(txn, { sheetIndexModelId: modelId, parentId: folder1Id, name: "TestFolder-2", priority: 1 }); expect(Id64.isValidId64(folder2Id)).to.be.true; const folder2 = iModel.elements.tryGetElement(folder2Id); expect(folder2).to.not.be.undefined; const relationship = iModel.relationships.tryGetInstanceProps(ElementOwnsChildElements.classFullName, { sourceId: folder1Id, targetId: folder2Id }); expect(relationship).to.not.be.undefined; expect(relationship?.classFullName).equals(SheetIndexFolderOwnsEntries.classFullName); expect(folder2?.parent?.id).equals(folder1Id); }); }); }); describe("SheetReferences", () => { it("Should not insert SheetReferences with the same name", () => { withEditTxn(iModel, (txn) => { const subjectId = iModel.elements.getRootSubject().id; const modelId = SheetIndexModel.insert(txn, subjectId, "TestSheetIndexModel"); expect(Id64.isValidId64(modelId)).to.be.true; const sheetIndex = SheetIndex.insert(txn, modelId, "TestSheetIndex"); expect(Id64.isValidId64(sheetIndex)).to.be.true; const sheetRef1 = SheetReference.insert(txn, { sheetIndexModelId: modelId, parentId: sheetIndex, name: "TestSheetRef", priority: 1 }); expect(Id64.isValidId64(sheetRef1)).to.be.true; const failInsert = () => SheetReference.insert(txn, { sheetIndexModelId: modelId, parentId: sheetIndex, name: "TestSheetRef", priority: 0 }); expect(failInsert).throws(); }); }); it("Should insert SheetReferences without a Sheet", () => { withEditTxn(iModel, (txn) => { const subjectId = iModel.elements.getRootSubject().id; const modelId = SheetIndexModel.insert(txn, subjectId, "TestSheetIndexModel"); expect(Id64.isValidId64(modelId)).to.be.true; const sheetIndex = SheetIndex.insert(txn, modelId, "TestSheetIndex"); expect(Id64.isValidId64(sheetIndex)).to.be.true; const sheetRef = SheetReference.insert(txn, { sheetIndexModelId: modelId, parentId: sheetIndex, name: "TestSheetRef", priority: 1 }); expect(Id64.isValidId64(sheetRef)).to.be.true; }); }); it("Should insert and with a Sheet", () => { withEditTxn(iModel, (txn) => { const sheetId = insertSheet(txn, "sheet-1"); const subjectId = iModel.elements.getRootSubject().id; const modelId = SheetIndexModel.insert(txn, subjectId, "TestSheetIndexModel"); expect(Id64.isValidId64(modelId)).to.be.true; const sheetIndex = SheetIndex.insert(txn, modelId, "TestSheetIndex"); expect(Id64.isValidId64(sheetIndex)).to.be.true; const sheetRefId = SheetReference.insert(txn, { sheetIndexModelId: modelId, parentId: sheetIndex, name: "TestSheetRef", priority: 1, sheetId }); expect(Id64.isValidId64(sheetRefId)).to.be.true; const ref = iModel.elements.tryGetElement(sheetRefId); expect(ref).to.not.be.undefined; const relationship = iModel.relationships.tryGetInstanceProps(SheetReferenceRefersToSheet.classFullName, { sourceId: sheetRefId, targetId: sheetId }); expect(relationship).to.not.be.undefined; expect(relationship?.classFullName).equals(SheetReferenceRefersToSheet.classFullName); expect(ref?.sheet?.id).equals(sheetId); }); }); it("supports deprecated SheetReference.insert overload when implicit writes are allowed", () => { const previousEnforcement = EditTxn.implicitWriteEnforcement; EditTxn.implicitWriteEnforcement = "allow"; try { withEditTxn(iModel, (txn) => { const sheetId = insertSheet(txn, "legacy-sheet"); const subjectId = iModel.elements.getRootSubject().id; const modelId = SheetIndexModel.insert(txn, subjectId, "LegacySheetRefModel"); const sheetIndex = SheetIndex.insert(txn, modelId, "LegacySheetIndex"); // eslint-disable-next-line @typescript-eslint/no-deprecated const sheetRefId = SheetReference.insert({ iModelDb: iModel, sheetIndexModelId: modelId, parentId: sheetIndex, name: "LegacySheetRef", priority: 1, sheetId, }); expect(Id64.isValidId64(sheetRefId)).to.be.true; const ref = iModel.elements.tryGetElement(sheetRefId); expect(ref?.sheet?.id).to.equal(sheetId); }); } finally { EditTxn.implicitWriteEnforcement = previousEnforcement; } }); it("rejects deprecated SheetReference.insert overload when implicit writes are disallowed", () => { const previousEnforcement = EditTxn.implicitWriteEnforcement; EditTxn.implicitWriteEnforcement = "throw"; try { withEditTxn(iModel, (txn) => { const sheetId = insertSheet(txn, "legacy-throw-sheet"); const subjectId = iModel.elements.getRootSubject().id; const modelId = SheetIndexModel.insert(txn, subjectId, "LegacyThrowSheetRefModel"); const sheetIndex = SheetIndex.insert(txn, modelId, "LegacyThrowSheetIndex"); // eslint-disable-next-line @typescript-eslint/no-deprecated expect(() => SheetReference.insert({ iModelDb: iModel, sheetIndexModelId: modelId, parentId: sheetIndex, name: "LegacyThrowSheetRef", priority: 1, sheetId, })).to.throw().that.satisfies((error) => EditTxnError.isError(error, "implicit-txn-write-disallowed")); }); } finally { EditTxn.implicitWriteEnforcement = previousEnforcement; } }); it.skip("Should not insert with the same Sheet twice", () => { withEditTxn(iModel, (txn) => { const sheetId = insertSheet(txn, "sheet-1"); const subjectId = iModel.elements.getRootSubject().id; const modelId = SheetIndexModel.insert(txn, subjectId, "TestSheetIndexModel"); expect(Id64.isValidId64(modelId)).to.be.true; const sheetIndex = SheetIndex.insert(txn, modelId, "TestSheetIndex"); SheetReference.insert(txn, { sheetIndexModelId: modelId, parentId: sheetIndex, name: "TestSheetRef-1", priority: 1, sheetId }); const sameIndex = () => SheetReference.insert(txn, { sheetIndexModelId: modelId, parentId: sheetIndex, name: "TestSheetRef-2", priority: 2, sheetId }); expect(sameIndex).throws(); }); }); }); describe("SheetIndexReferences", () => { it("Should not insert SheetIndexReferences with the same name", () => { withEditTxn(iModel, (txn) => { const subjectId = iModel.elements.getRootSubject().id; const modelId = SheetIndexModel.insert(txn, subjectId, "TestSheetIndexModel"); expect(Id64.isValidId64(modelId)).to.be.true; const sheetIndex = SheetIndex.insert(txn, modelId, "TestSheetIndex"); expect(Id64.isValidId64(sheetIndex)).to.be.true; const sheetIndexRef = SheetIndexReference.insert(txn, { sheetIndexModelId: modelId, parentId: sheetIndex, name: "TestSheetIndexRef", priority: 1 }); expect(Id64.isValidId64(sheetIndexRef)).to.be.true; const failInsert = () => SheetIndexReference.insert(txn, { sheetIndexModelId: modelId, parentId: sheetIndex, name: "TestSheetIndexRef", priority: 0 }); expect(failInsert).throws(); }); }); it("Should insert SheetIndexReferences without a SheetIndexRef", () => { withEditTxn(iModel, (txn) => { const subjectId = iModel.elements.getRootSubject().id; const modelId = SheetIndexModel.insert(txn, subjectId, "TestSheetIndexModel"); expect(Id64.isValidId64(modelId)).to.be.true; const sheetIndex1Id = SheetIndex.insert(txn, modelId, "TestSheetIndex"); expect(Id64.isValidId64(sheetIndex1Id)).to.be.true; const sheetRef = SheetIndexReference.insert(txn, { sheetIndexModelId: modelId, parentId: sheetIndex1Id, name: "TestSheetIndexRef", priority: 1 }); expect(Id64.isValidId64(sheetRef)).to.be.true; }); }); it("Should insert and with a SheetIndexRef", () => { withEditTxn(iModel, (txn) => { const subjectId = iModel.elements.getRootSubject().id; const modelId = SheetIndexModel.insert(txn, subjectId, "TestSheetIndexModel"); expect(Id64.isValidId64(modelId)).to.be.true; const sheetIndex1Id = SheetIndex.insert(txn, modelId, "TestSheetIndex-1"); expect(Id64.isValidId64(sheetIndex1Id)).to.be.true; const sheetIndex2Id = SheetIndex.insert(txn, modelId, "TestSheetIndex-2"); expect(Id64.isValidId64(sheetIndex1Id)).to.be.true; const sheetIndexRefId = SheetIndexReference.insert(txn, { sheetIndexModelId: modelId, parentId: sheetIndex1Id, name: "TestSheetRef", priority: 1, sheetIndexId: sheetIndex2Id }); expect(Id64.isValidId64(sheetIndexRefId)).to.be.true; const ref = iModel.elements.tryGetElement(sheetIndexRefId); expect(ref).to.not.be.undefined; const relationship = iModel.relationships.tryGetInstanceProps(SheetIndexReferenceRefersToSheetIndex.classFullName, { sourceId: sheetIndexRefId, targetId: sheetIndex2Id }); expect(relationship).to.not.be.undefined; expect(relationship?.classFullName).equals(SheetIndexReferenceRefersToSheetIndex.classFullName); expect(ref?.sheetIndex?.id).equals(sheetIndex2Id); }); }); }); }); //# sourceMappingURL=SheetIndex.test.js.map