diff --git a/.gitignore b/.gitignore index e660fd9..098c261 100644 --- a/.gitignore +++ b/.gitignore @@ -1 +1,2 @@ +thanks.yaml bin/ diff --git a/cmd/thanks/main.go b/cmd/thanks/main.go index 7ba6864..e1ba1d2 100644 --- a/cmd/thanks/main.go +++ b/cmd/thanks/main.go @@ -4,6 +4,7 @@ import ( "context" "flag" "fmt" + "log" "git.gentoo.party/sam/thanks/internal/jobs" ) @@ -13,10 +14,14 @@ var ( BuildTime = "unknown" ) -var flagVersion = false +var ( + flagVersion = false + jobsFile = "thanks.yaml" +) func init() { flag.BoolVar(&flagVersion, "v", false, "show program version") + flag.StringVar(&jobsFile, "jobs", "thanks.yaml", "backup job definitions file") } func main() { @@ -27,15 +32,15 @@ func main() { return } - myJob := jobs.BackupJob{ - Source: "zroot/home/sam/thanks", - Target: "zrust/backup/weller/thanks", - TargetHost: "backup@woodford.gentoo.party", - Keep: 30, - Prefix: "thanks-", - Recursive: false, + backupJobs, err := jobs.ParseFile(jobsFile) + if err != nil { + log.Fatalf("error reading backup job definitions: %s\n", err.Error()) } ctx := context.Background() - myJob.Do(ctx) + for _, myJob := range backupJobs { + myJob.Do(ctx) + } + + log.Printf("backups completed successfully") } diff --git a/go.mod b/go.mod index b3dc617..5206e69 100644 --- a/go.mod +++ b/go.mod @@ -1,3 +1,13 @@ module git.gentoo.party/sam/thanks go 1.25.5 + +require ( + github.com/stretchr/testify v1.11.1 + gopkg.in/yaml.v3 v3.0.1 +) + +require ( + github.com/davecgh/go-spew v1.1.1 // indirect + github.com/pmezard/go-difflib v1.0.0 // indirect +) diff --git a/go.sum b/go.sum new file mode 100644 index 0000000..c4c1710 --- /dev/null +++ b/go.sum @@ -0,0 +1,10 @@ +github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c= +github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= +github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM= +github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= +github.com/stretchr/testify v1.11.1 h1:7s2iGBzp5EwR7/aIZr8ao5+dra3wiQyKjjFuvgVKu7U= +github.com/stretchr/testify v1.11.1/go.mod h1:wZwfW3scLgRK+23gO65QZefKpKQRnfz6sD981Nm4B6U= +gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405 h1:yhCVgyC4o1eVCa2tZl7eS0r+SDo693bJlVdllGtEeKM= +gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= +gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA= +gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= diff --git a/internal/jobs/jobs.go b/internal/jobs/jobs.go index 8a41856..7c1f890 100644 --- a/internal/jobs/jobs.go +++ b/internal/jobs/jobs.go @@ -16,12 +16,12 @@ import ( ) type BackupJob struct { - Source string // the source dataset (e.g., zroot) - TargetHost string // SSH-compatible host - Target string // the target dataset - Keep int // number of snapshots to keep - Prefix string // name each snapshot with this prefix - Recursive bool // create recursive snapshots + Source string `yaml:"source"` // the source dataset (e.g., zroot) + TargetHost string `yaml:"targetHost"` // SSH-compatible host + Target string `yaml:"target"` // the target dataset + Keep int `yaml:"keep"` // number of snapshots to keep + Recursive bool `yaml:"recursive"` // create recursive snapshots + Prefix string `yaml:"prefix"` // name each snapshot with this prefix } // func (j *BackupJob) getBaseSnap() { diff --git a/internal/jobs/parse.go b/internal/jobs/parse.go new file mode 100644 index 0000000..8f2d6ea --- /dev/null +++ b/internal/jobs/parse.go @@ -0,0 +1,27 @@ +package jobs + +import ( + "io" + "os" + + "gopkg.in/yaml.v3" +) + +type JobsRoot struct { + Jobs []BackupJob `yaml:"jobs"` +} + +func Parse(reader io.Reader) ([]BackupJob, error) { + dec := yaml.NewDecoder(reader) + var jobsRoot JobsRoot + err := dec.Decode(&jobsRoot) + return jobsRoot.Jobs, err +} + +func ParseFile(path string) ([]BackupJob, error) { + f, err := os.Open(path) + if err != nil { + return nil, err + } + return Parse(f) +} diff --git a/internal/jobs/parse_test.go b/internal/jobs/parse_test.go new file mode 100644 index 0000000..e1f4bc4 --- /dev/null +++ b/internal/jobs/parse_test.go @@ -0,0 +1,26 @@ +package jobs_test + +import ( + "strings" + "testing" + + "git.gentoo.party/sam/thanks/internal/jobs" + "github.com/stretchr/testify/assert" +) + +const testParseStr = ` +jobs: + - source: "zroot/home/sam/thanks" + target: "zrust/backup/weller/thanks" + targetHost: "backup@woodford.gentoo.party" + keep: 30 + prefix: "thanks-" + recursive: false +` + +func TestParse(t *testing.T) { + reader := strings.NewReader(testParseStr) + backupJobs, err := jobs.Parse(reader) + assert.Nil(t, err) + assert.Equal(t, backupJobs[0].Source, "zroot/home/sam/thanks") +}