github.com/grafana/pyroscope@v1.18.0/pkg/pyroscope/runtime_config.go (about)

     1  package pyroscope
     2  
     3  import (
     4  	"net/http"
     5  
     6  	"github.com/grafana/dskit/runtimeconfig"
     7  
     8  	"github.com/grafana/pyroscope/pkg/util"
     9  	httputil "github.com/grafana/pyroscope/pkg/util/http"
    10  	"github.com/grafana/pyroscope/pkg/validation"
    11  )
    12  
    13  type tenantLimitsFromRuntimeConfig struct {
    14  	c *runtimeconfig.Manager
    15  }
    16  
    17  func (t *tenantLimitsFromRuntimeConfig) AllByTenantID() map[string]*validation.Limits {
    18  	if t.c == nil {
    19  		return nil
    20  	}
    21  
    22  	cfg, ok := t.c.GetConfig().(*validation.RuntimeConfigValues)
    23  	if cfg != nil && ok {
    24  		return cfg.TenantLimits
    25  	}
    26  
    27  	return nil
    28  }
    29  
    30  func (t *tenantLimitsFromRuntimeConfig) TenantLimits(userID string) *validation.Limits {
    31  	allByUserID := t.AllByTenantID()
    32  	if allByUserID == nil {
    33  		return nil
    34  	}
    35  
    36  	return allByUserID[userID]
    37  }
    38  
    39  func newTenantLimits(c *runtimeconfig.Manager) validation.TenantLimits {
    40  	return &tenantLimitsFromRuntimeConfig{c: c}
    41  }
    42  
    43  func runtimeConfigHandler(runtimeCfgManager *runtimeconfig.Manager, defaultLimits validation.Limits) http.HandlerFunc {
    44  	return func(w http.ResponseWriter, r *http.Request) {
    45  		cfg, ok := runtimeCfgManager.GetConfig().(*validation.RuntimeConfigValues)
    46  		if !ok || cfg == nil {
    47  			util.WriteTextResponse(w, "runtime config file doesn't exist")
    48  			return
    49  		}
    50  
    51  		var output interface{}
    52  		switch r.URL.Query().Get("mode") {
    53  		case "diff":
    54  			// Default runtime config is just empty struct, but to make diff work,
    55  			// we set defaultLimits for every tenant that exists in runtime config.
    56  			defaultCfg := validation.RuntimeConfigValues{}
    57  			defaultCfg.TenantLimits = map[string]*validation.Limits{}
    58  			for k, v := range cfg.TenantLimits {
    59  				if v != nil {
    60  					defaultCfg.TenantLimits[k] = &defaultLimits
    61  				}
    62  			}
    63  
    64  			cfgYaml, err := util.YAMLMarshalUnmarshal(cfg)
    65  			if err != nil {
    66  				httputil.Error(w, err)
    67  				return
    68  			}
    69  
    70  			defaultCfgYaml, err := util.YAMLMarshalUnmarshal(defaultCfg)
    71  			if err != nil {
    72  				httputil.Error(w, err)
    73  				return
    74  			}
    75  
    76  			output, err = util.DiffConfig(defaultCfgYaml, cfgYaml)
    77  			if err != nil {
    78  				httputil.Error(w, err)
    79  				return
    80  			}
    81  
    82  		default:
    83  			output = cfg
    84  		}
    85  		util.WriteYAMLResponse(w, output)
    86  	}
    87  }
    88  
    89  func (t *tenantLimitsFromRuntimeConfig) RuntimeConfig() *validation.RuntimeConfigValues {
    90  	cfg, ok := t.c.GetConfig().(*validation.RuntimeConfigValues)
    91  	if cfg != nil && ok {
    92  		return cfg
    93  	}
    94  	return nil
    95  }