mirror of
https://github.com/rjNemo/rentease.git
synced 2026-06-06 02:36:49 +00:00
98 lines
3.2 KiB
Go
98 lines
3.2 KiB
Go
package server
|
|
|
|
import (
|
|
"fmt"
|
|
"net/http"
|
|
"strconv"
|
|
"time"
|
|
|
|
"github.com/a-h/templ"
|
|
u "github.com/rjNemo/underscore"
|
|
|
|
"github.com/rjNemo/rentease/internal/config"
|
|
"github.com/rjNemo/rentease/internal/constant"
|
|
"github.com/rjNemo/rentease/internal/service/booking"
|
|
"github.com/rjNemo/rentease/internal/view"
|
|
)
|
|
|
|
func handleReportsPage() http.HandlerFunc {
|
|
return func(w http.ResponseWriter, r *http.Request) {
|
|
monthStr := r.URL.Query().Get("month")
|
|
month, err := strconv.Atoi(monthStr)
|
|
if err != nil || month < 1 || month > 12 {
|
|
month = int(time.Now().Month())
|
|
}
|
|
|
|
yearStr := r.URL.Query().Get("year")
|
|
if _, err = strconv.Atoi(yearStr); err != nil {
|
|
yearStr = time.Now().Format("2006")
|
|
}
|
|
|
|
component := view.Reports(u.Map(constant.Months, func(m constant.Month) string {
|
|
return string(m)
|
|
}), month, yearStr)
|
|
|
|
if err := renderTempl(w, r, http.StatusOK, component); err != nil {
|
|
http.Error(w, err.Error(), http.StatusInternalServerError)
|
|
}
|
|
}
|
|
}
|
|
|
|
func handleReportCompute(bs *booking.Service, hc *config.Host) http.HandlerFunc {
|
|
return func(w http.ResponseWriter, r *http.Request) {
|
|
if err := r.ParseForm(); err != nil {
|
|
http.Error(w, err.Error(), http.StatusBadRequest)
|
|
return
|
|
}
|
|
|
|
period := r.FormValue("period")
|
|
if !u.Contains([]string{"month", "year"}, period) {
|
|
http.Error(w, fmt.Sprintf("%q is not a valid period", period), http.StatusBadRequest)
|
|
return
|
|
}
|
|
|
|
monthStr := r.FormValue("month")
|
|
month, err := strconv.Atoi(monthStr)
|
|
if err != nil || month < 1 || month > 12 {
|
|
http.Error(w, fmt.Sprintf("%q is not a valid month", monthStr), http.StatusBadRequest)
|
|
return
|
|
}
|
|
|
|
yearStr := r.FormValue("year")
|
|
year, err := strconv.Atoi(yearStr)
|
|
if err != nil {
|
|
http.Error(w, fmt.Sprintf("%q is not a valid year", yearStr), http.StatusBadRequest)
|
|
return
|
|
}
|
|
|
|
report := bs.Report(period, month, year)
|
|
|
|
reportVm := &view.ReportViewModel{
|
|
Total: strconv.FormatFloat(report.Total, 'f', 2, 64),
|
|
PlatformFees: strconv.FormatFloat(report.PlatformFees, 'f', 2, 64),
|
|
Fee: strconv.FormatFloat(report.Fee, 'f', 2, 64),
|
|
Profit: strconv.FormatFloat(report.Profit, 'f', 2, 64),
|
|
CardTotal: strconv.FormatFloat(report.CardTotal, 'f', 2, 64),
|
|
BookingFees: strconv.FormatFloat(report.BookingFees, 'f', 2, 64),
|
|
PdfUrl: templ.URL(fmt.Sprintf("%s/pdf?period=%s&month=%d&year=%d", constant.RouteReports, period, month, year)),
|
|
Lines: u.Map(report.Lines, func(l *booking.Line) *view.ReportLine {
|
|
return &view.ReportLine{
|
|
Id: l.InvoiceNumber(hc),
|
|
Url: templ.SafeURL(fmt.Sprintf("%s/%d", constant.RouteBooking, l.ID)),
|
|
Total: strconv.FormatFloat(l.Total, 'f', 2, 64),
|
|
CustomerName: l.CustomerName,
|
|
From: l.From.Format(time.DateOnly),
|
|
To: l.To.Format(time.DateOnly),
|
|
Platform: l.Platform,
|
|
PlatformFees: strconv.FormatFloat(l.PlatformFees, 'f', 2, 64),
|
|
Fee: strconv.FormatFloat(l.Fee(), 'f', 2, 64),
|
|
Profit: strconv.FormatFloat(l.Profit(), 'f', 2, 64),
|
|
}
|
|
}),
|
|
}
|
|
|
|
if err := renderTempl(w, r, http.StatusOK, view.ReportSection(reportVm)); err != nil {
|
|
http.Error(w, err.Error(), http.StatusInternalServerError)
|
|
}
|
|
}
|
|
}
|