config

package
v0.1.16 Latest Latest
Warning

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

Go to latest
Published: Feb 16, 2023 License: Apache-2.0 Imports: 7 Imported by: 1

README

mu/config

config is a package for declaring and reading configuration variables.

To use config, create a Config object with New, and then call its NewInt, NewString, or NewBool methods to declare configuration variables. You can then call Int, String, or Bool to read the value of a variable.

Motivation

Cloud-native applications are usually configured using environment variables. However, accessing environment variables directly with os.Getenv is primitive and error-prone. config provides a simple, type-safe interface for declaring and reading configuration variables.

  • Configuration variables are loaded, type-checked, and validated when they are registered, not when they are accessed. This ensures that configuration errors are caught early, instead of causing application errors, crashes, or misbehavior at runtime.
  • Because validation happens at registration time, accessor methods like Int and String do not need to return an error. This simplifies the application code, and makes it easier to use configuration variables in places where error handling is not convenient.
  • All configuration variables are declared in a single place, instead of scattered throughout the application code. This makes it easy to see all configuration variables, and to find the code that uses them.
  • Description strings are attached to each configuration variable. This enables automatic documentation generation, and makes it easy to see what each variable is used for.

Example

package main

import (
    "fmt"
    "os"

    "github.com/neuralnorthwest/mu/config"
)

func main() {
    c := config.New()
    c.NewInt("PORT", 8080, "The port to listen on")
    c.NewString("MESSAGE", "Hello world!", "The message to print")
    c.NewBool("DEBUG", false, "Enable debug mode")

    fmt.Printf("Listening on port %d\n", c.Int("PORT"))
    fmt.Printf("Message: %s\n", c.String("MESSAGE"))
    if c.Bool("DEBUG") {
        fmt.Println("Debug mode is enabled")
    }
}

Options

Various options are available for customizing the behavior of config. Some options can be passed to New, while others are used with NewInt, NewString, and NewBool.

Options for New
  • WithEnvPrefix - Sets the prefix for environment variables. For example, if the prefix is MYAPP_, then the environment variable MYAPP_PORT will be used to set the value of the PORT configuration variable. Example:
package main

import (
    "fmt"
    "os"

    "github.com/neuralnorthwest/mu/config"
)

func main() {
    c := config.New(config.WithEnvPrefix("MYAPP_"))
    c.NewInt("PORT", 8080, "The port to listen on")
    fmt.Printf("Listening on port %d\n", c.Int("PORT"))
}
  • WithSource - Sets the source for configuration variables. The default source is os.Getenv, but you can also use a custom source that reads configuration variables from a file, or from a database.
package main

import (
    "fmt"
    "os"

    "github.com/neuralnorthwest/mu/config"
)

type customSource struct {
    prefix string
    // Other fields
}

func newCustomSource() *customSource {
    return &customSource{}
}

// Implement the Source interface
func (s *customSource) SetPrefix(prefix string) {
    s.prefix = prefix
}

func (s *customSource) LoadInt(name string) (int, error) {
    // Read the value of the configuration variable from a file or database
    value := ...
    return value, nil
}

func (s *customSource) LoadString(name string) (string, error) {
    // Read the value of the configuration variable from a file or database
    value := ...
    return value, nil
}

func (s *customSource) LoadBool(name string) (bool, error) {
    // Read the value of the configuration variable from a file or database
    value := ...
    return value, nil
}

func main() {
    c := config.New(config.WithSource(newCustomSource()))
    c.NewInt("PORT", 8080, "The port to listen on")
    fmt.Printf("Listening on port %d\n", c.Int("PORT"))
}
Options for NewInt
  • WithMinimumValue and WithMaximumValue - Sets the minimum and maximum allowed values for the configuration variable. If the value is outside the allowed range, NewInt will either return an error, or clamp the value to the nearest allowed value.
  • WithClamping - Enables clamping for the configuration variable. If the value is outside the allowed range, it will be clamped to the nearest allowed value. If clamping is disabled, NewInt will return an error if the value is outside the allowed range.
  • WithIntValidator - Sets a custom validator for the configuration variable. The validator is a function that takes an integer value and returns an error if the value is invalid. If the validator returns an error, NewInt will return the same error.

