From e82465aa74eb262f44c8530f8c575e758a0d739f Mon Sep 17 00:00:00 2001 From: Tom Wahl Date: Wed, 1 Nov 2023 13:30:52 +0100 Subject: [PATCH] [#10] Add page to check for room availability --- backend/service/db/dbRooms.go | 19 +- frontend/src/api/fetchRoom.ts | 30 +- frontend/src/components/MenuBar.vue | 5 + frontend/src/components/RoomFinder.vue | 4 + frontend/src/components/RoomOccupation.vue | 123 ++---- frontend/src/components/RoomOccupation2.vue | 404 -------------------- 6 files changed, 53 insertions(+), 532 deletions(-) delete mode 100644 frontend/src/components/RoomOccupation2.vue diff --git a/backend/service/db/dbRooms.go b/backend/service/db/dbRooms.go index 8d30ff4..7a40228 100644 --- a/backend/service/db/dbRooms.go +++ b/backend/service/db/dbRooms.go @@ -38,30 +38,15 @@ func GetRooms(app *pocketbase.PocketBase) []string { return roomArray } -func GetRoomScheduleForDay(app *pocketbase.PocketBase, room string, date string) []model.Event { - var events []model.Event - - // get all events from event records in the events collection - err := app.Dao().DB().Select("*").From("events"). - Where(dbx.Like("Rooms", room)). - AndWhere(dbx.Like("Start", date)). - GroupBy("Start", "End", "Rooms").All(&events) - if err != nil { - print("Error while getting events from database: ", err) - return nil - } - return events -} - func GetRoomSchedule(app *pocketbase.PocketBase, room string, from string, to string) []model.Event { var events []model.Event - fromDate, err := time.Parse("2000-01-02", from) + fromDate, err := time.Parse("2006-01-02", from) if err != nil { fmt.Println("Error parsing date 'from':", err) return nil } - toDate, err := time.Parse("2000-01-02", to) + toDate, err := time.Parse("2006-01-02", to) if err != nil { fmt.Println("Error parsing date 'to':", err) return nil diff --git a/frontend/src/api/fetchRoom.ts b/frontend/src/api/fetchRoom.ts index 56ac79d..3fb9e70 100644 --- a/frontend/src/api/fetchRoom.ts +++ b/frontend/src/api/fetchRoom.ts @@ -17,40 +17,20 @@ export async function fetchEventsByRoomAndDuration( from_date: string, to_date: string, ): Promise { - const occupations: Event[] = []; + const events: Event[] = []; await fetch("/api/schedule?room=" + room + "&from=" + from_date + "&to=" + to_date) .then((response) => { console.log(response); return response.json(); }) .then((eventsResponse) => { + console.log("Response:", eventsResponse); eventsResponse.forEach((event: Event) => - occupations.push(new Event(event.Days, event.Week, event.Start, event.End, event.Name, event.EventType, event.Prof, event.Rooms, event.Notes, event.BookedAt, event.Course, event.Semester)), - ); + events.push(event)); }).catch((error) => { console.log("Error fetching events: ", error); return null; }) - return occupations; -} - -export async function fetchEventsByRoomAndDay( - room: string, - date: string, -): Promise { - const occupations: Event[] = []; - await fetch("/api/schedule/day?room=" + room + "&sdate=" + date) - .then((response) => { - console.log(response); - return response.json(); - }) - .then((eventsResponse) => { - eventsResponse.forEach((event: Event) => - occupations.push(new Event(event.Days, event.Week, event.Start, event.End, event.Name, event.EventType, event.Prof, event.Rooms, event.Notes, event.BookedAt, event.Course, event.Semester)), - ); - }).catch((error) => { - console.log("Error fetching events: ", error); - return null; - }) - return occupations; + console.log("occupations: ", events); + return events; } \ No newline at end of file diff --git a/frontend/src/components/MenuBar.vue b/frontend/src/components/MenuBar.vue index c8cf9e5..a3b0ec7 100644 --- a/frontend/src/components/MenuBar.vue +++ b/frontend/src/components/MenuBar.vue @@ -12,6 +12,11 @@ const items = ref([ icon: "pi pi-fw pi-pencil", url: "/edit", }, + { + label: "Check Room Availability", + icon: "pi pi-fw pi-calendar", + url: "/rooms", + }, { label: "FAQ", icon: "pi pi-fw pi-book", diff --git a/frontend/src/components/RoomFinder.vue b/frontend/src/components/RoomFinder.vue index 1fe83c3..18c6935 100644 --- a/frontend/src/components/RoomFinder.vue +++ b/frontend/src/components/RoomFinder.vue @@ -41,6 +41,10 @@ rooms().then( placeholder="Select a Room" /> +
+
diff --git a/frontend/src/components/RoomOccupation.vue b/frontend/src/components/RoomOccupation.vue index edae47c..ab8cdbe 100644 --- a/frontend/src/components/RoomOccupation.vue +++ b/frontend/src/components/RoomOccupation.vue @@ -5,6 +5,7 @@ import interactionPlugin from '@fullcalendar/interaction' import timeGridPlugin from '@fullcalendar/timegrid' import {computed, ref, Ref, watch} from "vue"; import {CalendarOptions, EventInput} from "@fullcalendar/core"; +import {fetchEventsByRoomAndDuration} from "../api/fetchRoom.ts"; const props = defineProps({ room: { @@ -25,9 +26,8 @@ const occupations: Ref = ref([]); const selectedRoom = computed(() => props.room); -watch(selectedRoom, (newValue: string) => { +watch(selectedRoom, (_newValue: string) => { getOccupation(); - console.log("change room: " + newValue); }); const fullCalendar = ref>() @@ -36,87 +36,34 @@ async function getOccupation() { if (selectedRoom.value === "") { return; } - console.log("fetching events", selectedRoom.value, currentDateFrom.value, currentDateTo.value); - /*occupations.value = await fetchEventsByRoomAndDuration( + const events = await fetchEventsByRoomAndDuration( selectedRoom.value, currentDateFrom.value, currentDateTo.value - );*/ + ); + occupations.value = events.map((event, index) => { + return { + id: index, + start: event.start.replace(/\s\+\d{4}\s\w+$/, '').replace(' ', 'T'), + end: event.end.replace(/\s\+\d{4}\s\w+$/, '').replace(' ', 'T') + }; + }); - - /* - const events: Ref<{ id: number; start: string, end: string }[]> = ref( - props.occupations?.map((event, index) => { - return { - id: index, - start: event.Start.replace(/\s\+\d{4}\s\w+$/, '').replace(' ', 'T'), - end: event.End.replace(/\s\+\d{4}\s\w+$/, '').replace(' ', 'T') - }; - }), - );*/ let calendar = fullCalendar.value?.getApi() calendar?.refetchEvents() - console.log("events: ", calendar?.getEvents()) - } -function getEvents(){ - const mock = [ - { - "id": 0, - "start": "2023-10-16T09:30:00", - "end": "2023-10-16T11:00:00" - }, - { - "id": 1, - "start": "2023-10-16T11:15:00", - "end": "2023-10-16T12:45:00" - }, - { - "id": 2, - "start": "2023-10-17T13:45:00", - "end": "2023-10-17T15:15:00" - }, - { - "id": 3, - "start": "2023-10-16T07:30:00", - "end": "2023-10-16T9:00:00" - }, - { - "id": 4, - "start": "2023-10-20T15:30:00", - "end": "2023-10-20T17:00:00" - }, - { - "id": 5, - "start": "2023-10-16T17:15:00", - "end": "2023-10-16T18:45:00" - }] - console.log(currentDateFrom.value, currentDateTo.value) - const events = mock.map((event) => { - const randomInt = Math.floor(Math.random() * 2); - if (randomInt) - return { - id: event.id, - start: currentDateFrom.value + event.start.substring(10, event.start.length), - end: currentDateFrom.value + event.end.substring(10, event.end.length), - }; - else - return { - id: event.id, - start: currentDateTo.value + event.start.substring(10, event.start.length), - end: currentDateTo.value + event.end.substring(10, event.end.length), - }; - }); - console.log("generated events: ", events) - return events; -} const calendarOptions: CalendarOptions = { plugins: [dayGridPlugin, interactionPlugin, timeGridPlugin], initialView: 'week', dayHeaderFormat: {weekday: 'short', omitCommas: true}, slotDuration: "00:15:00", + eventTimeFormat: { + hour: "2-digit", + minute: "2-digit", + hour12: false + }, views: { week: { type: 'timeGrid', @@ -124,7 +71,8 @@ function getEvents(){ hour: 'numeric', minute: '2-digit', omitZeroMinute: false, - meridiem: false + meridiem: false, + hour12: false }, dateAlignment: "week", titleFormat: {month: 'short', day: 'numeric'}, @@ -142,7 +90,8 @@ function getEvents(){ hour: 'numeric', minute: '2-digit', omitZeroMinute: false, - meridiem: false + meridiem: false, + hour12: false }, titleFormat: {month: 'short', day: 'numeric'}, slotMinTime: "06:00:00", @@ -157,28 +106,30 @@ function getEvents(){ center: 'title', start: 'week,Day' }, + datesSet: function (dateInfo) { const view = dateInfo.view; - const startDate = view.activeStart; - const endDate = view.activeEnd; - endDate.setDate(endDate.getDate() - 1); - currentDateFrom.value = startDate.getFullYear() + "-" + (startDate.getMonth() + 1) + "-" + startDate.getDate(); - currentDateTo.value = endDate.getFullYear() + "-" + (endDate.getMonth() + 1) + "-" + endDate.getDate(); + const offset = (new Date()).getTimezoneOffset(); + const startDate = new Date(view.activeStart.getTime() - (offset*60*1000)); + const endDate = new Date(view.activeEnd.getTime() - (offset*60*1000)); + currentDateFrom.value = startDate.toISOString().split('T')[0] + currentDateTo.value = endDate.toISOString().split('T')[0] getOccupation(); }, events: function(_info, successCallback, failureCallback) { - if (!getEvents()){ + if (occupations.value.length === 0){ failureCallback(new Error("no events")) + }else{ + successCallback( + occupations.value.map((event) => { + return { + id: event.id.toString(), + start: event.start, + end: event.end, + } as EventInput; + }) + ) } - successCallback( - getEvents().map((event) => { - return { - id: event.id.toString(), - start: event.start, - end: event.end, - } as EventInput; - }) - ) } } diff --git a/frontend/src/components/RoomOccupation2.vue b/frontend/src/components/RoomOccupation2.vue deleted file mode 100644 index 70deffb..0000000 --- a/frontend/src/components/RoomOccupation2.vue +++ /dev/null @@ -1,404 +0,0 @@ - - - - - \ No newline at end of file