Merge master

Signed-off-by: Dave Richer <dave@imexsystems.ca>
This commit is contained in:
Dave Richer
2024-01-08 11:18:22 -05:00
16 changed files with 131 additions and 32 deletions

View File

@@ -215,10 +215,7 @@ export default function CourtesyCarCreateFormComponent({ form, saveLoading }) {
>
<CourtesyCarStatus />
</Form.Item>
<Form.Item
label={t("courtesycars.fields.readiness")}
name="readiness"
>
<Form.Item label={t("courtesycars.fields.readiness")} name="readiness">
<CourtesyCarReadiness />
</Form.Item>
<div>
@@ -235,8 +232,9 @@ export default function CourtesyCarCreateFormComponent({ form, saveLoading }) {
>
{() => {
const nextservicekm = form.getFieldValue("nextservicekm");
const mileageOver =
nextservicekm && nextservicekm <= form.getFieldValue("mileage");
const mileageOver = nextservicekm
? nextservicekm <= form.getFieldValue("mileage")
: false;
if (mileageOver)
return (
<Space direction="vertical" style={{ color: "tomato" }}>

View File

@@ -73,10 +73,10 @@ export default function CourtesyCarsList({ loading, courtesycars, refetch }) {
render: (text, record) => {
const { nextservicedate, nextservicekm, mileage } = record;
const mileageOver = nextservicekm <= mileage;
const mileageOver = nextservicekm ? nextservicekm <= mileage : false;
const dueForService =
nextservicedate && dayjs(nextservicedate).isBefore(dayjs());
nextservicedate && dayjs(nextservicedate).end('day').isSameOrBefore(dayjs());
return (
<Space>

View File

@@ -221,6 +221,11 @@ export function JobsDetailHeader({ job, bodyshop, disabled }) {
<VehicleVinDisplay>
{`${job.v_vin || t("general.labels.na")}`}
</VehicleVinDisplay>
{bodyshop.pbs_serialnumber || bodyshop.cdk_dealerid ? (
job.v_vin.length !== 17 ? (
<WarningFilled style={{ color: "tomato", marginLeft: ".3rem" }} />
) : null
) : null}
</DataLabel>
<DataLabel label={t("jobs.fields.regie_number")}>
{job.regie_number || t("general.labels.na")}

View File

@@ -24,6 +24,7 @@ export function ProductionColumnsComponent({
columnState,
technician,
bodyshop,
data,
tableState,
}) {
const [columns, setColumns] = columnState;
@@ -36,6 +37,7 @@ export function ProductionColumnsComponent({
bodyshop,
technician,
state: tableState,
data,
activeStatuses: bodyshop.md_ro_statuses.active_statuses,
}).filter((i) => i.key === e.key),
]);
@@ -44,6 +46,7 @@ export function ProductionColumnsComponent({
const columnKeys = columns.map((i) => i.key);
const cols = dataSource({
technician,
data,
state: tableState,
activeStatuses: bodyshop.md_ro_statuses.active_statuses,
});

View File

@@ -1,4 +1,4 @@
import { PauseCircleOutlined, BranchesOutlined } from "@ant-design/icons";
import { BranchesOutlined, PauseCircleOutlined } from "@ant-design/icons";
import { Space, Tooltip } from "antd";
import i18n from "i18next";
import dayjs from "../../utils/day";
@@ -6,6 +6,7 @@ import { Link } from "react-router-dom";
import CurrencyFormatter from "../../utils/CurrencyFormatter";
import { TimeFormatter } from "../../utils/DateFormatter";
import PhoneFormatter from "../../utils/PhoneFormatter";
import { onlyUnique } from "../../utils/arrayHelper";
import { alphaSort, dateSort, statusSort } from "../../utils/sorters";
import JobAltTransportChange from "../job-at-change/job-at-change.component";
import JobPartsQueueCount from "../job-parts-queue-count/job-parts-queue-count.component";
@@ -25,7 +26,7 @@ import ProductionListColumnCategory from "./production-list-columns.status.categ
import ProductionListColumnStatus from "./production-list-columns.status.component";
import ProductionlistColumnTouchTime from "./prodution-list-columns.touchtime.component";
const r = ({ technician, state, activeStatuses, bodyshop }) => {
const r = ({ technician, state, activeStatuses, data, bodyshop }) => {
return [
{
title: i18n.t("jobs.actions.viewdetail"),
@@ -536,6 +537,36 @@ const r = ({ technician, state, activeStatuses, bodyshop }) => {
<JobPartsQueueCount parts={record.joblines_status} record={record} />
),
},
{
title: i18n.t("jobs.labels.estimator"),
dataIndex: "estimator",
key: "estimator",
sorter: (a, b) =>
alphaSort(
`${a.est_ct_fn || ""} ${a.est_ct_ln || ""}`.trim(),
`${b.est_ct_fn || ""} ${b.est_ct_ln || ""}`.trim()
),
sortOrder:
state.sortedInfo.columnKey === "estimator" && state.sortedInfo.order,
filters:
(data &&
data
.map((j) => `${j.est_ct_fn || ""} ${j.est_ct_ln || ""}`.trim())
.filter(onlyUnique)
.map((s) => {
return {
text: s || "N/A",
value: [s],
};
})) ||
[],
onFilter: (value, record) =>
value.includes(
`${record.est_ct_fn || ""} ${record.est_ct_ln || ""}`.trim()
),
render: (text, record) =>
`${record.est_ct_fn || ""} ${record.est_ct_ln || ""}`.trim(),
},
//Added as a place holder for St Claude. Not implemented as it requires another join for a field used by only 1 client.
// {

View File

@@ -24,6 +24,7 @@ export function ProductionListTable({
technician,
currentUser,
state,
data,
setColumns,
setState,
}) {
@@ -41,6 +42,7 @@ export function ProductionListTable({
bodyshop,
technician,
state,
data: data,
activeStatuses: bodyshop.md_ro_statuses.active_statuses,
}).find((e) => e.key === k.key),
width: k.width,
@@ -95,6 +97,7 @@ export function ProductionListTable({
...ProductionListColumns({
technician,
state,
data: data,
activeStatuses: bodyshop.md_ro_statuses.active_statuses,
}).find((e) => e.key === k.key),
width: k.width,

View File

@@ -1,8 +1,8 @@
import {SyncOutlined} from "@ant-design/icons";
import {useSplitTreatments} from "@splitsoftware/splitio-react";
import {Button, Dropdown, Input, Space, Statistic, Table,} from "antd";
import {Button, Dropdown, Input, Space, Statistic, Table} from "antd";
import {PageHeader} from "@ant-design/pro-layout";
import React, {useMemo, useState} from "react";
import React, {useEffect, useMemo, useState} from "react";
import ReactDragListView from "react-drag-listview";
import {useTranslation} from "react-i18next";
import {connect} from "react-redux";
@@ -66,6 +66,7 @@ export function ProductionListTable({loading, data, refetch, bodyshop, technicia
bodyshop,
technician,
state,
data,
activeStatuses: bodyshop.md_ro_statuses.active_statuses,
}).find((e) => e.key === k.key),
width: k.width ?? 100,
@@ -74,6 +75,34 @@ export function ProductionListTable({loading, data, refetch, bodyshop, technicia
[]
);
useEffect(() => {
const newColumns =
(state &&
matchingColumnConfig &&
matchingColumnConfig.columns.columnKeys.map((k) => {
return {
...ProductionListColumns({
bodyshop,
technician,
state,
data: data,
activeStatuses: bodyshop.md_ro_statuses.active_statuses,
}).find((e) => e.key === k.key),
width: k.width ?? 100,
};
})) ||
[];
setColumns(newColumns);
// eslint-disable-next-line react-hooks/exhaustive-deps
}, [
//state,
matchingColumnConfig,
bodyshop,
technician,
data,
]); //State removed from dependency array as it causes race condition when removing columns from table view and is not needed.
const handleTableChange = (pagination, filters, sorter) => {
setState({
...state,
@@ -89,10 +118,11 @@ export function ProductionListTable({loading, data, refetch, bodyshop, technicia
setColumns(columnsCopy);
};
const removeColumn = (e) => {
const {key} = e;
setColumns(columns.filter((i) => i.key !== key));
};
const removeColumn = (e) => {
const { key } = e;
const newColumns = columns.filter((i) => i.key !== key);
setColumns(newColumns);
};
const handleResize =
(index) =>
@@ -221,6 +251,7 @@ export function ProductionListTable({loading, data, refetch, bodyshop, technicia
<ProductionListColumnsAdd
columnState={[columns, setColumns]}
tableState={state}
data={data}
/>
<ProductionListSaveConfigButton
columns={columns}
@@ -231,6 +262,7 @@ export function ProductionListTable({loading, data, refetch, bodyshop, technicia
state={state}
setState={setState}
setColumns={setColumns}
data={data}
/>
<Input

View File

@@ -364,6 +364,8 @@ export const QUERY_JOBS_IN_PRODUCTION = gql`
employee_refinish
employee_prep
employee_csr
est_ct_fn
est_ct_ln
suspended
date_repairstarted
joblines_status {

View File

@@ -2023,24 +2023,24 @@
- active:
_eq: true
columns:
- labor_rates
- percentage
- created_at
- updated_at
- employeeid
- id
- labor_rates
- percentage
- teamid
- updated_at
select_permissions:
- role: user
permission:
columns:
- labor_rates
- percentage
- created_at
- updated_at
- employeeid
- id
- labor_rates
- percentage
- teamid
- updated_at
filter:
employee_team:
bodyshop:
@@ -2055,13 +2055,13 @@
- role: user
permission:
columns:
- labor_rates
- percentage
- created_at
- updated_at
- employeeid
- id
- labor_rates
- percentage
- teamid
- updated_at
filter:
employee_team:
bodyshop:
@@ -2123,21 +2123,23 @@
_eq: true
columns:
- active
- name
- created_at
- updated_at
- bodyshopid
- created_at
- id
- max_load
- name
- updated_at
select_permissions:
- role: user
permission:
columns:
- active
- name
- created_at
- updated_at
- bodyshopid
- created_at
- id
- max_load
- name
- updated_at
filter:
bodyshop:
associations:
@@ -2153,6 +2155,7 @@
columns:
- active
- bodyshopid
- max_load
- name
- updated_at
filter:

View File

@@ -0,0 +1,4 @@
-- Could not auto-generate a down migration.
-- Please write an appropriate down migration for the SQL below:
-- alter table "public"."employee_team_members" add column "max_load" numeric
-- not null default '10000';

View File

@@ -0,0 +1,2 @@
alter table "public"."employee_team_members" add column "max_load" numeric
not null default '10000';

View File

@@ -0,0 +1,3 @@
alter table "public"."employee_team_members" alter column "max_load" set default '10000'::numeric;
alter table "public"."employee_team_members" alter column "max_load" drop not null;
alter table "public"."employee_team_members" add column "max_load" numeric;

View File

@@ -0,0 +1 @@
alter table "public"."employee_team_members" drop column "max_load" cascade;

View File

@@ -0,0 +1,4 @@
-- Could not auto-generate a down migration.
-- Please write an appropriate down migration for the SQL below:
-- alter table "public"."employee_teams" add column "max_load" numeric
-- not null default '10000';

View File

@@ -0,0 +1,2 @@
alter table "public"."employee_teams" add column "max_load" numeric
not null default '10000';

View File

@@ -132,6 +132,7 @@ exports.payment_refund = async (req, res) => {
exports.generate_payment_url = async (req, res) => {
logger.log("intellipay-payment-url", "DEBUG", req.user?.email, null, null);
const shopCredentials = await getShopCredentials(req.body.bodyshop);
try {
const options = {
method: "POST",
@@ -139,7 +140,12 @@ exports.generate_payment_url = async (req, res) => {
//TODO: Move these to environment variables/database.
data: qs.stringify({
...shopCredentials,
...req.body,
//...req.body,
amount: Dinero({ amount: Math.round(req.body.amount * 100) }).toFormat(
"0.00"
),
account: req.body.account,
invoice: req.body.invoice,
createshorturl: true,
//The postback URL is set at the CP teller global terminal settings page.
}),