Merge branch 'feature/cdk-cert' into feature/qbo

This commit is contained in:
Patrick Fic
2021-08-25 12:08:06 -07:00
35 changed files with 2402 additions and 1443 deletions

View File

@@ -7550,6 +7550,32 @@
<folder_node> <folder_node>
<name>dms</name> <name>dms</name>
<children> <children>
<folder_node>
<name>cdk</name>
<children>
<concept_node>
<name>payers</name>
<definition_loaded>false</definition_loaded>
<description></description>
<comment></comment>
<default_text></default_text>
<translations>
<translation>
<language>en-US</language>
<approved>false</approved>
</translation>
<translation>
<language>es-MX</language>
<approved>false</approved>
</translation>
<translation>
<language>fr-CA</language>
<approved>false</approved>
</translation>
</translations>
</concept_node>
</children>
</folder_node>
<concept_node> <concept_node>
<name>cdk_dealerid</name> <name>cdk_dealerid</name>
<definition_loaded>false</definition_loaded> <definition_loaded>false</definition_loaded>

View File

@@ -1,17 +1,21 @@
import { Button, Table } from "antd"; import { Button, Table, Typography } from "antd";
import React, { useState } from "react"; import React, { useState, useEffect } from "react";
import { useTranslation } from "react-i18next"; import { useTranslation } from "react-i18next";
import { connect } from "react-redux"; import { connect } from "react-redux";
import { createStructuredSelector } from "reselect"; import { createStructuredSelector } from "reselect";
import { selectBodyshop } from "../../redux/user/user.selectors"; import { selectBodyshop } from "../../redux/user/user.selectors";
import Dinero from "dinero.js"; import Dinero from "dinero.js";
import { SyncOutlined } from "@ant-design/icons";
const mapStateToProps = createStructuredSelector({ const mapStateToProps = createStructuredSelector({
//currentUser: selectCurrentUser //currentUser: selectCurrentUser
bodyshop: selectBodyshop, bodyshop: selectBodyshop,
}); });
const mapDispatchToProps = (dispatch) => ({ const mapDispatchToProps = (dispatch) => ({
//setUserLanguage: language => dispatch(setUserLanguage(language)) //setUserLanguage: language => dispatch(setUserLanguage(language))
}); });
export default connect( export default connect(
mapStateToProps, mapStateToProps,
mapDispatchToProps mapDispatchToProps
@@ -20,6 +24,15 @@ export default connect(
export function DmsAllocationsSummary({ socket, bodyshop, jobId }) { export function DmsAllocationsSummary({ socket, bodyshop, jobId }) {
const { t } = useTranslation(); const { t } = useTranslation();
const [allocationsSummary, setAllocationsSummary] = useState([]); const [allocationsSummary, setAllocationsSummary] = useState([]);
useEffect(() => {
if (socket.connected) {
socket.emit("cdk-calculate-allocations", jobId, (ack) =>
setAllocationsSummary(ack)
);
}
}, [socket, socket.connected, jobId]);
const columns = [ const columns = [
{ {
title: t("jobs.fields.dms.center"), title: t("jobs.fields.dms.center"),
@@ -71,13 +84,45 @@ export function DmsAllocationsSummary({ socket, bodyshop, jobId }) {
); );
}} }}
> >
Get <SyncOutlined />
</Button> </Button>
)} )}
pagination={{ position: "top", defaultPageSize: 50 }} pagination={{ position: "top", defaultPageSize: 50 }}
columns={columns} columns={columns}
rowKey="center" rowKey="center"
dataSource={allocationsSummary} dataSource={allocationsSummary}
summary={() => {
const totals = allocationsSummary.reduce(
(acc, val) => {
return {
totalSale: acc.totalSale.add(Dinero(val.sale)),
totalCost: acc.totalCost.add(Dinero(val.cost)),
};
},
{
totalSale: Dinero(),
totalCost: Dinero(),
}
);
return (
<Table.Summary.Row>
<Table.Summary.Cell>
<Typography.Title level={4}>
{t("general.labels.totals")}
</Typography.Title>
</Table.Summary.Cell>
<Table.Summary.Cell>
{totals.totalSale.toFormat()}
</Table.Summary.Cell>
<Table.Summary.Cell>
{totals.totalCost.toFormat()}
</Table.Summary.Cell>
<Table.Summary.Cell></Table.Summary.Cell>
<Table.Summary.Cell></Table.Summary.Cell>
</Table.Summary.Row>
);
}}
/> />
); );
} }

View File

