mirror of
https://gitlab.dit.htwk-leipzig.de/htwk-software/htwkalender.git
synced 2025-08-02 17:59:14 +02:00
fix:#5 added room table and changed sql query
This commit is contained in:
@@ -2,6 +2,7 @@ package db
|
|||||||
|
|
||||||
import (
|
import (
|
||||||
"fmt"
|
"fmt"
|
||||||
|
"github.com/pocketbase/pocketbase/tools/types"
|
||||||
"htwkalender/model"
|
"htwkalender/model"
|
||||||
"log/slog"
|
"log/slog"
|
||||||
"time"
|
"time"
|
||||||
@@ -265,3 +266,36 @@ func GetEventsInTimeRange(app *pocketbase.PocketBase, from time.Time, to time.Ti
|
|||||||
|
|
||||||
return events, nil
|
return events, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// GetEventsThatCollideWithTimeRange returns all events that collide with the given time range
|
||||||
|
// events that collide are events that start before the given time range and end after the given time range
|
||||||
|
// or events that start before the given time range and end in the given time range
|
||||||
|
// or events that start in the given time range and end after the given time range
|
||||||
|
// or events that start in the given time range and end in the given time range
|
||||||
|
func GetEventsThatCollideWithTimeRange(app *pocketbase.PocketBase, from time.Time, to time.Time) (model.Events, error) {
|
||||||
|
var events model.Events
|
||||||
|
|
||||||
|
var fromTypeTime, _ = types.ParseDateTime(from)
|
||||||
|
var toTypeTime, _ = types.ParseDateTime(to)
|
||||||
|
|
||||||
|
//TODO check if this query is correct returns null or events on complete other days
|
||||||
|
err := app.Dao().DB().Select("*").From("events").Where(
|
||||||
|
dbx.And(
|
||||||
|
dbx.NewExp("(Start <= {:startDate1}", dbx.Params{"startDate1": fromTypeTime}),
|
||||||
|
dbx.NewExp("AND End >= {:endDate1})", dbx.Params{"endDate1": toTypeTime}))).OrWhere(
|
||||||
|
dbx.And(
|
||||||
|
dbx.NewExp("(Start >= {:startDate2}", dbx.Params{"startDate2": fromTypeTime}),
|
||||||
|
dbx.NewExp("AND End <= {:endDate2})", dbx.Params{"endDate2": toTypeTime}))).OrWhere(
|
||||||
|
dbx.And(
|
||||||
|
dbx.NewExp("(Start <= {:startDate3}", dbx.Params{"startDate3": fromTypeTime}),
|
||||||
|
dbx.NewExp("AND End <= {:endDate3})", dbx.Params{"endDate3": toTypeTime}))).OrWhere(
|
||||||
|
dbx.And(
|
||||||
|
dbx.NewExp("(Start >= {:startDate4}", dbx.Params{"startDate4": fromTypeTime}),
|
||||||
|
dbx.NewExp("AND End >= {:endDate4})", dbx.Params{"endDate4": toTypeTime}))).All(&events)
|
||||||
|
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return events, nil
|
||||||
|
}
|
||||||
|
@@ -50,7 +50,7 @@ func GetFreeRooms(app *pocketbase.PocketBase, from time.Time, to time.Time) ([]s
|
|||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
var events model.Events
|
var events model.Events
|
||||||
events, err = db.GetEventsInTimeRange(app, from, to)
|
events, err = db.GetEventsThatCollideWithTimeRange(app, from, to)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
16
frontend/src/api/requestFreeRooms.ts
Normal file
16
frontend/src/api/requestFreeRooms.ts
Normal file
@@ -0,0 +1,16 @@
|
|||||||
|
|
||||||
|
|
||||||
|
// load free rooms as a list of strings form the backend
|
||||||
|
|
||||||
|
export async function requestFreeRooms(from: string, to: string): Promise<string[]> {
|
||||||
|
console.debug("requestFreeRooms: from=" + from + ", to=" + to)
|
||||||
|
const rooms: string[] = [];
|
||||||
|
await fetch("/api/rooms/free?from=" + from + "&to=" + to)
|
||||||
|
.then((response) => {
|
||||||
|
return response.json();
|
||||||
|
})
|
||||||
|
.then((roomsResponse: [] | null) => {
|
||||||
|
roomsResponse?.forEach((room: string) => rooms.push(room));
|
||||||
|
});
|
||||||
|
return rooms;
|
||||||
|
}
|
@@ -1,35 +1,85 @@
|
|||||||
<script setup lang="ts">
|
<script setup lang="ts">
|
||||||
import { Ref, ref } from "vue";
|
import { computed, Ref, ref } from "vue";
|
||||||
import DynamicPage from "@/view/DynamicPage.vue";
|
import DynamicPage from "@/view/DynamicPage.vue";
|
||||||
|
import { requestFreeRooms } from "@/api/requestFreeRooms.ts";
|
||||||
|
|
||||||
const selected: Ref<{ name: string }> = ref({ name: "" });
|
const date: Ref<Date> = ref(new Date(Date.now()));
|
||||||
|
const start: Ref<Date> = ref(new Date(Date.now()));
|
||||||
|
const end: Ref<Date> = ref(new Date(Date.now() + 3600000));
|
||||||
|
|
||||||
|
async function loadFreeRooms(): Promise<void> {
|
||||||
|
availableRooms.value = [];
|
||||||
|
const startDate = new Date(date.value.getTime());
|
||||||
|
startDate.setHours(start.value.getHours());
|
||||||
|
startDate.setMinutes(start.value.getMinutes());
|
||||||
|
const endDate = new Date(date.value.getTime());
|
||||||
|
endDate.setHours(end.value.getHours());
|
||||||
|
endDate.setMinutes(end.value.getMinutes());
|
||||||
|
await requestFreeRooms(startDate.toISOString(), endDate.toISOString()).then((data) => {
|
||||||
|
availableRooms.value = data.map((room, index) => {
|
||||||
|
return { id: index, room: room };
|
||||||
|
});
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
const isLater = computed(() => {
|
||||||
|
return start.value > end.value;
|
||||||
|
});
|
||||||
|
|
||||||
|
const availableRooms: Ref<{id: number, room: string}[]> = ref([]);
|
||||||
|
|
||||||
const dates = ref();
|
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<template>
|
<template>
|
||||||
<DynamicPage
|
<DynamicPage
|
||||||
:hide-content="selected.name === ''"
|
:hide-content="availableRooms.length === 0"
|
||||||
:headline="$t('freeRooms.freeRooms')"
|
:headline="$t('freeRooms.freeRooms')"
|
||||||
:sub-title="$t('freeRooms.detail')"
|
:sub-title="$t('freeRooms.detail')"
|
||||||
icon="pi pi-search"
|
icon="pi pi-search"
|
||||||
|
:button="{
|
||||||
|
label: 'Search',
|
||||||
|
icon: 'pi pi-search',
|
||||||
|
disabled: isLater,
|
||||||
|
onClick: loadFreeRooms,
|
||||||
|
}"
|
||||||
>
|
>
|
||||||
<template #selection>
|
<template #selection="{ flexSpecs }">
|
||||||
<Calendar
|
<Calendar
|
||||||
v-model="dates"
|
v-model="date"
|
||||||
class="flex-1 m-0"
|
:class="flexSpecs"
|
||||||
:placeholder="$t('roomFinderPage.dropDownSelect')"
|
:placeholder="$t('roomFinderPage.dropDownSelect')"
|
||||||
:empty-message="$t('roomFinderPage.noRoomsAvailable')"
|
:empty-message="$t('roomFinderPage.noRoomsAvailable')"
|
||||||
:auto-filter-focus="true"
|
:auto-filter-focus="true"
|
||||||
selection-mode="range"
|
date-format="dd.mm.yy"
|
||||||
:manual-input="false"
|
/>
|
||||||
:show-time="true"
|
<div class="break"/>
|
||||||
:show-seconds="true"
|
<Calendar
|
||||||
/>
|
v-model="start"
|
||||||
<Button icon="pi pi-search" />
|
placeholder="start"
|
||||||
|
time-only
|
||||||
|
date-format="HH:mm"
|
||||||
|
:class="[{'p-invalid':isLater}, flexSpecs]"
|
||||||
|
/>
|
||||||
|
<Calendar
|
||||||
|
v-model="end"
|
||||||
|
time-only
|
||||||
|
placeholder="end"
|
||||||
|
date-format="HH:mm"
|
||||||
|
:class="[{'p-invalid':isLater}, flexSpecs]"
|
||||||
|
/>
|
||||||
</template>
|
</template>
|
||||||
<template #content>
|
<template #content>
|
||||||
<Button>Button</Button>
|
<DataTable :value="availableRooms">
|
||||||
|
<Column field="id" header="ID"></Column>
|
||||||
|
<Column field="room" header="Room"></Column>
|
||||||
|
</DataTable>
|
||||||
</template>
|
</template>
|
||||||
</DynamicPage>
|
</DynamicPage>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
|
<style scoped>
|
||||||
|
.break {
|
||||||
|
flex-basis: 100%;
|
||||||
|
height: 0;
|
||||||
|
}
|
||||||
|
</style>
|
Reference in New Issue
Block a user