Import initail de calcul-astreintes v0.9.4 pour passage en paycheck 1.0

This commit is contained in:
2026-01-19 14:25:43 +01:00
commit cad0b2768a
44 changed files with 4183 additions and 0 deletions

View File

@@ -0,0 +1,15 @@
{
"rules": {
"forfait_dim_ferie": 120.0
},
"profiles": [
{
"id": "alban",
"label": "Alban",
"t456": 18.03,
"t458": 30.05,
"t459": 36.06,
"t471": 3.58
}
]
}

69
internal/store/repo.go Normal file
View File

@@ -0,0 +1,69 @@
package store
import (
"embed"
"encoding/json"
"fmt"
"sort"
"sync"
"git.dumerain.org/alban/calcul-astreintes/internal/models"
)
/*
On embarque internal/store/profiles.json dans le binaire.
Ça simplifie énormément le "standalone": pas de fichier externe obligatoire.
*/
//go:embed profiles.json
var embeddedFS embed.FS
type ProfileRepo struct {
mu sync.RWMutex
profiles map[string]models.Profile
}
type embeddedData struct {
Rules models.GlobalRules `json:"rules"`
Profiles []models.Profile `json:"profiles"`
}
func NewEmbeddedRepo() (*ProfileRepo, *models.GlobalRules, error) {
b, err := embeddedFS.ReadFile("profiles.json")
if err != nil {
return nil, nil, err
}
var data embeddedData
if err := json.Unmarshal(b, &data); err != nil {
return nil, nil, err
}
repo := &ProfileRepo{profiles: map[string]models.Profile{}}
for _, p := range data.Profiles {
repo.profiles[p.ID] = p
}
return repo, &data.Rules, nil
}
// List : profils triés par label (pour un dropdown stable).
func (r *ProfileRepo) List() ([]models.ProfileListItem, error) {
r.mu.RLock()
defer r.mu.RUnlock()
items := make([]models.ProfileListItem, 0, len(r.profiles))
for _, p := range r.profiles {
items = append(items, models.ProfileListItem{ID: p.ID, Label: p.Label})
}
sort.Slice(items, func(i, j int) bool { return items[i].Label < items[j].Label })
return items, nil
}
func (r *ProfileRepo) Get(id string) (models.Profile, error) {
r.mu.RLock()
defer r.mu.RUnlock()
p, ok := r.profiles[id]
if !ok {
return models.Profile{}, fmt.Errorf("profil introuvable: %s", id)
}
return p, nil
}