@@ -4,6 +4,9 @@ import { connect } from "react-redux";
import { createStructuredSelector } from "reselect"; import { createStructuredSelector } from "reselect";
import { selectBodyshop } from "../../redux/user/user.selectors"; import { selectBodyshop } from "../../redux/user/user.selectors";
import { useTranslation } from "react-i18next"; import { useTranslation } from "react-i18next";
import { useLazyQuery } from "@apollo/client";
import { SEARCH_DMS_VEHICLES } from "../../graphql/dms.queries";
import AlertComponent from "../alert/alert.component";
const mapStateToProps = createStructuredSelector({ const mapStateToProps = createStructuredSelector({
//currentUser: selectCurrentUser //currentUser: selectCurrentUser
@@ -12,83 +15,75 @@ const mapStateToProps = createStructuredSelector({
const mapDispatchToProps = (dispatch) => ({ const mapDispatchToProps = (dispatch) => ({
//setUserLanguage: language => dispatch(setUserLanguage(language)) //setUserLanguage: language => dispatch(setUserLanguage(language))
}); });
export default connect(mapStateToProps, mapDispatchToProps)(DmsCdkMakes); export default connect(mapStateToProps, mapDispatchToProps)(DmsCdkVehicles);
export function DmsCdkMakes({ bodyshop, form, socket }) { export function DmsCdkVehicles({ bodyshop, form, socket, job }) {
const [makesList, setMakesList] = useState([]);
const [searchText, setSearchText] = useState("");
const [loading, setLoading] = useState(false);
const [visible, setVisible] = useState(false); const [visible, setVisible] = useState(false);
const [selectedModel, setSelectedModel] = useState(null); const [selectedModel, setSelectedModel] = useState(null);
const { t } = useTranslation(); const { t } = useTranslation();
const [callSearch, { loading, error, data }] =
useLazyQuery(SEARCH_DMS_VEHICLES);
const columns = [ const columns = [
{ {
title: t("jobs.fields.dms.makeFullName"), title: t("jobs.fields.dms.make"),
dataIndex: "makeFullName", dataIndex: "make",
key: "makeFullName", key: "make",
}, },
{ {
title: t("jobs.fields.dms.modelFullName"), title: t("jobs.fields.dms.model"),
dataIndex: "modelFullName", dataIndex: "model",
key: "modelFullName", key: "model",
}, },
{ {
title: t("jobs.fields.dms.makeCode"), title: t("jobs.fields.dms.makecode"),
dataIndex: "makeCode", dataIndex: "makecode",
key: "makeCode", key: "makecode",
}, },
{ {
title: t("jobs.fields.dms.modelCode"), title: t("jobs.fields.dms.modelcode"),
dataIndex: "modelCode", dataIndex: "modelcode",
key: "modelCode", key: "modelcode",
}, },
]; ];
const filteredMakes = console.log(
searchText !== "" && searchText "🚀 ~ file: dms-cdk-makes.component.jsx ~ line 95 ~ selectedModel",
? makesList.filter( selectedModel
(make) => );
searchText
.split(" ")
.some((v) =>
make.makeFullName.toLowerCase().includes(v.toLowerCase())
) ||
searchText
.split(" ")
.some((v) =>
make.modelFullName.toLowerCase().includes(v.toLowerCase())
)
)
: makesList;
return ( return (
<div> <div>
<Modal width={"90%"} visible={visible} onCancel={() => setVisible(false)}> <Modal
width={"90%"}
visible={visible}
onCancel={() => setVisible(false)}
onOk={() => {
form.setFieldsValue({
dms_make: selectedModel.makecode,
dms_model: selectedModel.modelcode,
});
setVisible(false);
}}
>
{error && <AlertComponent error={error.message} />}
<Table <Table
title={() => ( title={() => (
<Input.Search <Input.Search
onSearch={(val) => setSearchText(val)} onSearch={(val) => callSearch({ variables: { search: val } })}
placeholder={t("general.labels.search")} placeholder={t("general.labels.search")}
/> />
)} )}
columns={columns} columns={columns}
loading={loading} loading={loading}
id="id" rowKey="id"
dataSource={filteredMakes} dataSource={data ? data.search_dms_vehicles : []}
onRow={(record) => { onRow={(record) => {
return { return {
onClick: setSelectedModel(record), onClick: () => setSelectedModel(record),
}; };
}} }}
rowSelection={{ rowSelection={{
onSelect: (record, selected, ...props) => { onSelect: (record) => {
console.log(
"🚀 ~ file: dms-cdk-makes.component.jsx ~ line 85 ~ record, selected, ...props",
record,
selected,
...props
);
setSelectedModel(record); setSelectedModel(record);
}, },
@@ -100,15 +95,14 @@ export function DmsCdkMakes({ bodyshop, form, socket }) {
<Button <Button
onClick={() => { onClick={() => {
setVisible(true); setVisible(true);
setLoading(true); callSearch({
socket.emit("cdk-get-makes", bodyshop.cdk_dealerid, (makes) => { variables: {
console.log("Called back", makes); search: job && job.v_model_desc && job.v_model_desc.substr(0, 3),
setMakesList(makes); },
setLoading(false);
}); });
}} }}
> >
Get Makes {t("jobs.actions.dms.getmakes")}
</Button> </Button>
</div> </div>
); );

View File

@@ -0,0 +1,32 @@
import { Button } from "antd";
import axios from "axios";
import React, { useState } from "react";
import { connect } from "react-redux";
import { createStructuredSelector } from "reselect";
import { selectBodyshop } from "../../redux/user/user.selectors";
const mapStateToProps = createStructuredSelector({
//currentUser: selectCurrentUser
bodyshop: selectBodyshop,
});
const mapDispatchToProps = (dispatch) => ({
//setUserLanguage: language => dispatch(setUserLanguage(language))
});
export default connect(mapStateToProps, mapDispatchToProps)(DmsCdkMakesRefetch);
export function DmsCdkMakesRefetch({ bodyshop, form, socket }) {
const [loading, setLoading] = useState(false);
const handleRefetch = async () => {
setLoading(true);
const response = await axios.post("/cdk/getvehicles", {
cdk_dealerid: bodyshop.cdk_dealerid,
bodyshopid: bodyshop.id,
});
console.log(response);
setLoading(false);
};
return (
<Button loading={loading} onClick={handleRefetch}>
Refetch Models
</Button>
);
}

View File

@@ -1,10 +1,24 @@
import { Button, Table } from "antd"; import { Button, Table } from "antd";
import React, { useState } from "react"; import React, { useState } from "react";
import { useTranslation } from "react-i18next"; import { useTranslation } from "react-i18next";
import { connect } from "react-redux";
import { createStructuredSelector } from "reselect";
import { socket } from "../../pages/dms/dms.container"; import { socket } from "../../pages/dms/dms.container";
import PhoneFormatter from "../../utils/PhoneFormatter"; import { selectBodyshop } from "../../redux/user/user.selectors";
import { alphaSort } from "../../utils/sorters"; import { alphaSort } from "../../utils/sorters";
export default function DmsCustomerSelector() {
const mapStateToProps = createStructuredSelector({
bodyshop: selectBodyshop,
});
const mapDispatchToProps = (dispatch) => ({
//setUserLanguage: language => dispatch(setUserLanguage(language))
});
export default connect(
mapStateToProps,
mapDispatchToProps
)(DmsCustomerSelector);
export function DmsCustomerSelector({ bodyshop }) {
const { t } = useTranslation(); const { t } = useTranslation();
const [customerList, setcustomerList] = useState([]); const [customerList, setcustomerList] = useState([]);
const [visible, setVisible] = useState(false); const [visible, setVisible] = useState(false);
@@ -15,11 +29,24 @@ export default function DmsCustomerSelector() {
setcustomerList(customerList); setcustomerList(customerList);
}); });
const onOk = () => { const onUseSelected = () => {
setVisible(false); setVisible(false);
socket.emit("cdk-selected-customer", selectedCustomer); socket.emit("cdk-selected-customer", selectedCustomer);
}; };
const onUseGeneric = () => {
setVisible(false);
socket.emit(
"cdk-selected-customer",
bodyshop.cdk_configuration.generic_customer_number
);
};
const onCreateNew = () => {
setVisible(false);
socket.emit("cdk-selected-customer", null);
};
const columns = [ const columns = [
{ {
title: t("dms.fields.name1"), title: t("dms.fields.name1"),
@@ -27,28 +54,13 @@ export default function DmsCustomerSelector() {
key: "name1", key: "name1",
sorter: (a, b) => alphaSort(a.name1?.fullName, b.name1?.fullName), sorter: (a, b) => alphaSort(a.name1?.fullName, b.name1?.fullName),
}, },
{
title: t("dms.fields.name2"),
dataIndex: ["name2", "fullName"],
key: "name2",
sorter: (a, b) => alphaSort(a.name2?.fullName, b.name2?.fullName),
},
{
title: t("dms.fields.phone"),
dataIndex: ["contactInfo", "mainTelephoneNumber", "value"],
key: "phone",
render: (record, value) => (
<PhoneFormatter>
{record.contactInfo?.mainTelephoneNumber?.value}
</PhoneFormatter>
),
},
{ {
title: t("dms.fields.address"), title: t("dms.fields.address"),
//dataIndex: ["name2", "fullName"], //dataIndex: ["name2", "fullName"],
key: "address", key: "address",
render: (record, value) => render: (record, value) =>
`${record.address?.addressLine[0]}, ${record.address?.city} ${record.address?.stateOrProvince} ${record.address?.postalCode}`, `${record?.address?.addressLine[0]}, ${record.address?.city} ${record.address?.stateOrProvince} ${record.address?.postalCode}`,
}, },
]; ];
@@ -57,7 +69,23 @@ export default function DmsCustomerSelector() {
<Table <Table
title={() => ( title={() => (
<div> <div>
<Button onClick={onOk}>Select</Button> <Button onClick={onUseSelected} disabled={!selectedCustomer}>
{t("jobs.actions.dms.useselected")}
</Button>
<Button
onClick={onUseGeneric}
disabled={
!(
bodyshop.cdk_configuration &&
bodyshop.cdk_configuration.generic_customer_number
)
}
>
{t("jobs.actions.dms.usegeneric")}
</Button>
<Button onClick={onCreateNew}>
{t("jobs.actions.dms.createnewcustomer")}
</Button>
</div> </div>
)} )}
pagination={{ position: "top" }} pagination={{ position: "top" }}

View File

@@ -1,5 +1,13 @@
import { DeleteFilled } from "@ant-design/icons"; import { DeleteFilled } from "@ant-design/icons";
import { Button, Form, Input } from "antd"; import {
Button,
Form,
Input,
InputNumber,
Select,
Space,
Statistic,
} from "antd";
import React from "react"; import React from "react";
import { useTranslation } from "react-i18next"; import { useTranslation } from "react-i18next";
import { connect } from "react-redux"; import { connect } from "react-redux";
@@ -8,7 +16,9 @@ import { selectBodyshop } from "../../redux/user/user.selectors";
import DmsCdkMakes from "../dms-cdk-makes/dms-cdk-makes.component"; import DmsCdkMakes from "../dms-cdk-makes/dms-cdk-makes.component";
import CurrencyInput from "../form-items-formatted/currency-form-item.component"; import CurrencyInput from "../form-items-formatted/currency-form-item.component";
import LayoutFormRow from "../layout-form-row/layout-form-row.component"; import LayoutFormRow from "../layout-form-row/layout-form-row.component";
import Dinero from "dinero.js";
import { determineDmsType } from "../../pages/dms/dms.container";
import DmsCdkMakesRefetch from "../dms-cdk-makes/dms-cdk-makes.refetch.component";
const mapStateToProps = createStructuredSelector({ const mapStateToProps = createStructuredSelector({
bodyshop: selectBodyshop, bodyshop: selectBodyshop,
}); });
@@ -17,11 +27,38 @@ const mapDispatchToProps = (dispatch) => ({
}); });
export default connect(mapStateToProps, mapDispatchToProps)(DmsPostForm); export default connect(mapStateToProps, mapDispatchToProps)(DmsPostForm);
export function DmsPostForm({ bodyshop, socket, jobId }) { export function DmsPostForm({ bodyshop, socket, job }) {
const [form] = Form.useForm(); const [form] = Form.useForm();
const { t } = useTranslation(); const { t } = useTranslation();
const handlePayerSelect = (value, index) => {
form.setFieldsValue({
payers: form.getFieldValue("payers").map((payer, mapIndex) => {
if (index !== mapIndex) return payer;
const cdkPayer =
bodyshop.cdk_configuration.payers &&
bodyshop.cdk_configuration.payers.find((i) => i.name === value);
if (!cdkPayer) return payer;
return {
...cdkPayer,
dms_acctnumber: cdkPayer.dms_acctnumber,
controlnumber: job && job[cdkPayer.control_type],
};
}),
});
};
const handleFinish = (values) => {
socket.emit(`${determineDmsType(bodyshop)}-export-job`, {
jobid: job.id,
txEnvelope: values,
});
};
return ( return (
<Form form={form} layout="vertical"> <Form form={form} layout="vertical" onFinish={handleFinish}>
<LayoutFormRow> <LayoutFormRow>
<Form.Item <Form.Item
name="journal" name="journal"
@@ -40,15 +77,41 @@ export function DmsPostForm({ bodyshop, socket, jobId }) {
<Input /> <Input />
</Form.Item> </Form.Item>
<Form.Item <Form.Item
name="dms_make" name="story"
label={t("jobs.fields.dms.dms_make")} label={t("jobs.fields.dms.story")}
rules={[ rules={[
{ {
required: true, required: true,
}, },
]} ]}
> >
<Input /> <Input.TextArea />
</Form.Item>
<Form.Item
name="kmin"
label={t("jobs.fields.kmin")}
initialValue={job && job.kmin}
rules={[
{
required: true,
//message: t("general.validation.required"),
},
]}
>
<InputNumber disabled />
</Form.Item>
<Form.Item
name="kmout"
label={t("jobs.fields.kmout")}
initialValue={job && job.kmout}
rules={[
{
required: true,
//message: t("general.validation.required"),
},
]}
>
<InputNumber disabled />
</Form.Item> </Form.Item>
<Form.Item <Form.Item
name="dms_make" name="dms_make"
@@ -59,9 +122,21 @@ export function DmsPostForm({ bodyshop, socket, jobId }) {
}, },
]} ]}
> >
<Input /> <Input disabled />
</Form.Item> </Form.Item>
<DmsCdkMakes form={form} socket={socket} /> <Form.Item
name="dms_model"
label={t("jobs.fields.dms.dms_model")}
rules={[
{
required: true,
},
]}
>
<Input disabled />
</Form.Item>
<DmsCdkMakes form={form} socket={socket} job={job} />
<DmsCdkMakesRefetch />
</LayoutFormRow> </LayoutFormRow>
<Form.List name={["payers"]}> <Form.List name={["payers"]}>
@@ -81,20 +156,30 @@ export function DmsPostForm({ bodyshop, socket, jobId }) {
}, },
]} ]}
> >
<Input /> <Select
onSelect={(value) => handlePayerSelect(value, index)}
>
{bodyshop.cdk_configuration &&
bodyshop.cdk_configuration.payers &&
bodyshop.cdk_configuration.payers.map((payer) => (
<Select.Option key={payer.name}>
{payer.name}
</Select.Option>
))}
</Select>
</Form.Item> </Form.Item>
<Form.Item <Form.Item
label={t("jobs.fields.dms.payer.account")} label={t("jobs.fields.dms.payer.dms_acctnumber")}
key={`${index}account`} key={`${index}dms_acctnumber`}
name={[field.name, "account"]} name={[field.name, "dms_acctnumber"]}
rules={[ rules={[
{ {
required: true, required: true,
}, },
]} ]}
> >
<Input /> <Input disabled />
</Form.Item> </Form.Item>
<Form.Item <Form.Item
@@ -107,8 +192,9 @@ export function DmsPostForm({ bodyshop, socket, jobId }) {
}, },
]} ]}
> >
<CurrencyInput /> <CurrencyInput min={0} />
</Form.Item> </Form.Item>
<Form.Item <Form.Item
label={t("jobs.fields.dms.payer.controlnumber")} label={t("jobs.fields.dms.payer.controlnumber")}
key={`${index}controlnumber`} key={`${index}controlnumber`}
@@ -122,6 +208,27 @@ export function DmsPostForm({ bodyshop, socket, jobId }) {
<Input /> <Input />
</Form.Item> </Form.Item>
<Form.Item shouldUpdate>
{() => {
const payers = form.getFieldValue("payers");
const row = payers && payers[index];
const cdkPayer =
bodyshop.cdk_configuration.payers &&
bodyshop.cdk_configuration.payers.find(
(i) => i && row && i.name === row.name
);
return (
<div>
{cdkPayer &&
t(`jobs.fields.${cdkPayer.control_type}`)}
</div>
);
}}
</Form.Item>
<DeleteFilled <DeleteFilled
onClick={() => { onClick={() => {
remove(field.name); remove(field.name);
@@ -133,18 +240,69 @@ export function DmsPostForm({ bodyshop, socket, jobId }) {
<Form.Item> <Form.Item>
<Button <Button
type="dashed" type="dashed"
disabled={!(fields.length < 3)}
onClick={() => { onClick={() => {
add(); if (fields.length < 3) add();
}} }}
style={{ width: "100%" }} style={{ width: "100%" }}
> >
{t("general.actions.add")} {t("dms.actions.addpayer")}
</Button> </Button>
</Form.Item> </Form.Item>
</div> </div>
); );
}} }}
</Form.List> </Form.List>
<Form.Item shouldUpdate>
{() => {
//Perform Calculation to determine discrepancy.
let totalAllocated = Dinero();
const payers = form.getFieldValue("payers");
payers &&
payers.forEach((payer) => {
totalAllocated = totalAllocated.add(
Dinero({ amount: Math.round((payer?.amount || 0) * 100) })
);
});
const discrep = Dinero(job.job_totals.totals.total_repairs).subtract(
totalAllocated
);
return (
<Space>
<Statistic
title={t("jobs.labels.dms.totalallocated")}
value={totalAllocated.toFormat()}
/>
<Statistic
title={t("jobs.fields.subtotal")}
value={Dinero(job.job_totals.totals.total_repairs).toFormat()}
/>
<Statistic
title={t("jobs.labels.dms.notallocated")}
valueStyle={{
color: discrep.getAmount() === 0 ? "green" : "red",
}}
value={discrep.toFormat()}
/>
<Button //disabled={discrep.getAmount() !== 0} //TODO: REMOVE THIS COMMENT.
htmlType="submit"
>
{t("jobs.actions.dms.post")}
</Button>
<Button
onClick={() => {
socket.emit(`${determineDmsType(bodyshop)}-export-job`, {
jobid: job.id,
});
}}
>
Bypass
</Button>
</Space>
);
}}
</Form.Item>
</Form> </Form>
); );
} }

