123 lines
3.5 KiB
Go
123 lines
3.5 KiB
Go
package excelread
|
|
|
|
import (
|
|
"business-engine/internal/database"
|
|
"fmt"
|
|
"os"
|
|
"slices"
|
|
"strings"
|
|
"time"
|
|
|
|
"github.com/gocarina/gocsv"
|
|
)
|
|
|
|
func sortSliceByDate[T any](slice []T, getDate func(T) time.Time) {
|
|
compare := func(a, b T) int {
|
|
aDate := getDate(a)
|
|
bDate := getDate(b)
|
|
|
|
if aDate.Before(bDate) {
|
|
return -1
|
|
}
|
|
if aDate.After(bDate) {
|
|
return 1
|
|
}
|
|
return 0
|
|
}
|
|
slices.SortFunc(slice, compare)
|
|
}
|
|
|
|
// Zu kalkulieren
|
|
// - Puenktlichkeitspraemie
|
|
// - Tourengeld Anzahl
|
|
// - Tourengeld Bonus
|
|
func GeneratePayrollStatement(data EmployeeDataRow, input PayrollInputData) PayrollStatement {
|
|
isKTW := slices.IndexFunc(input.Plannedtimes, func(pt database.ListPlannedTimesForEmployeeInPeriodRow) bool {
|
|
return strings.Contains(pt.Department.String, "KTW")
|
|
}) >= 0 && slices.IndexFunc(input.Plannedtimes, func(pt database.ListPlannedTimesForEmployeeInPeriodRow) bool {
|
|
return strings.Contains(pt.Department.String, "Leitstelle")
|
|
}) == -1
|
|
|
|
statement := PayrollStatement{
|
|
Nachname: data.Nachname,
|
|
Vorname: data.Vorname,
|
|
Verpflegungspauschale: data.AuszahlenVerpflegungspauschaleTage,
|
|
VertragStundenlohn: input.ContractSalaryHour,
|
|
Vertragsstunden: data.IstSollVertragsStunden,
|
|
GearbeiteteStunden: data.GearbeiteteStunden,
|
|
GearbeiteteTage: data.GearbeiteteTage,
|
|
Krankheitstage: data.Krankheitstage,
|
|
Ueberstunden: data.IstSollPlusMinusStunden,
|
|
Wochenendzuschlag15: data.AuszahlenZuschlag15Stunden,
|
|
Sonntagszuschlag50: data.AuszahlenZuschlag50Stunden,
|
|
Nachtzuschlag25: data.AuszahlenZuschlag25Stunden,
|
|
Nachtzuschlag40: data.AuszahlenZuschlag40Stunden,
|
|
}
|
|
|
|
if data.Krankheitstage > 0 || !isKTW {
|
|
statement.GesundheitsbonusAbzug = "ja"
|
|
}
|
|
|
|
if isKTW && data.GenommeneUrlaubstage > 0 {
|
|
statement.Urlaubsgeld = data.GenommeneUrlaubstage
|
|
}
|
|
|
|
if isKTW && data.AuszahlenAnzahlPSchein > 0 {
|
|
statement.PScheinZulage = data.AuszahlenAnzahlPSchein
|
|
}
|
|
|
|
if isKTW && input.Tourengeld > 0 {
|
|
statement.Tourengeld = float64(input.Tourengeld)
|
|
}
|
|
|
|
if isKTW && len(input.Worktimes) > 0 && len(input.Plannedtimes) > 0 {
|
|
ptGetStartDate := func(pt database.ListPlannedTimesForEmployeeInPeriodRow) time.Time {
|
|
return *pt.StartDate
|
|
}
|
|
wtGetStartDate := func(pt database.WorkTime) time.Time {
|
|
return *pt.StartDate
|
|
}
|
|
sortSliceByDate(input.Plannedtimes, ptGetStartDate)
|
|
sortSliceByDate(input.Worktimes, wtGetStartDate)
|
|
|
|
var employeeOnTime []EmployeeOnTime
|
|
for _, pt := range input.Plannedtimes {
|
|
for _, wt := range input.Worktimes {
|
|
if isSameDay(ptGetStartDate(pt), wtGetStartDate(wt)) && (wtGetStartDate(wt).Before(ptGetStartDate(pt)) || wtGetStartDate(wt) == ptGetStartDate(pt)) {
|
|
statement.PuenktlichkeitspraemieAnzahl++
|
|
|
|
employeeOnTime = append(employeeOnTime, EmployeeOnTime{
|
|
EmployeeId: fmt.Sprintf("%s %s", data.Vorname, data.Nachname),
|
|
WorkTime: *wt.StartDate,
|
|
PlannedTime: *pt.StartDate,
|
|
IsOnTime: true,
|
|
})
|
|
}
|
|
}
|
|
}
|
|
if data.Vorname == "David" && data.Nachname == "Hastedt" {
|
|
GenerateEmployeesOnTime(employeeOnTime)
|
|
}
|
|
}
|
|
|
|
return statement
|
|
}
|
|
|
|
func GenerateEmployeesOnTime(employeesontime []EmployeeOnTime) error {
|
|
file, err := os.Create("employees_on_time.csv")
|
|
if err != nil {
|
|
return err
|
|
}
|
|
defer file.Close()
|
|
|
|
if err := gocsv.MarshalFile(&employeesontime, file); err != nil {
|
|
return err
|
|
}
|
|
return nil
|
|
}
|
|
|
|
// isSameDay prüft, ob zwei Zeitpunkte am selben Kalendertag liegen.
|
|
func isSameDay(t1, t2 time.Time) bool {
|
|
return t1.Year() == t2.Year() && t1.Month() == t2.Month() && t1.Day() == t2.Day()
|
|
}
|