Involved Source Filesdecode.go
Package properties provides functions for reading and writing
ISO-8859-1 and UTF-8 encoded .properties files and has
support for recursive property expansion.
Java properties files are ISO-8859-1 encoded and use Unicode
literals for characters outside the ISO character set. Unicode
literals can be used in UTF-8 encoded properties files but
aren't necessary.
To load a single properties file use MustLoadFile():
p := properties.MustLoadFile(filename, properties.UTF8)
To load multiple properties files use MustLoadFiles()
which loads the files in the given order and merges the
result. Missing properties files can be ignored if the
'ignoreMissing' flag is set to true.
Filenames can contain environment variables which are expanded
before loading.
f1 := "/etc/myapp/myapp.conf"
f2 := "/home/${USER}/myapp.conf"
p := MustLoadFiles([]string{f1, f2}, properties.UTF8, true)
All of the different key/value delimiters ' ', ':' and '=' are
supported as well as the comment characters '!' and '#' and
multi-line values.
! this is a comment
# and so is this
# the following expressions are equal
key value
key=value
key:value
key = value
key : value
key = val\
ue
Properties stores all comments preceding a key and provides
GetComments() and SetComments() methods to retrieve and
update them. The convenience functions GetComment() and
SetComment() allow access to the last comment. The
WriteComment() method writes properties files including
the comments and with the keys in the original order.
This can be used for sanitizing properties files.
Property expansion is recursive and circular references
and malformed expressions are not allowed and cause an
error. Expansion of environment variables is supported.
# standard property
key = value
# property expansion: key2 = value
key2 = ${key}
# recursive expansion: key3 = value
key3 = ${key2}
# circular reference (error)
key = ${key}
# malformed expression (error)
key = ${ke
# refers to the users' home dir
home = ${HOME}
# local key takes precedence over env var: u = foo
USER = foo
u = ${USER}
The default property expansion format is ${key} but can be
changed by setting different pre- and postfix values on the
Properties object.
p := properties.NewProperties()
p.Prefix = "#["
p.Postfix = "]#"
Properties provides convenience functions for getting typed
values with default values if the key does not exist or the
type conversion failed.
# Returns true if the value is either "1", "on", "yes" or "true"
# Returns false for every other value and the default value if
# the key does not exist.
v = p.GetBool("key", false)
# Returns the value if the key exists and the format conversion
# was successful. Otherwise, the default value is returned.
v = p.GetInt64("key", 999)
v = p.GetUint64("key", 999)
v = p.GetFloat64("key", 123.0)
v = p.GetString("key", "def")
v = p.GetDuration("key", 999)
As an alternative properties may be applied with the standard
library's flag implementation at any time.
# Standard configuration
v = flag.Int("key", 999, "help message")
flag.Parse()
# Merge p into the flag set
p.MustFlag(flag.CommandLine)
Properties provides several MustXXX() convenience functions
which will terminate the app if an error occurs. The behavior
of the failure is configurable and the default is to call
log.Fatal(err). To have the MustXXX() functions panic instead
of logging the error set a different ErrorHandler before
you use the Properties package.
properties.ErrorHandler = properties.PanicHandler
# Will panic instead of logging an error
p := properties.MustLoadFile("config.properties")
You can also provide your own ErrorHandler function. The only requirement
is that the error handler function must exit after handling the error.
properties.ErrorHandler = func(err error) {
fmt.Println(err)
os.Exit(1)
}
# Will write to stdout and then exit
p := properties.MustLoadFile("config.properties")
Properties can also be loaded into a struct via the `Decode`
method, e.g.
type S struct {
A string `properties:"a,default=foo"`
D time.Duration `properties:"timeout,default=5s"`
E time.Time `properties:"expires,layout=2006-01-02,default=2015-01-01"`
}
See `Decode()` method for the full documentation.
The following documents provide a description of the properties
file format.
http://en.wikipedia.org/wiki/.properties
http://docs.oracle.com/javase/7/docs/api/java/util/Properties.html#load%28java.io.Reader%29
integrate.golex.goload.goparser.goproperties.gorangecheck.go
Code Examples
{
p, err := Load([]byte("key=value\nkey2=${key}"), ISO_8859_1)
if err != nil {
log.Fatal(err)
}
if v, ok := p.Get("key"); ok {
fmt.Println(v)
}
if _, ok := p.Get("does not exist"); !ok {
fmt.Println("invalid key")
}
v := p.GetString("does not exist", "some value")
fmt.Println(v)
fmt.Println("Expanded key/value pairs")
fmt.Println(p)
}
{
buf := []byte("key = ISO-8859-1 value with unicode literal \\u2318 and umlaut \xE4")
p, _ := Load(buf, ISO_8859_1)
v, ok := p.Get("key")
fmt.Println(ok)
fmt.Println(v)
}
{
p, _ := Load([]byte("key = UTF-8 value with unicode character ⌘ and umlaut ä"), UTF8)
v, ok := p.Get("key")
fmt.Println(ok)
fmt.Println(v)
}
{
var input = `
key=1
key2=On
key3=YES
key4=true`
p, _ := Load([]byte(input), ISO_8859_1)
fmt.Println(p.GetBool("key", false))
fmt.Println(p.GetBool("key2", false))
fmt.Println(p.GetBool("key3", false))
fmt.Println(p.GetBool("key4", false))
fmt.Println(p.GetBool("keyX", false))
}
{
p, _ := Load([]byte("key=value"), ISO_8859_1)
v := p.GetString("another key", "default value")
fmt.Println(v)
}
Package-Level Type Names (total 10, in which 5 are exported)
ErrorHandlerFunc defines the type of function which handles failures
of the MustXXX() functions. An error handler function must exit
the application after handling the error.
var ErrorHandler
DisableExpansion configures the property expansion of the
returned property object. When set to true, the property values
will not be expanded and the Property object will not be checked
for invalid expansion expressions.
Encoding determines how the data from files and byte buffers
is interpreted. For URLs the Content-Type header is used
to determine the encoding of the data.
IgnoreMissing configures whether missing files or URLs which return
404 are reported as errors. When set to true, missing files and 404
status codes are not reported as errors.
LoadAll reads the content of multiple URLs or files in the given order into
a Properties struct. If IgnoreMissing is true then a 404 status code or
missing file will not be reported as error. Encoding sets the encoding for
files. For the URLs see LoadURL for the Content-Type header and the
encoding.
Load reads a buffer into a Properties struct.
LoadFile reads a file into a Properties struct.
If IgnoreMissing is true then a missing file will not be
reported as error.
LoadURL reads the content of the URL into a Properties struct.
The encoding is determined via the Content-Type header which
should be set to 'text/plain'. If the 'charset' parameter is
missing, 'iso-8859-1' or 'latin1' the encoding is set to
ISO-8859-1. If the 'charset' parameter is set to 'utf-8' the
encoding is set to UTF-8. A missing content type header is
interpreted as 'text/plain; charset=utf-8'.
(*T) loadBytes(buf []byte, enc Encoding) (*Properties, error)
LogHandlerFunc defines the function prototype for logging errors.
var LogPrintf
A Properties contains the key/value pairs from the properties input.
All values are stored in unexpanded form and are expanded at runtime
DisableExpansion controls the expansion of properties on Get()
and the check for circular references on Set(). When set to
true Properties behaves like a simple key/value store and does
not check for circular references on Get() or on Set().
Postfixstring
Pre-/Postfix for property expansion.
WriteSeparator specifies the separator of key and value while writing the properties.
Stores the comments per key.
Stores the keys in order of appearance.
Stores the key/value pairs
ClearComments removes the comments for all keys.
Decode assigns property values to exported fields of a struct.
Decode traverses v recursively and returns an error if a value cannot be
converted to the field type or a required value is missing for a field.
The following type dependent decodings are used:
String, boolean, numeric fields have the value of the property key assigned.
The property key name is the name of the field. A different key and a default
value can be set in the field's tag. Fields without default value are
required. If the value cannot be converted to the field type an error is
returned.
time.Duration fields have the result of time.ParseDuration() assigned.
time.Time fields have the vaule of time.Parse() assigned. The default layout
is time.RFC3339 but can be set in the field's tag.
Arrays and slices of string, boolean, numeric, time.Duration and time.Time
fields have the value interpreted as a comma separated list of values. The
individual values are trimmed of whitespace and empty values are ignored. A
default value can be provided as a semicolon separated list in the field's
tag.
Struct fields are decoded recursively using the field name plus "." as
prefix. The prefix (without dot) can be overridden in the field's tag.
Default values are not supported in the field's tag. Specify them on the
fields of the inner struct instead.
Map fields must have a key of type string and are decoded recursively by
using the field's name plus ".' as prefix and the next element of the key
name as map key. The prefix (without dot) can be overridden in the field's
tag. Default values are not supported.
Examples:
// Field is ignored.
Field int `properties:"-"`
// Field is assigned value of 'Field'.
Field int
// Field is assigned value of 'myName'.
Field int `properties:"myName"`
// Field is assigned value of key 'myName' and has a default
// value 15 if the key does not exist.
Field int `properties:"myName,default=15"`
// Field is assigned value of key 'Field' and has a default
// value 15 if the key does not exist.
Field int `properties:",default=15"`
// Field is assigned value of key 'date' and the date
// is in format 2006-01-02
Field time.Time `properties:"date,layout=2006-01-02"`
// Field is assigned the non-empty and whitespace trimmed
// values of key 'Field' split by commas.
Field []string
// Field is assigned the non-empty and whitespace trimmed
// values of key 'Field' split by commas and has a default
// value ["a", "b", "c"] if the key does not exist.
Field []string `properties:",default=a;b;c"`
// Field is decoded recursively with "Field." as key prefix.
Field SomeStruct
// Field is decoded recursively with "myName." as key prefix.
Field SomeStruct `properties:"myName"`
// Field is decoded recursively with "Field." as key prefix
// and the next dotted element of the key as map key.
Field map[string]string
// Field is decoded recursively with "myName." as key prefix
// and the next dotted element of the key as map key.
Field map[string]string `properties:"myName"`
Delete removes the key and its comments.
Filter returns a new properties object which contains all properties
for which the key matches the pattern.
FilterFunc returns a copy of the properties which includes the values which passed all filters.
FilterPrefix returns a new properties object with a subset of all keys
with the given prefix.
FilterRegexp returns a new properties object which contains all properties
for which the key matches the regular expression.
FilterStripPrefix returns a new properties object with a subset of all keys
with the given prefix and the prefix removed from the keys.
Get returns the expanded value for the given key if exists.
Otherwise, ok is false.
GetBool checks if the expanded value is one of '1', 'yes',
'true' or 'on' if the key exists. The comparison is case-insensitive.
If the key does not exist the default value is returned.
GetComment returns the last comment before the given key or an empty string.
GetComments returns all comments that appeared before the given key or nil.
GetDuration parses the expanded value as an time.Duration (in ns) if the
key exists. If key does not exist or the value cannot be parsed the default
value is returned. In almost all cases you want to use GetParsedDuration().
GetFloat64 parses the expanded value as a float64 if the key exists.
If key does not exist or the value cannot be parsed the default
value is returned.
GetInt parses the expanded value as an int if the key exists.
If key does not exist or the value cannot be parsed the default
value is returned. If the value does not fit into an int the
function panics with an out of range error.
GetInt64 parses the expanded value as an int64 if the key exists.
If key does not exist or the value cannot be parsed the default
value is returned.
GetParsedDuration parses the expanded value with time.ParseDuration() if the key exists.
If key does not exist or the value cannot be parsed the default
value is returned.
GetString returns the expanded value for the given key if exists or
the default value otherwise.
GetUint parses the expanded value as an uint if the key exists.
If key does not exist or the value cannot be parsed the default
value is returned. If the value does not fit into an int the
function panics with an out of range error.
GetUint64 parses the expanded value as an uint64 if the key exists.
If key does not exist or the value cannot be parsed the default
value is returned.
Keys returns all keys in the same order as in the input.
Len returns the number of keys.
Load reads a buffer into the given Properties struct.
Map returns a copy of the properties as a map.
Merge merges properties, comments and keys from other *Properties into p
MustFlag sets flags that are skipped by dst.Parse when p contains
the respective key for flag.Flag.Name.
It's use is recommended with command line arguments as in:
flag.Parse()
p.MustFlag(flag.CommandLine)
MustGet returns the expanded value for the given key if exists.
Otherwise, it panics.
MustGetBool checks if the expanded value is one of '1', 'yes',
'true' or 'on' if the key exists. The comparison is case-insensitive.
If the key does not exist the function panics.
MustGetDuration parses the expanded value as an time.Duration (in ns) if
the key exists. If key does not exist or the value cannot be parsed the
function panics. In almost all cases you want to use MustGetParsedDuration().
MustGetFloat64 parses the expanded value as a float64 if the key exists.
If key does not exist or the value cannot be parsed the function panics.
MustGetInt parses the expanded value as an int if the key exists.
If key does not exist or the value cannot be parsed the function panics.
If the value does not fit into an int the function panics with
an out of range error.
MustGetInt64 parses the expanded value as an int if the key exists.
If key does not exist or the value cannot be parsed the function panics.
MustGetParsedDuration parses the expanded value with time.ParseDuration() if the key exists.
If key does not exist or the value cannot be parsed the function panics.
MustGetString returns the expanded value for the given key if exists or
panics otherwise.
MustGetUint parses the expanded value as an int if the key exists.
If key does not exist or the value cannot be parsed the function panics.
If the value does not fit into an int the function panics with
an out of range error.
MustGetUint64 parses the expanded value as an int if the key exists.
If key does not exist or the value cannot be parsed the function panics.
MustSet sets the property key to the corresponding value.
If a value for key existed before then ok is true and prev
contains the previous value. An empty key is silently ignored.
Set sets the property key to the corresponding value.
If a value for key existed before then ok is true and prev
contains the previous value. If the value contains a
circular reference or a malformed expression then
an error is returned.
An empty key is silently ignored.
SetComment sets the comment for the key.
SetComments sets the comments for the key. If the comments are nil then
all comments for this key are deleted.
SetValue sets property key to the default string value
as defined by fmt.Sprintf("%v").
Sort sorts the properties keys in alphabetical order.
This is helpfully before writing the properties.
String returns a string of all expanded 'key = value' pairs.
Write writes all unexpanded 'key = value' pairs to the given writer.
Write returns the number of bytes written and any write error encountered.
WriteComment writes all unexpanced 'key = value' pairs to the given writer.
If prefix is not empty then comments are written with a blank line and the
given prefix. The prefix should be either "# " or "! " to be compatible with
the properties file format. Otherwise, the properties parser will not be
able to read the file back in. It returns the number of bytes written and
any write error encountered.
check expands all values and returns an error if a circular reference or
a malformed expression was found.
(*T) expand(key, input string) (string, error)(*T) getBool(key string) (value bool, err error)(*T) getFloat64(key string) (value float64, err error)(*T) getInt64(key string) (value int64, err error)(*T) getUint64(key string) (value uint64, err error)
*T : fmt.Stringer
*T : context.stringer
*T : os/signal.stringer
*T : runtime.stringer
func Load(buf []byte, enc Encoding) (*Properties, error)
func LoadAll(names []string, enc Encoding, ignoreMissing bool) (*Properties, error)
func LoadFile(filename string, enc Encoding) (*Properties, error)
func LoadFiles(filenames []string, enc Encoding, ignoreMissing bool) (*Properties, error)
func LoadMap(m map[string]string) *Properties
func LoadString(s string) (*Properties, error)
func LoadURL(url string) (*Properties, error)
func LoadURLs(urls []string, ignoreMissing bool) (*Properties, error)
func MustLoadAll(names []string, enc Encoding, ignoreMissing bool) *Properties
func MustLoadFile(filename string, enc Encoding) *Properties
func MustLoadFiles(filenames []string, enc Encoding, ignoreMissing bool) *Properties
func MustLoadString(s string) *Properties
func MustLoadURL(url string) *Properties
func MustLoadURLs(urls []string, ignoreMissing bool) *Properties
func NewProperties() *Properties
func (*Loader).LoadAll(names []string) (*Properties, error)
func (*Loader).LoadBytes(buf []byte) (*Properties, error)
func (*Loader).LoadFile(filename string) (*Properties, error)
func (*Loader).LoadURL(url string) (*Properties, error)
func (*Properties).Filter(pattern string) (*Properties, error)
func (*Properties).FilterFunc(filters ...func(k, v string) bool) *Properties
func (*Properties).FilterPrefix(prefix string) *Properties
func (*Properties).FilterRegexp(re *regexp.Regexp) *Properties
func (*Properties).FilterStripPrefix(prefix string) *Properties
func must(p *Properties, err error) *Properties
func parse(input string) (properties *Properties, err error)
func (*Loader).loadBytes(buf []byte, enc Encoding) (*Properties, error)
func (*Properties).Merge(other *Properties)
func dec(p *Properties, key string, def *string, opts map[string]string, v reflect.Value) error
func must(p *Properties, err error) *Properties
item represents a token or text string returned from the scanner.
// The starting position, in bytes, of this item in the input string.
// The type of this item.
// The value of this item.
( T) String() string
T : fmt.Stringer
T : context.stringer
T : os/signal.stringer
T : runtime.stringer
lexer holds the state of the scanner.
// the string being scanned
// channel of scanned items
// position of most recent item returned by nextItem
// current position in the input
// scanned runes for this item
// start position of this item
// the next lexing function to enter
// width of last rune read from input
accept consumes the next rune if it's from the valid set.
acceptRun consumes a run of runes from the valid set.
acceptRunUntil consumes a run of runes up to a terminator.
appends the rune to the current value
backup steps back one rune. Can only be called once per call of next.
emit passes an item back to the client.
errorf returns an error token and terminates the scan by passing
back a nil pointer that will be the next state, terminating l.nextItem.
ignore skips over the pending input before this point.
hasText returns true if the current parsed text is not empty.
lineNumber reports which line we're on, based on the position of
the previous item returned by nextItem. Doing it this way
means we don't have to worry about peek double counting.
next returns the next rune in the input.
nextItem returns the next item from the input.
peek returns but does not consume the next rune in the input.
run runs the state machine for the lexer.
scanEscapeSequence scans either one of the escaped characters
or a unicode literal. We expect to be after the escape character.
scans a unicode literal in the form \uXXXX. We expect to be after the \u.
func lex(input string) *lexer
func lexBeforeKey(l *lexer) stateFn
func lexBeforeValue(l *lexer) stateFn
func lexComment(l *lexer) stateFn
func lexKey(l *lexer) stateFn
func lexValue(l *lexer) stateFn
Package-Level Functions (total 59, in which 17 are exported)
Load reads a buffer into a Properties struct.
LoadAll reads the content of multiple URLs or files in the given order into a
Properties struct. If 'ignoreMissing' is true then a 404 status code or missing file will
not be reported as error. Encoding sets the encoding for files. For the URLs please see
LoadURL for the Content-Type header and the encoding.
LoadFile reads a file into a Properties struct.
LoadFiles reads multiple files in the given order into
a Properties struct. If 'ignoreMissing' is true then
non-existent files will not be reported as error.
LoadMap creates a new Properties struct from a string map.
LoadString reads an UTF8 string into a properties struct.
LoadURL reads the content of the URL into a Properties struct.
See Loader#LoadURL for details.
LoadURLs reads the content of multiple URLs in the given order into a
Properties struct. If IgnoreMissing is true then a 404 status code will
not be reported as error. See Loader#LoadURL for the Content-Type header
and the encoding.
LogFatalHandler handles the error by logging a fatal error and exiting.
MustLoadAll reads the content of multiple URLs or files in the given order into a
Properties struct. If 'ignoreMissing' is true then a 404 status code or missing file will
not be reported as error. Encoding sets the encoding for files. For the URLs please see
LoadURL for the Content-Type header and the encoding. It panics on error.
MustLoadFile reads a file into a Properties struct and
panics on error.
MustLoadFiles reads multiple files in the given order into
a Properties struct and panics on error. If 'ignoreMissing'
is true then non-existent files will not be reported as error.
MustLoadString reads an UTF8 string into a Properties struct and
panics on error.
MustLoadURL reads the content of a URL into a Properties struct and
panics on error.
MustLoadURLs reads the content of multiple URLs in the given order into a
Properties struct and panics on error. If 'ignoreMissing' is true then a 404
status code will not be reported as error.
NewProperties creates a new Properties struct with the default
configuration for "${key}" expressions.
PanicHandler handles the error by panicking.
atUnicodeLiteral reports whether we are at a unicode literal.
The escape character has already been consumed.
Interprets a byte buffer either as an ISO-8859-1 or UTF-8 encoded string.
For ISO-8859-1 we can convert each byte straight into a rune since the
first 256 unicode code points cover ISO-8859-1.
expand recursively expands expressions of '(prefix)key(postfix)' to their corresponding values.
The function keeps track of the keys that were already expanded and stops if it
detects a circular reference or a malformed expression of the form '(prefix)key'.
expandName expands ${ENV_VAR} expressions in a name.
If the environment variable does not exist then it will be replaced
with an empty string. Malformed expressions like "${ENV_VAR" will
be reported as error.
intRangeCheck checks if the value fits into the int type and
panics if it does not.
utf8Default is a private placeholder for the zero value of Encoding to
ensure that it has the correct meaning. UTF8 is the default encoding but
was assigned a non-zero value which cannot be changed without breaking
existing code. Clients should continue to use the public constants.
permitted whitespace characters space, FF and TAB
The pages are generated with Goldsv0.3.2. (GOOS=linux GOARCH=amd64)
Golds is a Go 101 project developed by Tapir Liu.
PR and bug reports are welcome and can be submitted to the issue list.
Please follow @Go100and1 (reachable from the left QR code) to get the latest news of Golds.