View File

@@ -0,0 +1,13 @@
import { gql } from "@apollo/client";
export const SEARCH_DMS_VEHICLES = gql`
query SEARCH_DMS_VEHICLES($search: String) {
search_dms_vehicles(args: { search: $search }) {
id
make
makecode
model
modelcode
}
}
`;

View File

@@ -1726,6 +1726,8 @@ export const QUERY_JOB_CLOSE_DETAILS = gql`
actual_delivery actual_delivery
scheduled_in scheduled_in
actual_in actual_in
kmin
kmout
joblines(where: { removed: { _eq: false } }) { joblines(where: { removed: { _eq: false } }) {
id id
removed removed
@@ -1878,98 +1880,16 @@ export const FIND_JOBS_BY_CLAIM = gql`
`; `;
export const QUERY_JOB_EXPORT_DMS = gql` export const QUERY_JOB_EXPORT_DMS = gql`
query QUERY_JOB_CLOSE_DETAILS($id: uuid!) { query QUERY_JOB_EXPORT_DMS($id: uuid!) {
jobs_by_pk(id: $id) { jobs_by_pk(id: $id) {
ro_number
invoice_allocation
ins_co_id
id id
ded_amt ro_number
ded_status po_number
depreciation_taxes clm_no
other_amount_payable
towing_payable
storage_payable
adjustment_bottom_line
federal_tax_rate
state_tax_rate
local_tax_rate
tax_tow_rt
tax_str_rt
tax_paint_mat_rt
tax_sub_rt
tax_lbr_rt
tax_levies_rt
parts_tax_rates
job_totals job_totals
rate_la1 kmin
rate_la2 kmout
rate_la3 v_model_desc
rate_la4
rate_laa
rate_lab
rate_lad
rate_lae
rate_laf
rate_lag
rate_lam
rate_lar
rate_las
rate_lau
rate_ma2s
rate_ma2t
rate_ma3s
rate_mabl
rate_macs
rate_mahw
rate_mapa
rate_mash
rate_matd
status
date_exported
date_invoiced
voided
scheduled_completion
actual_completion
scheduled_delivery
actual_delivery
scheduled_in
actual_in
bills {
id
federal_tax_rate
local_tax_rate
state_tax_rate
is_credit_memo
billlines {
actual_cost
cost_center
id
quantity
}
}
joblines(where: { removed: { _eq: false } }) {
id
removed
tax_part
line_desc
prt_dsmk_p
prt_dsmk_m
part_type
oem_partno
db_price
act_price
part_qty
mod_lbr_ty
db_hrs
mod_lb_hrs
lbr_op
lbr_amt
op_code_desc
profitcenter_labor
profitcenter_part
prt_dsmk_p
}
} }
} }
`; `;

