@measurequick/measurequick-report-generator 1.5.206 → 1.5.208

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@measurequick/measurequick-report-generator",
3
- "version": "1.5.206",
3
+ "version": "1.5.208",
4
4
  "description": "Generates PDF documents for various measureQuick applications.",
5
5
  "main": "index.js",
6
6
  "scripts": {
@@ -1,4 +1,7 @@
1
1
  import * as base64 from "../base-64/icons.js";
2
+ import { PDFDocument } from "pdf-lib";
3
+ import * as notesSummaryPage from "./notes-summary-page.js";
4
+ import * as util from "../util.js";
2
5
 
3
6
  let doc,
4
7
  globalVars,
@@ -7065,7 +7068,33 @@ export async function getReport(payload) {
7065
7068
  );
7066
7069
  }
7067
7070
 
7068
- return { status: 200, data: await doc.output("datauristring") };
7071
+ // Get jsPDF output as base64
7072
+ const jsPdfOutput = await doc.output("datauristring");
7073
+
7074
+ // Add AI summary pages if available
7075
+ const aiSummary = util.getAiSummary ? util.getAiSummary(payload) : null;
7076
+ const notes = util.getAiNotes ? util.getAiNotes(payload) : null;
7077
+
7078
+ if (aiSummary || notes) {
7079
+ try {
7080
+ // Convert jsPDF output to pdf-lib format
7081
+ const base64Data = jsPdfOutput.split(",")[1];
7082
+ const pdfBytes = util._base64ToArrayBuffer(base64Data);
7083
+ const pdfDoc = await PDFDocument.load(pdfBytes);
7084
+
7085
+ // Add AI summary pages
7086
+ await notesSummaryPage.addNotesSummaryPages(pdfDoc, payload);
7087
+
7088
+ // Return combined PDF
7089
+ return { status: 200, data: await pdfDoc.saveAsBase64({ dataUri: true }) };
7090
+ } catch (aiError) {
7091
+ // If AI summary fails, return original PDF without it
7092
+ console.error("Failed to add AI summary pages:", aiError);
7093
+ return { status: 200, data: jsPdfOutput };
7094
+ }
7095
+ }
7096
+
7097
+ return { status: 200, data: jsPdfOutput };
7069
7098
  } catch (error) {
7070
7099
  return { status: 400, data: error };
7071
7100
  }
@@ -15,6 +15,7 @@ import * as vitalsHeatpumpHeatingReport from "./vitals-heatpump-heating-report.j
15
15
  import * as nciReport from "./nci-report.js";
16
16
  import * as energyStarCertificate from "./energy-star-certificate.js";
17
17
  import * as accaCertificate from "./acca-certificate.js";
18
+ import * as notesSummaryPage from "./notes-summary-page.js";
18
19
  import * as util from "../util.js";
19
20
 
20
21
  let docs = [];
@@ -487,6 +488,13 @@ export async function getReport(payload) {
487
488
  errors.push(`System Info: ${error}`);
488
489
  }
489
490
 
491
+ /******** AI SUMMARY / NOTES (1+ PAGES) *********/
492
+ try {
493
+ await notesSummaryPage.addNotesSummaryPages(coreDoc, payload);
494
+ } catch (error) {
495
+ errors.push(`AI Summary: ${error}`);
496
+ }
497
+
490
498
  return errors.length > 0
491
499
  ? { status: 400, data: errors.join("\n") }
492
500
  : { status: 200, data: await coreDoc.saveAsBase64({ dataUri: true }) };
