diff --git a/client/src/components/job-lifecycle/job-lifecycle.component.jsx b/client/src/components/job-lifecycle/job-lifecycle.component.jsx new file mode 100644 index 000000000..dc6925055 --- /dev/null +++ b/client/src/components/job-lifecycle/job-lifecycle.component.jsx @@ -0,0 +1,77 @@ +import {createStructuredSelector} from "reselect"; +import {selectBodyshop} from "../../redux/user/user.selectors"; +import {connect} from "react-redux"; +import {useEffect, useState} from "react"; +import axios from "axios"; +import {Card, Space, Table, Timeline} from "antd"; + +const mapStateToProps = createStructuredSelector({ + bodyshop: selectBodyshop, +}); +const mapDispatchToProps = (dispatch) => ({ + //setUserLanguage: language => dispatch(setUserLanguage(language)) +}); + +export function JobLifecycleComponent({bodyshop, job, ...rest}) { + const [loading, setLoading] = useState(false); + const [lifecycleData, setLifecycleData] = useState(null); + + + useEffect(() => { + async function getLifecycleData() { + if (job && job.id) { + setLoading(true); + const response = await axios.post("/job/lifecycle", { + jobids: job.id, + }); + console.dir(response.data.data.transitions, {depth: null}); + setLifecycleData(response.data.data.transitions); + setLoading(false); + } + } + + getLifecycleData().catch((err) => { + console.log(`Something went wrong getting Job Lifecycle Data: ${err.message}`); + setLoading(false); + }); + }, [job]); + + const columnKeys = [ + 'start', + 'end', + 'value', + 'prev_value', + 'next_value', + 'duration', + 'type', + 'created_at', + 'updated_at' + ]; + + const columns = columnKeys.map(key => ({ + title: key.charAt(0).toUpperCase() + key.slice(1), // Capitalize the first letter for the title + dataIndex: key, + key: key, + })); + + return ( + + + + + + + + {lifecycleData.map((item, index) => ( + + {item.value} - {new Date(item.start).toLocaleString()} + + ))} + + + + + ); +} + +export default connect(mapStateToProps, mapDispatchToProps)(JobLifecycleComponent); diff --git a/client/src/pages/jobs-detail/jobs-detail.page.component.jsx b/client/src/pages/jobs-detail/jobs-detail.page.component.jsx index 001a18166..a7d51d5e3 100644 --- a/client/src/pages/jobs-detail/jobs-detail.page.component.jsx +++ b/client/src/pages/jobs-detail/jobs-detail.page.component.jsx @@ -54,6 +54,7 @@ import { selectBodyshop } from "../../redux/user/user.selectors"; import AuditTrailMapping from "../../utils/AuditTrailMappings"; import UndefinedToNull from "../../utils/undefinedtonull"; import { DateTimeFormat } from "./../../utils/DateFormatter"; +import JobLifecycleComponent from "../../components/job-lifecycle/job-lifecycle.component"; const mapStateToProps = createStructuredSelector({ bodyshop: selectBodyshop, @@ -288,6 +289,13 @@ export function JobsDetailPage({ form={form} /> + Lifecycle} + key="lifecycle" + > + + { const {jobids} = req.body; @@ -11,11 +12,17 @@ const handleMultipleJobs = (jobIDs, req, res) => { return res.status(200).send(jobIDs); } -const handleSingleJob = (req, res) => { - +const handleSingleJob = async (jobIds, req, res) => { const client = req.userGraphQLClient; - return res.status(200).send(req.body); + const resp = await client.request(queries.QUERY_TRANSITIONS_BY_JOBID, {jobid: jobIds,}); + + const response = { + jobIds, + data: resp + } + + return res.status(200).json(response); } module.exports = jobLifecycle; \ No newline at end of file diff --git a/server/middleware/eventAuthorizationMIddleware.js b/server/middleware/eventAuthorizationMIddleware.js index c766ceda5..423fbc73f 100644 --- a/server/middleware/eventAuthorizationMIddleware.js +++ b/server/middleware/eventAuthorizationMIddleware.js @@ -1,3 +1,11 @@ +const path = require("path"); +require("dotenv").config({ + path: path.resolve( + process.cwd(), + `.env.${process.env.NODE_ENV || "development"}` + ), +}); + /** * Checks if the event secret is correct * It adds the following properties to the request object: diff --git a/server/routes/jobRoutes.js b/server/routes/jobRoutes.js index e11187041..9b4a5e9f6 100644 --- a/server/routes/jobRoutes.js +++ b/server/routes/jobRoutes.js @@ -7,14 +7,12 @@ const validateFirebaseIdTokenMiddleware = require("../middleware/validateFirebas const {totals, statustransition, totalsSsu, costing, lifecycle, costingmulti} = require("../job/job"); const withUserGraphQLClientMiddleware = require("../middleware/withUserGraphQLClientMiddleware"); -router.use(validateFirebaseIdTokenMiddleware); - -router.post('/totals', withUserGraphQLClientMiddleware, totals); +router.post('/totals', validateFirebaseIdTokenMiddleware, withUserGraphQLClientMiddleware, totals); router.post('/statustransition', eventAuthorizationMiddleware, statustransition); -router.post('/totalsssu', withUserGraphQLClientMiddleware,totalsSsu); -router.post('/costing', withUserGraphQLClientMiddleware,costing); -router.get('/lifecycle', withUserGraphQLClientMiddleware, lifecycle); -router.post('/costingmulti', withUserGraphQLClientMiddleware, costingmulti); -router.post('/partsscan', withUserGraphQLClientMiddleware, partsScan); +router.post('/totalsssu', validateFirebaseIdTokenMiddleware, withUserGraphQLClientMiddleware,totalsSsu); +router.post('/costing', validateFirebaseIdTokenMiddleware, withUserGraphQLClientMiddleware,costing); +router.post('/lifecycle', validateFirebaseIdTokenMiddleware, withUserGraphQLClientMiddleware, lifecycle); +router.post('/costingmulti', validateFirebaseIdTokenMiddleware, withUserGraphQLClientMiddleware, costingmulti); +router.post('/partsscan', validateFirebaseIdTokenMiddleware, withUserGraphQLClientMiddleware, partsScan); module.exports = router;