config.go 4.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129
  1. package prom
  2. import (
  3. "crypto/x509"
  4. "fmt"
  5. "time"
  6. "github.com/opencost/opencost/core/pkg/log"
  7. "github.com/opencost/opencost/modules/prometheus-source/pkg/env"
  8. restclient "k8s.io/client-go/rest"
  9. certutil "k8s.io/client-go/util/cert"
  10. )
  11. const (
  12. ServiceCA = `/var/run/secrets/kubernetes.io/serviceaccount/service-ca.crt`
  13. )
  14. type OpenCostPrometheusConfig struct {
  15. ServerEndpoint string
  16. Version string
  17. IsOffsetResolution bool
  18. ClientConfig *PrometheusClientConfig
  19. ScrapeInterval time.Duration
  20. JobName string
  21. Offset string
  22. QueryOffset time.Duration
  23. MaxQueryDuration time.Duration
  24. ClusterLabel string
  25. ClusterID string
  26. ClusterFilter string
  27. DataResolution time.Duration
  28. DataResolutionMinutes int
  29. }
  30. func (ocpc *OpenCostPrometheusConfig) IsRateLimitRetryEnabled() bool {
  31. return ocpc.ClientConfig.RateLimitRetryOpts != nil
  32. }
  33. // NewOpenCostPrometheusConfigFromEnv creates a new OpenCostPrometheusConfig from environment variables.
  34. func NewOpenCostPrometheusConfigFromEnv() (*OpenCostPrometheusConfig, error) {
  35. serverEndpoint := env.GetPrometheusServerEndpoint()
  36. if serverEndpoint == "" {
  37. return nil, fmt.Errorf("no address for prometheus set in $%s", env.PrometheusServerEndpointEnvVar)
  38. }
  39. queryConcurrency := env.GetMaxQueryConcurrency()
  40. log.Infof("Prometheus Client Max Concurrency set to %d", queryConcurrency)
  41. timeout := env.GetPrometheusQueryTimeout()
  42. keepAlive := env.GetPrometheusKeepAlive()
  43. tlsHandshakeTimeout := env.GetPrometheusTLSHandshakeTimeout()
  44. jobName := env.GetJobName()
  45. scrapeInterval := env.GetScrapeInterval()
  46. maxQueryDuration := env.GetETLMaxPrometheusQueryDuration()
  47. clusterId := env.GetClusterID()
  48. clusterLabel := env.GetPromClusterLabel()
  49. clusterFilter := env.GetPromClusterFilter()
  50. var rateLimitRetryOpts *RateLimitRetryOpts = nil
  51. if env.IsPrometheusRetryOnRateLimitResponse() {
  52. rateLimitRetryOpts = &RateLimitRetryOpts{
  53. MaxRetries: env.GetPrometheusRetryOnRateLimitMaxRetries(),
  54. DefaultRetryWait: env.GetPrometheusRetryOnRateLimitDefaultWait(),
  55. }
  56. }
  57. auth := &ClientAuth{
  58. Username: env.GetDBBasicAuthUsername(),
  59. Password: env.GetDBBasicAuthUserPassword(),
  60. BearerToken: env.GetDBBearerToken(),
  61. }
  62. // We will use the service account token and service-ca.crt to authenticate with the Prometheus server via kube-rbac-proxy.
  63. // We need to ensure that the service account has the necessary permissions to access the Prometheus server by binding it to the appropriate role.
  64. var tlsCaCert *x509.CertPool
  65. if env.IsKubeRbacProxyEnabled() {
  66. restConfig, err := restclient.InClusterConfig()
  67. if err != nil {
  68. log.Errorf("%s was set to true but failed to get in-cluster config: %s", env.KubeRbacProxyEnabledEnvVar, err)
  69. }
  70. auth.BearerToken = restConfig.BearerToken
  71. tlsCaCert, err = certutil.NewPool(ServiceCA)
  72. if err != nil {
  73. log.Errorf("%s was set to true but failed to load service-ca.crt: %s", env.KubeRbacProxyEnabledEnvVar, err)
  74. }
  75. }
  76. dataResolution := env.GetETLResolution()
  77. // Ensuring if data resolution is less than 60s default it to 1m
  78. resolutionMinutes := int(dataResolution.Minutes())
  79. if resolutionMinutes == 0 {
  80. resolutionMinutes = 1
  81. }
  82. clientConfig := &PrometheusClientConfig{
  83. Timeout: timeout,
  84. KeepAlive: keepAlive,
  85. TLSHandshakeTimeout: tlsHandshakeTimeout,
  86. TLSInsecureSkipVerify: env.IsInsecureSkipVerify(),
  87. RootCAs: tlsCaCert,
  88. RateLimitRetryOpts: rateLimitRetryOpts,
  89. Auth: auth,
  90. QueryConcurrency: queryConcurrency,
  91. QueryLogFile: "",
  92. HeaderXScopeOrgId: env.GetPrometheusHeaderXScopeOrgId(),
  93. }
  94. return &OpenCostPrometheusConfig{
  95. ServerEndpoint: serverEndpoint,
  96. Version: "0.0.0",
  97. IsOffsetResolution: false,
  98. ClientConfig: clientConfig,
  99. ScrapeInterval: scrapeInterval,
  100. JobName: jobName,
  101. Offset: "",
  102. QueryOffset: time.Duration(0),
  103. MaxQueryDuration: maxQueryDuration,
  104. ClusterLabel: clusterLabel,
  105. ClusterID: clusterId,
  106. ClusterFilter: clusterFilter,
  107. DataResolution: dataResolution,
  108. DataResolutionMinutes: resolutionMinutes,
  109. }, nil
  110. }