package/util.js CHANGED
@@ -164,10 +164,22 @@ export function capitalizeFirstLetter(string) {
164
164
 
165
165
  export function getToolIcon(test, ref, embeddedIcons) {
166
166
  let toolIcon;
167
+ // Get source value, with fallback for L2/L3 to use L1 source (3-phase systems often only set L1 source)
168
+ let sourceValue = test.source[ref];
169
+ if (!sourceValue && ref) {
170
+ // Try L1 fallback for L2/L3 measurements
171
+ if (ref.includes("_l2") || ref.includes("_l3")) {
172
+ const l1Ref = ref.replace(/_l[23]/, "_l1");
173
+ sourceValue = test.source[l1Ref];
174
+ } else if (ref.includes("_l2_") || ref.includes("_l3_")) {
175
+ const l1Ref = ref.replace(/_l[23]_/, "_l1_");
176
+ sourceValue = test.source[l1Ref];
177
+ }
178
+ }
167
179
  if (test.data.calculated && test.data.calculated[ref])
168
180
  toolIcon = embeddedIcons.iconCalculator;
169
181
  else {
170
- switch (test.source[ref]) {
182
+ switch (sourceValue) {
171
183
  case "Testo":
172
184
  toolIcon = embeddedIcons.iconTesto;
173
185
  break;
@@ -238,7 +250,7 @@ export function getToolIcon(test, ref, embeddedIcons) {
238
250
  break;
239
251
  }
240
252
  }
241
- if (test.source[ref] == "iDVM510" && ref.includes("amperage"))
253
+ if (sourceValue == "iDVM510" && ref.includes("amperage"))
242
254
  toolIcon = embeddedIcons.iconRedfish510333;
243
255
  return toolIcon;
244
256
  }
@@ -281,99 +293,104 @@ export function getElectricalData(test, suffix, embeddedIcons) {
281
293
  if (phase === "Single") {
282
294
  if (
283
295
  (voltage == "115" || voltage == "120") &&
284
- test.data[`voltage_l1`] &&
285
- test.data[`amperage_l1`]
296
+ test.data[`voltage_l1${suffix}`] &&
297
+ test.data[`amperage_l1${suffix}`]
286
298
  ) {
287
- vDisplay = (+test.data[`voltage_l1`]).toFixed(1);
288
- aDisplay = (+test.data[`amperage_l1`]).toFixed(1);
299
+ vDisplay = (+test.data[`voltage_l1${suffix}`]).toFixed(1);
300
+ aDisplay = (+test.data[`amperage_l1${suffix}`]).toFixed(1);
289
301
  } else if (
290
302
  (voltage == "115" || voltage == "120") &&
291
- test.data[`voltage_l1_ph_to_gnd`] &&
292
- test.data[`amperage_l1_ph_to_gnd`]
303
+ test.data[`voltage_l1${suffix}_ph_to_gnd`] &&
304
+ test.data[`amperage_l1${suffix}_ph_to_gnd`]
293
305
  ) {
294
- vDisplay = (+test.data[`voltage_l1_ph_to_gnd`]).toFixed(1);
295
- aDisplay = (+test.data[`amperage_l1_ph_to_gnd`]).toFixed(1);
296
- src = "_l1_ph_to_gnd";
306
+ vDisplay = (+test.data[`voltage_l1${suffix}_ph_to_gnd`]).toFixed(1);
307
+ aDisplay = (+test.data[`amperage_l1${suffix}_ph_to_gnd`]).toFixed(1);
308
+ src = `_l1${suffix}_ph_to_gnd`;
297
309
  } else if (
298
310
  (voltage == "208" ||
299
311
  voltage == "230" ||
300
312
  voltage == "240" ||
301
313
  voltage == "460" ||
302
314
  voltage == "480") &&
303
- test.data[`voltage_l1`] &&
304
- test.data[`amperage_l1`]
315
+ test.data[`voltage_l1${suffix}`] &&
316
+ test.data[`amperage_l1${suffix}`]
305
317
  ) {
306
- vDisplay = (+test.data[`voltage_l1`]).toFixed(1);
307
- aDisplay = (+test.data[`amperage_l1`]).toFixed(1);
318
+ vDisplay = (+test.data[`voltage_l1${suffix}`]).toFixed(1);
319
+ aDisplay = (+test.data[`amperage_l1${suffix}`]).toFixed(1);
308
320
  } else if (
309
321
  (voltage == "208" ||
310
322
  voltage == "230" ||
311
323
  voltage == "240" ||
312
324
  voltage == "460" ||
313
325
  voltage == "480") &&
314
- test.data[`voltage_l1_ph_to_gnd`] &&
315
- test.data[`voltage_l2_ph_to_gnd`] &&
316
- test.data[`amperage_l1_ph_to_gnd`] &&
317
- test.data[`amperage_l2_ph_to_gnd`]
326
+ test.data[`voltage_l1${suffix}_ph_to_gnd`] &&
327
+ test.data[`voltage_l2${suffix}_ph_to_gnd`] &&
328
+ test.data[`amperage_l1${suffix}_ph_to_gnd`] &&
329
+ test.data[`amperage_l2${suffix}_ph_to_gnd`]
318
330
  ) {
319
331
  vDisplay =
320
- (+test.data[`voltage_l1_ph_to_gnd`]).toFixed(1) +
332
+ (+test.data[`voltage_l1${suffix}_ph_to_gnd`]).toFixed(1) +
321
333
  " / " +
322
- (+test.data[`voltage_l2_ph_to_gnd`]).toFixed(1);
334
+ (+test.data[`voltage_l2${suffix}_ph_to_gnd`]).toFixed(1);
323
335
  aDisplay =
324
- (+test.data[`amperage_l1_ph_to_gnd`]).toFixed(1) +
336
+ (+test.data[`amperage_l1${suffix}_ph_to_gnd`]).toFixed(1) +
325
337
  " / " +
326
- (+test.data[`amperage_l2_ph_to_gnd`]).toFixed(1);
327
- src = "_l1_ph_to_gnd";
338
+ (+test.data[`amperage_l2${suffix}_ph_to_gnd`]).toFixed(1);
339
+ src = `_l1${suffix}_ph_to_gnd`;
328
340
  }
329
341
  } else if (
330
342
  phase === "Three" &&
331
- test.data[`voltage_l1`] &&
332
- test.data.voltage_l2 &&
333
- test.data[`voltage_l3`] &&
334
- test.data[`amperage_l1`] &&
335
- test.data.amperage_l2 &&
336
- test.data[`amperage_l3`]
343
+ test.data[`voltage_l1${suffix}`] &&
344
+ test.data[`voltage_l2${suffix}`] &&
345
+ test.data[`voltage_l3${suffix}`] &&
346
+ test.data[`amperage_l1${suffix}`] &&
347
+ test.data[`amperage_l2${suffix}`] &&
348
+ test.data[`amperage_l3${suffix}`]
337
349
  ) {
338
350
  vDisplay =
339
- (+test.data[`voltage_l1`]).toFixed(1) +
351
+ (+test.data[`voltage_l1${suffix}`]).toFixed(1) +
340
352
  " / " +
341
- (+test.data[`voltage_l2`]).toFixed(1) +
353
+ (+test.data[`voltage_l2${suffix}`]).toFixed(1) +
342
354
  " / " +
343
- (+test.data[`voltage_l3`]).toFixed(1);
355
+ (+test.data[`voltage_l3${suffix}`]).toFixed(1);
344
356
  aDisplay =
345
- (+test.data[`amperage_l1`]).toFixed(1) +
357
+ (+test.data[`amperage_l1${suffix}`]).toFixed(1) +
346
358
  " / " +
347
- (+test.data[`amperage_l2`]).toFixed(1) +
359
+ (+test.data[`amperage_l2${suffix}`]).toFixed(1) +
348
360
  " / " +
349
- (+test.data[`amperage_l3`]).toFixed(1);
361
+ (+test.data[`amperage_l3${suffix}`]).toFixed(1);
350
362
  }
351
363
  } else if (test.electrical_capture_type === "Power") {
352
364
  vDisplay = (+test.data[`voltage_l1`]).toFixed(1);
353
365
  aDisplay = (+test.data[`amperage_l1`]).toFixed(1);
354
366
  }
367
+ // Build the source key with suffix for AHU support
368
+ // Note: for ph_to_gnd cases, src already includes the suffix, so don't add it again
369
+ const suffixAlreadyInSrc = src.includes(suffix) && suffix !== "";
370
+ const vSourceKey = suffixAlreadyInSrc ? "voltage" + src : "voltage" + src + suffix;
371
+ const aSourceKey = suffixAlreadyInSrc ? "amperage" + src : "amperage" + src + suffix;
355
372
  if (vDisplay) {
356
- if (test.source["voltage" + src] == "ComfortGuard")
373
+ if (test.source[vSourceKey] == "ComfortGuard")
357
374
  vIcon = embeddedIcons.iconSensi;
358
- else if (test.source["voltage" + src] == "iDVM550" || test.source["voltage" + src] == "iDVM-550")
375
+ else if (test.source[vSourceKey] == "iDVM550" || test.source[vSourceKey] == "iDVM-550")
359
376
  vIcon = embeddedIcons.iconRedfish550;
360
- else if (test.source["voltage" + src] == "VOLT-100")
377
+ else if (test.source[vSourceKey] == "VOLT-100")
361
378
  vIcon = embeddedIcons.iconVolt100;
362
- else if (test.source["voltage" + src] == "iDVM510")
379
+ else if (test.source[vSourceKey] == "iDVM510")
363
380
  vIcon = embeddedIcons.iconRedfish510;
364
- else if (test.source["voltage" + src] == "Fieldpiece")
381
+ else if (test.source[vSourceKey] == "Fieldpiece")
365
382
  vIcon = embeddedIcons.iconFieldpiece;
366
383
  }
367
384
  if (aDisplay) {
368
- if (test.source["amperage" + src] == "ComfortGuard")
385
+ if (test.source[aSourceKey] == "ComfortGuard")
369
386
  aIcon = embeddedIcons.iconSensi;
370
- else if (test.source["amperage" + src] == "iDVM550" || test.source["amperage" + src] == "iDVM-550")
387
+ else if (test.source[aSourceKey] == "iDVM550" || test.source[aSourceKey] == "iDVM-550")
371
388
  aIcon = embeddedIcons.iconRedfish550;
372
- else if (test.source["amperage" + src] == "VOLT-100")
389
+ else if (test.source[aSourceKey] == "VOLT-100")
373
390
  aIcon = embeddedIcons.iconVolt100;
374
- else if (test.source["amperage" + src] == "iDVM510")
391
+ else if (test.source[aSourceKey] == "iDVM510")
375
392
  aIcon = embeddedIcons.iconRedfish510;
376
- else if (test.source["amperage" + src] == "Fieldpiece")
393
+ else if (test.source[aSourceKey] == "Fieldpiece")
377
394
  aIcon = embeddedIcons.iconFieldpiece;
378
395
  }
379
396
  return {