diff options
| author | Bobby <[email protected]> | 2026-03-29 22:52:46 +0530 |
|---|---|---|
| committer | Bobby <[email protected]> | 2026-03-29 22:52:46 +0530 |
| commit | 9eb9b7f4bd552a641235764f66483e1f940fcfd9 (patch) | |
| tree | da520b923b5e6758d5457b6233dd6671fc640914 /nexus/utils/env | |
| parent | 65a143a0871c35989b7c7ea6723d39a0585c089e (diff) | |
| download | echoes-of-vaelun-main.tar.xz echoes-of-vaelun-main.zip | |
Diffstat (limited to 'nexus/utils/env')
| -rw-r--r-- | nexus/utils/env/defaults.go | 6 | ||||
| -rw-r--r-- | nexus/utils/env/extract.go | 33 | ||||
| -rw-r--r-- | nexus/utils/env/getenv.go | 75 | ||||
| -rw-r--r-- | nexus/utils/env/messages.go | 5 | ||||
| -rw-r--r-- | nexus/utils/env/parse.go | 27 | ||||
| -rw-r--r-- | nexus/utils/env/setenv.go | 62 |
6 files changed, 208 insertions, 0 deletions
diff --git a/nexus/utils/env/defaults.go b/nexus/utils/env/defaults.go new file mode 100644 index 0000000..70c3b41 --- /dev/null +++ b/nexus/utils/env/defaults.go @@ -0,0 +1,6 @@ +package env
+
+const (
+ keyEnv = "env"
+ keyDefault = "default"
+)
diff --git a/nexus/utils/env/extract.go b/nexus/utils/env/extract.go new file mode 100644 index 0000000..72db69f --- /dev/null +++ b/nexus/utils/env/extract.go @@ -0,0 +1,33 @@ +package env
+
+import (
+ "errors"
+ "reflect"
+)
+
+func extractConfig(config any) (reflect.Value, reflect.Type, error) {
+ v := reflect.ValueOf(config)
+ if v.Kind() != reflect.Pointer || v.Elem().Kind() != reflect.Struct {
+ return reflect.Value{}, nil, errors.New(ConfigMustBePointer)
+ }
+ elem := v.Elem()
+ return elem, elem.Type(), nil
+}
+
+func extractFieldEnvInfo(element reflect.Value, elementType reflect.Type, index int) (*reflect.Value, string, string, bool) {
+ field := element.Field(index)
+ fieldType := elementType.Field(index)
+
+ if !field.CanSet() {
+ return nil, "", "", false
+ }
+
+ envKey := fieldType.Tag.Get(keyEnv)
+ defaultVal := fieldType.Tag.Get(keyDefault)
+
+ if envKey == "" {
+ return nil, "", "", false
+ }
+
+ return &field, envKey, defaultVal, true
+}
diff --git a/nexus/utils/env/getenv.go b/nexus/utils/env/getenv.go new file mode 100644 index 0000000..fde01ae --- /dev/null +++ b/nexus/utils/env/getenv.go @@ -0,0 +1,75 @@ +package env
+
+import (
+ "os"
+ "strconv"
+ "strings"
+ "time"
+)
+
+func getEnv(key, defaultVal string) string {
+ if value := os.Getenv(key); value != "" {
+ return value
+ }
+ return defaultVal
+}
+
+func getEnvBool(key string, defaultVal bool) bool {
+ if value := os.Getenv(key); value != "" {
+ if parsed, err := strconv.ParseBool(value); err == nil {
+ return parsed
+ }
+ }
+ return defaultVal
+}
+
+func getEnvDuration(key string, defaultVal time.Duration) time.Duration {
+ if value := os.Getenv(key); value != "" {
+ if parsed, err := time.ParseDuration(value); err == nil {
+ return parsed
+ }
+ }
+ return defaultVal
+}
+
+func getEnvInt(key string, defaultVal int64) int64 {
+ if value := os.Getenv(key); value != "" {
+ if parsed, err := strconv.ParseInt(value, 10, 64); err == nil {
+ return parsed
+ }
+ }
+ return defaultVal
+}
+
+func getEnvFloat(key string, defaultVal float64) float64 {
+ if value := os.Getenv(key); value != "" {
+ if parsed, err := strconv.ParseFloat(value, 64); err == nil {
+ return parsed
+ }
+ }
+ return defaultVal
+}
+
+func getEnvStringSlice(key string, defaultVal []string) []string {
+ if value := os.Getenv(key); value != "" {
+ parts := strings.Split(value, ",")
+ result := make([]string, 0, len(parts))
+ for _, part := range parts {
+ trimmed := strings.TrimSpace(part)
+ if trimmed != "" {
+ result = append(result, trimmed)
+ }
+ }
+ return result
+ }
+ return defaultVal
+}
+
+func getEnvUint(key string, defaultVal uint64) uint64 {
+ if value := os.Getenv(key); value != "" {
+ if parsed, err := strconv.ParseUint(value, 10, 64); err == nil {
+ return parsed
+ }
+ }
+ return defaultVal
+}
diff --git a/nexus/utils/env/messages.go b/nexus/utils/env/messages.go new file mode 100644 index 0000000..f5c7c91 --- /dev/null +++ b/nexus/utils/env/messages.go @@ -0,0 +1,5 @@ +package env
+
+const (
+ ConfigMustBePointer = "config must be a pointer to struct"
+)
diff --git a/nexus/utils/env/parse.go b/nexus/utils/env/parse.go new file mode 100644 index 0000000..2c494b5 --- /dev/null +++ b/nexus/utils/env/parse.go @@ -0,0 +1,27 @@ +package env
+
+import (
+ "github.com/joho/godotenv"
+)
+
+func init() {
+ godotenv.Load()
+}
+
+func Parse(config any) error {
+ element, elementType, err := extractConfig(config)
+ if err != nil {
+ return err
+ }
+
+ for index := range element.NumField() {
+ field, envKey, defaultVal, ok := extractFieldEnvInfo(element, elementType, index)
+ if !ok {
+ continue
+ }
+
+ setFieldFromEnv(*field, envKey, defaultVal)
+ }
+
+ return nil
+}
diff --git a/nexus/utils/env/setenv.go b/nexus/utils/env/setenv.go new file mode 100644 index 0000000..9001e68 --- /dev/null +++ b/nexus/utils/env/setenv.go @@ -0,0 +1,62 @@ +package env
+
+import (
+ "reflect"
+ "strconv"
+ "strings"
+ "time"
+)
+
+func setFieldFromEnv(field reflect.Value, envKey, defaultVal string) {
+ if field.Type() == reflect.TypeFor[time.Duration]() {
+ setDurationField(field, envKey, defaultVal)
+ return
+ }
+
+ switch field.Kind() {
+ case reflect.String:
+ field.SetString(getEnv(envKey, defaultVal))
+ case reflect.Bool:
+ defaultBool, _ := strconv.ParseBool(defaultVal)
+ field.SetBool(getEnvBool(envKey, defaultBool))
+ case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
+ defaultInt, _ := strconv.ParseInt(defaultVal, 10, 64)
+ field.SetInt(getEnvInt(envKey, defaultInt))
+ case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64:
+ defaultUint, _ := strconv.ParseUint(defaultVal, 10, 64)
+ setUintField(field, envKey, defaultUint)
+ case reflect.Float32, reflect.Float64:
+ defaultFloat, _ := strconv.ParseFloat(defaultVal, 64)
+ field.SetFloat(getEnvFloat(envKey, defaultFloat))
+ case reflect.Slice:
+ setSliceField(field, envKey, defaultVal)
+ }
+}
+
+func setUintField(field reflect.Value, envKey string, defaultVal uint64) {
+ field.SetUint(getEnvUint(envKey, defaultVal))
+}
+
+func setDurationField(field reflect.Value, envKey, defaultVal string) {
+ if field.Type() == reflect.TypeFor[time.Duration]() {
+ defaultDuration, _ := time.ParseDuration(defaultVal)
+ field.Set(reflect.ValueOf(getEnvDuration(envKey, defaultDuration)))
+ }
+}
+
+func setSliceField(field reflect.Value, envKey, defaultVal string) {
+ if field.Type().Elem().Kind() == reflect.String {
+ var defaultSlice []string
+ if defaultVal != "" {
+ parts := strings.Split(defaultVal, ",")
+ for _, part := range parts {
+ trimmed := strings.TrimSpace(part)
+ if trimmed != "" {
+ defaultSlice = append(defaultSlice, trimmed)
+ }
+ }
+ }
+ result := getEnvStringSlice(envKey, defaultSlice)
+ field.Set(reflect.ValueOf(result))
+ }
+}
|
