49 lines
1.1 KiB
Go
49 lines
1.1 KiB
Go
package domain
|
|
|
|
import (
|
|
"errors"
|
|
"math"
|
|
"time"
|
|
)
|
|
|
|
type ETAInput struct {
|
|
PeopleAhead int
|
|
IntervalPerPerson time.Duration
|
|
Running bool
|
|
}
|
|
|
|
type ETAResult struct {
|
|
Available bool `json:"available"`
|
|
EstimateMinutes int `json:"estimate_minutes"`
|
|
MinMinutes int `json:"min_minutes"`
|
|
MaxMinutes int `json:"max_minutes"`
|
|
Reason string `json:"reason,omitempty"`
|
|
}
|
|
|
|
func CalculateETA(input ETAInput) (ETAResult, error) {
|
|
if !input.Running {
|
|
return ETAResult{Available: false, Reason: "queue_not_running"}, nil
|
|
}
|
|
if input.PeopleAhead < 0 {
|
|
return ETAResult{}, errors.New("people ahead cannot be negative")
|
|
}
|
|
if input.IntervalPerPerson <= 0 {
|
|
return ETAResult{Available: false, Reason: "missing_interval_configuration"}, nil
|
|
}
|
|
rawMinutes := float64(input.PeopleAhead) * input.IntervalPerPerson.Minutes()
|
|
estimate := roundUpFive(rawMinutes)
|
|
return ETAResult{
|
|
Available: true,
|
|
EstimateMinutes: estimate,
|
|
MinMinutes: estimate,
|
|
MaxMinutes: estimate,
|
|
}, nil
|
|
}
|
|
|
|
func roundUpFive(value float64) int {
|
|
if value <= 0 {
|
|
return 0
|
|
}
|
|
return int(math.Ceil(value/5) * 5)
|
|
}
|