README.md
1# envconfig
2
3[![Build Status](https://travis-ci.org/kelseyhightower/envconfig.svg)](https://travis-ci.org/kelseyhightower/envconfig)
4
5```Go
6import "github.com/kelseyhightower/envconfig"
7```
8
9## Documentation
10
11See [godoc](http://godoc.org/github.com/kelseyhightower/envconfig)
12
13## Usage
14
15Set some environment variables:
16
17```Bash
18export MYAPP_DEBUG=false
19export MYAPP_PORT=8080
20export MYAPP_USER=Kelsey
21export MYAPP_RATE="0.5"
22export MYAPP_TIMEOUT="3m"
23export MYAPP_USERS="rob,ken,robert"
24export MYAPP_COLORCODES="red:1,green:2,blue:3"
25```
26
27Write some code:
28
29```Go
30package main
31
32import (
33 "fmt"
34 "log"
35 "time"
36
37 "github.com/kelseyhightower/envconfig"
38)
39
40type Specification struct {
41 Debug bool
42 Port int
43 User string
44 Users []string
45 Rate float32
46 Timeout time.Duration
47 ColorCodes map[string]int
48}
49
50func main() {
51 var s Specification
52 err := envconfig.Process("myapp", &s)
53 if err != nil {
54 log.Fatal(err.Error())
55 }
56 format := "Debug: %v\nPort: %d\nUser: %s\nRate: %f\nTimeout: %s\n"
57 _, err = fmt.Printf(format, s.Debug, s.Port, s.User, s.Rate, s.Timeout)
58 if err != nil {
59 log.Fatal(err.Error())
60 }
61
62 fmt.Println("Users:")
63 for _, u := range s.Users {
64 fmt.Printf(" %s\n", u)
65 }
66
67 fmt.Println("Color codes:")
68 for k, v := range s.ColorCodes {
69 fmt.Printf(" %s: %d\n", k, v)
70 }
71}
72```
73
74Results:
75
76```Bash
77Debug: false
78Port: 8080
79User: Kelsey
80Rate: 0.500000
81Timeout: 3m0s
82Users:
83 rob
84 ken
85 robert
86Color codes:
87 red: 1
88 green: 2
89 blue: 3
90```
91
92## Struct Tag Support
93
94Envconfig supports the use of struct tags to specify alternate, default, and required
95environment variables.
96
97For example, consider the following struct:
98
99```Go
100type Specification struct {
101 ManualOverride1 string `envconfig:"manual_override_1"`
102 DefaultVar string `default:"foobar"`
103 RequiredVar string `required:"true"`
104 IgnoredVar string `ignored:"true"`
105 AutoSplitVar string `split_words:"true"`
106 RequiredAndAutoSplitVar string `required:"true" split_words:"true"`
107}
108```
109
110Envconfig has automatic support for CamelCased struct elements when the
111`split_words:"true"` tag is supplied. Without this tag, `AutoSplitVar` above
112would look for an environment variable called `MYAPP_AUTOSPLITVAR`. With the
113setting applied it will look for `MYAPP_AUTO_SPLIT_VAR`. Note that numbers
114will get globbed into the previous word. If the setting does not do the
115right thing, you may use a manual override.
116
117Envconfig will process value for `ManualOverride1` by populating it with the
118value for `MYAPP_MANUAL_OVERRIDE_1`. Without this struct tag, it would have
119instead looked up `MYAPP_MANUALOVERRIDE1`. With the `split_words:"true"` tag
120it would have looked up `MYAPP_MANUAL_OVERRIDE1`.
121
122```Bash
123export MYAPP_MANUAL_OVERRIDE_1="this will be the value"
124
125# export MYAPP_MANUALOVERRIDE1="and this will not"
126```
127
128If envconfig can't find an environment variable value for `MYAPP_DEFAULTVAR`,
129it will populate it with "foobar" as a default value.
130
131If envconfig can't find an environment variable value for `MYAPP_REQUIREDVAR`,
132it will return an error when asked to process the struct. If
133`MYAPP_REQUIREDVAR` is present but empty, envconfig will not return an error.
134
135If envconfig can't find an environment variable in the form `PREFIX_MYVAR`, and there
136is a struct tag defined, it will try to populate your variable with an environment
137variable that directly matches the envconfig tag in your struct definition:
138
139```shell
140export SERVICE_HOST=127.0.0.1
141export MYAPP_DEBUG=true
142```
143```Go
144type Specification struct {
145 ServiceHost string `envconfig:"SERVICE_HOST"`
146 Debug bool
147}
148```
149
150Envconfig won't process a field with the "ignored" tag set to "true", even if a corresponding
151environment variable is set.
152
153## Supported Struct Field Types
154
155envconfig supports these struct field types:
156
157 * string
158 * int8, int16, int32, int64
159 * bool
160 * float32, float64
161 * slices of any supported type
162 * maps (keys and values of any supported type)
163 * [encoding.TextUnmarshaler](https://golang.org/pkg/encoding/#TextUnmarshaler)
164 * [encoding.BinaryUnmarshaler](https://golang.org/pkg/encoding/#BinaryUnmarshaler)
165 * [time.Duration](https://golang.org/pkg/time/#Duration)
166
167Embedded structs using these fields are also supported.
168
169## Custom Decoders
170
171Any field whose type (or pointer-to-type) implements `envconfig.Decoder` can
172control its own deserialization:
173
174```Bash
175export DNS_SERVER=8.8.8.8
176```
177
178```Go
179type IPDecoder net.IP
180
181func (ipd *IPDecoder) Decode(value string) error {
182 *ipd = IPDecoder(net.ParseIP(value))
183 return nil
184}
185
186type DNSConfig struct {
187 Address IPDecoder `envconfig:"DNS_SERVER"`
188}
189```
190
191Also, envconfig will use a `Set(string) error` method like from the
192[flag.Value](https://godoc.org/flag#Value) interface if implemented.
193