github.com/smugmug/godynamo@v0.0.0-20151122084750-7913028f6623/conf_file/conf_file.go (about) 1 // Manages reading the conf file into the global var as described in the `conf` package. 2 package conf_file 3 4 import ( 5 "encoding/json" 6 "errors" 7 "fmt" 8 "github.com/smugmug/godynamo/aws_const" 9 "github.com/smugmug/godynamo/conf" 10 "io/ioutil" 11 "log" 12 "net" 13 "net/url" 14 "os" 15 "path/filepath" 16 "strconv" 17 ) 18 19 // ReadConfFile will attempt to read in the conf file path passed as a parameter 20 // and convert it into a conf.AWS_Conf struct pointer. You can use this to read in 21 // a conf for a file of your own choosing. 22 func ReadConfFile(conf_file string) (*conf.AWS_Conf, error) { 23 conf_bytes, conf_err := ioutil.ReadFile(conf_file) 24 if conf_err != nil { 25 e := fmt.Sprintf("conf_file.ReadConfFile: cannot read conf file %s", conf_file) 26 return nil, errors.New(e) 27 } 28 29 var cf conf.SDK_conf_file 30 um_err := json.Unmarshal(conf_bytes, &cf) 31 if um_err != nil { 32 e := fmt.Sprintf("conf_file.ReadConfFile: cannot unmarshal %s. json err %s", 33 conf_file, um_err.Error()) 34 return nil, errors.New(e) 35 } 36 37 var c conf.AWS_Conf 38 // make sure the dynamo endpoint is available 39 addrs, addrs_err := net.LookupIP(cf.Services.Dynamo_db.Host) 40 if addrs_err != nil { 41 e := fmt.Sprintf("conf_file.ReadConfFile: cannot lookup hostname %s", 42 cf.Services.Dynamo_db.Host) 43 return nil, errors.New(e) 44 } 45 dynamo_ip := (addrs[0]).String() 46 47 // assign the values to our globally-available c struct instance 48 c.Auth.AccessKey = cf.Services.Default_settings.Params.Access_key_id 49 c.Auth.Secret = cf.Services.Default_settings.Params.Secret_access_key 50 c.UseSysLog = cf.Services.Default_settings.Params.Use_sys_log 51 c.Network.DynamoDB.Host = cf.Services.Dynamo_db.Host 52 c.Network.DynamoDB.IP = dynamo_ip 53 c.Network.DynamoDB.Zone = cf.Services.Dynamo_db.Zone 54 scheme := "http" 55 port := aws_const.PORT // already a string 56 if cf.Services.Dynamo_db.Scheme != "" { 57 scheme = cf.Services.Dynamo_db.Scheme 58 } 59 if cf.Services.Dynamo_db.Port != 0 { 60 port = strconv.Itoa(cf.Services.Dynamo_db.Port) 61 } 62 c.Network.DynamoDB.Port = port 63 c.Network.DynamoDB.Scheme = scheme 64 c.Network.DynamoDB.URL = scheme + "://" + c.Network.DynamoDB.Host + 65 ":" + port 66 _, url_err := url.Parse(c.Network.DynamoDB.URL) 67 if url_err != nil { 68 return nil, errors.New("conf_file.ReadConfFile: conf.Network.DynamoDB.URL malformed") 69 } 70 71 // If set to true, programs that are written with godynamo may 72 // opt to launch the keepalive goroutine to keep conns open. 73 c.Network.DynamoDB.KeepAlive = cf.Services.Dynamo_db.KeepAlive 74 75 // read in flags for IAM support 76 if cf.Services.Dynamo_db.IAM.Use_iam == true { 77 // caller will have to check the RoleProvider to dispatch further Roles features 78 c.IAM.RoleProvider = cf.Services.Dynamo_db.IAM.Role_provider 79 c.IAM.File.BaseDir = cf.Services.Dynamo_db.IAM.Base_dir 80 c.IAM.File.AccessKey = cf.Services.Dynamo_db.IAM.Access_key 81 c.IAM.File.Secret = cf.Services.Dynamo_db.IAM.Secret_key 82 c.IAM.File.Token = cf.Services.Dynamo_db.IAM.Token 83 if cf.Services.Dynamo_db.IAM.Watch == true { 84 c.IAM.Watch = true 85 } else { 86 c.IAM.Watch = false 87 } 88 c.UseIAM = true 89 } 90 c.Initialized = true 91 return &c, nil 92 } 93 94 // ReadDefaultConfs will check the preset standard locations for conf files and 95 // attempt to create a conf.AWS_Conf struct pointer with the first one found. 96 // The order of precedence is: 97 // 1. file in $GODYNAMO_CONF_FILE if you wish to set it. 98 // 2. $HOME/.aws-config.json 99 // 3. /etc/aws-config.json (note lack of prefix '.') 100 // This function can be useful when moving back and forth between environments 101 // where you wish to have a conf file in $HOME that precludes one in /etc. 102 func ReadDefaultConfs() (*conf.AWS_Conf, error) { 103 local_conf := os.Getenv("HOME") + string(filepath.Separator) + "." + conf.CONF_NAME 104 etc_conf := string(filepath.Separator) + "etc" + string(filepath.Separator) + conf.CONF_NAME 105 conf_files := make([]string, 0) 106 // assumes that if set, this is a fully-qualified file path 107 const env_conf = "GODYNAMO_CONF_FILE" 108 // assumes that if set, this is a fully-qualified file path 109 if os.Getenv(env_conf) != "" { 110 conf_files = append(conf_files, os.Getenv(env_conf)) 111 } 112 conf_files = append(conf_files, local_conf) 113 conf_files = append(conf_files, etc_conf) 114 115 CONF_LOCATIONS: 116 for _, conf_file := range conf_files { 117 c, c_err := ReadConfFile(conf_file) 118 if c_err != nil { 119 e := fmt.Sprintf("conf_file.ReadDefaultConfs: problem with conf %s: %s", 120 conf_file, c_err.Error()) 121 log.Printf(e) 122 continue CONF_LOCATIONS 123 } else { 124 return c, nil 125 } 126 } 127 e := fmt.Sprintf("conf_File.ReadDefaultConfs: no conf struct found in %v", conf_files) 128 return nil, errors.New(e) 129 } 130 131 // ReadGlobal will take a configuration and assign it to the global conf.Vals struct instance. 132 func ReadGlobal() { 133 local_conf, conf_err := ReadDefaultConfs() 134 if conf_err != nil { 135 e := fmt.Sprintf("cannot locate a valid global configuration: %s", conf_err.Error()) 136 panic(e) 137 } 138 conf.Vals.Copy(local_conf) 139 } 140 141 // Read assigns a configuration to the global conf.Vals struct instance. 142 // This function exists as backwards compatibility only. Do not use it in new code, 143 // instead use ReadLocal. 144 func Read() { 145 ReadGlobal() 146 }