View File

@@ -1,4 +1,4 @@
//import { useQuery } from "@apollo/client"; import { useQuery } from "@apollo/client";
import { Button, Col, Result, Row, Select, Space } from "antd"; import { Button, Col, Result, Row, Select, Space } from "antd";
import queryString from "query-string"; import queryString from "query-string";
import React, { useEffect, useState } from "react"; import React, { useEffect, useState } from "react";
@@ -7,14 +7,14 @@ import { connect } from "react-redux";
import { useLocation } from "react-router-dom"; import { useLocation } from "react-router-dom";
import { createStructuredSelector } from "reselect"; import { createStructuredSelector } from "reselect";
import SocketIO from "socket.io-client"; import SocketIO from "socket.io-client";
//import AlertComponent from "../../components/alert/alert.component"; import AlertComponent from "../../components/alert/alert.component";
import DmsAllocationsSummary from "../../components/dms-allocations-summary/dms-allocations-summary.component"; import DmsAllocationsSummary from "../../components/dms-allocations-summary/dms-allocations-summary.component";
import DmsCustomerSelector from "../../components/dms-customer-selector/dms-customer-selector.component"; import DmsCustomerSelector from "../../components/dms-customer-selector/dms-customer-selector.component";
import DmsLogEvents from "../../components/dms-log-events/dms-log-events.component"; import DmsLogEvents from "../../components/dms-log-events/dms-log-events.component";
import DmsPostForm from "../../components/dms-post-form/dms-post-form.component"; import DmsPostForm from "../../components/dms-post-form/dms-post-form.component";
//import LoadingSpinner from "../../components/loading-spinner/loading-spinner.component"; import LoadingSpinner from "../../components/loading-spinner/loading-spinner.component";
import { auth } from "../../firebase/firebase.utils"; import { auth } from "../../firebase/firebase.utils";
//import { QUERY_JOB_EXPORT_DMS } from "../../graphql/jobs.queries"; import { QUERY_JOB_EXPORT_DMS } from "../../graphql/jobs.queries";
import { import {
setBreadcrumbs, setBreadcrumbs,
setSelectedHeader, setSelectedHeader,
@@ -52,10 +52,10 @@ export function DmsContainer({ bodyshop, setBreadcrumbs, setSelectedHeader }) {
const search = queryString.parse(useLocation().search); const search = queryString.parse(useLocation().search);
const { jobId } = search; const { jobId } = search;
// const { loading, error } = useQuery(QUERY_JOB_EXPORT_DMS, { const { loading, error, data } = useQuery(QUERY_JOB_EXPORT_DMS, {
// variables: { id: jobId }, variables: { id: jobId },
// skip: true, //!jobId, skip: !jobId,
// }); });
useEffect(() => { useEffect(() => {
document.title = t("titles.dms"); document.title = t("titles.dms");
@@ -73,7 +73,6 @@ export function DmsContainer({ bodyshop, setBreadcrumbs, setSelectedHeader }) {
console.log("Connected again."); console.log("Connected again.");
}); });
socket.on("reconnect", () => { socket.on("reconnect", () => {
console.log("Connected again.");
setLogs((logs) => { setLogs((logs) => {
return [ return [
...logs, ...logs,
@@ -104,46 +103,39 @@ export function DmsContainer({ bodyshop, setBreadcrumbs, setSelectedHeader }) {
if (!jobId || !bodyshop.cdk_dealerid) return <Result status="404" />; if (!jobId || !bodyshop.cdk_dealerid) return <Result status="404" />;
const dmsType = determineDmsType(bodyshop); if (loading) return <LoadingSpinner />;
if (error) return <AlertComponent message={error.message} type="error" />;
// if (loading) return <LoadingSpinner />;
// if (error) return <AlertComponent message={error.message} type="error" />;
return ( return (
<div> <div>
<Space>
<Button
onClick={() => {
socket.emit(
`${dmsType}-export-job`,
"752a4f5f-22ab-414b-b182-98d4e62227ef"
);
}}
>
Export
</Button>
<Select
placeholder="Log Level"
value={logLevel}
onChange={(value) => {
setLogLevel(value);
socket.emit("set-log-level", value);
}}
>
<Select.Option key="TRACE">TRACE</Select.Option>
<Select.Option key="DEBUG">DEBUG</Select.Option>
<Select.Option key="INFO">INFO</Select.Option>
<Select.Option key="WARNING">WARNING</Select.Option>
<Select.Option key="ERROR">ERROR</Select.Option>
</Select>
<Button onClick={() => setLogs([])}>Clear Logs</Button>
</Space>
<Row gutter={32}> <Row gutter={32}>
<Col span={18}> <Col span={18}>
{data && data.jobs_by_pk.ro_number}
<DmsAllocationsSummary socket={socket} jobId={jobId} /> <DmsAllocationsSummary socket={socket} jobId={jobId} />
<DmsPostForm socket={socket} jobId={jobId} /> <DmsPostForm
socket={socket}
jobId={jobId}
job={data && data.jobs_by_pk}
/>
</Col> </Col>
<Col span={6}> <Col span={6}>
<Space>
<Select
placeholder="Log Level"
value={logLevel}
onChange={(value) => {
setLogLevel(value);
socket.emit("set-log-level", value);
}}
>
<Select.Option key="TRACE">TRACE</Select.Option>
<Select.Option key="DEBUG">DEBUG</Select.Option>
<Select.Option key="INFO">INFO</Select.Option>
<Select.Option key="WARNING">WARNING</Select.Option>
<Select.Option key="ERROR">ERROR</Select.Option>
</Select>
<Button onClick={() => setLogs([])}>Clear Logs</Button>
</Space>
<div style={{ maxHeight: "500px", overflowY: "auto" }}> <div style={{ maxHeight: "500px", overflowY: "auto" }}>
<DmsLogEvents socket={socket} logs={logs} /> <DmsLogEvents socket={socket} logs={logs} />
</div> </div>
@@ -155,7 +147,7 @@ export function DmsContainer({ bodyshop, setBreadcrumbs, setSelectedHeader }) {
); );
} }
const determineDmsType = (bodyshop) => { export const determineDmsType = (bodyshop) => {
if (bodyshop.cdk_dealerid) return "cdk"; if (bodyshop.cdk_dealerid) return "cdk";
else { else {
return "pbs"; return "pbs";

View File

@@ -8,6 +8,7 @@ import {
Alert, Alert,
Divider, Divider,
PageHeader, PageHeader,
InputNumber,
} from "antd"; } from "antd";
import React, { useState } from "react"; import React, { useState } from "react";
import { useTranslation } from "react-i18next"; import { useTranslation } from "react-i18next";
@@ -56,6 +57,8 @@ export function JobsCloseComponent({ job, bodyshop, jobRO }) {
actual_in: values.actual_in, actual_in: values.actual_in,
actual_completion: values.actual_completion, actual_completion: values.actual_completion,
actual_delivery: values.actual_delivery, actual_delivery: values.actual_delivery,
kmin: values.kmin,
kmout: values.kmout,
}, },
}, },
refetchQueries: ["QUERY_JOB_CLOSE_DETAILS"], refetchQueries: ["QUERY_JOB_CLOSE_DETAILS"],
@@ -112,6 +115,8 @@ export function JobsCloseComponent({ job, bodyshop, jobRO }) {
actual_delivery: job.actual_delivery actual_delivery: job.actual_delivery
? moment(job.actual_delivery) ? moment(job.actual_delivery)
: job.scheduled_delivery && moment(job.scheduled_delivery), : job.scheduled_delivery && moment(job.scheduled_delivery),
kmin: job.kmin,
kmout: job.kmout,
}} }}
scrollToFirstError scrollToFirstError
> >
@@ -203,6 +208,45 @@ export function JobsCloseComponent({ job, bodyshop, jobRO }) {
> >
<DateTimePicker disabled={jobRO} /> <DateTimePicker disabled={jobRO} />
</Form.Item> </Form.Item>
{bodyshop.cdk_dealerid && (
<Form.Item
label={t("jobs.fields.kmin")}
name="kmin"
rules={[
{
required: true,
},
]}
>
<InputNumber disabled={jobRO} />
</Form.Item>
)}
{bodyshop.cdk_dealerid && (
<Form.Item
label={t("jobs.fields.kmout")}
name="kmout"
dependencies={["kmin"]}
hasFeedback
rules={[
{
required: true,
},
({ getFieldValue }) => ({
validator(_, value) {
if (!value || getFieldValue("kmin") <= value) {
return Promise.resolve();
}
return Promise.reject(
new Error(t("jobs.labels.dms.kmoutnotgreaterthankmin"))
);
},
}),
]}
>
<InputNumber disabled={jobRO} />
</Form.Item>
)}
</LayoutFormRow> </LayoutFormRow>
<Divider /> <Divider />
<JobsCloseLines job={job} /> <JobsCloseLines job={job} />

View File

@@ -474,6 +474,9 @@
"defaultprofitsmapping": "Default Profits Mapping", "defaultprofitsmapping": "Default Profits Mapping",
"deliverchecklist": "Delivery Checklist", "deliverchecklist": "Delivery Checklist",
"dms": { "dms": {
"cdk": {
"payers": "CDK Payers"
},
"cdk_dealerid": "CDK Dealer ID", "cdk_dealerid": "CDK Dealer ID",
"title": "DMS" "title": "DMS"
}, },

View File

@@ -474,6 +474,9 @@
"defaultprofitsmapping": "", "defaultprofitsmapping": "",
"deliverchecklist": "", "deliverchecklist": "",
"dms": { "dms": {
"cdk": {
"payers": ""
},
"cdk_dealerid": "", "cdk_dealerid": "",
"title": "" "title": ""
}, },

View File

@@ -474,6 +474,9 @@
"defaultprofitsmapping": "", "defaultprofitsmapping": "",
"deliverchecklist": "", "deliverchecklist": "",
"dms": { "dms": {
"cdk": {
"payers": ""
},
"cdk_dealerid": "", "cdk_dealerid": "",
"title": "" "title": ""
}, },

View File

@@ -0,0 +1,5 @@
- args:
cascade: false
read_only: false
sql: DROP TABLE "public"."dms_vehicles";
type: run_sql

View File

@@ -0,0 +1,18 @@
- args:
cascade: false
read_only: false
sql: CREATE EXTENSION IF NOT EXISTS pgcrypto;
type: run_sql
- args:
cascade: false
read_only: false
sql: CREATE TABLE "public"."dms_vehicles"("id" uuid NOT NULL DEFAULT gen_random_uuid(),
"created_at" timestamptz NOT NULL DEFAULT now(), "makecode" text NOT NULL, "modelcode"
text NOT NULL, "make" text NOT NULL, "model" text NOT NULL, "bodyshopid" uuid
NOT NULL, PRIMARY KEY ("id") , FOREIGN KEY ("bodyshopid") REFERENCES "public"."bodyshops"("id")
ON UPDATE cascade ON DELETE cascade);
type: run_sql
- args:
name: dms_vehicles
schema: public
type: add_existing_table_or_view

View File

@@ -0,0 +1,12 @@
- args:
relationship: dms_vehicles
table:
name: bodyshops
schema: public
type: drop_relationship
- args:
relationship: bodyshop
table:
name: dms_vehicles
schema: public
type: drop_relationship

View File

@@ -0,0 +1,20 @@
- args:
name: dms_vehicles
table:
name: bodyshops
schema: public
using:
foreign_key_constraint_on:
column: bodyshopid
table:
name: dms_vehicles
schema: public
type: create_array_relationship
- args:
name: bodyshop
table:
name: dms_vehicles
schema: public
using:
foreign_key_constraint_on: bodyshopid
type: create_object_relationship

View File

@@ -0,0 +1,6 @@
- args:
role: user
table:
name: dms_vehicles
schema: public
type: drop_select_permission

View File

@@ -0,0 +1,28 @@
- args:
permission:
allow_aggregations: false
backend_only: false
columns:
- id
- created_at
- makecode
- modelcode
- make
- model
- bodyshopid
computed_fields: []
filter:
bodyshop:
associations:
_and:
- user:
authid:
_eq: X-Hasura-User-Id
- active:
_eq: true
limit: null
role: user
table:
name: dms_vehicles
schema: public
type: create_select_permission

View File

@@ -0,0 +1,6 @@
- args:
role: user
table:
name: dms_vehicles
schema: public
type: drop_insert_permission

View File

@@ -0,0 +1,27 @@
- args:
permission:
allow_upsert: true
backend_only: false
check:
bodyshop:
associations:
_and:
- user:
authid:
_eq: X-Hasura-User-Id
- active:
_eq: true
columns:
- id
- created_at
- makecode
- modelcode
- make
- model
- bodyshopid
set: {}
role: user
table:
name: dms_vehicles
schema: public
type: create_insert_permission

View File

@@ -0,0 +1,6 @@
- args:
role: user
table:
name: dms_vehicles
schema: public
type: drop_update_permission

View File

@@ -0,0 +1,26 @@
- args:
permission:
backend_only: false
columns:
- make
- makecode
- model
- modelcode
- created_at
- bodyshopid
- id
filter:
bodyshop:
associations:
_and:
- user:
authid:
_eq: X-Hasura-User-Id
- active:
_eq: true
set: {}
role: user
table:
name: dms_vehicles
schema: public
type: create_update_permission

View File

@@ -0,0 +1,6 @@
- args:
role: user
table:
name: dms_vehicles
schema: public
type: drop_delete_permission

View File

@@ -0,0 +1,17 @@
- args:
permission:
backend_only: false
filter:
bodyshop:
associations:
_and:
- user:
authid:
_eq: X-Hasura-User-Id
- active:
_eq: true
role: user
table:
name: dms_vehicles
schema: public
type: create_delete_permission

View File

@@ -0,0 +1 @@
[]

View File

@@ -0,0 +1,13 @@
- args:
cascade: true
read_only: false
sql: CREATE OR REPLACE FUNCTION public.search_dms_vehicles(search text)RETURNS
SETOF dms_vehicles LANGUAGE plpgsql STABLE AS $FUNCTION$ BEGIN IF search=''
THEN RETURN query SELECT*FROM dms_vehicles;ELSE RETURN query SELECT*FROM dms_vehicles
WHERE make ILIKE'%'||search||'%' OR model ILIKE'%'||search||'%' ORDER BY make
ILIKE'%'||search||'%' OR NULL,model ILIKE'%'||search||'%' OR NULL;END IF;END$FUNCTION$;
type: run_sql
- args:
name: search_dms_vehicles
schema: public
type: track_function

View File

@@ -721,6 +721,13 @@ tables:
table: table:
schema: public schema: public
name: csiquestions name: csiquestions
- name: dms_vehicles
using:
foreign_key_constraint_on:
column: bodyshopid
table:
schema: public
name: dms_vehicles
- name: documents - name: documents
using: using:
foreign_key_constraint_on: foreign_key_constraint_on:
@@ -1527,6 +1534,87 @@ tables:
- active: - active:
_eq: true _eq: true
check: null check: null
- table:
schema: public
name: dms_vehicles
object_relationships:
- name: bodyshop
using:
foreign_key_constraint_on: bodyshopid
insert_permissions:
- role: user
permission:
check:
bodyshop:
associations:
_and:
- user:
authid:
_eq: X-Hasura-User-Id
- active:
_eq: true
columns:
- id
- created_at
- makecode
- modelcode
- make
- model
- bodyshopid
backend_only: false
select_permissions:
- role: user
permission:
columns:
- id
- created_at
- makecode
- modelcode
- make
- model
- bodyshopid
filter:
bodyshop:
associations:
_and:
- user:
authid:
_eq: X-Hasura-User-Id
- active:
_eq: true
update_permissions:
- role: user
permission:
columns:
- make
- makecode
- model
- modelcode
- created_at
- bodyshopid
- id
filter:
bodyshop:
associations:
_and:
- user:
authid:
_eq: X-Hasura-User-Id
- active:
_eq: true
check: null
delete_permissions:
- role: user
permission:
filter:
bodyshop:
associations:
_and:
- user:
authid:
_eq: X-Hasura-User-Id
- active:
_eq: true
- table: - table:
schema: public schema: public
name: documents name: documents
@@ -4554,6 +4642,9 @@ functions:
- function: - function:
schema: public schema: public
name: search_cccontracts name: search_cccontracts
- function:
schema: public
name: search_dms_vehicles
- function: - function:
schema: public schema: public
name: search_exportlog name: search_exportlog

View File

@@ -21,6 +21,23 @@ const app = express();
const port = process.env.PORT || 5000; const port = process.env.PORT || 5000;
//const port = 5000; //const port = 5000;
const http = require("http");
const server = http.createServer(app);
const { Server } = require("socket.io");
const io = new Server(server, {
path: "/ws",
cors: {
origin: [
"https://test.imex.online",
"http://localhost:3000",
"https://imex.online",
],
methods: ["GET", "POST"],
},
});
exports.io = io;
require("./server/web-sockets/web-socket");
//app.use(fb.validateFirebaseIdToken); //app.use(fb.validateFirebaseIdToken);
app.use(compression()); app.use(compression());
app.use(bodyParser.json({ limit: "50mb" })); app.use(bodyParser.json({ limit: "50mb" }));
@@ -136,25 +153,13 @@ app.post("/data/ah", data.autohouse);
var ioevent = require("./server/ioevent/ioevent"); var ioevent = require("./server/ioevent/ioevent");
app.post("/ioevent", ioevent.default); app.post("/ioevent", ioevent.default);
var cdkGetMake = require("./server/cdk/cdk-get-makes");
app.post("/cdk/getvehicles", fb.validateFirebaseIdToken, cdkGetMake.default);
app.get("/", async function (req, res) { app.get("/", async function (req, res) {
res.status(200).send("Access Forbidden."); res.status(200).send("Access Forbidden.");
}); });
const http = require("http");
const server = http.createServer(app);
const { Server } = require("socket.io");
const io = new Server(server, {
path: "/ws",
cors: {
origin: [
"https://test.imex.online",
"http://localhost:3000",
"https://imex.online",
],
methods: ["GET", "POST"],
},
});
server.listen(port, (error) => { server.listen(port, (error) => {
if (error) throw error; if (error) throw error;
logger.log( logger.log(
@@ -163,5 +168,3 @@ server.listen(port, (error) => {
"api" "api"
); );
}); });
exports.io = io;
require("./server/web-sockets/web-socket");

View File

@@ -15,32 +15,101 @@ const Dinero = require("dinero.js");
const _ = require("lodash"); const _ = require("lodash");
const { CDK_CREDENTIALS, CheckCdkResponseForError } = require("./cdk-wsdl"); const { CDK_CREDENTIALS, CheckCdkResponseForError } = require("./cdk-wsdl");
const { performance } = require("perf_hooks"); const { performance } = require("perf_hooks");
const apiGqlClient = require("../graphql-client/graphql-client").client;
exports.default = async function (socket, cdk_dealerid) { // exports.default = async function (socket, cdk_dealerid) {
// try {
// CdkBase.createLogEvent(
// socket,
// "DEBUG",
// `Getting makes and models list from CDK.`
// );
// return await GetCdkMakes(socket, cdk_dealerid);
// } catch (error) {
// CdkBase.createLogEvent(
// socket,
// "ERROR",
// `Error encountered in CdkGetMakes. ${error}`
// );
// }
// };
exports.default = async function ReloadCdkMakes(req, res) {
const { bodyshopid, cdk_dealerid } = req.body;
try { try {
CdkBase.createLogEvent( const BearerToken = req.headers.authorization;
socket, //Query all CDK Models
"DEBUG", const newList = await GetCdkMakes(req, cdk_dealerid);
`Getting makes and models list from CDK.` console.log("🚀 ~ file: cdk-get-makes.js ~ line 40 ~ newList", newList);
//Clear out the existing records
const client = new GraphQLClient(process.env.GRAPHQL_ENDPOINT, {
headers: {
Authorization: BearerToken,
},
});
const deleteResult = await client
.setHeaders({ Authorization: BearerToken })
.request(queries.DELETE_ALL_DMS_VEHICLES, {});
console.log(
"🚀 ~ file: cdk-get-makes.js ~ line 53 ~ deleteResult",
deleteResult
);
//Insert the new ones.
const insertResult = await client
.setHeaders({ Authorization: BearerToken })
.request(queries.INSERT_DMS_VEHICLES, {
vehicles: newList.map((i) => {
return {
bodyshopid,
makecode: i.makeCode,
modelcode: i.modelCode,
make: i.makeFullName,
model: i.modelFullName,
};
}),
});
console.log(
"🚀 ~ file: cdk-get-makes.js ~ line 66 ~ insertResult",
insertResult
);
logger.log(
"cdk-replace-makes-models-success",
"DEBUG",
req.user.email,
null,
{
cdk_dealerid,
count: newList.length,
}
); );
return await GetCdkMakes(socket, cdk_dealerid);
} catch (error) { } catch (error) {
CdkBase.createLogEvent( logger.log(
socket, "cdk-replace-makes-models-error",
"ERROR", "ERROR",
`Error encountered in CdkGetMakes. ${error}` req.user.email,
null,
{
cdk_dealerid,
error,
}
); );
} }
}; };
async function GetCdkMakes(socket, cdk_dealerid) { async function GetCdkMakes(req, cdk_dealerid) {
CdkBase.createLogEvent(socket, "TRACE", `{1} Begin GetCDkMakes WSDL Call`); logger.log("cdk-replace-makes-models", "DEBUG", req.user.email, null, {
cdk_dealerid,
});
try { try {
const soapClientVehicleInsert = await soap.createClientAsync( const soapClientVehicleInsert = await soap.createClientAsync(
CdkWsdl.VehicleInsert CdkWsdl.VehicleInsert
); );
const start = performance.now();
const soapResponseVehicleSearch = const soapResponseVehicleSearch =
await soapClientVehicleInsert.getMakeModelAsync( await soapClientVehicleInsert.getMakeModelAsync(
@@ -51,28 +120,25 @@ async function GetCdkMakes(socket, cdk_dealerid) {
{} {}
); );
CheckCdkResponseForError(socket, soapResponseVehicleSearch);
CheckCdkResponseForError(null, soapResponseVehicleSearch);
const [ const [
result, //rawResponse, soapheader, rawRequest result, //rawResponse, soapheader, rawRequest
] = soapResponseVehicleSearch; ] = soapResponseVehicleSearch;
const end = performance.now();
CdkBase.createLogEvent( return result.return;
socket, } catch (error) {
"TRACE", logger.log(
`soapClientVehicleInsert.getMakeModelAsync Result Length ${ "cdk-replace-makes-models-error",
result.return.length "ERROR",
} and took ${end - start}ms` req.user.email,
null,
{
cdk_dealerid,
error,
}
); );
return result.return.map((element, index) => {
return { id: index, ...element };
});
} catch (error) {
CdkBase.createLogEvent(
socket,
"ERROR",
`Error in GetCdkMakes - ${JSON.stringify(error, null, 2)}`
);
throw new Error(error); throw new Error(error);
} }
} }

File diff suppressed because it is too large Load Diff

View File

@@ -78,11 +78,11 @@ exports.checkIndividualResult = checkIndividualResult;
const cdkDomain = "https://uat-3pa.dmotorworks.com"; const cdkDomain = "https://uat-3pa.dmotorworks.com";
exports.default = { exports.default = {
// VehicleSearch: `${cdkDomain}/pip-vehicle/services/VehicleSearch?wsdl`, // VehicleSearch: `${cdkDomain}/pip-vehicle/services/VehicleSearch?wsdl`,
AccountingGLInsertUpdate: `${cdkDomain}/pip-accounting-gl/services/AccountingGLInsertUpdate?wsdl`,
VehicleInsertUpdate: `${cdkDomain}/pip-vehicle/services/VehicleInsertUpdate?wsdl`, VehicleInsertUpdate: `${cdkDomain}/pip-vehicle/services/VehicleInsertUpdate?wsdl`,
CustomerInsertUpdate: `${cdkDomain}/pip-customer/services/CustomerInsertUpdate?wsdl`, CustomerInsertUpdate: `${cdkDomain}/pip-customer/services/CustomerInsertUpdate?wsdl`,
CustomerSearch: `${cdkDomain}/pip-customer/services/CustomerSearch?wsdl`, CustomerSearch: `${cdkDomain}/pip-customer/services/CustomerSearch?wsdl`,
VehicleSearch: `${cdkDomain}/pip-vehicle/services/VehicleSearch?wsdl`, VehicleSearch: `${cdkDomain}/pip-vehicle/services/VehicleSearch?wsdl`,
VehicleInsert: `${cdkDomain}/pip-vehicle/services/VehicleInsertUpdate?wsdl`,
}; };
// The following login credentials will be used for all PIPs and all environments (User Acceptance Testing and Production). // The following login credentials will be used for all PIPs and all environments (User Acceptance Testing and Production).

View File

@@ -133,6 +133,7 @@ query QUERY_JOBS_FOR_CDK_EXPORT($id: uuid!) {
ownr_fn ownr_fn
ownr_addr1 ownr_addr1
ownr_addr2 ownr_addr2
ownr_ph1
ownr_zip ownr_zip
ownr_city ownr_city
ownr_st ownr_st
@@ -932,6 +933,19 @@ exports.GET_AUTOHOUSE_SHOPS = `query GET_AUTOHOUSE_SHOPS {
imexshopid imexshopid
} }
} }
`;
exports.DELETE_ALL_DMS_VEHICLES = `mutation DELETE_ALL_DMS_VEHICLES{
delete_dms_vehicles(where: {}) {
affected_rows
}
}
`;
exports.INSERT_DMS_VEHICLES = `mutation INSERT_DMS_VEHICLES($vehicles: [dms_vehicles_insert_input!]!) {
insert_dms_vehicles(objects: $vehicles) {
affected_rows
}
}
`; `;
exports.GET_CDK_ALLOCATIONS = ` exports.GET_CDK_ALLOCATIONS = `

View File

@@ -8,7 +8,10 @@ require("dotenv").config({
const { io } = require("../../server"); const { io } = require("../../server");
const { admin } = require("../firebase/firebase-handler"); const { admin } = require("../firebase/firebase-handler");
const CdkJobExport = require("../cdk/cdk-job-export").default; const {
default: CdkJobExport,
CdkSelectedCustomer,
} = require("../cdk/cdk-job-export");
const CdkGetMakes = require("../cdk/cdk-get-makes").default; const CdkGetMakes = require("../cdk/cdk-get-makes").default;
const CdkCalculateAllocations = const CdkCalculateAllocations =
require("../cdk/cdk-calculate-allocations").default; require("../cdk/cdk-calculate-allocations").default;
@@ -60,7 +63,7 @@ io.on("connection", (socket) => {
`User selected customer ID ${selectedCustomerId}` `User selected customer ID ${selectedCustomerId}`
); );
socket.selectedCustomerId = selectedCustomerId; socket.selectedCustomerId = selectedCustomerId;
//CdkJobExport(socket, jobid); CdkSelectedCustomer(socket, selectedCustomerId);
}); });
socket.on("cdk-get-makes", async (cdk_dealerid, callback) => { socket.on("cdk-get-makes", async (cdk_dealerid, callback) => {
@@ -123,8 +126,40 @@ function createLogEvent(socket, level, message) {
} }
} }
function createXmlEvent(socket, xml, message, isError = false) {
if (LogLevelHierarchy(socket.log_level) >= LogLevelHierarchy("TRACE")) {
socket.emit("log-event", {
timestamp: new Date(),
level: isError ? "ERROR" : "TRACE",
message: `${message}: ${xml}`,
});
}
logger.log(
isError ? "ws-log-event-xml-error" : "ws-log-event-xml",
isError ? "ERROR" : "TRACE",
socket.user.email,
socket.recordid,
{
wsmessage: message,
xml,
}
);
if (socket.logEvents && isArray(socket.logEvents)) {
socket.logEvents.push({
timestamp: new Date(),
level: isError ? "ERROR" : "TRACE",
message,
xml,
});
}
}
function LogLevelHierarchy(level) { function LogLevelHierarchy(level) {
switch (level) { switch (level) {
case "XML":
return 5;
case "TRACE": case "TRACE":
return 5; return 5;
case "DEBUG": case "DEBUG":
@@ -141,3 +176,4 @@ function LogLevelHierarchy(level) {
} }
exports.createLogEvent = createLogEvent; exports.createLogEvent = createLogEvent;
exports.createXmlEvent = createXmlEvent;