Implemented a configurable buffer between events
This commit is contained in:
parent
49cb191254
commit
68bca9e703
5 changed files with 41 additions and 10 deletions
|
@ -1,6 +1,7 @@
|
||||||
import type { NextApiRequest, NextApiResponse } from 'next';
|
import type { NextApiRequest, NextApiResponse } from 'next';
|
||||||
import prisma from '../../../lib/prisma';
|
import prisma from '../../../lib/prisma';
|
||||||
import { getBusyTimes } from '../../../lib/calendarClient';
|
import { getBusyTimes } from '../../../lib/calendarClient';
|
||||||
|
import dayjs from "dayjs";
|
||||||
|
|
||||||
export default async function handler(req: NextApiRequest, res: NextApiResponse) {
|
export default async function handler(req: NextApiRequest, res: NextApiResponse) {
|
||||||
const { user } = req.query
|
const { user } = req.query
|
||||||
|
@ -11,10 +12,17 @@ export default async function handler(req: NextApiRequest, res: NextApiResponse)
|
||||||
},
|
},
|
||||||
select: {
|
select: {
|
||||||
credentials: true,
|
credentials: true,
|
||||||
timeZone: true
|
timeZone: true,
|
||||||
|
bufferTime: true
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
const availability = await getBusyTimes(currentUser.credentials, req.query.dateFrom, req.query.dateTo);
|
let availability = await getBusyTimes(currentUser.credentials, req.query.dateFrom, req.query.dateTo);
|
||||||
|
|
||||||
|
availability = availability.map(a => ({
|
||||||
|
start: dayjs(a.start).subtract(currentUser.bufferTime, 'minute').toString(),
|
||||||
|
end: dayjs(a.end).add(currentUser.bufferTime, 'minute').toString()
|
||||||
|
}));
|
||||||
|
|
||||||
res.status(200).json(availability);
|
res.status(200).json(availability);
|
||||||
}
|
}
|
||||||
|
|
|
@ -13,6 +13,7 @@ export default async function handler(req: NextApiRequest, res: NextApiResponse)
|
||||||
if (req.method == "PATCH") {
|
if (req.method == "PATCH") {
|
||||||
const startMins = req.body.start;
|
const startMins = req.body.start;
|
||||||
const endMins = req.body.end;
|
const endMins = req.body.end;
|
||||||
|
const bufferMins = req.body.buffer;
|
||||||
|
|
||||||
const updateDay = await prisma.user.update({
|
const updateDay = await prisma.user.update({
|
||||||
where: {
|
where: {
|
||||||
|
@ -20,7 +21,8 @@ export default async function handler(req: NextApiRequest, res: NextApiResponse)
|
||||||
},
|
},
|
||||||
data: {
|
data: {
|
||||||
startTime: startMins,
|
startTime: startMins,
|
||||||
endTime: endMins
|
endTime: endMins,
|
||||||
|
bufferTime: bufferMins
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
|
@ -25,6 +25,8 @@ export default function Availability(props) {
|
||||||
const startMinsRef = useRef<HTMLInputElement>();
|
const startMinsRef = useRef<HTMLInputElement>();
|
||||||
const endHoursRef = useRef<HTMLInputElement>();
|
const endHoursRef = useRef<HTMLInputElement>();
|
||||||
const endMinsRef = useRef<HTMLInputElement>();
|
const endMinsRef = useRef<HTMLInputElement>();
|
||||||
|
const bufferHoursRef = useRef<HTMLInputElement>();
|
||||||
|
const bufferMinsRef = useRef<HTMLInputElement>();
|
||||||
|
|
||||||
if (loading) {
|
if (loading) {
|
||||||
return <p className="text-gray-400">Loading...</p>;
|
return <p className="text-gray-400">Loading...</p>;
|
||||||
|
@ -80,15 +82,18 @@ export default function Availability(props) {
|
||||||
const enteredStartMins = parseInt(startMinsRef.current.value);
|
const enteredStartMins = parseInt(startMinsRef.current.value);
|
||||||
const enteredEndHours = parseInt(endHoursRef.current.value);
|
const enteredEndHours = parseInt(endHoursRef.current.value);
|
||||||
const enteredEndMins = parseInt(endMinsRef.current.value);
|
const enteredEndMins = parseInt(endMinsRef.current.value);
|
||||||
|
const enteredBufferHours = parseInt(bufferHoursRef.current.value);
|
||||||
|
const enteredBufferMins = parseInt(bufferMinsRef.current.value);
|
||||||
|
|
||||||
const startMins = enteredStartHours * 60 + enteredStartMins;
|
const startMins = enteredStartHours * 60 + enteredStartMins;
|
||||||
const endMins = enteredEndHours * 60 + enteredEndMins;
|
const endMins = enteredEndHours * 60 + enteredEndMins;
|
||||||
|
const bufferMins = enteredBufferHours * 60 + enteredBufferMins;
|
||||||
|
|
||||||
// TODO: Add validation
|
// TODO: Add validation
|
||||||
|
|
||||||
const response = await fetch('/api/availability/day', {
|
const response = await fetch('/api/availability/day', {
|
||||||
method: 'PATCH',
|
method: 'PATCH',
|
||||||
body: JSON.stringify({start: startMins, end: endMins}),
|
body: JSON.stringify({start: startMins, end: endMins, buffer: bufferMins}),
|
||||||
headers: {
|
headers: {
|
||||||
'Content-Type': 'application/json'
|
'Content-Type': 'application/json'
|
||||||
}
|
}
|
||||||
|
@ -298,7 +303,7 @@ export default function Availability(props) {
|
||||||
</h3>
|
</h3>
|
||||||
<div>
|
<div>
|
||||||
<p className="text-sm text-gray-500">
|
<p className="text-sm text-gray-500">
|
||||||
Set the start and end time of your day.
|
Set the start and end time of your day and a minimum buffer between your meetings.
|
||||||
</p>
|
</p>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
@ -316,7 +321,7 @@ export default function Availability(props) {
|
||||||
<input ref={startMinsRef} type="number" name="minutes" id="minutes" className="shadow-sm focus:ring-blue-500 focus:border-blue-500 block w-full sm:text-sm border-gray-300 rounded-md" placeholder="30" defaultValue={convertMinsToHrsMins(props.user.startTime).split(":")[1]} />
|
<input ref={startMinsRef} type="number" name="minutes" id="minutes" className="shadow-sm focus:ring-blue-500 focus:border-blue-500 block w-full sm:text-sm border-gray-300 rounded-md" placeholder="30" defaultValue={convertMinsToHrsMins(props.user.startTime).split(":")[1]} />
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div className="flex">
|
<div className="flex mb-4">
|
||||||
<label className="w-1/4 pt-2 block text-sm font-medium text-gray-700">End time</label>
|
<label className="w-1/4 pt-2 block text-sm font-medium text-gray-700">End time</label>
|
||||||
<div>
|
<div>
|
||||||
<label htmlFor="hours" className="sr-only">Hours</label>
|
<label htmlFor="hours" className="sr-only">Hours</label>
|
||||||
|
@ -328,6 +333,18 @@ export default function Availability(props) {
|
||||||
<input ref={endMinsRef} type="number" name="minutes" id="minutes" className="shadow-sm focus:ring-blue-500 focus:border-blue-500 block w-full sm:text-sm border-gray-300 rounded-md" placeholder="30" defaultValue={convertMinsToHrsMins(props.user.endTime).split(":")[1]} />
|
<input ref={endMinsRef} type="number" name="minutes" id="minutes" className="shadow-sm focus:ring-blue-500 focus:border-blue-500 block w-full sm:text-sm border-gray-300 rounded-md" placeholder="30" defaultValue={convertMinsToHrsMins(props.user.endTime).split(":")[1]} />
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
<div className="flex mb-4">
|
||||||
|
<label className="w-1/4 pt-2 block text-sm font-medium text-gray-700">Buffer</label>
|
||||||
|
<div>
|
||||||
|
<label htmlFor="hours" className="sr-only">Hours</label>
|
||||||
|
<input ref={bufferHoursRef} type="number" name="hours" id="hours" className="shadow-sm focus:ring-blue-500 focus:border-blue-500 block w-full sm:text-sm border-gray-300 rounded-md" placeholder="0" defaultValue={convertMinsToHrsMins(props.user.bufferTime).split(":")[0]} />
|
||||||
|
</div>
|
||||||
|
<span className="mx-2 pt-1">:</span>
|
||||||
|
<div>
|
||||||
|
<label htmlFor="minutes" className="sr-only">Minutes</label>
|
||||||
|
<input ref={bufferMinsRef} type="number" name="minutes" id="minutes" className="shadow-sm focus:ring-blue-500 focus:border-blue-500 block w-full sm:text-sm border-gray-300 rounded-md" placeholder="10" defaultValue={convertMinsToHrsMins(props.user.bufferTime).split(":")[1]} />
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
<div className="mt-5 sm:mt-4 sm:flex sm:flex-row-reverse">
|
<div className="mt-5 sm:mt-4 sm:flex sm:flex-row-reverse">
|
||||||
<button type="submit" className="btn btn-primary">
|
<button type="submit" className="btn btn-primary">
|
||||||
Update
|
Update
|
||||||
|
@ -361,7 +378,8 @@ export async function getServerSideProps(context) {
|
||||||
id: true,
|
id: true,
|
||||||
username: true,
|
username: true,
|
||||||
startTime: true,
|
startTime: true,
|
||||||
endTime: true
|
endTime: true,
|
||||||
|
bufferTime: true
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,2 @@
|
||||||
|
-- AlterTable
|
||||||
|
ALTER TABLE "users" ADD COLUMN "bufferTime" INTEGER NOT NULL DEFAULT 0;
|
|
@ -44,6 +44,7 @@ model User {
|
||||||
weekStart String? @default("Sunday")
|
weekStart String? @default("Sunday")
|
||||||
startTime Int @default(0)
|
startTime Int @default(0)
|
||||||
endTime Int @default(1440)
|
endTime Int @default(1440)
|
||||||
|
bufferTime Int @default(0)
|
||||||
createdDate DateTime @default(now()) @map(name: "created")
|
createdDate DateTime @default(now()) @map(name: "created")
|
||||||
eventTypes EventType[]
|
eventTypes EventType[]
|
||||||
credentials Credential[]
|
credentials Credential[]
|
||||||
|
|
Loading…
Reference in a new issue