Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

program will oom cause massive metrics in memory without expiring mechanism #56

Open
jingb opened this issue Oct 16, 2023 · 2 comments
Open
Labels
question Further information is requested

Comments

@jingb
Copy link

jingb commented Oct 16, 2023

there has a program and it consumes massive message from kafka. then it will trans the message to metrics format and use the vm metrics sdk to push to victoriametrics.
cause the vm metrics sdk holds global map to store the all the metrics in it and there has no expiring mechanism, the map will expand infinitely and finally the program oom. The process described above will be more obvious. Any solution to solve it?
and it seems there has a similar problem in https://github.com/prometheus/client_golang
prometheus/client_golang#920

// Set is a set of metrics.
//
// Metrics belonging to a set are exported separately from global metrics.
//
// Set.WritePrometheus must be called for exporting metrics from the set.
type Set struct {
	mu        sync.Mutex
	a         []*namedMetric
	m         map[string]*namedMetric
	summaries []*Summary
}
@f41gh7
Copy link
Contributor

f41gh7 commented Nov 1, 2023

You can use metric Sets for this case and manage expiration at your code.
https://github.com/VictoriaMetrics/metrics/blob/master/set.go#L17
Pseudo code of Sets usage:

var  (
  ms  *metrics.Set
  expireTime  time.Time
)


func collectMetrics(srcMetrics []metricsWithValues){
  if ms == nil {
         ms = metrics.NewSet()
         metrics.RegisterSet(ms)
         expireTime = time.Now().Add(time.Minute)
  }
  if time.After(expireTime) {
      metrics.UnRegister(ms)
      ms =  metrics.NewSet()
      metrics.RegisterSet(ms)
       expireTime = time.Now().Add(time.Minute)
  }
  for _, mv := range srcMetrics{ 
     ms.GetOrCreateCounter(mv.name).Inc()
  } 
}

@valyala valyala added the question Further information is requested label Dec 19, 2023
@valyala
Copy link
Contributor

valyala commented Dec 19, 2023

FYI, it isn't OK if the number of exposed metrics grows without bounds, since this may result in high cardinality issues and high churn rate issues at the monitoring system side.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
question Further information is requested
Projects
None yet
Development

No branches or pull requests

3 participants