treat empty jobs & empty YAML as valid & ship empty jobs in deb/rpm (#788)

fixes https://github.com/zrepl/zrepl/issues/784
obsoletes https://github.com/zrepl/zrepl/pull/787
This commit is contained in:
Christian Schwarz 2024-05-14 19:18:22 +02:00 committed by GitHub
parent 830536715e
commit 9c63736489
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
5 changed files with 30 additions and 28 deletions

View File

@ -5,7 +5,6 @@ import (
"io/ioutil" "io/ioutil"
"log/syslog" "log/syslog"
"os" "os"
"reflect"
"time" "time"
"github.com/pkg/errors" "github.com/pkg/errors"
@ -24,7 +23,7 @@ const (
) )
type Config struct { type Config struct {
Jobs []JobEnum `yaml:"jobs"` Jobs []JobEnum `yaml:"jobs,optional"`
Global *Global `yaml:"global,optional,fromdefaults"` Global *Global `yaml:"global,optional,fromdefaults"`
} }
@ -299,18 +298,6 @@ type Global struct {
Serve *GlobalServe `yaml:"serve,optional,fromdefaults"` Serve *GlobalServe `yaml:"serve,optional,fromdefaults"`
} }
func Default(i interface{}) {
v := reflect.ValueOf(i)
if v.Kind() != reflect.Ptr {
panic(v)
}
y := `{}`
err := yaml.Unmarshal([]byte(y), v.Interface())
if err != nil {
panic(err)
}
}
type ConnectEnum struct { type ConnectEnum struct {
Ret interface{} Ret interface{}
} }
@ -696,8 +683,16 @@ func ParseConfigBytes(bytes []byte) (*Config, error) {
if err := yaml.UnmarshalStrict(bytes, &c); err != nil { if err := yaml.UnmarshalStrict(bytes, &c); err != nil {
return nil, err return nil, err
} }
if c != nil {
return c, nil
}
// There was no yaml document in the file, deserialize from default.
// => See TestFromdefaultsEmptyDoc in yaml-config package.
if err := yaml.UnmarshalStrict([]byte("{}"), &c); err != nil {
return nil, err
}
if c == nil { if c == nil {
return nil, fmt.Errorf("config is empty or only consists of comments") panic("the fallback to deserialize from `{}` should work")
} }
return c, nil return c, nil
} }

View File

@ -2,16 +2,8 @@ package config
import ( import (
"testing" "testing"
"github.com/stretchr/testify/assert"
) )
func TestConfigEmptyFails(t *testing.T) {
conf, err := testConfig(t, "\n")
assert.Nil(t, conf)
assert.Error(t, err)
}
func TestJobsOnlyWorks(t *testing.T) { func TestJobsOnlyWorks(t *testing.T) {
testValidConfig(t, ` testValidConfig(t, `
jobs: jobs:
@ -34,7 +26,7 @@ jobs:
keep_sender: keep_sender:
- type: not_replicated - type: not_replicated
keep_receiver: keep_receiver:
- type: last_n - type: last_n
count: 1 count: 1
`) `)
} }

View File

@ -22,6 +22,8 @@ func TestSampleConfigsAreParsedWithoutErrors(t *testing.T) {
t.Errorf("glob failed: %+v", err) t.Errorf("glob failed: %+v", err)
} }
paths = append(paths, "../packaging/systemd-default-zrepl.yml")
for _, p := range paths { for _, p := range paths {
if path.Ext(p) != ".yml" { if path.Ext(p) != ".yml" {
@ -84,7 +86,7 @@ func trimSpaceEachLineAndPad(s, pad string) string {
func TestTrimSpaceEachLineAndPad(t *testing.T) { func TestTrimSpaceEachLineAndPad(t *testing.T) {
foo := ` foo := `
foo foo
bar baz bar baz
` `
assert.Equal(t, " \n foo\n bar baz\n \n", trimSpaceEachLineAndPad(foo, " ")) assert.Equal(t, " \n foo\n bar baz\n \n", trimSpaceEachLineAndPad(foo, " "))
} }
@ -138,3 +140,18 @@ func TestCronSpec(t *testing.T) {
} }
} }
func TestEmptyConfig(t *testing.T) {
cases := []string{
"",
"\n",
"---",
"---\n",
}
for _, input := range cases {
config := testValidConfig(t, input)
require.NotNil(t, config)
require.NotNil(t, config.Global)
require.Empty(t, config.Jobs)
}
}

0
config/samples/empty.yml Normal file
View File

View File

@ -5,9 +5,7 @@ global:
format: human format: human
level: warn level: warn
jobs: jobs: []
# - name: foo
# type: bar
# see USR_SHARE_ZREPL/examples # see USR_SHARE_ZREPL/examples
# or https://zrepl.github.io/configuration/overview.html # or https://zrepl.github.io/configuration/overview.html