@@ -20,6 +20,7 @@ import (
2020 "os"
2121 "slices"
2222 "strings"
23+ "time"
2324
2425 "github.com/PuerkitoBio/rehttp"
2526 "github.com/alecthomas/kingpin/v2"
@@ -185,6 +186,7 @@ type handler struct {
185186 metricsExtraFilters []collectors.MetricFilter
186187 additionalGatherer prometheus.Gatherer
187188 m * monitoring.Service
189+ collectors * collectors.CollectorCache
188190}
189191
190192func (h * handler ) ServeHTTP (w http.ResponseWriter , r * http.Request ) {
@@ -203,35 +205,65 @@ func (h *handler) ServeHTTP(w http.ResponseWriter, r *http.Request) {
203205}
204206
205207func newHandler (projectIDs []string , metricPrefixes []string , metricExtraFilters []collectors.MetricFilter , m * monitoring.Service , logger * slog.Logger , additionalGatherer prometheus.Gatherer ) * handler {
208+ var ttl time.Duration
209+ // Add collector caching TTL as max of deltas aggregation or descriptor caching
210+ if * monitoringMetricsAggregateDeltas || * monitoringDescriptorCacheTTL > 0 {
211+ ttl = * monitoringMetricsDeltasTTL
212+ if * monitoringDescriptorCacheTTL > ttl {
213+ ttl = * monitoringDescriptorCacheTTL
214+ }
215+ } else {
216+ ttl = 2 * time .Hour
217+ }
218+
219+ logger .Info ("Creating collector cache" , "ttl" , ttl )
220+
206221 h := & handler {
207222 logger : logger ,
208223 projectIDs : projectIDs ,
209224 metricsPrefixes : metricPrefixes ,
210225 metricsExtraFilters : metricExtraFilters ,
211226 additionalGatherer : additionalGatherer ,
212227 m : m ,
228+ collectors : collectors .NewCollectorCache (ttl ),
213229 }
214230
215231 h .handler = h .innerHandler (nil )
216232 return h
217233}
218234
235+ func (h * handler ) getCollector (project string , filters map [string ]bool ) (* collectors.MonitoringCollector , error ) {
236+ filterdPrefixes := h .filterMetricTypePrefixes (filters )
237+ collectorKey := fmt .Sprintf ("%s-%v" , project , filterdPrefixes )
238+
239+ if collector , found := h .collectors .Get (collectorKey ); found {
240+ return collector , nil
241+ }
242+
243+ collector , err := collectors .NewMonitoringCollector (project , h .m , collectors.MonitoringCollectorOptions {
244+ MetricTypePrefixes : filterdPrefixes ,
245+ ExtraFilters : h .metricsExtraFilters ,
246+ RequestInterval : * monitoringMetricsInterval ,
247+ RequestOffset : * monitoringMetricsOffset ,
248+ IngestDelay : * monitoringMetricsIngestDelay ,
249+ FillMissingLabels : * collectorFillMissingLabels ,
250+ DropDelegatedProjects : * monitoringDropDelegatedProjects ,
251+ AggregateDeltas : * monitoringMetricsAggregateDeltas ,
252+ DescriptorCacheTTL : * monitoringDescriptorCacheTTL ,
253+ DescriptorCacheOnlyGoogle : * monitoringDescriptorCacheOnlyGoogle ,
254+ }, h .logger , delta .NewInMemoryCounterStore (h .logger , * monitoringMetricsDeltasTTL ), delta .NewInMemoryHistogramStore (h .logger , * monitoringMetricsDeltasTTL ))
255+ if err != nil {
256+ return nil , err
257+ }
258+ h .collectors .Store (collectorKey , collector )
259+ return collector , nil
260+ }
261+
219262func (h * handler ) innerHandler (filters map [string ]bool ) http.Handler {
220263 registry := prometheus .NewRegistry ()
221264
222265 for _ , project := range h .projectIDs {
223- monitoringCollector , err := collectors .NewMonitoringCollector (project , h .m , collectors.MonitoringCollectorOptions {
224- MetricTypePrefixes : h .filterMetricTypePrefixes (filters ),
225- ExtraFilters : h .metricsExtraFilters ,
226- RequestInterval : * monitoringMetricsInterval ,
227- RequestOffset : * monitoringMetricsOffset ,
228- IngestDelay : * monitoringMetricsIngestDelay ,
229- FillMissingLabels : * collectorFillMissingLabels ,
230- DropDelegatedProjects : * monitoringDropDelegatedProjects ,
231- AggregateDeltas : * monitoringMetricsAggregateDeltas ,
232- DescriptorCacheTTL : * monitoringDescriptorCacheTTL ,
233- DescriptorCacheOnlyGoogle : * monitoringDescriptorCacheOnlyGoogle ,
234- }, h .logger , delta .NewInMemoryCounterStore (h .logger , * monitoringMetricsDeltasTTL ), delta .NewInMemoryHistogramStore (h .logger , * monitoringMetricsDeltasTTL ))
266+ monitoringCollector , err := h .getCollector (project , filters )
235267 if err != nil {
236268 h .logger .Error ("error creating monitoring collector" , "err" , err )
237269 os .Exit (1 )
0 commit comments