env.go 4.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183
  1. package env
  2. import (
  3. "fmt"
  4. "log"
  5. "os"
  6. "path/filepath"
  7. "runtime"
  8. "strings"
  9. "testing"
  10. "github.com/wuntsong-org/go-zero-plus/tools/goctlwt/internal/version"
  11. sortedmap "github.com/wuntsong-org/go-zero-plus/tools/goctlwt/pkg/collection"
  12. "github.com/wuntsong-org/go-zero-plus/tools/goctlwt/pkg/protoc"
  13. "github.com/wuntsong-org/go-zero-plus/tools/goctlwt/pkg/protocgengo"
  14. "github.com/wuntsong-org/go-zero-plus/tools/goctlwt/pkg/protocgengogrpc"
  15. "github.com/wuntsong-org/go-zero-plus/tools/goctlwt/util/pathx"
  16. )
  17. var goctlEnv *sortedmap.SortedMap
  18. const (
  19. GoctlOS = "GOCTL_OS"
  20. GoctlArch = "GOCTL_ARCH"
  21. GoctlHome = "GOCTL_HOME"
  22. GoctlDebug = "GOCTL_DEBUG"
  23. GoctlCache = "GOCTL_CACHE"
  24. GoctlVersion = "GOCTL_VERSION"
  25. GoctlExperimental = "GOCTL_EXPERIMENTAL"
  26. ProtocVersion = "PROTOC_VERSION"
  27. ProtocGenGoVersion = "PROTOC_GEN_GO_VERSION"
  28. ProtocGenGoGRPCVersion = "PROTO_GEN_GO_GRPC_VERSION"
  29. envFileDir = "env"
  30. ExperimentalOn = "on"
  31. ExperimentalOff = "off"
  32. )
  33. // init initializes the goctl environment variables, the environment variables of the function are set in order,
  34. // please do not change the logic order of the code.
  35. func init() {
  36. defaultGoctlHome, err := pathx.GetDefaultGoctlHome()
  37. if err != nil {
  38. log.Fatalln(err)
  39. }
  40. goctlEnv = sortedmap.New()
  41. goctlEnv.SetKV(GoctlOS, runtime.GOOS)
  42. goctlEnv.SetKV(GoctlArch, runtime.GOARCH)
  43. existsEnv := readEnv(defaultGoctlHome)
  44. if existsEnv != nil {
  45. goctlHome, ok := existsEnv.GetString(GoctlHome)
  46. if ok && len(goctlHome) > 0 {
  47. goctlEnv.SetKV(GoctlHome, goctlHome)
  48. }
  49. if debug := existsEnv.GetOr(GoctlDebug, "").(string); debug != "" {
  50. if strings.EqualFold(debug, "true") || strings.EqualFold(debug, "false") {
  51. goctlEnv.SetKV(GoctlDebug, debug)
  52. }
  53. }
  54. if value := existsEnv.GetStringOr(GoctlCache, ""); value != "" {
  55. goctlEnv.SetKV(GoctlCache, value)
  56. }
  57. experimental := existsEnv.GetOr(GoctlExperimental, ExperimentalOn)
  58. goctlEnv.SetKV(GoctlExperimental, experimental)
  59. }
  60. if !goctlEnv.HasKey(GoctlHome) {
  61. goctlEnv.SetKV(GoctlHome, defaultGoctlHome)
  62. }
  63. if !goctlEnv.HasKey(GoctlDebug) {
  64. goctlEnv.SetKV(GoctlDebug, "False")
  65. }
  66. if !goctlEnv.HasKey(GoctlCache) {
  67. cacheDir, _ := pathx.GetCacheDir()
  68. goctlEnv.SetKV(GoctlCache, cacheDir)
  69. }
  70. if !goctlEnv.HasKey(GoctlExperimental) {
  71. goctlEnv.SetKV(GoctlExperimental, ExperimentalOn)
  72. }
  73. goctlEnv.SetKV(GoctlVersion, version.BuildVersion)
  74. protocVer, _ := protoc.Version()
  75. goctlEnv.SetKV(ProtocVersion, protocVer)
  76. protocGenGoVer, _ := protocgengo.Version()
  77. goctlEnv.SetKV(ProtocGenGoVersion, protocGenGoVer)
  78. protocGenGoGrpcVer, _ := protocgengogrpc.Version()
  79. goctlEnv.SetKV(ProtocGenGoGRPCVersion, protocGenGoGrpcVer)
  80. }
  81. func Print(args ...string) string {
  82. if len(args) == 0 {
  83. return strings.Join(goctlEnv.Format(), "\n")
  84. }
  85. var values []string
  86. for _, key := range args {
  87. value, ok := goctlEnv.GetString(key)
  88. if !ok {
  89. value = fmt.Sprintf("%s=%%not found%%", key)
  90. }
  91. values = append(values, fmt.Sprintf("%s=%s", key, value))
  92. }
  93. return strings.Join(values, "\n")
  94. }
  95. func Get(key string) string {
  96. return GetOr(key, "")
  97. }
  98. // Set sets the environment variable for testing
  99. func Set(t *testing.T, key, value string) {
  100. goctlEnv.SetKV(key, value)
  101. t.Cleanup(func() {
  102. goctlEnv.Remove(key)
  103. })
  104. }
  105. func GetOr(key, def string) string {
  106. return goctlEnv.GetStringOr(key, def)
  107. }
  108. func UseExperimental() bool {
  109. return GetOr(GoctlExperimental, ExperimentalOff) == ExperimentalOn
  110. }
  111. func readEnv(goctlHome string) *sortedmap.SortedMap {
  112. envFile := filepath.Join(goctlHome, envFileDir)
  113. data, err := os.ReadFile(envFile)
  114. if err != nil {
  115. return nil
  116. }
  117. dataStr := string(data)
  118. lines := strings.Split(dataStr, "\n")
  119. sm := sortedmap.New()
  120. for _, line := range lines {
  121. _, _, err = sm.SetExpression(line)
  122. if err != nil {
  123. continue
  124. }
  125. }
  126. return sm
  127. }
  128. func WriteEnv(kv []string) error {
  129. defaultGoctlHome, err := pathx.GetDefaultGoctlHome()
  130. if err != nil {
  131. log.Fatalln(err)
  132. }
  133. data := sortedmap.New()
  134. for _, e := range kv {
  135. _, _, err := data.SetExpression(e)
  136. if err != nil {
  137. return err
  138. }
  139. }
  140. data.RangeIf(func(key, value any) bool {
  141. switch key.(string) {
  142. case GoctlHome, GoctlCache:
  143. path := value.(string)
  144. if !pathx.FileExists(path) {
  145. err = fmt.Errorf("[writeEnv]: path %q is not exists", path)
  146. return false
  147. }
  148. }
  149. if goctlEnv.HasKey(key) {
  150. goctlEnv.SetKV(key, value)
  151. return true
  152. } else {
  153. err = fmt.Errorf("[writeEnv]: invalid key: %v", key)
  154. return false
  155. }
  156. })
  157. if err != nil {
  158. return err
  159. }
  160. envFile := filepath.Join(defaultGoctlHome, envFileDir)
  161. return os.WriteFile(envFile, []byte(strings.Join(goctlEnv.Format(), "\n")), 0o777)
  162. }