package main import ( "flag" "fmt" "io" "os" yaml "gopkg.in/yaml.v3" ) const ( defaultPort = 7099 defaultInstanceName = "BBJ" defaultHost = "127.0.0.1" ) type Config struct { Admins []string Port int Host string InstanceName string `yaml:"instance_name"` AllowAnon bool Debug bool } type iostreams struct { Err io.Writer Out io.Writer } type Opts struct { ConfigPath string IO iostreams } func main() { var configFlag = flag.String("config", "config.yml", "A path to a config file.") flag.Parse() opts := Opts{ ConfigPath: *configFlag, IO: iostreams{ Err: os.Stderr, Out: os.Stdout, }, } err := _main(opts) if err != nil { fmt.Fprintf(os.Stderr, "failed: %s", err) } } func _main(opts Opts) error { cfg, err := parseConfig(opts.ConfigPath) if err != nil { fmt.Fprintf(os.Stderr, "could not read config file '%s'", opts.ConfigPath) os.Exit(1) } fmt.Printf("DBG %#v\n", cfg.InstanceName) return nil } func parseConfig(configPath string) (*Config, error) { cfgBytes, err := os.ReadFile(configPath) if err != nil { return nil, fmt.Errorf("failed to read config file: %w", err) } fmt.Printf("DBG %#v\n", string(cfgBytes)) var cfg Config if err := yaml.Unmarshal(cfgBytes, &cfg); err != nil { return nil, fmt.Errorf("failed to parse config: %w", err) } fmt.Printf("DBG %#v\n", cfg) if cfg.Port == 0 { cfg.Port = defaultPort } if cfg.InstanceName == "" { cfg.InstanceName = defaultInstanceName } if cfg.Host == "" { cfg.Host = defaultHost } return &cfg, nil }