github.com/astaxie/beego@v1.12.3/config/xml/xml.go (about) 1 // Copyright 2014 beego Author. All Rights Reserved. 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); 4 // you may not use this file except in compliance with the License. 5 // You may obtain a copy of the License at 6 // 7 // http://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 // See the License for the specific language governing permissions and 13 // limitations under the License. 14 15 // Package xml for config provider. 16 // 17 // depend on github.com/beego/x2j. 18 // 19 // go install github.com/beego/x2j. 20 // 21 // Usage: 22 // import( 23 // _ "github.com/astaxie/beego/config/xml" 24 // "github.com/astaxie/beego/config" 25 // ) 26 // 27 // cnf, err := config.NewConfig("xml", "config.xml") 28 // 29 //More docs http://beego.me/docs/module/config.md 30 package xml 31 32 import ( 33 "encoding/xml" 34 "errors" 35 "fmt" 36 "io/ioutil" 37 "os" 38 "strconv" 39 "strings" 40 "sync" 41 42 "github.com/astaxie/beego/config" 43 "github.com/beego/x2j" 44 ) 45 46 // Config is a xml config parser and implements Config interface. 47 // xml configurations should be included in <config></config> tag. 48 // only support key/value pair as <key>value</key> as each item. 49 type Config struct{} 50 51 // Parse returns a ConfigContainer with parsed xml config map. 52 func (xc *Config) Parse(filename string) (config.Configer, error) { 53 context, err := ioutil.ReadFile(filename) 54 if err != nil { 55 return nil, err 56 } 57 58 return xc.ParseData(context) 59 } 60 61 // ParseData xml data 62 func (xc *Config) ParseData(data []byte) (config.Configer, error) { 63 x := &ConfigContainer{data: make(map[string]interface{})} 64 65 d, err := x2j.DocToMap(string(data)) 66 if err != nil { 67 return nil, err 68 } 69 70 x.data = config.ExpandValueEnvForMap(d["config"].(map[string]interface{})) 71 72 return x, nil 73 } 74 75 // ConfigContainer A Config represents the xml configuration. 76 type ConfigContainer struct { 77 data map[string]interface{} 78 sync.Mutex 79 } 80 81 // Bool returns the boolean value for a given key. 82 func (c *ConfigContainer) Bool(key string) (bool, error) { 83 if v := c.data[key]; v != nil { 84 return config.ParseBool(v) 85 } 86 return false, fmt.Errorf("not exist key: %q", key) 87 } 88 89 // DefaultBool return the bool value if has no error 90 // otherwise return the defaultval 91 func (c *ConfigContainer) DefaultBool(key string, defaultval bool) bool { 92 v, err := c.Bool(key) 93 if err != nil { 94 return defaultval 95 } 96 return v 97 } 98 99 // Int returns the integer value for a given key. 100 func (c *ConfigContainer) Int(key string) (int, error) { 101 return strconv.Atoi(c.data[key].(string)) 102 } 103 104 // DefaultInt returns the integer value for a given key. 105 // if err != nil return defaultval 106 func (c *ConfigContainer) DefaultInt(key string, defaultval int) int { 107 v, err := c.Int(key) 108 if err != nil { 109 return defaultval 110 } 111 return v 112 } 113 114 // Int64 returns the int64 value for a given key. 115 func (c *ConfigContainer) Int64(key string) (int64, error) { 116 return strconv.ParseInt(c.data[key].(string), 10, 64) 117 } 118 119 // DefaultInt64 returns the int64 value for a given key. 120 // if err != nil return defaultval 121 func (c *ConfigContainer) DefaultInt64(key string, defaultval int64) int64 { 122 v, err := c.Int64(key) 123 if err != nil { 124 return defaultval 125 } 126 return v 127 128 } 129 130 // Float returns the float value for a given key. 131 func (c *ConfigContainer) Float(key string) (float64, error) { 132 return strconv.ParseFloat(c.data[key].(string), 64) 133 } 134 135 // DefaultFloat returns the float64 value for a given key. 136 // if err != nil return defaultval 137 func (c *ConfigContainer) DefaultFloat(key string, defaultval float64) float64 { 138 v, err := c.Float(key) 139 if err != nil { 140 return defaultval 141 } 142 return v 143 } 144 145 // String returns the string value for a given key. 146 func (c *ConfigContainer) String(key string) string { 147 if v, ok := c.data[key].(string); ok { 148 return v 149 } 150 return "" 151 } 152 153 // DefaultString returns the string value for a given key. 154 // if err != nil return defaultval 155 func (c *ConfigContainer) DefaultString(key string, defaultval string) string { 156 v := c.String(key) 157 if v == "" { 158 return defaultval 159 } 160 return v 161 } 162 163 // Strings returns the []string value for a given key. 164 func (c *ConfigContainer) Strings(key string) []string { 165 v := c.String(key) 166 if v == "" { 167 return nil 168 } 169 return strings.Split(v, ";") 170 } 171 172 // DefaultStrings returns the []string value for a given key. 173 // if err != nil return defaultval 174 func (c *ConfigContainer) DefaultStrings(key string, defaultval []string) []string { 175 v := c.Strings(key) 176 if v == nil { 177 return defaultval 178 } 179 return v 180 } 181 182 // GetSection returns map for the given section 183 func (c *ConfigContainer) GetSection(section string) (map[string]string, error) { 184 if v, ok := c.data[section].(map[string]interface{}); ok { 185 mapstr := make(map[string]string) 186 for k, val := range v { 187 mapstr[k] = config.ToString(val) 188 } 189 return mapstr, nil 190 } 191 return nil, fmt.Errorf("section '%s' not found", section) 192 } 193 194 // SaveConfigFile save the config into file 195 func (c *ConfigContainer) SaveConfigFile(filename string) (err error) { 196 // Write configuration file by filename. 197 f, err := os.Create(filename) 198 if err != nil { 199 return err 200 } 201 defer f.Close() 202 b, err := xml.MarshalIndent(c.data, " ", " ") 203 if err != nil { 204 return err 205 } 206 _, err = f.Write(b) 207 return err 208 } 209 210 // Set writes a new value for key. 211 func (c *ConfigContainer) Set(key, val string) error { 212 c.Lock() 213 defer c.Unlock() 214 c.data[key] = val 215 return nil 216 } 217 218 // DIY returns the raw value by a given key. 219 func (c *ConfigContainer) DIY(key string) (v interface{}, err error) { 220 if v, ok := c.data[key]; ok { 221 return v, nil 222 } 223 return nil, errors.New("not exist key") 224 } 225 226 func init() { 227 config.Register("xml", &Config{}) 228 }