Ändere Wochenfeld von Auswahl "Jede/gerade Vorlesungswochen/ungerade Vorlesungswochen" zu Freitextfeld mit Vorschlag.

Closes 
This commit is contained in:
Gonne 2025-04-01 19:21:17 +02:00
parent 5e954ca751
commit deced3e596
Signed by: Gonne
SSH key fingerprint: SHA256:J8w3ZCNyz9MoTLV+eU7YRTVw59NYig44i0IWhbsgQG8
10 changed files with 35 additions and 41 deletions

View file

@ -69,13 +69,6 @@ func (b *BaseHandler) AddOfficeHourHandler(w http.ResponseWriter, req *http.Requ
errors = append(errors, "Der Raum muss existieren.")
}
//Parse date
week, err := strconv.Atoi(req.FormValue("woche"))
if err != nil {
errors = append(errors, "Die Vorlesungswoche muss eine ganze Zahl sein.")
}
if !(week >= 0 && week <= 2) {
errors = append(errors, "Sprechstunden müssen jede, jede gerade oder jede ungerade Vorlesungswoche stattfinden.")
}
day, err := strconv.Atoi(req.FormValue("tag"))
if err != nil {
errors = append(errors, "Der Tag muss eine ganze Zahl sein.")
@ -106,7 +99,7 @@ func (b *BaseHandler) AddOfficeHourHandler(w http.ResponseWriter, req *http.Requ
errors = append(errors, fmt.Sprintf("Sprechstunden dürfen nur alle %d Minuten starten.", b.config.Date.MinuteGranularity))
}
}
date := models.Date{Week: week, Day: day, Hour: hour, Minute: minute}
date := models.Date{Week: req.FormValue("woche"), Day: day, Hour: hour, Minute: minute}
duration, err := strconv.Atoi(req.FormValue("dauer"))
if err != nil {
errors = append(errors, "Die Dauer muss eine ganze Zahl sein.")

View file

@ -61,16 +61,16 @@ func (b *BaseHandler) printTimetable(timetable map[models.Date]map[int]models.Of
}
for day := 0; day < 5; day += 1 {
for slot := 0; slot < slots[day]; slot += 1 {
current, currentExists := timetable[models.Date{Week: 0, Day: day, Hour: hour, Minute: minute}][slot]
current, currentExists := timetable[models.Date{Week: "", Day: day, Hour: hour, Minute: minute}][slot]
if currentExists { // This slot is taken by some office hour
var continued bool = false // is this slot occupied by the same office hour the previous minute?
var predecessorExists bool
var predecessor models.OfficeHour
if hour > 0 && minute < b.config.Date.MinuteGranularity {
predecessor, predecessorExists = timetable[models.Date{Week: 0, Day: day, Hour: hour - 1, Minute: 60 - b.config.Date.MinuteGranularity}][slot]
predecessor, predecessorExists = timetable[models.Date{Week: "", Day: day, Hour: hour - 1, Minute: 60 - b.config.Date.MinuteGranularity}][slot]
} else {
predecessor, predecessorExists = timetable[models.Date{Week: 0, Day: day, Hour: hour, Minute: minute - b.config.Date.MinuteGranularity}][slot]
predecessor, predecessorExists = timetable[models.Date{Week: "", Day: day, Hour: hour, Minute: minute - b.config.Date.MinuteGranularity}][slot]
}
if predecessorExists {
continued = (predecessor == current)

View file

@ -5,7 +5,7 @@ import (
)
type Date struct {
Week int // Set whether the date is all weeks (0), odd weeks (1) or even weeks (2).
Week string
Day int
Hour int
Minute int
@ -54,7 +54,7 @@ func DateLess(first Date, second Date) bool {
func GetEndDate(date Date, duration int, ignoreWeek bool) Date {
var endDate Date
if ignoreWeek {
endDate = Date{0, date.Day, date.Hour, date.Minute} // deep copy
endDate = Date{"", date.Day, date.Hour, date.Minute} // deep copy
} else {
endDate = Date{date.Week, date.Day, date.Hour, date.Minute}
}

View file

@ -11,11 +11,11 @@ func TestEndDate(t *testing.T) {
duration int
endDate Date
}{
{Date{Week: 0, Day: 0, Hour: 8, Minute: 0}, 10, Date{Week: 0, Day: 0, Hour: 8, Minute: 10}},
{Date{Week: 0, Day: 0, Hour: 8, Minute: 0}, 90, Date{Week: 0, Day: 0, Hour: 9, Minute: 30}}, // More than one hour
{Date{Week: 0, Day: 0, Hour: 8, Minute: 0}, 130, Date{Week: 0, Day: 0, Hour: 10, Minute: 10}}, // More than two hours
{Date{Week: 0, Day: 0, Hour: 8, Minute: 15}, 90, Date{Week: 0, Day: 0, Hour: 9, Minute: 45}}, // More than one hour and start not 0
{Date{Week: 0, Day: 0, Hour: 23, Minute: 15}, 90, Date{Week: 0, Day: 1, Hour: 0, Minute: 45}}, // More than one day
{Date{Week: "", Day: 0, Hour: 8, Minute: 0}, 10, Date{Week: "", Day: 0, Hour: 8, Minute: 10}},
{Date{Week: "", Day: 0, Hour: 8, Minute: 0}, 90, Date{Week: "", Day: 0, Hour: 9, Minute: 30}}, // More than one hour
{Date{Week: "", Day: 0, Hour: 8, Minute: 0}, 130, Date{Week: "", Day: 0, Hour: 10, Minute: 10}}, // More than two hours
{Date{Week: "", Day: 0, Hour: 8, Minute: 15}, 90, Date{Week: "", Day: 0, Hour: 9, Minute: 45}}, // More than one hour and start not 0
{Date{Week: "", Day: 0, Hour: 23, Minute: 15}, 90, Date{Week: "", Day: 1, Hour: 0, Minute: 45}}, // More than one day
}
for _, tc := range testCases {
t.Run(fmt.Sprintf("%d:%d, Dauer %d", tc.startDate.Hour, tc.startDate.Minute, tc.duration), func(t *testing.T) {
@ -35,21 +35,21 @@ func TestDateLess(t *testing.T) {
less bool
}{
{"earlier day",
Date{Week: 0, Day: 1, Hour: 8, Minute: 10}, Date{Week: 0, Day: 0, Hour: 7, Minute: 10}, false},
Date{Week: "", Day: 1, Hour: 8, Minute: 10}, Date{Week: "", Day: 0, Hour: 7, Minute: 10}, false},
{"earlier hour",
Date{Week: 0, Day: 1, Hour: 8, Minute: 10}, Date{Week: 0, Day: 1, Hour: 7, Minute: 10}, false},
Date{Week: "", Day: 1, Hour: 8, Minute: 10}, Date{Week: "", Day: 1, Hour: 7, Minute: 10}, false},
{"earlier minute",
Date{Week: 0, Day: 1, Hour: 8, Minute: 10}, Date{Week: 0, Day: 1, Hour: 8, Minute: 0}, false},
Date{Week: "", Day: 1, Hour: 8, Minute: 10}, Date{Week: "", Day: 1, Hour: 8, Minute: 0}, false},
{"same date",
Date{Week: 0, Day: 1, Hour: 8, Minute: 10}, Date{Week: 0, Day: 1, Hour: 8, Minute: 10}, false},
Date{Week: "", Day: 1, Hour: 8, Minute: 10}, Date{Week: "", Day: 1, Hour: 8, Minute: 10}, false},
{"later minute",
Date{Week: 0, Day: 1, Hour: 8, Minute: 10}, Date{Week: 0, Day: 1, Hour: 8, Minute: 20}, true},
Date{Week: "", Day: 1, Hour: 8, Minute: 10}, Date{Week: "", Day: 1, Hour: 8, Minute: 20}, true},
{"later hour",
Date{Week: 0, Day: 1, Hour: 8, Minute: 10}, Date{Week: 0, Day: 1, Hour: 9, Minute: 10}, true},
Date{Week: "", Day: 1, Hour: 8, Minute: 10}, Date{Week: "", Day: 1, Hour: 9, Minute: 10}, true},
{"later day",
Date{Week: 0, Day: 1, Hour: 8, Minute: 10}, Date{Week: 0, Day: 2, Hour: 8, Minute: 10}, true},
Date{Week: "", Day: 1, Hour: 8, Minute: 10}, Date{Week: "", Day: 2, Hour: 8, Minute: 10}, true},
{"week should not matter",
Date{Week: 1, Day: 1, Hour: 8, Minute: 10}, Date{Week: 0, Day: 1, Hour: 9, Minute: 30}, true},
Date{Week: "", Day: 1, Hour: 8, Minute: 10}, Date{Week: "every", Day: 1, Hour: 9, Minute: 30}, true},
}
for _, tc := range testCases {
t.Run(tc.name, func(t *testing.T) {

View file

@ -47,7 +47,7 @@ CREATE TABLE `officeHour` (
`room` int DEFAULT NULL,
`roomname` text DEFAULT NULL,
`course` int DEFAULT NULL,
`week` int DEFAULT NULL,
`week` varchar(255) DEFAULT NULL,
`info` text DEFAULT NULL,
`active` bool DEFAULT NULL,
`duration` int DEFAULT NULL,

View file

@ -36,7 +36,7 @@ CREATE TABLE `officeHour` (
`room` int DEFAULT NULL,
`roomname` text DEFAULT NULL,
`course` int DEFAULT NULL,
`week` int DEFAULT NULL,
`week` tinytext DEFAULT NULL,
`info` text DEFAULT NULL,
`active` bool DEFAULT NULL,
`duration` int DEFAULT NULL,

View file

@ -157,7 +157,8 @@ func (r *OfficeHourRepo) Delete(officeHour models.OfficeHour) error {
func (r *OfficeHourRepo) getFromRow(row *sql.Row) (models.OfficeHour, error) {
var officeHour models.OfficeHour
var week, day, hour, minute, tutorId, courseId, roomId int
var day, hour, minute, tutorId, courseId, roomId int
var week string
err := row.Scan(&officeHour.Id, &tutorId, &day, &hour, &minute, &roomId, &officeHour.RoomName, &courseId, &week, &officeHour.Info, &officeHour.Active, &officeHour.Duration)
if err != nil {
err = fmt.Errorf("error getting single officeHour row from database: %w", err)
@ -190,7 +191,8 @@ func (r *OfficeHourRepo) getFromRows(rows *sql.Rows) ([]models.OfficeHour, error
var officeHours []models.OfficeHour
for rows.Next() {
var officeHour models.OfficeHour
var week, day, hour, minute, tutorId, roomId, courseId int
var day, hour, minute, tutorId, roomId, courseId int
var week string
var err error
if err := rows.Scan(&officeHour.Id, &tutorId, &day, &hour, &minute, &roomId, &officeHour.RoomName, &courseId, &week, &officeHour.Info, &officeHour.Active, &officeHour.Duration); err != nil {
return officeHours, fmt.Errorf("error getting multiple officeHour rows from database: %w", err)
@ -245,9 +247,7 @@ func (r *OfficeHourRepo) NumberByTimeSpanAndRoom(date models.Date, duration int,
for _, officeHour := range officeHours {
// increase count if officehour starts before this point in time and ends later
if models.DateLess(officeHour.Date, models.GetEndDate(date, minute, false)) && models.DateLess(models.GetEndDate(date, minute, false), models.GetEndDate(officeHour.Date, officeHour.Duration, false)) {
if date.Week == 0 || officeHour.Week == 0 || date.Week == officeHour.Week { // office hours in alternating weeks should not collide
minuteCount += 1
}
minuteCount += 1
}
}
if minuteCount > count {

View file

@ -58,12 +58,13 @@
<div class="col-md-6">
<div class="form-floating mb-3">
<select class="form-control form-select required" required name="woche" id="woche">
<option value="0"{{if eq 0 $.Date.Week}} selected{{end}}>Jede</option>
<option value="1"{{if eq 1 $.Date.Week}} selected{{end}}>Ungerade</option>
<option value="2"{{if eq 2 $.Date.Week}} selected{{end}}>Gerade</option>
</select>
<label for="woche">Vorlesungswoche</label>
<input class="form-control form-text" type="text" name="woche" id="woche" list="woche_list" value="{{$.Date.Week}}">
<datalist id="woche_list">
<option>Jede Woche</option>
<option>In Wochen mit Übung</option>
<option>In Wochen ohne Übung</option>
</datalist>
<label for="woche">Vorlesungswoche (z.B. jede / mit Übung / ohne Übung)</label>
</div>
</div>

View file

@ -11,7 +11,7 @@
<p>
Willst du die Sprechstunde<br>
{{printf "%02d" .OfficeHour.Date.Hour}}:{{printf "%02d" .OfficeHour.Date.Minute}} - {{printf "%02d" .OfficeHour.EndDate.Hour}}:{{printf "%02d" .OfficeHour.EndDate.Minute}}<br>
{{if eq .OfficeHour.Date.Week 1}}in ungeraden Vorlesungswochen<br>{{end}}{{if eq .OfficeHour.Date.Week 2}}in geraden Vorlesungswochen<br>{{end}}
{{if not (eq .OfficeHour.Date.Week "")}}{{ .OfficeHour.Date.Week }}<br>{{end}}
{{.OfficeHour.Course.Name}}<br>
{{.OfficeHour.Tutor.Name}}<br>
{{.OfficeHour.Room.Name}}<br>

View file

@ -1,7 +1,7 @@
<td class="officeHour" rowspan="{{divide .OfficeHour.Duration .MinuteGranularity}}">
{{if .DeleteIcons}}<div style="text-align: right;"><a href="/deleteOfficeHour?id={{.OfficeHour.Id}}"></a></div>{{end}}
{{printf "%02d" .OfficeHour.Date.Hour}}:{{printf "%02d" .OfficeHour.Date.Minute}} - {{printf "%02d" .OfficeHour.EndDate.Hour}}:{{printf "%02d" .OfficeHour.EndDate.Minute}}<br>
{{if eq .OfficeHour.Date.Week 1}}in ungeraden Vorlesungswochen<br>{{end}}{{if eq .OfficeHour.Date.Week 2}}in geraden Vorlesungswochen<br>{{end}}
{{if not (eq .OfficeHour.Date.Week "")}}{{.OfficeHour.Date.Week}}<br>{{end}}
{{.OfficeHour.Course.Name}}<br>
{{.OfficeHour.Tutor.Name}}<br>
{{.OfficeHour.Room.Name}}