rehydrate

package
v0.8.7 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Oct 29, 2026 License: Apache-2.0 Imports: 9 Imported by: 0

Documentation

Overview

Package rehydrate plans and runs the data half of a whole-server recovery: after the control plane itself is restored, it pulls each database and app volume back from its latest usable backup and reports what happened.

Index

Constants

View Source
const (
	EnvMaxBackupAge = "APP_REHYDRATE_MAX_BACKUP_AGE"
	EnvConcurrency  = "APP_REHYDRATE_CONCURRENCY"
)

Environment variables that tune a rehydrate pass.

View Source
const (
	KindDatabase = "database"
	KindVolume   = "volume"
)

Item kinds.

View Source
const (
	StatusPlanned   = "planned"
	StatusRunning   = "running"
	StatusSucceeded = "succeeded"
	StatusFailed    = "failed"
	StatusSkipped   = "skipped"
	StatusBlocked   = "blocked"
)

Item statuses. Planned is the dry-run state of an item a run would restore.

View Source
const (
	ReasonNoBackup        = "no_backup"
	ReasonBackupTooOld    = "backup_too_old"
	ReasonNoBackupsEngine = "engine_keeps_no_data"
)

Reasons an item is skipped or blocked.

View Source
const (
	StateRunning   = "running"
	StatePlanned   = "planned"
	StateSucceeded = "succeeded"
	StatePartial   = "partial"
	StateFailed    = "failed"
)

Report states.

View Source
const (
	ModePlan = "plan"
	ModeRun  = "run"
)

Modes of a report.

Variables

View Source
var ErrBusy = errors.New("rehydrate: a run is already in progress")

ErrBusy is returned when a run is already in progress.

View Source
var ErrNotConfigured = errors.New("rehydrate: restores are not configured")

ErrNotConfigured is returned when restores cannot run on this control plane.

Functions

This section is empty.

Types

type Backup

type Backup struct {
	ID         string
	Kind       string
	Database   string
	App        string
	Volume     string
	Succeeded  bool
	FinishedAt time.Time
	SizeBytes  int64
}

Backup is one backup attempt, reduced to what planning needs.

type BackupRef

type BackupRef struct {
	ID         string    `json:"id"`
	FinishedAt time.Time `json:"finished_at"`
	SizeBytes  int64     `json:"size_bytes"`
	AgeSeconds int64     `json:"age_seconds"`
}

BackupRef is the backup an item restores from.

type Config

type Config struct {
	// MaxBackupAge is the oldest backup a run will restore from; 0 disables the check.
	MaxBackupAge time.Duration
	Concurrency  int
}

Config holds the env-driven limits.

func ConfigFromEnv

func ConfigFromEnv(lookup func(string) (string, bool)) (Config, error)

ConfigFromEnv reads the limits, falling back to defaults when unset.

type Database

type Database struct {
	Name   string
	Engine string
	// Stateless engines keep nothing on disk and have nothing to restore.
	Stateless bool
}

Database is one desired database.

type Inventory

type Inventory interface {
	Databases(ctx context.Context) ([]Database, error)
	Volumes(ctx context.Context) ([]Volume, error)
	Backups(ctx context.Context) ([]Backup, error)
}

Inventory reads what the restored control plane believes should exist.

type Item

type Item struct {
	ID         string     `json:"id"`
	Kind       string     `json:"kind"`
	App        string     `json:"app,omitempty"`
	Volume     string     `json:"volume,omitempty"`
	Database   string     `json:"database,omitempty"`
	Engine     string     `json:"engine,omitempty"`
	Status     string     `json:"status"`
	Reason     string     `json:"reason,omitempty"`
	Backup     *BackupRef `json:"backup,omitempty"`
	RestoreID  string     `json:"restore_id,omitempty"`
	Error      string     `json:"error,omitempty"`
	StartedAt  *time.Time `json:"started_at,omitempty"`
	FinishedAt *time.Time `json:"finished_at,omitempty"`
}

Item is one resource in the plan and, after a run, its outcome.

type PlanOptions

type PlanOptions struct {
	// AllowStale restores from backups older than MaxBackupAge instead of blocking them.
	AllowStale bool
}

PlanOptions tunes planning.

type Report

type Report struct {
	ID                  string     `json:"id"`
	Mode                string     `json:"mode"`
	State               string     `json:"state"`
	GeneratedAt         time.Time  `json:"generated_at"`
	FinishedAt          *time.Time `json:"finished_at,omitempty"`
	MaxBackupAgeSeconds int64      `json:"max_backup_age_seconds"`
	Concurrency         int        `json:"concurrency"`
	AllowStale          bool       `json:"allow_stale"`
	Items               []Item     `json:"items"`
	Summary             Summary    `json:"summary"`
}

Report is the plan and the DR report of a run; the same shape serves both.

func BuildPlan

func BuildPlan(ctx context.Context, inv Inventory, cfg Config, opts PlanOptions, now time.Time) (Report, error)

BuildPlan matches every database and volume to its newest usable backup.

type Restorer

type Restorer interface {
	RestoreDatabase(ctx context.Context, d Database, backupID string) (string, error)
	RestoreVolume(ctx context.Context, v Volume, backupID string) (string, error)
}

Restorer applies one backup through the existing restore runners and blocks until it finishes. It returns the restore history ID.

type RunStore

type RunStore interface {
	SaveRehydrateRun(ctx context.Context, r store.RehydrateRun) error
	LatestRehydrateRun(ctx context.Context) (store.RehydrateRun, error)
}

RunStore persists the latest report so it survives a restart mid-recovery.

type Service

type Service struct {
	Inventory Inventory
	Restorer  Restorer // nil means restores are not configured
	Store     RunStore // nil keeps the report in memory only
	Config    Config
	Logger    *slog.Logger
	Now       func() time.Time
	// contains filtered or unexported fields
}

Service plans, runs and remembers rehydrate passes. One run at a time.

func (*Service) Plan

func (s *Service) Plan(ctx context.Context, opts PlanOptions) (Report, error)

Plan is a dry run: it changes nothing.

func (*Service) Report

func (s *Service) Report(ctx context.Context) (Report, bool, error)

Report returns the live run when one exists, else the last saved report.

func (*Service) Start

func (s *Service) Start(ctx context.Context, opts PlanOptions) (Report, error)

Start builds the plan and works it in the background. It returns the report in its initial running state.

type Summary

type Summary struct {
	Total      int `json:"total"`
	Restorable int `json:"restorable"`
	Succeeded  int `json:"succeeded"`
	Failed     int `json:"failed"`
	Skipped    int `json:"skipped"`
	Blocked    int `json:"blocked"`
	// WorstBackupAgeSeconds is the data-loss window: the oldest backup used or planned.
	WorstBackupAgeSeconds int64 `json:"worst_backup_age_seconds"`
}

Summary counts items by outcome.

type Volume

type Volume struct {
	App  string
	Name string
}

Volume is one named volume of a desired app.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL