sprout

package module
v0.1.0 Latest Latest
Warning

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

Go to latest
Published: Apr 1, 2023 License: MIT Imports: 11 Imported by: 0

README

Sprout

Sprout is a library to build microservices in Go. It provides a way to set up shared things such as configuration, logging, telemetry and metrics.

Usage

Sprout provides a small wrapper around Fx that bootstraps the application. Sprout encourages the use of modules to keep things organized.

The main application may look something like this:

package main

import "github.com/levelfourab/sprout-go"

func main() {
  sprout.New("ExampleApp", "v1.0.0").With(
    example.Module
  ).Run()
}

A module can then be defined like this:

package main

import "github.com/levelfourab/sprout-go"
import "go.uber.org/fx"

func main() {
  sprout.New("ExampleApp", "v1.0.0").With(
    example.Module
  ).Run()
}

type Config struct {
  Name string `env:"NAME" envDefault:"Test"`
}

var Module = fx.Module(
  "example",
  fx.Provide(sprout.Config("", &Config{})),
  fx.Provide(sprout.Logger("example")),
  fx.Invoke(func(cfg *Config, logger *logr.Logger) {
    logger.Info("Hello", "name", cfg.Name)
  })
)

Configuration

Sprout uses environment variables to configure the application. Variables are read via env into structs.

sprout.Config will create a function that reads the environment variables, which can be used with fx.Provide.

Example:

type Config struct {
  Host string `env:"HOST" envDefault:"localhost"`
  Port int    `env:"PORT" envDefault:"8080"`
}

var Module = fx.Module(
  "example",
  fx.Provide(sprout.Config("", &Config{})),
  fx.Invoke(func(cfg *Config) {
    // Config is now available for use with Fx
  })
)

Logging

Sprout provides logging via Logr. Sprout will automatically configure logging based on if the application is running in development or production mode. In development mode, logs are pretty printed to stderr. In production mode, logs are formatted as JSON and sent to stderr.

sprout.Logger will create a function that returns a logger, which can be used with fx.Decorate to create a logger for a certain module.

Example:

var Module = fx.Module(
  "example",
  fx.Decorate(sprout.Logger("example")),
  fx.Invoke(func(logger *logr.Logger) {
    // Logger is now available for use with Fx
  })
)

Observability

Sprout integrates with OpenTelemetry and will push data to an OpenTelemetry Collector instance. This decouples the application from the telemetry backend, allowing for easy migration to other backends.

The following environment variables are used to configure the OpenTelemetry integration:

Variable Description Default
OTEL_PROPAGATORS The default propagators to use tracecontext,baggage
OTEL_EXPORTER_OTLP_ENDPOINT The endpoint to send traces, metrics and logs to https://localhost:4317
OTEL_EXPORTER_OTLP_TIMEOUT The timeout for sending data 10s
OTEL_EXPORTER_OTLP_TRACES_ENDPOINT Custom endpoint to send traces to, overrides OTEL_EXPORTER_OTLP_ENDPOINT https://localhost:4317
OTEL_EXPORTER_OTLP_TRACES_TIMEOUT Custom timeout for sending traces 10s
OTEL_EXPORTER_OTLP_METRICS_ENDPOINT Custom endpoint to send metrics to, overrides OTEL_EXPORTER_OTLP_ENDPOINT https://localhost:4317
OTEL_EXPORTER_OTLP_METRICS_TIMEOUT Custom timeout for sending metrics 10s
Tracing

Sprout provides tracing via OpenTelemetry. Sprout will automatically configure tracing based on if the application is running in development or production mode. In development mode, traces are currently not sent anywhere. In production mode, traces are sent to an OpenTelemetry Collector instance.

var Module = fx.Module(
  "example",
  fx.Provide(sprout.Tracer("example")),
  fx.Invoke(func(tracer *trace.Tracer) {
    // Tracer is now available for use with Fx
  })
)
Metrics

Sprout provides metrics via OpenTelemetry. Sprout will automatically configure metrics based on if the application is running in development or production mode. In development mode, metrics are currently not sent anywhere. In production mode, metrics are sent to an OpenTelemetry Collector instance.

var Module = fx.Module(
  "example",
  fx.Provide(sprout.Meter("example")),
  fx.Invoke(func(meter *otel.Meter) {
    // Meter is now available for use with Fx
  })
)

License

Sprout is licensed under the MIT License. See LICENSE for the full license text.

Documentation

Index

Constants

This section is empty.

Variables

This section is empty.

Functions

func AsLivenessCheck

func AsLivenessCheck(f any) any

AsLivenessCheck takes a function that returns a HealthCheck and annotates it to be invoked as a liveness check. Liveness checks will be made available on the health server at the path /healthz.

Example:

fx.Provide(sprout.AsLivenessCheck(func(depsHere...) sprout.HealthCheck {
	return sprout.HealthCheck{
		Name: "example",
		Check: func(ctx context.Context) error {
			return nil
		},
	}
}))

func AsReadinessCheck

func AsReadinessCheck(f any) any

AsReadinessCheck takes a function that returns a HealthCheck and annotates it to be invoked as a readiness check. Readiness checks will be made available on the health server at the path /readyz.

Example:

fx.Provide(sprout.asReadinessCheck(func(depsHere...) sprout.HealthCheck {
	return sprout.HealthCheck{
		Name: "example",
		Check: func(ctx context.Context) error {
			return nil
		},
	}
}))

func BindConfig

func BindConfig(prefix string, value any) any

BindConfig is an on-demand version of Config. It will read configuration from the environment and bind them to the specified struct.

func Config

func Config[T any](prefix string, value T) any

Config will read configuration from the environment and provide the specified type to the application.

Example:

type Config struct {
	Host string `env:"HOST" envDefault:"localhost"`
	Port int    `env:"PORT" envDefault:"8080"`
}

sprout.New("my-service", "1.0.0").With(
	fx.Provide(sprout.Config("HTTP", Config{})),
	fx.Invoke(func(config Config) {
		// ...
	}),
).Run()

func Logger

func Logger(name ...string) any

Logger creates a function that can be used to create a logger with a name. Can be used with fx.Decorate or fx.Provide.

It is mostly used when creating a module, to supply a logger with a name that is specific to the module.

Example:

var Module = fx.Module(
	"example",
	fx.Decorate(sprout.Logger("name", "of", "logger")),
	fx.Invoke(func(logger logr.Logger) {
		// ...
	}),
)

func Meter

func Meter(name string, opts ...metric.MeterOption) any

Meter returns a function that can be used with fx.Provide to make a meter available to the application.

func Tracer

func Tracer(name string, opts ...trace.TracerOption) any

Tracer returns a function that can be used with fx.Provide to make a tracer available to the application.

Types

type HealthCheck

type HealthCheck = health.Check

type Sprout

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

func New

func New(name string, version string) *Sprout

New creates a new Sprout application. The name and version will be used to identify the application in logs, traces and metrics.

func (*Sprout) With

func (s *Sprout) With(options ...fx.Option) *fx.App

With lets you specify Fx options to be used when creating the application.

Directories

Path Synopsis

Jump to

Keyboard shortcuts

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