mirror of
https://github.com/garethgeorge/backrest.git
synced 2025-12-13 17:25:38 +00:00
92 lines
1.8 KiB
Go
92 lines
1.8 KiB
Go
package config
|
|
|
|
import (
|
|
"errors"
|
|
"fmt"
|
|
"sync"
|
|
|
|
v1 "github.com/garethgeorge/backrest/gen/go/v1"
|
|
"github.com/garethgeorge/backrest/internal/config/migrations"
|
|
"go.uber.org/zap"
|
|
)
|
|
|
|
var ErrConfigNotFound = fmt.Errorf("config not found")
|
|
|
|
type ConfigStore interface {
|
|
Get() (*v1.Config, error)
|
|
Update(config *v1.Config) error
|
|
}
|
|
|
|
func NewDefaultConfig() *v1.Config {
|
|
return &v1.Config{
|
|
Instance: "",
|
|
Repos: []*v1.Repo{},
|
|
Plans: []*v1.Plan{},
|
|
}
|
|
}
|
|
|
|
type CachingValidatingStore struct {
|
|
ConfigStore
|
|
mu sync.Mutex
|
|
config *v1.Config
|
|
}
|
|
|
|
func (c *CachingValidatingStore) Get() (*v1.Config, error) {
|
|
c.mu.Lock()
|
|
defer c.mu.Unlock()
|
|
|
|
if c.config != nil {
|
|
return c.config, nil
|
|
}
|
|
|
|
config, err := c.ConfigStore.Get()
|
|
if err != nil {
|
|
if errors.Is(err, ErrConfigNotFound) {
|
|
c.config = NewDefaultConfig()
|
|
return c.config, nil
|
|
}
|
|
return c.config, err
|
|
}
|
|
|
|
// Check if we need to migrate
|
|
if config.Version < migrations.CurrentVersion {
|
|
zap.S().Infof("migrating config from version %d to %d", config.Version, migrations.CurrentVersion)
|
|
if err := migrations.ApplyMigrations(config); err != nil {
|
|
return nil, err
|
|
}
|
|
|
|
if config.Version != migrations.CurrentVersion {
|
|
return nil, fmt.Errorf("migration failed to update config to version %d", migrations.CurrentVersion)
|
|
}
|
|
|
|
// Write back the migrated config.
|
|
if err := c.ConfigStore.Update(config); err != nil {
|
|
return nil, err
|
|
}
|
|
}
|
|
|
|
// Validate the config
|
|
if err := ValidateConfig(config); err != nil {
|
|
return nil, err
|
|
}
|
|
|
|
c.config = config
|
|
return config, nil
|
|
}
|
|
|
|
func (c *CachingValidatingStore) Update(config *v1.Config) error {
|
|
c.mu.Lock()
|
|
defer c.mu.Unlock()
|
|
|
|
if err := ValidateConfig(config); err != nil {
|
|
return err
|
|
}
|
|
|
|
if err := c.ConfigStore.Update(config); err != nil {
|
|
return err
|
|
}
|
|
|
|
c.config = config
|
|
return nil
|
|
}
|