220 lines
7.5 KiB
JavaScript

import React, { useEffect } from "react";
import { useServiceProjectJobDetails } from "../../hooks/useServiceProject";
import { SpinnerLoader } from "../common/Loader";
import Error from "../common/Error";
import { formatUTCToLocalTime } from "../../utils/dateUtils";
import Avatar from "../common/Avatar";
import EmployeeAvatarGroup from "../common/EmployeeAvatarGroup";
import JobStatusLog from "./JobStatusLog";
import JobComments from "./JobComments";
import { daysLeft, getJobStatusBadge } from "../../utils/appUtils";
import HoverPopup from "../common/HoverPopup";
import ChangeStatus from "./ChangeStatus";
import { useParams } from "react-router-dom";
import { STATUS_JOB_CLOSED } from "../../utils/constants";
import Tooltip from "../common/Tooltip";
const ManageJobTicket = ({ Job }) => {
const { projectId } = useParams();
const { data, isLoading, isError, error } = useServiceProjectJobDetails(
Job?.job
);
const tabsData = [
{
id: "comment",
title: "Comments",
icon: "bx bx-comment me-2",
active: true,
content: <JobComments data={data} />,
},
{
id: "history",
title: "History",
icon: "bx bx-time me-2",
active: false,
content: <JobStatusLog data={data?.updateLogs} />,
},
];
if (isLoading) return <SpinnerLoader />;
if (isError)
return (
<div>
<Error error={error} />
</div>
);
return (
<div className="row text-start">
<div className="col-12">
<h6 className="fs-5 fw-semibold">{data?.title}</h6>
<div className="d-flex justify-content-between align-items-start flex-wrap mb-2">
<p className="mb-0">
<span className="fw-medium me-1">Job Id :</span>
{data?.jobTicketUId || "N/A"}
</p>
<div className="d-flex flex-column align-items-end gap-3 mb-3">
<div className="d-flex flex-row gap-2">
<span className={`badge ${getJobStatusBadge(data?.status?.id)}`}>
{data?.status?.displayName}
</span>
{STATUS_JOB_CLOSED !== data?.status?.id && (
<HoverPopup
id="STATUS_CHANEG"
title="Change Status"
Mode="click"
className=""
content={
<ChangeStatus
statusId={data?.status?.id}
projectId={projectId}
jobId={Job?.job}
popUpId="STATUS_CHANEG"
/>
}
>
<Tooltip
text={"Change Status"}
placement="left"
children={
<i className="bx bx-edit bx-sm cursor-pointer"></i>
}
/>
</HoverPopup>
)}
</div>
</div>
</div>
<div className="d-flex flex-wrap">
<p>{data?.description || "N/A"}</p>
</div>
<div className="d-flex justify-content-between mb-4">
<div className="d-flex flex-row gap-1 fw-medium">
<i className="bx bx-calendar"></i>{" "}
<span>
Created Date : {formatUTCToLocalTime(data?.createdAt, true)}
</span>
</div>
</div>
<div className="d-flex justify-content-md-between ">
<div className="d-flex flex-row gap-5">
<span className="fw-medium">
<i className="bx bx-calendar"></i> Start Date :{" "}
{formatUTCToLocalTime(data?.startDate)}
</span>{" "}
<i className="bx bx-right-arrow-alt"></i>{" "}
<span className="fw-medium">
<i className="bx bx-calendar"></i> Due on :{" "}
{formatUTCToLocalTime(data?.startDate)}
</span>
</div>
{data?.dueDate &&
(() => {
const { days, color } = daysLeft(data?.startDate, data?.dueDate);
return (
<span>
<span className="fw-medium me-1">Days Left:</span>
<span className={`badge bg-${color}`}>
{days !== null ? `${days} days` : "N/A"}
</span>
</span>
);
})()}
</div>
<div className="d-block mt-4 mb-3">
<div className="row align-items-start align-items-md-start gap-2 mb-1">
<div className="col-12 col-md-auto">
<small className="fs-6 fw-medium">Created By</small>
</div>
<div className="col d-flex flex-row align-items-center ">
<Avatar
size="xs"
firstName={data?.createdBy?.firstName}
lastName={data?.createdBy?.lastName}
/>{" "}
<div className="d-flex flex-row align-items-center">
<p className="m-0">{`${data?.createdBy?.firstName} ${data?.createdBy?.lastName}`}</p>
<small className="text-secondary ms-1">
({data?.createdBy?.jobRoleName})
</small>
</div>
</div>
</div>
{data?.assignees?.length > 0 && (
<div className="row align-items-start align-items-md-start gap-2">
<div className="col-12 col-md-auto">
<small className="fs-6 fw-medium">Assigned To</small>
</div>
<div className="col">
<div className="row gap-4">
{data?.assignees?.map((emp) => (
<div
key={emp.id}
className="col-6 col-sm-6 col-md-4 col-lg-4"
>
<div className="d-flex align-items-center gap-2">
<Avatar
size="xs"
firstName={emp.firstName}
lastName={emp.lastName}
/>
<div className="d-flex flex-column">
<span className=" text-truncate">
{emp.firstName} {emp.lastName}
</span>
<small className="text-secondary text-truncate">
{emp.jobRoleName}
</small>
</div>
</div>
</div>
))}
</div>
</div>
</div>
)}
</div>
</div>
<div className="nav-align-top nav-tabs-shadow p-0 shadow-none">
<ul className="nav nav-tabs" role="tablist">
{tabsData.map((tab) => (
<li className="nav-item" key={tab.id}>
<button
type="button"
className={`nav-link ${tab.active ? "active" : ""}`}
data-bs-toggle="tab"
data-bs-target={`#tab-${tab.id}`}
role="tab"
>
<i className={tab.icon} /> {tab.title}
</button>
</li>
))}
</ul>
<div className="tab-content p-1 px-sm-3">
{tabsData.map((tab) => (
<div
key={tab.id}
className={`tab-pane fade ${tab.active ? "show active" : ""}`}
id={`tab-${tab.id}`}
role="tabpanel"
>
{tab.content}
</div>
))}
</div>
</div>
</div>
);
};
export default ManageJobTicket;