Autosave: 20260217-030629
This commit is contained in:
parent
24c501e587
commit
71e8f75485
24
backend/check_pto.js
Normal file
24
backend/check_pto.js
Normal file
@ -0,0 +1,24 @@
|
||||
const db = require('./src/db/models');
|
||||
|
||||
async function check() {
|
||||
try {
|
||||
const requests = await db.time_off_requests.findAll({
|
||||
limit: 10,
|
||||
order: [['createdAt', 'DESC']],
|
||||
include: ['requester']
|
||||
});
|
||||
|
||||
console.log("Found " + requests.length + " requests.");
|
||||
requests.forEach(r => {
|
||||
console.log(`ID: ${r.id}, Status: ${r.status}, Requester: ${r.requester?.firstName} ${r.requester?.lastName}`);
|
||||
console.log(` Starts: ${r.starts_at}, Ends: ${r.ends_at}, Days: ${r.days}`);
|
||||
console.log(` Reason: ${r.reason}`);
|
||||
});
|
||||
} catch (err) {
|
||||
console.error(err);
|
||||
} finally {
|
||||
await db.sequelize.close();
|
||||
}
|
||||
}
|
||||
|
||||
check();
|
||||
@ -7,20 +7,10 @@ type Props = {
|
||||
}
|
||||
|
||||
export default function FooterBar({ children }: Props) {
|
||||
const year = new Date().getFullYear()
|
||||
|
||||
return (
|
||||
<footer className={`py-2 px-6 ${containerMaxW}`}>
|
||||
<div className="block md:flex items-center justify-between">
|
||||
<div className="text-center md:text-left mb-6 md:mb-0">
|
||||
<b>
|
||||
©{year},{` `}
|
||||
<a href="https://flatlogic.com/" rel="noreferrer" target="_blank">
|
||||
Flatlogic
|
||||
</a>
|
||||
.
|
||||
</b>
|
||||
{` `}
|
||||
{children}
|
||||
</div>
|
||||
|
||||
|
||||
@ -40,6 +40,28 @@ const KanbanCard = ({
|
||||
[item, isEditable],
|
||||
);
|
||||
|
||||
const renderCardContent = () => {
|
||||
if (entityName === 'time_off_requests') {
|
||||
const requesterName = item.requester ? `${item.requester.firstName} ${item.requester.lastName}` : 'Unknown Requester';
|
||||
const dateRange = `${moment(item.starts_at).format('MMM DD')} - ${moment(item.ends_at).format('MMM DD')}`;
|
||||
const reason = item.reason ? item.reason : 'No reason provided';
|
||||
|
||||
return (
|
||||
<div className="flex flex-col">
|
||||
<span className="font-bold text-sm">{requesterName}</span>
|
||||
<span className="text-xs text-gray-500 dark:text-gray-400">{dateRange}</span>
|
||||
<span className="text-sm italic mt-1 truncate">{reason}</span>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
return (
|
||||
<span className={'text-base font-semibold'}>
|
||||
{item[showFieldName] ?? 'No data'}
|
||||
</span>
|
||||
);
|
||||
};
|
||||
|
||||
return (
|
||||
<div
|
||||
ref={drag}
|
||||
@ -50,13 +72,13 @@ const KanbanCard = ({
|
||||
<div className={'flex items-center justify-between'}>
|
||||
<Link
|
||||
href={`/${entityName}/${entityName}-view/?id=${item.id}`}
|
||||
className={'text-base font-semibold'}
|
||||
className={'block w-full'}
|
||||
>
|
||||
{item[showFieldName] ?? 'No data'}
|
||||
{renderCardContent()}
|
||||
</Link>
|
||||
</div>
|
||||
<div className={'flex items-center justify-between'}>
|
||||
<p>{moment(item.createdAt).format('MMM DD hh:mm a')}</p>
|
||||
<div className={'flex items-center justify-between mt-2'}>
|
||||
<p className="text-xs text-gray-400">{moment(item.createdAt).format('MMM DD hh:mm a')}</p>
|
||||
<div className='flex items-center'>
|
||||
<ListActionsPopover
|
||||
itemId={item.id}
|
||||
|
||||
@ -111,8 +111,8 @@ export default function LayoutAuthenticated({
|
||||
<div className="max-w-7xl mx-auto">
|
||||
{children}
|
||||
</div>
|
||||
<FooterBar>Hand-crafted & Made with ❤️</FooterBar>
|
||||
<FooterBar />
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
@ -11,6 +11,7 @@ import TableTime_off_requests from '../../components/Time_off_requests/TableTime
|
||||
import BaseButton from '../../components/BaseButton'
|
||||
import axios from "axios";
|
||||
import Link from "next/link";
|
||||
import { useRouter } from 'next/router';
|
||||
import {useAppDispatch, useAppSelector} from "../../stores/hooks";
|
||||
import CardBoxModal from "../../components/CardBoxModal";
|
||||
import DragDropFilePicker from "../../components/DragDropFilePicker";
|
||||
@ -22,6 +23,7 @@ import {hasPermission} from "../../helpers/userPermissions";
|
||||
|
||||
|
||||
const Time_off_requestsTablesPage = () => {
|
||||
const router = useRouter();
|
||||
const [filterItems, setFilterItems] = useState([]);
|
||||
const [csvFile, setCsvFile] = useState<File | null>(null);
|
||||
const [isModalActive, setIsModalActive] = useState(false);
|
||||
@ -54,6 +56,12 @@ const Time_off_requestsTablesPage = () => {
|
||||
|
||||
const hasCreatePermission = currentUser && hasPermission(currentUser, 'CREATE_TIME_OFF_REQUESTS');
|
||||
|
||||
const showPending = () => {
|
||||
router.push({
|
||||
pathname: router.pathname,
|
||||
query: { ...router.query, status: 'pending_approval' },
|
||||
}, undefined, { shallow: true });
|
||||
};
|
||||
|
||||
const addFilter = () => {
|
||||
const newItem = {
|
||||
@ -111,6 +119,12 @@ const Time_off_requestsTablesPage = () => {
|
||||
label='Filter'
|
||||
onClick={addFilter}
|
||||
/>
|
||||
<BaseButton
|
||||
className={'mr-3'}
|
||||
color='warning'
|
||||
label='Pending'
|
||||
onClick={showPending}
|
||||
/>
|
||||
<BaseButton className={'mr-3'} color='info' label='Download CSV' onClick={getTime_off_requestsCSV} />
|
||||
|
||||
{hasCreatePermission && (
|
||||
@ -170,4 +184,4 @@ Time_off_requestsTablesPage.getLayout = function getLayout(page: ReactElement) {
|
||||
)
|
||||
}
|
||||
|
||||
export default Time_off_requestsTablesPage
|
||||
export default Time_off_requestsTablesPage
|
||||
@ -11,6 +11,7 @@ import TableTime_off_requests from '../../components/Time_off_requests/TableTime
|
||||
import BaseButton from '../../components/BaseButton'
|
||||
import axios from "axios";
|
||||
import Link from "next/link";
|
||||
import { useRouter } from 'next/router';
|
||||
import {useAppDispatch, useAppSelector} from "../../stores/hooks";
|
||||
import CardBoxModal from "../../components/CardBoxModal";
|
||||
import DragDropFilePicker from "../../components/DragDropFilePicker";
|
||||
@ -22,6 +23,7 @@ import {hasPermission} from "../../helpers/userPermissions";
|
||||
|
||||
|
||||
const Time_off_requestsTablesPage = () => {
|
||||
const router = useRouter();
|
||||
const [filterItems, setFilterItems] = useState([]);
|
||||
const [csvFile, setCsvFile] = useState<File | null>(null);
|
||||
const [isModalActive, setIsModalActive] = useState(false);
|
||||
@ -53,6 +55,12 @@ const Time_off_requestsTablesPage = () => {
|
||||
|
||||
const hasCreatePermission = currentUser && hasPermission(currentUser, 'CREATE_TIME_OFF_REQUESTS');
|
||||
|
||||
const showPending = () => {
|
||||
router.push({
|
||||
pathname: router.pathname,
|
||||
query: { ...router.query, status: 'pending_approval' },
|
||||
}, undefined, { shallow: true });
|
||||
};
|
||||
|
||||
const addFilter = () => {
|
||||
const newItem = {
|
||||
@ -110,6 +118,12 @@ const Time_off_requestsTablesPage = () => {
|
||||
label='Filter'
|
||||
onClick={addFilter}
|
||||
/>
|
||||
<BaseButton
|
||||
className={'mr-3'}
|
||||
color='warning'
|
||||
label='Pending'
|
||||
onClick={showPending}
|
||||
/>
|
||||
<BaseButton className={'mr-3'} color='info' label='Download CSV' onClick={getTime_off_requestsCSV} />
|
||||
|
||||
{hasCreatePermission && (
|
||||
@ -169,4 +183,4 @@ Time_off_requestsTablesPage.getLayout = function getLayout(page: ReactElement) {
|
||||
)
|
||||
}
|
||||
|
||||
export default Time_off_requestsTablesPage
|
||||
export default Time_off_requestsTablesPage
|
||||
Loading…
x
Reference in New Issue
Block a user