yamlcfg

package module
v0.6.0 Latest Latest
Warning

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

Go to latest
Published: May 5, 2026 License: MIT Imports: 6 Imported by: 2

README

yamlcfg

yamlcfg is a wrapper around the go.yaml.in/yaml/v4 library and provides a convenient way to configure Go applications with YAML and environment variables.

The library can also automatically call Validate functions if present on the given config struct.

Installation

go get github.com/aranw/yamlcfg

Environment Variables

yamlcfg expands environment variables in YAML values using the ${VAR} syntax:

database_url: "${DATABASE_URL}"

Default values are supported with ${VAR:default}:

log_level: "${LOG_LEVEL:info}"
port: "${PORT:8080}"

Environment variables can also appear within larger strings:

dsn: "host=${DB_HOST:localhost} port=${DB_PORT:5432} dbname=${DB_NAME:myapp}"

Note: bare $VAR references (without braces) are treated as literal strings and not expanded.

Usage

Parse

Reads a YAML file from disk and unmarshals it into the given type:

type Config struct {
    LogLevel string `yaml:"log_level"`
    Port     int    `yaml:"port"`
}

cfg, err := yamlcfg.Parse[Config]("config.yaml")
if err != nil {
    log.Fatal(err)
}
ParseWithConfig

Parses a YAML file with pre-populated default values. Fields not present in the YAML file retain their defaults:

defaults := &Config{
    LogLevel: "info",
    Port:     8080,
}

cfg, err := yamlcfg.ParseWithConfig(defaults, "config.yaml")
if err != nil {
    log.Fatal(err)
}
ParseFS

Reads a YAML file from an embed.FS:

//go:embed config.yaml
var configFS embed.FS

cfg, err := yamlcfg.ParseFS[Config](configFS, "config.yaml")
if err != nil {
    log.Fatal(err)
}
UnmarshalConfig

Unmarshals raw YAML bytes directly, expanding environment variables:

data := []byte(`log_level: "${LOG_LEVEL:debug}"`)

var cfg Config
if err := yamlcfg.UnmarshalConfig(&cfg, data); err != nil {
    log.Fatal(err)
}

Validation

If your config struct implements a Validate() error method, it will be called automatically after unmarshalling:

type Config struct {
    LogLevel string `yaml:"log_level"`
}

func (c *Config) Validate() error {
    validLevels := []string{"debug", "info", "warn", "error"}
    if !slices.Contains(validLevels, c.LogLevel) {
        return fmt.Errorf("invalid log level: %s", c.LogLevel)
    }
    return nil
}

License

The yamlcfg package is licensed under the MIT license. Please see the LICENSE file for details.

Documentation

Index

Examples

Constants

This section is empty.

Variables

This section is empty.

Functions

func Parse

func Parse[T any](path string) (*T, error)

Parse takes the given path and attempts to read and unmarshal the config The given config will also be validated if it has a Validate function on it

Example
package main

import (
	"log/slog"

	"github.com/aranw/yamlcfg"
)

type Config struct {
	LogLevel string `yaml:"log_level"`
}

func main() {
	cfg, err := yamlcfg.Parse[Config]("config.yaml")
	if err != nil {
		slog.Error("loading yaml config", "err", err)
		return
	}

	_ = cfg.LogLevel
}

func ParseFS

func ParseFS[T any](fs embed.FS, path string) (*T, error)

ParseFS attempts to load the given path and config from a embed.FS

Example
package main

import (
	"embed"
	"log/slog"

	"github.com/aranw/yamlcfg"
)

type Config struct {
	LogLevel string `yaml:"log_level"`
}

//go:embed testdata
var testdata embed.FS

func main() {
	cfg, err := yamlcfg.ParseFS[Config](testdata, "config.yaml")
	if err != nil {
		slog.Error("loading yaml config", "err", err)
		return
	}

	_ = cfg.LogLevel
}

func ParseWithConfig added in v0.2.0

func ParseWithConfig[T any](cfg *T, path string) (*T, error)

ParseWithConfig takes the given config and path and attempts to read and unmarshal the config The given config can be populated with default values If the given config implements a `Validate() error` function this will be called

Example
package main

import (
	"log/slog"

	"github.com/aranw/yamlcfg"
)

type Config struct {
	LogLevel string `yaml:"log_level"`
}

func main() {
	defaults := &Config{
		LogLevel: "info",
	}

	cfg, err := yamlcfg.ParseWithConfig(defaults, "config.yaml")
	if err != nil {
		slog.Error("loading yaml config", "err", err)
		return
	}

	_ = cfg.LogLevel
}

func UnmarshalConfig

func UnmarshalConfig[T any](cfg *T, data []byte) error

UnmarshalConfig takes the provided yaml data and unmarshals it into the provided config struct. It will return an error if the decoding fails or if the yaml data is not in the expected format. It will also expand any environment variables in the yaml data

Example
package main

import (
	"fmt"
	"log/slog"

	"github.com/aranw/yamlcfg"
)

type Config struct {
	LogLevel string `yaml:"log_level"`
}

func main() {
	data := []byte(`log_level: "debug"`)

	var cfg Config
	if err := yamlcfg.UnmarshalConfig(&cfg, data); err != nil {
		slog.Error("unmarshalling config", "err", err)
		return
	}

	fmt.Println(cfg.LogLevel)
}
Output:
debug

Types

This section is empty.

Jump to

Keyboard shortcuts

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