conf/get.go

190 lines
5.0 KiB
Go
Raw Normal View History

2010-03-28 22:44:26 +00:00
package conf
import (
"os"
"strings"
"strconv"
)
// GetSections returns the list of sections in the configuration.
// (The default section always exists.)
func (c *ConfigFile) GetSections() (sections []string) {
2010-04-08 17:39:05 +00:00
sections = make([]string, len(c.data))
2010-03-28 22:44:26 +00:00
2010-04-08 17:39:05 +00:00
i := 0
2010-03-28 22:44:26 +00:00
for s, _ := range c.data {
2010-04-08 17:39:05 +00:00
sections[i] = s
i++
2010-03-28 22:44:26 +00:00
}
2010-04-08 17:39:05 +00:00
return sections
2010-03-28 22:44:26 +00:00
}
// HasSection checks if the configuration has the given section.
// (The default section always exists.)
func (c *ConfigFile) HasSection(section string) bool {
2010-04-08 17:39:05 +00:00
if section == "" {
section = "default"
}
_, ok := c.data[strings.ToLower(section)]
2010-03-28 22:44:26 +00:00
2010-04-08 17:39:05 +00:00
return ok
2010-03-28 22:44:26 +00:00
}
// GetOptions returns the list of options available in the given section.
// It returns an error if the section does not exist and an empty list if the section is empty.
// Options within the default section are also included.
func (c *ConfigFile) GetOptions(section string) (options []string, err os.Error) {
2010-04-08 17:39:05 +00:00
if section == "" {
section = "default"
}
section = strings.ToLower(section)
2010-03-28 22:44:26 +00:00
if _, ok := c.data[section]; !ok {
return nil, GetError{SectionNotFound, "", "", section, ""}
}
2010-04-08 17:39:05 +00:00
options = make([]string, len(c.data[DefaultSection])+len(c.data[section]))
i := 0
2010-03-28 22:44:26 +00:00
for s, _ := range c.data[DefaultSection] {
2010-04-08 17:39:05 +00:00
options[i] = s
i++
2010-03-28 22:44:26 +00:00
}
for s, _ := range c.data[section] {
2010-04-08 17:39:05 +00:00
options[i] = s
i++
2010-03-28 22:44:26 +00:00
}
2010-04-08 17:39:05 +00:00
return options, nil
2010-03-28 22:44:26 +00:00
}
// HasOption checks if the configuration has the given option in the section.
// It returns false if either the option or section do not exist.
func (c *ConfigFile) HasOption(section string, option string) bool {
2010-04-08 17:39:05 +00:00
if section == "" {
section = "default"
}
section = strings.ToLower(section)
option = strings.ToLower(option)
2010-03-28 22:44:26 +00:00
if _, ok := c.data[section]; !ok {
return false
}
2010-04-08 17:39:05 +00:00
_, okd := c.data[DefaultSection][option]
_, oknd := c.data[section][option]
2010-03-28 22:44:26 +00:00
2010-04-08 17:39:05 +00:00
return okd || oknd
2010-03-28 22:44:26 +00:00
}
// GetRawString gets the (raw) string value for the given option in the section.
// The raw string value is not subjected to unfolding, which was illustrated in the beginning of this documentation.
// It returns an error if either the section or the option do not exist.
func (c *ConfigFile) GetRawString(section string, option string) (value string, err os.Error) {
2010-04-08 17:39:05 +00:00
if section == "" {
section = "default"
}
section = strings.ToLower(section)
option = strings.ToLower(option)
2010-03-28 22:44:26 +00:00
if _, ok := c.data[section]; ok {
if value, ok = c.data[section][option]; ok {
return value, nil
}
2010-04-08 17:39:05 +00:00
return "", GetError{OptionNotFound, "", "", section, option}
2010-03-28 22:44:26 +00:00
}
2010-04-08 17:39:05 +00:00
return "", GetError{SectionNotFound, "", "", section, option}
2010-03-28 22:44:26 +00:00
}
// GetString gets the string value for the given option in the section.
// If the value needs to be unfolded (see e.g. %(host)s example in the beginning of this documentation),
// then GetString does this unfolding automatically, up to DepthValues number of iterations.
// It returns an error if either the section or the option do not exist, or the unfolding cycled.
func (c *ConfigFile) GetString(section string, option string) (value string, err os.Error) {
2010-04-08 17:39:05 +00:00
value, err = c.GetRawString(section, option)
2010-03-28 22:44:26 +00:00
if err != nil {
return "", err
}
2010-04-08 17:39:05 +00:00
section = strings.ToLower(section)
2010-03-28 22:44:26 +00:00
2010-04-08 17:39:05 +00:00
var i int
2010-03-28 22:44:26 +00:00
2010-04-08 17:39:05 +00:00
for i = 0; i < DepthValues; i++ { // keep a sane depth
2010-08-22 10:17:36 +00:00
vr := varRegExp.FindString(value)
2010-03-28 22:44:26 +00:00
if len(vr) == 0 {
break
}
2010-04-08 17:39:05 +00:00
noption := value[vr[2]:vr[3]]
noption = strings.ToLower(noption)
2010-03-28 22:44:26 +00:00
2010-04-08 17:39:05 +00:00
nvalue, _ := c.data[DefaultSection][noption] // search variable in default section
2010-03-28 22:44:26 +00:00
if _, ok := c.data[section][noption]; ok {
nvalue = c.data[section][noption]
}
if nvalue == "" {
return "", GetError{OptionNotFound, "", "", section, option}
}
// substitute by new value and take off leading '%(' and trailing ')s'
2010-04-08 17:39:05 +00:00
value = value[0:vr[2]-2] + nvalue + value[vr[3]+2:]
2010-03-28 22:44:26 +00:00
}
if i == DepthValues {
return "", GetError{MaxDepthReached, "", "", section, option}
}
2010-04-08 17:39:05 +00:00
return value, nil
2010-03-28 22:44:26 +00:00
}
// GetInt has the same behaviour as GetString but converts the response to int.
func (c *ConfigFile) GetInt(section string, option string) (value int, err os.Error) {
2010-04-08 17:39:05 +00:00
sv, err := c.GetString(section, option)
2010-03-28 22:44:26 +00:00
if err == nil {
value, err = strconv.Atoi(sv)
if err != nil {
err = GetError{CouldNotParse, "int", sv, section, option}
}
}
2010-04-08 17:39:05 +00:00
return value, err
2010-03-28 22:44:26 +00:00
}
// GetFloat has the same behaviour as GetString but converts the response to float.
func (c *ConfigFile) GetFloat64(section string, option string) (value float64, err os.Error) {
2010-04-08 17:39:05 +00:00
sv, err := c.GetString(section, option)
2010-03-28 22:44:26 +00:00
if err == nil {
value, err = strconv.Atof64(sv)
2010-03-28 22:44:26 +00:00
if err != nil {
err = GetError{CouldNotParse, "float64", sv, section, option}
2010-03-28 22:44:26 +00:00
}
}
2010-04-08 17:39:05 +00:00
return value, err
2010-03-28 22:44:26 +00:00
}
// GetBool has the same behaviour as GetString but converts the response to bool.
// See constant BoolStrings for string values converted to bool.
func (c *ConfigFile) GetBool(section string, option string) (value bool, err os.Error) {
2010-04-08 17:39:05 +00:00
sv, err := c.GetString(section, option)
2010-03-28 22:44:26 +00:00
if err != nil {
return false, err
}
2010-04-08 17:39:05 +00:00
value, ok := BoolStrings[strings.ToLower(sv)]
2010-03-28 22:44:26 +00:00
if !ok {
return false, GetError{CouldNotParse, "bool", sv, section, option}
}
2010-04-08 17:39:05 +00:00
return value, nil
2010-03-28 22:44:26 +00:00
}