forked from jappel/leistungsbilanz-ts
tsx runs tests without type checking and tsconfig.json covers only src, so 71 type errors had accumulated unnoticed. tsconfig.tests.json now checks every test and helper, and npm run typecheck includes it. Fixtures gain the fields the DTOs have grown since they were written (manualQuantity, circuit apparent power/cos phi, downstream board loads, section totals, building, cover and board info fields). Repository lookups that return "row ?? null" now declare the null in their type, which their callers already handle. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
173 lines
5.1 KiB
TypeScript
173 lines
5.1 KiB
TypeScript
import ExcelJS from "exceljs";
|
|
import {
|
|
createDefaultExternalXlsxTransportConfiguration,
|
|
type ExternalXlsxTransportConfiguration,
|
|
} from "../../src/external-model/xlsx/external-xlsx-contracts.js";
|
|
|
|
export const firstWorksharingId =
|
|
"AAAAAAAA-BBBB-CCCC-DDDD-EEEEEEEEEEEE-00000001";
|
|
export const secondWorksharingId =
|
|
"AAAAAAAA-BBBB-CCCC-DDDD-EEEEEEEEEEEE-00000002";
|
|
|
|
export const externalXlsxTestConfiguration: ExternalXlsxTransportConfiguration =
|
|
createDefaultExternalXlsxTransportConfiguration();
|
|
|
|
/**
|
|
* Loads workbook bytes for editing in a test. ExcelJS declares its own Buffer
|
|
* type, which Node 24's generic Buffer does not satisfy (see loadWorkbook in
|
|
* external-xlsx-transport.ts).
|
|
*/
|
|
export async function loadXlsxWorkbook(bytes: Uint8Array) {
|
|
const workbook = new ExcelJS.Workbook();
|
|
await workbook.xlsx.load(
|
|
Buffer.from(bytes) as unknown as Parameters<typeof workbook.xlsx.load>[0]
|
|
);
|
|
return workbook;
|
|
}
|
|
|
|
export async function createRevitXlsxFixture(options?: {
|
|
duplicateWorksharingId?: boolean;
|
|
secondWorksharingId?: string;
|
|
firstIfcGuid?: string;
|
|
secondIfcGuid?: string;
|
|
includeFormula?: boolean;
|
|
includeRequiredFormulaWithoutResult?: boolean;
|
|
headerRow?: number;
|
|
firstDataRow?: number;
|
|
firstDataColumn?: number;
|
|
}) {
|
|
const workbook = new ExcelJS.Workbook();
|
|
const worksheet = workbook.addWorksheet("Linear Export");
|
|
const headerRow = options?.headerRow ?? 1;
|
|
const firstDataRow = options?.firstDataRow ?? 3;
|
|
const firstDataColumn = options?.firstDataColumn ?? 1;
|
|
const headers = [
|
|
"Worksharing-ID",
|
|
"CAx_Auswahlkenner",
|
|
"MEP-Raum: Nummer",
|
|
"MEP-Raum: Name",
|
|
"Familie und Typ",
|
|
"CAX_AnzahlObjekte",
|
|
"CAx_Anmerkung",
|
|
"kbp_Stromkreisnummer",
|
|
"kbp-E-Verteiler",
|
|
"kbp-E-Stromkreis",
|
|
"kbp-E-Bezeichnung",
|
|
"kbp-E-Elektrische Leistung",
|
|
"kbp-E-Spannung",
|
|
"kbp-E-Stromstärke",
|
|
"IfcGUID",
|
|
"Unbekannt",
|
|
];
|
|
headers.forEach((header, index) => {
|
|
const columnNumber = firstDataColumn + index;
|
|
const cell = worksheet.getCell(headerRow, columnNumber);
|
|
cell.value = header;
|
|
cell.note = `Kommentar ${header}`;
|
|
cell.font = { bold: true };
|
|
worksheet.getColumn(columnNumber).width = 12 + index;
|
|
});
|
|
|
|
setRowValues(worksheet, firstDataRow, firstDataColumn, [
|
|
firstWorksharingId,
|
|
"Steckdose",
|
|
"01.101",
|
|
"Büro",
|
|
"Steckdose: Standard",
|
|
2,
|
|
"Quelle A",
|
|
"UV01-2F1",
|
|
"UV01",
|
|
"-2F1",
|
|
"Arbeitsplatz",
|
|
250,
|
|
230,
|
|
1.09,
|
|
options?.firstIfcGuid ?? "IfcCaseSensitive",
|
|
true,
|
|
]);
|
|
worksheet.getCell(firstDataRow, firstDataColumn + 11).numFmt = "0.00";
|
|
worksheet.getCell(firstDataRow, firstDataColumn + 12).numFmt = "0";
|
|
worksheet.getCell(firstDataRow, firstDataColumn + 13).numFmt = "0.00";
|
|
if (options?.includeFormula) {
|
|
worksheet.getCell(firstDataRow, firstDataColumn + 11).value = {
|
|
formula: "125*2",
|
|
result: 250,
|
|
};
|
|
}
|
|
if (options?.includeRequiredFormulaWithoutResult) {
|
|
worksheet.getCell(firstDataRow, firstDataColumn).value = { formula: "\"\"" };
|
|
}
|
|
|
|
setRowValues(worksheet, firstDataRow + 1, firstDataColumn, [
|
|
options?.duplicateWorksharingId
|
|
? firstWorksharingId
|
|
: options?.secondWorksharingId ?? secondWorksharingId,
|
|
"Leuchte",
|
|
null,
|
|
null,
|
|
"Leuchte: Decke",
|
|
1,
|
|
"Quelle B",
|
|
"UV01-1F1",
|
|
"UV01",
|
|
"-1F1",
|
|
"Beleuchtung",
|
|
42.5,
|
|
230,
|
|
0.18,
|
|
options?.secondIfcGuid ?? "IfcCaseSensitive2",
|
|
"bleibt",
|
|
]);
|
|
worksheet.getCell(firstDataRow + 1, firstDataColumn + 11).numFmt = "0.00";
|
|
setRowValues(worksheet, firstDataRow + 2, firstDataColumn, [
|
|
null,
|
|
"verdächtig",
|
|
null,
|
|
null,
|
|
"Gerät: Ohne ID",
|
|
]);
|
|
setRowValues(worksheet, firstDataRow + 3, firstDataColumn, [
|
|
null,
|
|
"Summe: 292,5 W",
|
|
]);
|
|
|
|
return new Uint8Array(await workbook.xlsx.writeBuffer());
|
|
}
|
|
|
|
export async function createLargeRevitXlsxFixture(objectCount: number) {
|
|
const workbook = new ExcelJS.Workbook();
|
|
const worksheet = workbook.addWorksheet("Linear Export");
|
|
worksheet.addRow([
|
|
"Worksharing-ID", "CAx_Auswahlkenner", "MEP-Raum: Nummer", "MEP-Raum: Name",
|
|
"Familie und Typ", "CAX_AnzahlObjekte", "CAx_Anmerkung", "kbp_Stromkreisnummer",
|
|
"kbp-E-Verteiler", "kbp-E-Stromkreis", "kbp-E-Bezeichnung",
|
|
"kbp-E-Elektrische Leistung", "kbp-E-Spannung", "kbp-E-Stromstärke", "IfcGUID",
|
|
]);
|
|
worksheet.addRow([]);
|
|
for (let index = 0; index < objectCount; index += 1) {
|
|
const suffix = String(index + 1).padStart(8, "0");
|
|
worksheet.addRow([
|
|
`AAAAAAAA-BBBB-CCCC-DDDD-EEEEEEEEEEEE-${suffix}`,
|
|
`Steckdose ${index + 1}`,
|
|
String(100 + (index % 250)),
|
|
`Raum ${index % 250}`,
|
|
"Steckdose: Standard",
|
|
(index % 4) + 1,
|
|
null, null, null, null, null, null, null, null,
|
|
`IFC-${suffix}`,
|
|
]);
|
|
}
|
|
return new Uint8Array(await workbook.xlsx.writeBuffer());
|
|
}
|
|
|
|
function setRowValues(
|
|
worksheet: ExcelJS.Worksheet,
|
|
rowNumber: number,
|
|
firstColumn: number,
|
|
values: ExcelJS.CellValue[]
|
|
) {
|
|
values.forEach((value, index) => {
|
|
worksheet.getCell(rowNumber, firstColumn + index).value = value;
|
|
});
|
|
}
|