diff --git a/client/src/components/print-center-item/print-center-item.component.jsx b/client/src/components/print-center-item/print-center-item.component.jsx
index 3016e1373..ed369f17f 100644
--- a/client/src/components/print-center-item/print-center-item.component.jsx
+++ b/client/src/components/print-center-item/print-center-item.component.jsx
@@ -1,5 +1,6 @@
import { MailOutlined, PrinterOutlined } from "@ant-design/icons";
-import React from "react";
+import { Spin } from "antd";
+import React, { useState } from "react";
import { connect } from "react-redux";
import { createStructuredSelector } from "reselect";
import { setEmailOptions } from "../../redux/email/email.actions";
@@ -22,8 +23,10 @@ export function PrintCenterItemComponent({
bodyshop,
disabled,
}) {
+ const [loading, setLoading] = useState(false);
const { context } = printCenterModal;
const renderToNewWindow = async () => {
+ setLoading(true);
await GenerateDocument(
{
name: item.key,
@@ -32,6 +35,7 @@ export function PrintCenterItemComponent({
{},
"p"
);
+ setLoading(false);
};
if (disabled) return
{item.title} ;
@@ -51,6 +55,7 @@ export function PrintCenterItemComponent({
);
}}
/>
+ {loading && }
);
}
diff --git a/client/src/components/print-center-speed-print/print-center-speed-print.component.jsx b/client/src/components/print-center-speed-print/print-center-speed-print.component.jsx
index fa05515d3..090faee38 100644
--- a/client/src/components/print-center-speed-print/print-center-speed-print.component.jsx
+++ b/client/src/components/print-center-speed-print/print-center-speed-print.component.jsx
@@ -1,11 +1,11 @@
import { Button, List, Typography } from "antd";
-import React from "react";
+import React, { useState } from "react";
import { useTranslation } from "react-i18next";
import { connect } from "react-redux";
import { createStructuredSelector } from "reselect";
import { logImEXEvent } from "../../firebase/firebase.utils";
import { selectBodyshop } from "../../redux/user/user.selectors";
-import { GenerateDocument } from "../../utils/RenderTemplate";
+import { GenerateDocuments } from "../../utils/RenderTemplate";
import { TemplateList } from "../../utils/TemplateConstants";
const mapStateToProps = createStructuredSelector({
@@ -16,26 +16,19 @@ const mapDispatchToProps = (dispatch) => ({
});
export function PrintCenterSpeedPrint({ bodyshop, jobId }) {
+ const [loading, setLoading] = useState(false);
const { speedprint } = bodyshop;
const { t } = useTranslation();
- const renderTemplate = async (templateKey) => {
- logImEXEvent("speed_print_template_render");
-
- GenerateDocument(
- {
- name: templateKey,
- variables: { id: jobId },
- },
- {},
- "p"
- );
- };
-
- const renderAllTemplates = (templateKeys) => {
+ const renderAllTemplates = async (templateKeys) => {
logImEXEvent("speed_print_render_all_templates");
-
- templateKeys.forEach((templateKey) => renderTemplate(templateKey));
+ setLoading(true);
+ await GenerateDocuments(
+ templateKeys.map((key) => {
+ return { name: key, variables: { id: jobId } };
+ })
+ );
+ setLoading(false);
};
return (
@@ -50,7 +43,10 @@ export function PrintCenterSpeedPrint({ bodyshop, jobId }) {
renderItem={(sp) => (
renderAllTemplates(sp.templates)}>
+ ,
]}
diff --git a/client/src/components/shop-template-test-render/shop-template-test-render.component.jsx b/client/src/components/shop-template-test-render/shop-template-test-render.component.jsx
index d27885e15..d2b83c865 100644
--- a/client/src/components/shop-template-test-render/shop-template-test-render.component.jsx
+++ b/client/src/components/shop-template-test-render/shop-template-test-render.component.jsx
@@ -50,7 +50,7 @@ export function ShopTemplateTestRender({
view: inlineHtml.data,
context: { ...contextData, bodyshop: bodyshop },
});
- displayTemplateInWindowNoprint(renderResponse.data);
+ // displayTemplateInWindowNoprint(renderResponse.data);
setLoading(false);
} catch (error) {
diff --git a/client/src/components/time-tickets-summary-employees/time-tickets-summary-employees.component.jsx b/client/src/components/time-tickets-summary-employees/time-tickets-summary-employees.component.jsx
index e6322f862..3f3c59955 100644
--- a/client/src/components/time-tickets-summary-employees/time-tickets-summary-employees.component.jsx
+++ b/client/src/components/time-tickets-summary-employees/time-tickets-summary-employees.component.jsx
@@ -1,16 +1,14 @@
-import React from "react";
-import { Statistic, Space, List, Button, Typography } from "antd";
-import LoadingSkeleton from "../loading-skeleton/loading-skeleton.component";
-import { useTranslation } from "react-i18next";
+import { Button, List, Space, Statistic, Typography } from "antd";
import moment from "moment";
-import RenderTemplate, {
- displayTemplateInWindow,
-} from "../../utils/RenderTemplate";
-import { TemplateList } from "../../utils/TemplateConstants";
+import React from "react";
+import { useTranslation } from "react-i18next";
import { connect } from "react-redux";
import { createStructuredSelector } from "reselect";
import { selectBodyshop } from "../../redux/user/user.selectors";
import { onlyUnique } from "../../utils/arrayHelper";
+import { GenerateDocument } from "../../utils/RenderTemplate";
+import { TemplateList } from "../../utils/TemplateConstants";
+import LoadingSkeleton from "../loading-skeleton/loading-skeleton.component";
const mapStateToProps = createStructuredSelector({
bodyshop: selectBodyshop,
@@ -68,15 +66,14 @@ export function TimeTicketsSummaryEmployees({
});
const handlePrintEmployeeTicket = async (empId) => {
- alert("Missing Key!");
- const html = await RenderTemplate(
+ GenerateDocument(
{
name: TemplateList().time_tickets_by_employee.key,
variables: { id: empId, start: startDate, end: endDate },
},
- bodyshop
+ {},
+ "p"
);
- displayTemplateInWindow(html);
};
return (
diff --git a/client/src/utils/RenderTemplate.js b/client/src/utils/RenderTemplate.js
index d0db5e0d0..4d6502db1 100644
--- a/client/src/utils/RenderTemplate.js
+++ b/client/src/utils/RenderTemplate.js
@@ -1,3 +1,4 @@
+import { notification } from "antd";
import axios from "axios";
import gql from "graphql-tag";
import jsreport from "jsreport-browser-client-dist";
@@ -5,16 +6,149 @@ import { auth } from "../firebase/firebase.utils";
import { setEmailOptions } from "../redux/email/email.actions";
import { store } from "../redux/store";
import client from "../utils/GraphQLClient";
+import { TemplateList } from "./TemplateConstants";
+
const server = process.env.REACT_APP_REPORTS_SERVER_URL;
jsreport.serverUrl = server;
+const Templates = TemplateList();
+
export default async function RenderTemplate(
templateObject,
bodyshop,
renderAsHtml = false
) {
//Query assets that match the template name. Must be in format <>.query
+ let { contextData, useShopSpecificTemplate } = await fetchContextData(
+ templateObject
+ );
+ let reportRequest = {
+ template: {
+ name: useShopSpecificTemplate
+ ? `/${bodyshop.imexshopid}/${templateObject.name}`
+ : `/${templateObject.name}`,
+ ...(renderAsHtml ? {} : { recipe: "chrome-pdf" }),
+ },
+ data: {
+ ...contextData,
+ ...templateObject.variables,
+ ...templateObject.context,
+ headerpath: `/${bodyshop.imexshopid}/header.html`,
+ bodyshop: bodyshop,
+ },
+ };
+ try {
+ const render = await jsreport.renderAsync(reportRequest);
+ if (!renderAsHtml) {
+ render.download(Templates[templateObject.name].title || "");
+ } else {
+ return new Promise((resolve, reject) => {
+ resolve(render.toString());
+ });
+ }
+ } catch (error) {
+ notification["error"]({ message: JSON.stringify(error) });
+ }
+}
+
+export async function RenderTemplates(
+ templateObjects,
+ bodyshop,
+ renderAsHtml = false
+) {
+ //Query assets that match the template name. Must be in format <>.query
+ let templateAndData = [];
+ let proms = [];
+ templateObjects.forEach((template) => {
+ proms.push(
+ (async () => {
+ let { contextData, useShopSpecificTemplate } = await fetchContextData(
+ template
+ );
+ templateAndData.push({
+ templateObject: template,
+ contextData,
+ useShopSpecificTemplate,
+ });
+ })()
+ );
+ });
+ await Promise.all(proms);
+ let rootTemplate = templateAndData.shift();
+
+ let reportRequest = {
+ template: {
+ name: rootTemplate.useShopSpecificTemplate
+ ? `/${bodyshop.imexshopid}/${rootTemplate.templateObject.name}`
+ : `/${rootTemplate.templateObject.name}`,
+ ...(renderAsHtml ? {} : { recipe: "chrome-pdf" }),
+ pdfOperations: templateAndData.map((template) => {
+ return {
+ template: {
+ name: template.useShopSpecificTemplate
+ ? `/${bodyshop.imexshopid}/${template.templateObject.name}`
+ : `/${template.templateObject.name}`,
+ ...(renderAsHtml ? {} : { recipe: "chrome-pdf" }),
+ },
+ data: {
+ ...template.contextData,
+ ...template.templateObject.variables,
+ ...template.templateObject.context,
+ headerpath: `/${bodyshop.imexshopid}/header.html`,
+ bodyshop: bodyshop,
+ },
+ type: "append",
+ mergeWholeDocument: true,
+ renderForEveryPage: true,
+ };
+ }),
+ },
+ data: {
+ ...rootTemplate.contextData,
+ ...rootTemplate.templateObject.variables,
+ ...rootTemplate.templateObject.context,
+ headerpath: `/${bodyshop.imexshopid}/header.html`,
+ bodyshop: bodyshop,
+ },
+ };
+
+ console.log("reportRequest", reportRequest);
+
+ try {
+ const render = await jsreport.renderAsync(reportRequest);
+ if (!renderAsHtml) {
+ render.download("Speed Print");
+ } else {
+ return new Promise((resolve, reject) => {
+ resolve(render.toString());
+ });
+ }
+ } catch (error) {
+ notification["error"]({ message: JSON.stringify(error) });
+ }
+}
+
+export const GenerateDocument = async (template, messageOptions, sendType) => {
+ const bodyshop = store.getState().user.bodyshop;
+ if (sendType === "e") {
+ store.dispatch(
+ setEmailOptions({
+ messageOptions,
+ template,
+ })
+ );
+ } else {
+ await RenderTemplate(template, bodyshop);
+ }
+};
+
+export const GenerateDocuments = async (templates) => {
+ const bodyshop = store.getState().user.bodyshop;
+ await RenderTemplates(templates, bodyshop);
+};
+
+const fetchContextData = async (templateObject) => {
jsreport.headers["Authorization"] =
"Bearer " + (await auth.currentUser.getIdToken());
@@ -44,7 +178,7 @@ export default async function RenderTemplate(
"There are too many queries to choose from. Please ensure there are no conflicting keys."
);
}
- let contextData;
+ let contextData = {};
if (templateQueryToExecute) {
const { data } = await client.query({
query: gql(templateQueryToExecute),
@@ -54,83 +188,37 @@ export default async function RenderTemplate(
contextData = data;
}
- let reportRequest = {
- template: {
- name: useShopSpecificTemplate
- ? `/${bodyshop.imexshopid}/${templateObject.name}`
- : `/${templateObject.name}`,
- ...(renderAsHtml ? {} : { recipe: "chrome-pdf" }),
- },
- data: {
- ...(templateQueryToExecute ? contextData : {}),
- ...templateObject.variables,
- ...templateObject.context,
- headerpath: `/${bodyshop.imexshopid}/header.html`,
- bodyshop: bodyshop,
- },
- };
- const render = await jsreport.renderAsync(reportRequest);
-
- if (!renderAsHtml) {
- render.download();
- // var html =
- // "" +
- // "" +
- // "" +
- // '' +
- // "";
- // displayTemplateInWindowNoprint(html);
- } else {
- return new Promise((resolve, reject) => {
- resolve(render.toString());
- });
- }
-}
-
-export const displayTemplateInWindow = (html) => {
- try {
- var newWin = window.open("", "_blank", "toolbar=0,location=0,menubar=0");
- newWin.document.write(html);
-
- setTimeout(function () {
- newWin.document.close();
- newWin.focus();
- newWin.print();
- newWin.close();
- }, 500);
- } catch (error) {
- console.log("Unable to write to new window.", error);
- }
+ return { contextData, useShopSpecificTemplate };
};
-export const displayTemplateInWindowNoprint = (html) => {
- try {
- var newWin = window.open("", "_blank", "toolbar=0,location=0,menubar=0");
- newWin.document.write(html);
+//export const displayTemplateInWindow = (html) => {
+// try {
+// var newWin = window.open("", "_blank", "toolbar=0,location=0,menubar=0");
+// newWin.document.write(html);
- setTimeout(function () {
- newWin.document.close();
- newWin.focus();
- //newWin.print();
- //newWin.close();
- }, 500);
- } catch (error) {
- console.log("Unable to write to new window.", error);
- }
-};
+// setTimeout(function () {
+// newWin.document.close();
+// newWin.focus();
+// newWin.print();
+// newWin.close();
+// }, 500);
+// } catch (error) {
+// console.log("Unable to write to new window.", error);
+// }
+// };
-export const GenerateDocument = async (template, messageOptions, sendType) => {
- const bodyshop = store.getState().user.bodyshop;
- if (sendType === "e") {
- store.dispatch(
- setEmailOptions({
- messageOptions,
- template,
- })
- );
- } else {
- await RenderTemplate(template, bodyshop);
- }
-};
+// export const displayTemplateInWindowNoprint = (html) => {
+// try {
+// var newWin = window.open("", "_blank", "toolbar=0,location=0,menubar=0");
+// newWin.document.write(html);
+
+// setTimeout(function () {
+// newWin.document.close();
+// newWin.focus();
+// //newWin.print();
+// //newWin.close();
+// }, 500);
+// } catch (error) {
+// console.log("Unable to write to new window.", error);
+// }
+// };
diff --git a/client/src/utils/TemplateConstants.js b/client/src/utils/TemplateConstants.js
index 129161477..61c23a049 100644
--- a/client/src/utils/TemplateConstants.js
+++ b/client/src/utils/TemplateConstants.js
@@ -12,15 +12,6 @@ export const TemplateList = (type, context) => {
//If there's no type or the type is job, send it back.
...(!type || type === "job"
? {
- estimate_detail: {
- title: i18n.t("printcenter.jobs.estimate_detail"),
- description: "Est Detail",
- subject: `${i18n.t("printcenter.jobs.estimate_detail")} - ${
- context && context.job && context.job.ro_number
- }`,
- key: "estimate_detail",
- disabled: false,
- },
casl_authorization: {
title: i18n.t("printcenter.jobs.casl_authorization"),
description: "CASL Authorization",
@@ -209,7 +200,7 @@ export const TemplateList = (type, context) => {
title: i18n.t("printcenter.jobs.parts_order"),
description: "Parts Order",
key: "parts_order",
- subject: `${bodyshop.shopname} Parts Order ${
+ subject: `${bodyshop && bodyshop.shopname} Parts Order ${
(context &&
context &&
context.job &&