configreader

package module
v0.2.0 Latest Latest
Warning

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

Go to latest
Published: Apr 2, 2024 License: MIT Imports: 18 Imported by: 0

README

configreader

Simple configuration reader and validator that accepts a variety of sources.

Load behavior

The library starts retrieves data from a source and, optionally, expands embedded variables delimited by ${ and }.

The library accepts dotenv files, key/value pairs or JSON objects. Depending on the source type, C-style and/or # comment texts will be removed.

Quick start

  1. Import the library
import (
    "github.com/mxmauro/configreader"
)
  1. Create a struct that defines your configuration settings and add the required config and validate tags to it.
type ConfigurationSettings struct {
    Name         string  `config:"TEST_NAME" validate:"required"`
    IntegerValue int     `config:"TEST_INTEGER_VALUE" validate:"required,min=1"`
    FloatValue   float64 `config:"TEST_FLOAT_VALUE"`
}
  1. Load the application settings like the following example:
func main() {
    settings, err := configreader.New[ConfigurationSettings]().
        WithLoader(loader.NewFile().WithFilename("./config.env")).
        Load(context.Background())
    if err != nil {
        panic(err.Error())
    }
    ....
}

How to use

Create the configuration reader. Set the name of the struct that defines the configuration definition as the generic type parameter.

reader := configreader.New[{structure-name}]()

Apply reader options like:

reader.WithLoader(...).WithMonitor(...)
Method Description
WithExtendedValidator Sets an optional settings validator callback.
WithLoader Sets the content loader. See the loader section for details.
WithMonitor Sets a monitor that will inform about configuration settings changes. See the monitor section for details.
WithDisableEnvVarOverride Ignore a list of environment variables that can override values.

And load the settings:

ctx := context.Background() // Setup a context
settings, err := reader.Load(ctx)

Loaders

Settings loaders are referenced by importing the following module:

import (
    "github.com/mxmauro/configreader/loader"
)

And then instantiated using the loader.NewXXX() functions.

ld := loader.NewMemory().WithXXX(...).WithXXX(...)....
reader.WithLoader(ld)

You can add more than one loader, overlapping values will be overridden as sources are processed.

See this document for details about the available loaders.

Validation

Data validation is executed in two phases. The first inspects validate tags using the Go Playground Validator library. Please check the full documentation here.

The second is through the WithExtendedValidator method. This library calls the specified function so the developer can execute further custom checks.

Monitor

A monitor periodically checks if the configuration setting changed by reloading the settings based on the configuration reader parameters.

On successful reads, it compares the current values with the previously loaded and, if a different setting is found, the callback is called with the new values.

If read fails, the callback is called with the error object.

Notes:
  • The developer is responsible to notify other application components about the changes.
  • If settings are stored in global variables, the developer must ensure synchronized access to them.
  • If a reload error occurs, the developer is free to decide the next actions. The monitor will continue trying to load settings until explicitly destroyed.
m := configreader.NewMonitor[{structure-name}](30 * time.Second, func(settings *{structure-name}, loadErr error) {
    // do whatever you need here
})
defer m.Destroy()

settings, err := configreader.New[{structure-name}]().
    WithXXX(...).
    WithMonitor(m).
    Load(...)

The callback is called eve

Variable expansion

Once the key/values are loaded, string values containing expansion macros patterns like ${NAME} will be automatically expanded by looking for the specified key.

Tests

If you want to run the tests of this library, take into consideration the following:

Hashicorp Vault tests requires a running instance launched with the following command:

vault server -dev -dev-root-token-id="root" -dev-listen-address="0.0.0.0:8200" -dev-no-store-token

If Vault is running on AWS, the EC2 instance requires an IAM role with following policies:

  • ec2:DescribeInstances
  • iam:GetInstanceProfile (if IAM Role binding is used)

LICENSE

See LICENSE file for details.

Documentation

Index

Constants

This section is empty.

Variables

This section is empty.

Functions

func AddressOfString

func AddressOfString(s string) *string

AddressOfString returns the address of the provided string

func Escape

func Escape(s string) string

Escape escapes a string to avoid embedded % characters to be recognized as environment variable tags.

Types

type ConfigReader

type ConfigReader[T any] struct {
	// contains filtered or unexported fields
}

ConfigReader contains configurable loader options.

func New

func New[T any]() *ConfigReader[T]

New creates a new configuration reader

func (*ConfigReader[T]) Load

func (cr *ConfigReader[T]) Load(ctx context.Context) (*T, error)

Load settings from the specified source

func (*ConfigReader[T]) WithDisableEnvVarOverride added in v0.2.0

func (cr *ConfigReader[T]) WithDisableEnvVarOverride(vars ...string) *ConfigReader[T]

WithDisableEnvVarOverride stops the loader from replacing environment variables that can be found inside

func (*ConfigReader[T]) WithExtendedValidator

func (cr *ConfigReader[T]) WithExtendedValidator(validator ExtendedValidator[T]) *ConfigReader[T]

WithExtendedValidator sets an optional settings validator callback

func (*ConfigReader[T]) WithLoader

func (cr *ConfigReader[T]) WithLoader(l ...model.Loader) *ConfigReader[T]

WithLoader sets the content loader

func (*ConfigReader[T]) WithMonitor

func (cr *ConfigReader[T]) WithMonitor(m *Monitor[T]) *ConfigReader[T]

WithMonitor sets a monitor that will inform about configuration settings changes

NOTE: First send a value to stop monitoring and then wait until a value is received on the same channel

type ExtendedValidator

type ExtendedValidator[T any] func(settings *T) error

ExtendedValidator is a function to call in order to do configuration validation not covered by this library.

type Monitor

type Monitor[T any] struct {
	// contains filtered or unexported fields
}

Monitor implements a module that periodically checks if the configuration setting changed.

func NewMonitor

func NewMonitor[T any](pollInterval time.Duration, callback SettingsChangedCallback[T]) *Monitor[T]

NewMonitor creates a new configuration settings change monitor

func (*Monitor[T]) Destroy

func (m *Monitor[T]) Destroy()

Destroy stops a running configuration settings monitor and destroys it

type SettingsChangedCallback

type SettingsChangedCallback[T any] func(settings *T, loadErr error)

SettingsChangedCallback is a function to call when the re-loader detects a change in the configuration settings.

type ValidationError

type ValidationError struct {
	Failures []ValidationErrorFailure
}

ValidationError represents a set of ValidationErrorFailure.

func (*ValidationError) Error

func (e *ValidationError) Error() string

func (*ValidationError) Unwrap

func (*ValidationError) Unwrap() error

type ValidationErrorFailure

type ValidationErrorFailure struct {
	Field string
	Tag   string
}

ValidationErrorFailure represents a specific JSON schema validation error.

func (*ValidationErrorFailure) Error added in v0.2.0

func (e *ValidationErrorFailure) Error() string

Directories

Path Synopsis
internal

Jump to

Keyboard shortcuts

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