Documentation

Index

Constants

This section is empty.

Variables

This section is empty.

Functions

This section is empty.

Types

type Bool

type Bool struct {
	// contains filtered or unexported fields
}

Bool is a configuration value that is a bool.

type Config

type Config interface {
	// NewInt creates a new int variable.
	NewInt(name string, defaultValue int, description string, options ...IntOption) error
	// Int returns the value of the int variable with the given name. If the variable does not exist, it calls bug.Bug.
	// If bug.Bug does not panic, Int returns 0.
	Int(name string) int
	// DescribeInt returns the description of the int variable with the given name. If the variable does not exist, it calls bug.Bug.
	// If bug.Bug does not panic, DescribeInt returns "".
	DescribeInt(name string) string
	// NewString creates a new string variable.
	NewString(name string, defaultValue string, description string, options ...StringOption) error
	// String returns the value of the string variable with the given name. If the variable does not exist, it calls bug.Bug.
	// If bug.Bug does not panic, String returns "".
	String(name string) string
	// DescribeString returns the description of the string variable with the given name. If the variable does not exist, it calls bug.Bug.
	// If bug.Bug does not panic, DescribeString returns "".
	DescribeString(name string) string
	// NewBool creates a new bool variable.
	NewBool(name string, defaultValue bool, description string) error
	// Bool returns the value of the bool variable with the given name. If the variable does not exist, it calls bug.Bug.
	// If bug.Bug does not panic, Bool returns false.
	Bool(name string) bool
	// DescribeBool returns the description of the bool variable with the given name. If the variable does not exist, it calls bug.Bug.
	// If bug.Bug does not panic, DescribeBool returns "".
	DescribeBool(name string) string
}

Config holds configuration variables.

func New

func New(opts ...Option) Config

New creates a new Config.

type Int

type Int struct {
	// contains filtered or unexported fields
}

Int is a configuration value that is an integer.

type IntOption

type IntOption func(*configImpl, *Int) error

IntOption is an option for an int variable.

func WithClamping

func WithClamping() IntOption

WithClamping returns an option that enables clamping for an int variable.

func WithIntValidator

func WithIntValidator(f func(int) error) IntOption

WithIntValidator returns an option that sets the validator for an int variable.

func WithMaximumValue

func WithMaximumValue(max int) IntOption

WithMaximumValue returns an option that sets the maximum value for an int variable.

func WithMinimumValue

func WithMinimumValue(min int) IntOption

WithMinimumValue returns an option that sets the minimum value for an int variable.

type Option

type Option func(c *configImpl)

Option is an option for Config.

func WithLoadPrefix

func WithLoadPrefix(prefix string) Option

WithLoadPrefix returns an Option that prepends a prefix to the names of the configuration variables when loading them.

func WithSource

func WithSource(source Source) Option

WithSource returns an Option that sets the source of the configuration variables.

type Source

type Source interface {
	// SetPrefix sets the prefix of the names of the configuration variables.
	SetPrefix(prefix string)
	// LoadInt loads the value of the int variable with the given name. If the
	// variable does not exist, it must return 0 and status.ErrNotFound.
	LoadInt(name string) (int, error)
	// LoadString loads the value of the string variable with the given name. If
	// the variable does not exist, it must return "" and status.ErrNotFound.
	LoadString(name string) (string, error)
	// LoadBool loads the value of the bool variable with the given name. If the
	// variable does not exist, it must return false and status.ErrNotFound.
	LoadBool(name string) (bool, error)
}

Source is an interface that loads the values of the configuration variables.

type String

type String struct {
	// contains filtered or unexported fields
}

String is a configuration value that is a string.

type StringOption

type StringOption func(*configImpl, *String) error

StringOption is an option for a string variable.

func WithStringValidator

func WithStringValidator(f func(string) error) StringOption

WithStringValidator returns an option that sets the validator for a string variable.

Jump to

Keyboard shortcuts

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