money/state.go

63 lines
1.5 KiB
Go

package main
import (
"encoding/json"
"errors"
"os"
"path/filepath"
"strings"
"time"
)
// ================== Stato locale (anti-doppio ordine) ==================
type Lock struct {
TS time.Time `json:"ts"`
From string `json:"from"`
To string `json:"to"`
AmountFrom float64 `json:"amount_from"`
Status string `json:"status"` // pending/confirmed/cancelled
}
type PortfolioState struct {
Version int `json:"version"`
UpdatedAt time.Time `json:"updated_at"`
Balances map[string]float64 `json:"balances"`
Locks []Lock `json:"locks"`
}
func loadState(path string) (PortfolioState, error) {
b, err := os.ReadFile(path)
if errors.Is(err, os.ErrNotExist) {
return PortfolioState{Version: 1, UpdatedAt: time.Now().UTC(), Balances: map[string]float64{}, Locks: []Lock{}}, nil
}
if err != nil {
return PortfolioState{}, err
}
var s PortfolioState
if err := json.Unmarshal(b, &s); err != nil {
return PortfolioState{}, err
}
return s, nil
}
func saveState(path string, s PortfolioState) error {
s.UpdatedAt = time.Now().UTC()
if err := os.MkdirAll(filepath.Dir(path), 0o755); err != nil {
return err
}
b, _ := json.Marshal(s)
return os.WriteFile(path, b, 0o644)
}
func assetShort(label string) string {
parts := strings.Split(label, ".")
if len(parts) != 2 {
return label
}
right := parts[1]
if i := strings.Index(right, "-"); i > 0 {
right = right[:i]
}
return parts[0] + "." + right
}