confik

package module
v0.0.1 Latest Latest
Warning

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

Go to latest
Published: Oct 30, 2023 License: MIT Imports: 13 Imported by: 0

README

confik

Confik parses environment files and variables and loads them into a struct.

Usage

go get github.com/42z-io/confik
import (
    "os"
    "fmt"
    "github.com/42z-io/confik"
)

type ExampleConfig struct {
    Name   string
    Age    uint8 `env:"AGE,optional"`
    Height float32
}

func init() {
    os.Setenv("NAME", "Bob")
    os.Setenv("AGE", "20")
    os.Setenv("HEIGHT", "5.3")

    cfg, _ := confik.LoadFromEnv(Config[ExampleConfig]{
        UseEnvFile: false,
    })

    fmt.Println(cfg.Name)
    fmt.Println(cfg.Age)
    fmt.Println(cfg.Height)
    // Output: Bob
    // 20
    // 5.3
}

Documentation

Overview

confik will build structs from environment files and variables.

confik works by reading special struct tags on your fields.

Supported Types

Tag Options

You can control how each field is configured through struct tags under the "env" key.

Tags are specified like such:

type MyStruct struct {
  Name: `env:"NAME_OF_VARIABLE,flag1,flag2,setting1=value,setting2=value"`
}

Available flags:

  • optional: Dont require this value to exist in the environment.
  • unset: Remove this environment value after load.

Available settings:

  • default=value: Set the default (string) value if it is not found in the environment.
  • validator=validator: Set the name of the validator to use for this field.

Validators

Fields can have their string values validated during environment load.

Available validators:

  • file: Verify that the path exists and is a file.
  • dir: Verify that the path exists and is a directory.
  • uri: Verify that the value is a URI.
  • ip: Verify that the value is an IP address.
  • port: Verify that the value is a port.
  • hostport: Verify that the value is a host/port combination.
  • cidr: Verify that the value is a CIDR.

Custom Validators

Fields can be implement custom validators by specifying a Validator in Config.

See the examples below.

Custom Types

Custom types can be supported by specifying a Parser in Config.

See the examples below.

Examples

Example
os.Clearenv()
os.Setenv("NAME", "Bob")
os.Setenv("AGE", "20")
os.Setenv("HEIGHT", "5.3")
type ExampleConfig struct {
	Name   string
	Age    uint8 `env:"AGE,optional"`
	Height float32
}

cfg, _ := LoadFromEnv(Config[ExampleConfig]{
	UseEnvFile: false,
})

fmt.Println(cfg.Name)
fmt.Println(cfg.Age)
fmt.Println(cfg.Height)
Output:

Bob
20
5.3
Example (CustomParser)
os.Clearenv()
os.Setenv("NAME", "Bob")
os.Setenv("AGE", "20")
os.Setenv("HEIGHT", "5.3")

type MyName struct {
	Name string
}
type ExampleConfig struct {
	Name   MyName `env:"NAME"`
	Age    uint8  `env:"AGE,optional"`
	Height float32
}

cfg, _ := LoadFromEnv(Config[ExampleConfig]{
	UseEnvFile: false,
	Parsers: map[reflect.Type]Parser{
		reflect.TypeOf((*MyName)(nil)).Elem(): func(fieldConfig *FieldConfig, fieldValue string, rv reflect.Value) error {
			name := MyName{
				Name: fieldValue,
			}

			rv.Set(reflect.ValueOf(name))
			return nil
		},
	},
})

fmt.Println(cfg.Name.Name)
Output:

Bob
Example (CustomValidator)
os.Clearenv()
os.Setenv("NAME", "Bob")
os.Setenv("AGE", "20")
os.Setenv("HEIGHT", "5.3")
type ExampleConfig struct {
	Name   string `env:"NAME,validate=uppercase"`
	Age    uint8  `env:"AGE,optional"`
	Height float32
}

_, err := LoadFromEnv(Config[ExampleConfig]{
	UseEnvFile: false,
	Validators: map[string]Validator{
		"uppercase": func(envName, value string) error {
			for _, c := range value {
				if !unicode.IsUpper(c) {
					return fmt.Errorf("%s must be uppercase", envName)
				}
			}
			return nil
		},
	},
})

fmt.Println(err.Error())
Output:

NAME must be uppercase
Example (DefaultTag)
os.Clearenv()

type ExampleConfig struct {
	Age uint8 `env:"AGE,default=30"`
}

cfg, _ := LoadFromEnv(Config[ExampleConfig]{
	UseEnvFile: false,
})

fmt.Println(cfg.Age)
Output:

30
Example (DefaultValue)
os.Clearenv()

type ExampleConfig struct {
	Age uint8 `env:"AGE"`
}

cfg, _ := LoadFromEnv(Config[ExampleConfig]{
	UseEnvFile: false,
	DefaultValue: &ExampleConfig{
		Age: 31,
	},
})

fmt.Println(cfg.Age)
Output:

31

Index

Examples

Constants

This section is empty.

Variables

This section is empty.

Functions

func LoadFromEnv

func LoadFromEnv[T any](cfgs ...Config[T]) (*T, error)

LoadFromEnv will build a T by reading values from environment files and variables.

Types

type Config

type Config[T any] struct {
	UseEnvFile      bool                    // read from an environment file on disk?
	EnvFilePath     string                  // custom path to the environment file (otherwise search for ".env")
	EnvFileOverride bool                    // should variables found in the env file override environment variables?
	Validators      map[string]Validator    // a map of custom validators to be used by the loader
	Parsers         map[reflect.Type]Parser // a map of custom type parsers to be used by the loader
	DefaultValue    *T                      // default values to use if they do not exist in the environment
}

Config[T] is the configuration for reading environment variables.

func DefaultConfig

func DefaultConfig[T any]() Config[T]

DefaultConfig will create a new Config with the default values.

type ConfigTag

type ConfigTag struct {
	Name      string  // name of the environment variable
	Validator *string // field validator name
	Optional  bool    // is the environment variable optional?
	Default   *string // default value to use if the environment variable does not exist
	Unset     bool    // clear the environment variable after load?
}

ConfigTag represents the name, flags and settings on the struct field.

func NewConfigTag

func NewConfigTag(name string) ConfigTag

NewConfigTag will create a new ConfigTag with the default values.

type FieldConfig

type FieldConfig struct {
	ConfigTag            // the configuration specified in the tag
	Validate  *Validator // the custom validator for this field
}

FieldConfig is the representation of the configuration for a field within a struct (after tags have been parsed).

type Parser

type Parser = func(fc *FieldConfig, fieldValue string, rv reflect.Value) error

Parser is the type a function must implement to provide type conversion for types.

type Validator

type Validator = func(envName, value string) error

Validator is the type a function must implement to provide string validation on environment variables.

Jump to

Keyboard shortcuts

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