github.com/prebid/prebid-server@v0.275.0/metrics/prometheus/prometheus.go (about)

     1  package prometheusmetrics
     2  
     3  import (
     4  	"fmt"
     5  	"strconv"
     6  	"time"
     7  
     8  	"github.com/prebid/prebid-server/config"
     9  	"github.com/prebid/prebid-server/metrics"
    10  	"github.com/prebid/prebid-server/openrtb_ext"
    11  	"github.com/prometheus/client_golang/prometheus"
    12  	promCollector "github.com/prometheus/client_golang/prometheus/collectors"
    13  )
    14  
    15  // Metrics defines the Prometheus metrics backing the MetricsEngine implementation.
    16  type Metrics struct {
    17  	Registerer prometheus.Registerer
    18  	Gatherer   *prometheus.Registry
    19  
    20  	// General Metrics
    21  	tmaxTimeout                  prometheus.Counter
    22  	connectionsClosed            prometheus.Counter
    23  	connectionsError             *prometheus.CounterVec
    24  	connectionsOpened            prometheus.Counter
    25  	cookieSync                   *prometheus.CounterVec
    26  	setUid                       *prometheus.CounterVec
    27  	impressions                  *prometheus.CounterVec
    28  	prebidCacheWriteTimer        *prometheus.HistogramVec
    29  	requests                     *prometheus.CounterVec
    30  	debugRequests                prometheus.Counter
    31  	requestsTimer                *prometheus.HistogramVec
    32  	requestsQueueTimer           *prometheus.HistogramVec
    33  	requestsWithoutCookie        *prometheus.CounterVec
    34  	storedImpressionsCacheResult *prometheus.CounterVec
    35  	storedRequestCacheResult     *prometheus.CounterVec
    36  	accountCacheResult           *prometheus.CounterVec
    37  	storedAccountFetchTimer      *prometheus.HistogramVec
    38  	storedAccountErrors          *prometheus.CounterVec
    39  	storedAMPFetchTimer          *prometheus.HistogramVec
    40  	storedAMPErrors              *prometheus.CounterVec
    41  	storedCategoryFetchTimer     *prometheus.HistogramVec
    42  	storedCategoryErrors         *prometheus.CounterVec
    43  	storedRequestFetchTimer      *prometheus.HistogramVec
    44  	storedRequestErrors          *prometheus.CounterVec
    45  	storedVideoFetchTimer        *prometheus.HistogramVec
    46  	storedVideoErrors            *prometheus.CounterVec
    47  	timeoutNotifications         *prometheus.CounterVec
    48  	dnsLookupTimer               prometheus.Histogram
    49  	tlsHandhakeTimer             prometheus.Histogram
    50  	privacyCCPA                  *prometheus.CounterVec
    51  	privacyCOPPA                 *prometheus.CounterVec
    52  	privacyLMT                   *prometheus.CounterVec
    53  	privacyTCF                   *prometheus.CounterVec
    54  	storedResponses              prometheus.Counter
    55  	storedResponsesFetchTimer    *prometheus.HistogramVec
    56  	storedResponsesErrors        *prometheus.CounterVec
    57  	adsCertRequests              *prometheus.CounterVec
    58  	adsCertSignTimer             prometheus.Histogram
    59  	bidderServerResponseTimer    prometheus.Histogram
    60  
    61  	// Adapter Metrics
    62  	adapterBids                           *prometheus.CounterVec
    63  	adapterErrors                         *prometheus.CounterVec
    64  	adapterPanics                         *prometheus.CounterVec
    65  	adapterPrices                         *prometheus.HistogramVec
    66  	adapterRequests                       *prometheus.CounterVec
    67  	overheadTimer                         *prometheus.HistogramVec
    68  	adapterRequestsTimer                  *prometheus.HistogramVec
    69  	adapterReusedConnections              *prometheus.CounterVec
    70  	adapterCreatedConnections             *prometheus.CounterVec
    71  	adapterConnectionWaitTime             *prometheus.HistogramVec
    72  	adapterGDPRBlockedRequests            *prometheus.CounterVec
    73  	adapterBidResponseValidationSizeError *prometheus.CounterVec
    74  	adapterBidResponseValidationSizeWarn  *prometheus.CounterVec
    75  	adapterBidResponseSecureMarkupError   *prometheus.CounterVec
    76  	adapterBidResponseSecureMarkupWarn    *prometheus.CounterVec
    77  
    78  	// Syncer Metrics
    79  	syncerRequests *prometheus.CounterVec
    80  	syncerSets     *prometheus.CounterVec
    81  
    82  	// Account Metrics
    83  	accountRequests                       *prometheus.CounterVec
    84  	accountDebugRequests                  *prometheus.CounterVec
    85  	accountStoredResponses                *prometheus.CounterVec
    86  	accountBidResponseValidationSizeError *prometheus.CounterVec
    87  	accountBidResponseValidationSizeWarn  *prometheus.CounterVec
    88  	accountBidResponseSecureMarkupError   *prometheus.CounterVec
    89  	accountBidResponseSecureMarkupWarn    *prometheus.CounterVec
    90  
    91  	// Account Deprecation Metrics
    92  	accountDeprecationWarningsPurpose1  prometheus.Counter
    93  	accountDeprecationWarningsPurpose2  prometheus.Counter
    94  	accountDeprecationWarningsPurpose3  prometheus.Counter
    95  	accountDeprecationWarningsPurpose4  prometheus.Counter
    96  	accountDeprecationWarningsPurpose5  prometheus.Counter
    97  	accountDeprecationWarningsPurpose6  prometheus.Counter
    98  	accountDeprecationWarningsPurpose7  prometheus.Counter
    99  	accountDeprecationWarningsPurpose8  prometheus.Counter
   100  	accountDeprecationWarningsPurpose9  prometheus.Counter
   101  	accountDeprecationWarningsPurpose10 prometheus.Counter
   102  	channelEnabledGDPR                  prometheus.Counter
   103  	channelEnabledCCPA                  prometheus.Counter
   104  	accountDeprecationSummary           prometheus.Counter
   105  
   106  	// Module Metrics as a map where the key is the module name
   107  	moduleDuration        map[string]*prometheus.HistogramVec
   108  	moduleCalls           map[string]*prometheus.CounterVec
   109  	moduleFailures        map[string]*prometheus.CounterVec
   110  	moduleSuccessNoops    map[string]*prometheus.CounterVec
   111  	moduleSuccessUpdates  map[string]*prometheus.CounterVec
   112  	moduleSuccessRejects  map[string]*prometheus.CounterVec
   113  	moduleExecutionErrors map[string]*prometheus.CounterVec
   114  	moduleTimeouts        map[string]*prometheus.CounterVec
   115  
   116  	metricsDisabled config.DisabledMetrics
   117  }
   118  
   119  const (
   120  	accountLabel         = "account"
   121  	actionLabel          = "action"
   122  	adapterErrorLabel    = "adapter_error"
   123  	adapterLabel         = "adapter"
   124  	bidTypeLabel         = "bid_type"
   125  	cacheResultLabel     = "cache_result"
   126  	connectionErrorLabel = "connection_error"
   127  	cookieLabel          = "cookie"
   128  	hasBidsLabel         = "has_bids"
   129  	isAudioLabel         = "audio"
   130  	isBannerLabel        = "banner"
   131  	isNativeLabel        = "native"
   132  	isVideoLabel         = "video"
   133  	markupDeliveryLabel  = "delivery"
   134  	optOutLabel          = "opt_out"
   135  	overheadTypeLabel    = "overhead_type"
   136  	privacyBlockedLabel  = "privacy_blocked"
   137  	requestStatusLabel   = "request_status"
   138  	requestTypeLabel     = "request_type"
   139  	stageLabel           = "stage"
   140  	statusLabel          = "status"
   141  	successLabel         = "success"
   142  	syncerLabel          = "syncer"
   143  	versionLabel         = "version"
   144  )
   145  
   146  const (
   147  	connectionAcceptError = "accept"
   148  	connectionCloseError  = "close"
   149  )
   150  
   151  const (
   152  	markupDeliveryAdm  = "adm"
   153  	markupDeliveryNurl = "nurl"
   154  )
   155  
   156  const (
   157  	requestSuccessLabel = "requestAcceptedLabel"
   158  	requestRejectLabel  = "requestRejectedLabel"
   159  )
   160  
   161  const (
   162  	requestSuccessful = "ok"
   163  	requestFailed     = "failed"
   164  )
   165  
   166  const (
   167  	sourceLabel   = "source"
   168  	sourceRequest = "request"
   169  )
   170  
   171  const (
   172  	storedDataFetchTypeLabel = "stored_data_fetch_type"
   173  	storedDataErrorLabel     = "stored_data_error"
   174  )
   175  
   176  // NewMetrics initializes a new Prometheus metrics instance with preloaded label values.
   177  func NewMetrics(cfg config.PrometheusMetrics, disabledMetrics config.DisabledMetrics, syncerKeys []string, moduleStageNames map[string][]string) *Metrics {
   178  	standardTimeBuckets := []float64{0.05, 0.1, 0.15, 0.20, 0.25, 0.3, 0.4, 0.5, 0.75, 1}
   179  	cacheWriteTimeBuckets := []float64{0.001, 0.002, 0.005, 0.01, 0.025, 0.05, 0.1, 0.2, 0.3, 0.4, 0.5, 1}
   180  	priceBuckets := []float64{250, 500, 750, 1000, 1500, 2000, 2500, 3000, 3500, 4000}
   181  	queuedRequestTimeBuckets := []float64{0, 1, 5, 30, 60, 120, 180, 240, 300}
   182  	overheadTimeBuckets := []float64{0.05, 0.06, 0.07, 0.08, 0.09, 0.1, 0.2, 0.3, 0.4, 0.5, 0.6, 0.7, 0.8, 0.9, 1}
   183  
   184  	metrics := Metrics{}
   185  	reg := prometheus.NewRegistry()
   186  	metrics.metricsDisabled = disabledMetrics
   187  
   188  	metrics.connectionsClosed = newCounterWithoutLabels(cfg, reg,
   189  		"connections_closed",
   190  		"Count of successful connections closed to Prebid Server.")
   191  
   192  	metrics.connectionsError = newCounter(cfg, reg,
   193  		"connections_error",
   194  		"Count of errors for connection open and close attempts to Prebid Server labeled by type.",
   195  		[]string{connectionErrorLabel})
   196  
   197  	metrics.connectionsOpened = newCounterWithoutLabels(cfg, reg,
   198  		"connections_opened",
   199  		"Count of successful connections opened to Prebid Server.")
   200  
   201  	metrics.tmaxTimeout = newCounterWithoutLabels(cfg, reg,
   202  		"tmax_timeout",
   203  		"Count of requests rejected due to Tmax timeout exceed.")
   204  
   205  	metrics.cookieSync = newCounter(cfg, reg,
   206  		"cookie_sync_requests",
   207  		"Count of cookie sync requests to Prebid Server.",
   208  		[]string{statusLabel})
   209  
   210  	metrics.setUid = newCounter(cfg, reg,
   211  		"setuid_requests",
   212  		"Count of set uid requests to Prebid Server.",
   213  		[]string{statusLabel})
   214  
   215  	metrics.impressions = newCounter(cfg, reg,
   216  		"impressions_requests",
   217  		"Count of requested impressions to Prebid Server labeled by type.",
   218  		[]string{isBannerLabel, isVideoLabel, isAudioLabel, isNativeLabel})
   219  
   220  	metrics.prebidCacheWriteTimer = newHistogramVec(cfg, reg,
   221  		"prebidcache_write_time_seconds",
   222  		"Seconds to write to Prebid Cache labeled by success or failure. Failure timing is limited by Prebid Server enforced timeouts.",
   223  		[]string{successLabel},
   224  		cacheWriteTimeBuckets)
   225  
   226  	metrics.requests = newCounter(cfg, reg,
   227  		"requests",
   228  		"Count of total requests to Prebid Server labeled by type and status.",
   229  		[]string{requestTypeLabel, requestStatusLabel})
   230  
   231  	metrics.debugRequests = newCounterWithoutLabels(cfg, reg,
   232  		"debug_requests",
   233  		"Count of total requests to Prebid Server that have debug enabled")
   234  
   235  	metrics.requestsTimer = newHistogramVec(cfg, reg,
   236  		"request_time_seconds",
   237  		"Seconds to resolve successful Prebid Server requests labeled by type.",
   238  		[]string{requestTypeLabel},
   239  		standardTimeBuckets)
   240  
   241  	metrics.requestsWithoutCookie = newCounter(cfg, reg,
   242  		"requests_without_cookie",
   243  		"Count of total requests to Prebid Server without a cookie labeled by type.",
   244  		[]string{requestTypeLabel})
   245  
   246  	metrics.storedImpressionsCacheResult = newCounter(cfg, reg,
   247  		"stored_impressions_cache_performance",
   248  		"Count of stored impression cache requests attempts by hits or miss.",
   249  		[]string{cacheResultLabel})
   250  
   251  	metrics.storedRequestCacheResult = newCounter(cfg, reg,
   252  		"stored_request_cache_performance",
   253  		"Count of stored request cache requests attempts by hits or miss.",
   254  		[]string{cacheResultLabel})
   255  
   256  	metrics.accountCacheResult = newCounter(cfg, reg,
   257  		"account_cache_performance",
   258  		"Count of account cache lookups by hits or miss.",
   259  		[]string{cacheResultLabel})
   260  
   261  	metrics.storedAccountFetchTimer = newHistogramVec(cfg, reg,
   262  		"stored_account_fetch_time_seconds",
   263  		"Seconds to fetch stored accounts labeled by fetch type",
   264  		[]string{storedDataFetchTypeLabel},
   265  		standardTimeBuckets)
   266  
   267  	metrics.storedAccountErrors = newCounter(cfg, reg,
   268  		"stored_account_errors",
   269  		"Count of stored account errors by error type",
   270  		[]string{storedDataErrorLabel})
   271  
   272  	metrics.storedAMPFetchTimer = newHistogramVec(cfg, reg,
   273  		"stored_amp_fetch_time_seconds",
   274  		"Seconds to fetch stored AMP requests labeled by fetch type",
   275  		[]string{storedDataFetchTypeLabel},
   276  		standardTimeBuckets)
   277  
   278  	metrics.storedAMPErrors = newCounter(cfg, reg,
   279  		"stored_amp_errors",
   280  		"Count of stored AMP errors by error type",
   281  		[]string{storedDataErrorLabel})
   282  
   283  	metrics.storedCategoryFetchTimer = newHistogramVec(cfg, reg,
   284  		"stored_category_fetch_time_seconds",
   285  		"Seconds to fetch stored categories labeled by fetch type",
   286  		[]string{storedDataFetchTypeLabel},
   287  		standardTimeBuckets)
   288  
   289  	metrics.storedCategoryErrors = newCounter(cfg, reg,
   290  		"stored_category_errors",
   291  		"Count of stored category errors by error type",
   292  		[]string{storedDataErrorLabel})
   293  
   294  	metrics.storedRequestFetchTimer = newHistogramVec(cfg, reg,
   295  		"stored_request_fetch_time_seconds",
   296  		"Seconds to fetch stored requests labeled by fetch type",
   297  		[]string{storedDataFetchTypeLabel},
   298  		standardTimeBuckets)
   299  
   300  	metrics.storedRequestErrors = newCounter(cfg, reg,
   301  		"stored_request_errors",
   302  		"Count of stored request errors by error type",
   303  		[]string{storedDataErrorLabel})
   304  
   305  	metrics.storedVideoFetchTimer = newHistogramVec(cfg, reg,
   306  		"stored_video_fetch_time_seconds",
   307  		"Seconds to fetch stored video labeled by fetch type",
   308  		[]string{storedDataFetchTypeLabel},
   309  		standardTimeBuckets)
   310  
   311  	metrics.storedVideoErrors = newCounter(cfg, reg,
   312  		"stored_video_errors",
   313  		"Count of stored video errors by error type",
   314  		[]string{storedDataErrorLabel})
   315  
   316  	metrics.timeoutNotifications = newCounter(cfg, reg,
   317  		"timeout_notification",
   318  		"Count of timeout notifications triggered, and if they were successfully sent.",
   319  		[]string{successLabel})
   320  
   321  	metrics.dnsLookupTimer = newHistogram(cfg, reg,
   322  		"dns_lookup_time",
   323  		"Seconds to resolve DNS",
   324  		standardTimeBuckets)
   325  
   326  	metrics.tlsHandhakeTimer = newHistogram(cfg, reg,
   327  		"tls_handshake_time",
   328  		"Seconds to perform TLS Handshake",
   329  		standardTimeBuckets)
   330  
   331  	metrics.privacyCCPA = newCounter(cfg, reg,
   332  		"privacy_ccpa",
   333  		"Count of total requests to Prebid Server where CCPA was provided by source and opt-out .",
   334  		[]string{sourceLabel, optOutLabel})
   335  
   336  	metrics.privacyCOPPA = newCounter(cfg, reg,
   337  		"privacy_coppa",
   338  		"Count of total requests to Prebid Server where the COPPA flag was set by source",
   339  		[]string{sourceLabel})
   340  
   341  	metrics.privacyTCF = newCounter(cfg, reg,
   342  		"privacy_tcf",
   343  		"Count of TCF versions for requests where GDPR was enforced by source and version.",
   344  		[]string{versionLabel, sourceLabel})
   345  
   346  	metrics.privacyLMT = newCounter(cfg, reg,
   347  		"privacy_lmt",
   348  		"Count of total requests to Prebid Server where the LMT flag was set by source",
   349  		[]string{sourceLabel})
   350  
   351  	if !metrics.metricsDisabled.AdapterGDPRRequestBlocked {
   352  		metrics.adapterGDPRBlockedRequests = newCounter(cfg, reg,
   353  			"adapter_gdpr_requests_blocked",
   354  			"Count of total bidder requests blocked due to unsatisfied GDPR purpose 2 legal basis",
   355  			[]string{adapterLabel})
   356  	}
   357  
   358  	metrics.storedResponsesFetchTimer = newHistogramVec(cfg, reg,
   359  		"stored_response_fetch_time_seconds",
   360  		"Seconds to fetch stored responses labeled by fetch type",
   361  		[]string{storedDataFetchTypeLabel},
   362  		standardTimeBuckets)
   363  
   364  	metrics.storedResponsesErrors = newCounter(cfg, reg,
   365  		"stored_response_errors",
   366  		"Count of stored video errors by error type",
   367  		[]string{storedDataErrorLabel})
   368  
   369  	metrics.storedResponses = newCounterWithoutLabels(cfg, reg,
   370  		"stored_responses",
   371  		"Count of total requests to Prebid Server that have stored responses")
   372  
   373  	metrics.adapterBids = newCounter(cfg, reg,
   374  		"adapter_bids",
   375  		"Count of bids labeled by adapter and markup delivery type (adm or nurl).",
   376  		[]string{adapterLabel, markupDeliveryLabel})
   377  
   378  	metrics.adapterErrors = newCounter(cfg, reg,
   379  		"adapter_errors",
   380  		"Count of errors labeled by adapter and error type.",
   381  		[]string{adapterLabel, adapterErrorLabel})
   382  
   383  	metrics.adapterPanics = newCounter(cfg, reg,
   384  		"adapter_panics",
   385  		"Count of panics labeled by adapter.",
   386  		[]string{adapterLabel})
   387  
   388  	metrics.adapterPrices = newHistogramVec(cfg, reg,
   389  		"adapter_prices",
   390  		"Monetary value of the bids labeled by adapter.",
   391  		[]string{adapterLabel},
   392  		priceBuckets)
   393  
   394  	metrics.adapterRequests = newCounter(cfg, reg,
   395  		"adapter_requests",
   396  		"Count of requests labeled by adapter, if has a cookie, and if it resulted in bids.",
   397  		[]string{adapterLabel, cookieLabel, hasBidsLabel})
   398  
   399  	if !metrics.metricsDisabled.AdapterConnectionMetrics {
   400  		metrics.adapterCreatedConnections = newCounter(cfg, reg,
   401  			"adapter_connection_created",
   402  			"Count that keeps track of new connections when contacting adapter bidder endpoints.",
   403  			[]string{adapterLabel})
   404  
   405  		metrics.adapterReusedConnections = newCounter(cfg, reg,
   406  			"adapter_connection_reused",
   407  			"Count that keeps track of reused connections when contacting adapter bidder endpoints.",
   408  			[]string{adapterLabel})
   409  
   410  		metrics.adapterConnectionWaitTime = newHistogramVec(cfg, reg,
   411  			"adapter_connection_wait",
   412  			"Seconds from when the connection was requested until it is either created or reused",
   413  			[]string{adapterLabel},
   414  			standardTimeBuckets)
   415  	}
   416  
   417  	metrics.adapterBidResponseValidationSizeError = newCounter(cfg, reg,
   418  		"adapter_response_validation_size_err",
   419  		"Count that tracks number of bids removed from bid response that had a creative size greater than maxWidth/maxHeight",
   420  		[]string{adapterLabel, successLabel})
   421  
   422  	metrics.adapterBidResponseValidationSizeWarn = newCounter(cfg, reg,
   423  		"adapter_response_validation_size_warn",
   424  		"Count that tracks number of bids removed from bid response that had a creative size greater than maxWidth/maxHeight (warn)",
   425  		[]string{adapterLabel, successLabel})
   426  
   427  	metrics.adapterBidResponseSecureMarkupError = newCounter(cfg, reg,
   428  		"adapter_response_validation_secure_err",
   429  		"Count that tracks number of bids removed from bid response that had a invalid bidAdm",
   430  		[]string{adapterLabel, successLabel})
   431  
   432  	metrics.adapterBidResponseSecureMarkupWarn = newCounter(cfg, reg,
   433  		"adapter_response_validation_secure_warn",
   434  		"Count that tracks number of bids removed from bid response that had a invalid bidAdm (warn)",
   435  		[]string{adapterLabel, successLabel})
   436  
   437  	metrics.overheadTimer = newHistogramVec(cfg, reg,
   438  		"overhead_time_seconds",
   439  		"Seconds to prepare adapter request or resolve adapter response",
   440  		[]string{overheadTypeLabel},
   441  		overheadTimeBuckets)
   442  
   443  	metrics.adapterRequestsTimer = newHistogramVec(cfg, reg,
   444  		"adapter_request_time_seconds",
   445  		"Seconds to resolve each successful request labeled by adapter.",
   446  		[]string{adapterLabel},
   447  		standardTimeBuckets)
   448  
   449  	metrics.bidderServerResponseTimer = newHistogram(cfg, reg,
   450  		"bidder_server_response_time_seconds",
   451  		"Duration needed to send HTTP request and receive response back from bidder server.",
   452  		standardTimeBuckets)
   453  
   454  	metrics.syncerRequests = newCounter(cfg, reg,
   455  		"syncer_requests",
   456  		"Count of cookie sync requests where a syncer is a candidate to be synced labeled by syncer key and status.",
   457  		[]string{syncerLabel, statusLabel})
   458  
   459  	metrics.syncerSets = newCounter(cfg, reg,
   460  		"syncer_sets",
   461  		"Count of setuid set requests for a syncer labeled by syncer key and status.",
   462  		[]string{syncerLabel, statusLabel})
   463  
   464  	metrics.accountRequests = newCounter(cfg, reg,
   465  		"account_requests",
   466  		"Count of total requests to Prebid Server labeled by account.",
   467  		[]string{accountLabel})
   468  
   469  	metrics.accountDebugRequests = newCounter(cfg, reg,
   470  		"account_debug_requests",
   471  		"Count of total requests to Prebid Server that have debug enabled labled by account",
   472  		[]string{accountLabel})
   473  
   474  	metrics.accountBidResponseValidationSizeError = newCounter(cfg, reg,
   475  		"account_response_validation_size_err",
   476  		"Count that tracks number of bids removed from bid response that had a creative size greater than maxWidth/maxHeight labeled by account (enforce) ",
   477  		[]string{accountLabel, successLabel})
   478  
   479  	metrics.accountBidResponseValidationSizeWarn = newCounter(cfg, reg,
   480  		"account_response_validation_size_warn",
   481  		"Count that tracks number of bids removed from bid response that had a creative size greater than maxWidth/maxHeight labeled by account (warn)",
   482  		[]string{accountLabel, successLabel})
   483  
   484  	metrics.accountBidResponseSecureMarkupError = newCounter(cfg, reg,
   485  		"account_response_validation_secure_err",
   486  		"Count that tracks number of bids removed from bid response that had a invalid bidAdm labeled by account (enforce) ",
   487  		[]string{accountLabel, successLabel})
   488  
   489  	metrics.accountBidResponseSecureMarkupWarn = newCounter(cfg, reg,
   490  		"account_response_validation_secure_warn",
   491  		"Count that tracks number of bids removed from bid response that had a invalid bidAdm labeled by account (warn)",
   492  		[]string{accountLabel, successLabel})
   493  
   494  	metrics.requestsQueueTimer = newHistogramVec(cfg, reg,
   495  		"request_queue_time",
   496  		"Seconds request was waiting in queue",
   497  		[]string{requestTypeLabel, requestStatusLabel},
   498  		queuedRequestTimeBuckets)
   499  
   500  	metrics.accountStoredResponses = newCounter(cfg, reg,
   501  		"account_stored_responses",
   502  		"Count of total requests to Prebid Server that have stored responses labled by account",
   503  		[]string{accountLabel})
   504  
   505  	metrics.adsCertSignTimer = newHistogram(cfg, reg,
   506  		"ads_cert_sign_time",
   507  		"Seconds to generate an AdsCert header",
   508  		standardTimeBuckets)
   509  
   510  	metrics.adsCertRequests = newCounter(cfg, reg,
   511  		"ads_cert_requests",
   512  		"Count of AdsCert request, and if they were successfully sent.",
   513  		[]string{successLabel})
   514  
   515  	metrics.accountDeprecationWarningsPurpose1 = newCounterWithoutLabels(cfg, reg,
   516  		"account_config_gdpr_tcf2_purpose1_warn",
   517  		"Count of requests referencing an account whose config specifies a deprecated gdpr.tcf2.purpose1 field")
   518  	metrics.accountDeprecationWarningsPurpose2 = newCounterWithoutLabels(cfg, reg,
   519  		"account_config_gdpr_tcf2_purpose2_warn",
   520  		"Count of requests referencing an account whose config specifies a deprecated gdpr.tcf2.purpose2 field")
   521  	metrics.accountDeprecationWarningsPurpose3 = newCounterWithoutLabels(cfg, reg,
   522  		"account_config_gdpr_tcf2_purpose3_warn",
   523  		"Count of requests referencing an account whose config specifies a deprecated gdpr.tcf2.purpose3 field")
   524  	metrics.accountDeprecationWarningsPurpose4 = newCounterWithoutLabels(cfg, reg,
   525  		"account_config_gdpr_tcf2_purpose4_warn",
   526  		"Count of requests referencing an account whose config specifies a deprecated gdpr.tcf2.purpose4 field")
   527  	metrics.accountDeprecationWarningsPurpose5 = newCounterWithoutLabels(cfg, reg,
   528  		"account_config_gdpr_tcf2_purpose5_warn",
   529  		"Count of requests referencing an account whose config specifies a deprecated gdpr.tcf2.purpose5 field")
   530  	metrics.accountDeprecationWarningsPurpose6 = newCounterWithoutLabels(cfg, reg,
   531  		"account_config_gdpr_tcf2_purpose6_warn",
   532  		"Count of requests referencing an account whose config specifies a deprecated gdpr.tcf2.purpose6 field")
   533  	metrics.accountDeprecationWarningsPurpose7 = newCounterWithoutLabels(cfg, reg,
   534  		"account_config_gdpr_tcf2_purpose7_warn",
   535  		"Count of requests referencing an account whose config specifies a deprecated gdpr.tcf2.purpose7 field")
   536  	metrics.accountDeprecationWarningsPurpose8 = newCounterWithoutLabels(cfg, reg,
   537  		"account_config_gdpr_tcf2_purpose8_warn",
   538  		"Count of requests referencing an account whose config specifies a deprecated gdpr.tcf2.purpose8 field")
   539  	metrics.accountDeprecationWarningsPurpose9 = newCounterWithoutLabels(cfg, reg,
   540  		"account_config_gdpr_tcf2_purpose9_warn",
   541  		"Count of requests referencing an account whose config specifies a deprecated gdpr.tcf2.purpose9 field")
   542  	metrics.accountDeprecationWarningsPurpose10 = newCounterWithoutLabels(cfg, reg,
   543  		"account_config_gdpr_tcf2_purpose10_warn",
   544  		"Count of requests referencing an account whose config specifies a deprecated gdpr.tcf2.purpose10 field")
   545  
   546  	metrics.channelEnabledCCPA = newCounterWithoutLabels(cfg, reg,
   547  		"account_config_ccpa_channel_enabled_warn",
   548  		"Count of requests referencing an account whose config specifies a depreceated ccpa.channel_enabled field")
   549  	metrics.channelEnabledGDPR = newCounterWithoutLabels(cfg, reg,
   550  		"account_config_gdpr_channel_enabled_warn",
   551  		"Count of requests referencing an account whose config specifies a depreceated gdpr.channel_enabled field")
   552  
   553  	metrics.accountDeprecationSummary = newCounterWithoutLabels(cfg, reg,
   554  		"account_config_summary",
   555  		"Count of deprecated account config fields encountered across all accounts")
   556  
   557  	createModulesMetrics(cfg, reg, &metrics, moduleStageNames, standardTimeBuckets)
   558  
   559  	metrics.Gatherer = reg
   560  
   561  	metricsPrefix := ""
   562  	if len(cfg.Namespace) > 0 {
   563  		metricsPrefix += fmt.Sprintf("%s_", cfg.Namespace)
   564  	}
   565  	if len(cfg.Subsystem) > 0 {
   566  		metricsPrefix += fmt.Sprintf("%s_", cfg.Subsystem)
   567  	}
   568  
   569  	metrics.Registerer = prometheus.WrapRegistererWithPrefix(metricsPrefix, reg)
   570  	metrics.Registerer.MustRegister(promCollector.NewGoCollector())
   571  
   572  	preloadLabelValues(&metrics, syncerKeys, moduleStageNames)
   573  
   574  	return &metrics
   575  }
   576  
   577  func createModulesMetrics(cfg config.PrometheusMetrics, registry *prometheus.Registry, m *Metrics, moduleStageNames map[string][]string, standardTimeBuckets []float64) {
   578  	l := len(moduleStageNames)
   579  	m.moduleDuration = make(map[string]*prometheus.HistogramVec, l)
   580  	m.moduleCalls = make(map[string]*prometheus.CounterVec, l)
   581  	m.moduleFailures = make(map[string]*prometheus.CounterVec, l)
   582  	m.moduleSuccessNoops = make(map[string]*prometheus.CounterVec, l)
   583  	m.moduleSuccessUpdates = make(map[string]*prometheus.CounterVec, l)
   584  	m.moduleSuccessRejects = make(map[string]*prometheus.CounterVec, l)
   585  	m.moduleExecutionErrors = make(map[string]*prometheus.CounterVec, l)
   586  	m.moduleTimeouts = make(map[string]*prometheus.CounterVec, l)
   587  
   588  	// create for each registered module its own metric
   589  	for module := range moduleStageNames {
   590  		m.moduleDuration[module] = newHistogramVec(cfg, registry,
   591  			fmt.Sprintf("modules_%s_duration", module),
   592  			"Amount of seconds a module processed a hook labeled by stage name.",
   593  			[]string{stageLabel},
   594  			standardTimeBuckets)
   595  
   596  		m.moduleCalls[module] = newCounter(cfg, registry,
   597  			fmt.Sprintf("modules_%s_called", module),
   598  			"Count of module calls labeled by stage name.",
   599  			[]string{stageLabel})
   600  
   601  		m.moduleFailures[module] = newCounter(cfg, registry,
   602  			fmt.Sprintf("modules_%s_failed", module),
   603  			"Count of module fails labeled by stage name.",
   604  			[]string{stageLabel})
   605  
   606  		m.moduleSuccessNoops[module] = newCounter(cfg, registry,
   607  			fmt.Sprintf("modules_%s_success_noops", module),
   608  			"Count of module successful noops labeled by stage name.",
   609  			[]string{stageLabel})
   610  
   611  		m.moduleSuccessUpdates[module] = newCounter(cfg, registry,
   612  			fmt.Sprintf("modules_%s_success_updates", module),
   613  			"Count of module successful updates labeled by stage name.",
   614  			[]string{stageLabel})
   615  
   616  		m.moduleSuccessRejects[module] = newCounter(cfg, registry,
   617  			fmt.Sprintf("modules_%s_success_rejects", module),
   618  			"Count of module successful rejects labeled by stage name.",
   619  			[]string{stageLabel})
   620  
   621  		m.moduleExecutionErrors[module] = newCounter(cfg, registry,
   622  			fmt.Sprintf("modules_%s_execution_errors", module),
   623  			"Count of module execution errors labeled by stage name.",
   624  			[]string{stageLabel})
   625  
   626  		m.moduleTimeouts[module] = newCounter(cfg, registry,
   627  			fmt.Sprintf("modules_%s_timeouts", module),
   628  			"Count of module timeouts labeled by stage name.",
   629  			[]string{stageLabel})
   630  	}
   631  }
   632  
   633  func newCounter(cfg config.PrometheusMetrics, registry *prometheus.Registry, name, help string, labels []string) *prometheus.CounterVec {
   634  	opts := prometheus.CounterOpts{
   635  		Namespace: cfg.Namespace,
   636  		Subsystem: cfg.Subsystem,
   637  		Name:      name,
   638  		Help:      help,
   639  	}
   640  	counter := prometheus.NewCounterVec(opts, labels)
   641  	registry.MustRegister(counter)
   642  	return counter
   643  }
   644  
   645  func newCounterWithoutLabels(cfg config.PrometheusMetrics, registry *prometheus.Registry, name, help string) prometheus.Counter {
   646  	opts := prometheus.CounterOpts{
   647  		Namespace: cfg.Namespace,
   648  		Subsystem: cfg.Subsystem,
   649  		Name:      name,
   650  		Help:      help,
   651  	}
   652  	counter := prometheus.NewCounter(opts)
   653  	registry.MustRegister(counter)
   654  	return counter
   655  }
   656  
   657  func newHistogramVec(cfg config.PrometheusMetrics, registry *prometheus.Registry, name, help string, labels []string, buckets []float64) *prometheus.HistogramVec {
   658  	opts := prometheus.HistogramOpts{
   659  		Namespace: cfg.Namespace,
   660  		Subsystem: cfg.Subsystem,
   661  		Name:      name,
   662  		Help:      help,
   663  		Buckets:   buckets,
   664  	}
   665  	histogram := prometheus.NewHistogramVec(opts, labels)
   666  	registry.MustRegister(histogram)
   667  	return histogram
   668  }
   669  
   670  func newHistogram(cfg config.PrometheusMetrics, registry *prometheus.Registry, name, help string, buckets []float64) prometheus.Histogram {
   671  	opts := prometheus.HistogramOpts{
   672  		Namespace: cfg.Namespace,
   673  		Subsystem: cfg.Subsystem,
   674  		Name:      name,
   675  		Help:      help,
   676  		Buckets:   buckets,
   677  	}
   678  	histogram := prometheus.NewHistogram(opts)
   679  	registry.MustRegister(histogram)
   680  	return histogram
   681  }
   682  
   683  func (m *Metrics) RecordConnectionAccept(success bool) {
   684  	if success {
   685  		m.connectionsOpened.Inc()
   686  	} else {
   687  		m.connectionsError.With(prometheus.Labels{
   688  			connectionErrorLabel: connectionAcceptError,
   689  		}).Inc()
   690  	}
   691  }
   692  
   693  func (m *Metrics) RecordTMaxTimeout() {
   694  	m.tmaxTimeout.Inc()
   695  }
   696  
   697  func (m *Metrics) RecordConnectionClose(success bool) {
   698  	if success {
   699  		m.connectionsClosed.Inc()
   700  	} else {
   701  		m.connectionsError.With(prometheus.Labels{
   702  			connectionErrorLabel: connectionCloseError,
   703  		}).Inc()
   704  	}
   705  }
   706  
   707  func (m *Metrics) RecordRequest(labels metrics.Labels) {
   708  	m.requests.With(prometheus.Labels{
   709  		requestTypeLabel:   string(labels.RType),
   710  		requestStatusLabel: string(labels.RequestStatus),
   711  	}).Inc()
   712  
   713  	if labels.CookieFlag == metrics.CookieFlagNo {
   714  		m.requestsWithoutCookie.With(prometheus.Labels{
   715  			requestTypeLabel: string(labels.RType),
   716  		}).Inc()
   717  	}
   718  
   719  	if labels.PubID != metrics.PublisherUnknown {
   720  		m.accountRequests.With(prometheus.Labels{
   721  			accountLabel: labels.PubID,
   722  		}).Inc()
   723  	}
   724  }
   725  
   726  func (m *Metrics) RecordDebugRequest(debugEnabled bool, pubID string) {
   727  	if debugEnabled {
   728  		m.debugRequests.Inc()
   729  		if !m.metricsDisabled.AccountDebug && pubID != metrics.PublisherUnknown {
   730  			m.accountDebugRequests.With(prometheus.Labels{
   731  				accountLabel: pubID,
   732  			}).Inc()
   733  		}
   734  	}
   735  }
   736  
   737  func (m *Metrics) RecordAccountGDPRPurposeWarning(account string, purposeName string) {
   738  	if account != metrics.PublisherUnknown {
   739  		switch purposeName {
   740  		case "purpose1":
   741  			m.accountDeprecationWarningsPurpose1.Inc()
   742  		case "purpose2":
   743  			m.accountDeprecationWarningsPurpose2.Inc()
   744  		case "purpose3":
   745  			m.accountDeprecationWarningsPurpose3.Inc()
   746  		case "purpose4":
   747  			m.accountDeprecationWarningsPurpose4.Inc()
   748  		case "purpose5":
   749  			m.accountDeprecationWarningsPurpose5.Inc()
   750  		case "purpose6":
   751  			m.accountDeprecationWarningsPurpose6.Inc()
   752  		case "purpose7":
   753  			m.accountDeprecationWarningsPurpose7.Inc()
   754  		case "purpose8":
   755  			m.accountDeprecationWarningsPurpose8.Inc()
   756  		case "purpose9":
   757  			m.accountDeprecationWarningsPurpose9.Inc()
   758  		case "purpose10":
   759  			m.accountDeprecationWarningsPurpose10.Inc()
   760  		}
   761  	}
   762  }
   763  
   764  func (m *Metrics) RecordAccountGDPRChannelEnabledWarning(account string) {
   765  	if account != metrics.PublisherUnknown {
   766  		m.channelEnabledGDPR.Inc()
   767  	}
   768  }
   769  
   770  func (m *Metrics) RecordAccountCCPAChannelEnabledWarning(account string) {
   771  	if account != metrics.PublisherUnknown {
   772  		m.channelEnabledCCPA.Inc()
   773  	}
   774  }
   775  
   776  func (m *Metrics) RecordAccountUpgradeStatus(account string) {
   777  	if account != metrics.PublisherUnknown {
   778  		m.accountDeprecationSummary.Inc()
   779  	}
   780  }
   781  
   782  func (m *Metrics) RecordStoredResponse(pubId string) {
   783  	m.storedResponses.Inc()
   784  	if !m.metricsDisabled.AccountStoredResponses && pubId != metrics.PublisherUnknown {
   785  		m.accountStoredResponses.With(prometheus.Labels{
   786  			accountLabel: pubId,
   787  		}).Inc()
   788  	}
   789  }
   790  
   791  func (m *Metrics) RecordImps(labels metrics.ImpLabels) {
   792  	m.impressions.With(prometheus.Labels{
   793  		isBannerLabel: strconv.FormatBool(labels.BannerImps),
   794  		isVideoLabel:  strconv.FormatBool(labels.VideoImps),
   795  		isAudioLabel:  strconv.FormatBool(labels.AudioImps),
   796  		isNativeLabel: strconv.FormatBool(labels.NativeImps),
   797  	}).Inc()
   798  }
   799  
   800  func (m *Metrics) RecordRequestTime(labels metrics.Labels, length time.Duration) {
   801  	if labels.RequestStatus == metrics.RequestStatusOK {
   802  		m.requestsTimer.With(prometheus.Labels{
   803  			requestTypeLabel: string(labels.RType),
   804  		}).Observe(length.Seconds())
   805  	}
   806  }
   807  
   808  func (m *Metrics) RecordStoredDataFetchTime(labels metrics.StoredDataLabels, length time.Duration) {
   809  	switch labels.DataType {
   810  	case metrics.AccountDataType:
   811  		m.storedAccountFetchTimer.With(prometheus.Labels{
   812  			storedDataFetchTypeLabel: string(labels.DataFetchType),
   813  		}).Observe(length.Seconds())
   814  	case metrics.AMPDataType:
   815  		m.storedAMPFetchTimer.With(prometheus.Labels{
   816  			storedDataFetchTypeLabel: string(labels.DataFetchType),
   817  		}).Observe(length.Seconds())
   818  	case metrics.CategoryDataType:
   819  		m.storedCategoryFetchTimer.With(prometheus.Labels{
   820  			storedDataFetchTypeLabel: string(labels.DataFetchType),
   821  		}).Observe(length.Seconds())
   822  	case metrics.RequestDataType:
   823  		m.storedRequestFetchTimer.With(prometheus.Labels{
   824  			storedDataFetchTypeLabel: string(labels.DataFetchType),
   825  		}).Observe(length.Seconds())
   826  	case metrics.VideoDataType:
   827  		m.storedVideoFetchTimer.With(prometheus.Labels{
   828  			storedDataFetchTypeLabel: string(labels.DataFetchType),
   829  		}).Observe(length.Seconds())
   830  	case metrics.ResponseDataType:
   831  		m.storedResponsesFetchTimer.With(prometheus.Labels{
   832  			storedDataFetchTypeLabel: string(labels.DataFetchType),
   833  		}).Observe(length.Seconds())
   834  	}
   835  }
   836  
   837  func (m *Metrics) RecordStoredDataError(labels metrics.StoredDataLabels) {
   838  	switch labels.DataType {
   839  	case metrics.AccountDataType:
   840  		m.storedAccountErrors.With(prometheus.Labels{
   841  			storedDataErrorLabel: string(labels.Error),
   842  		}).Inc()
   843  	case metrics.AMPDataType:
   844  		m.storedAMPErrors.With(prometheus.Labels{
   845  			storedDataErrorLabel: string(labels.Error),
   846  		}).Inc()
   847  	case metrics.CategoryDataType:
   848  		m.storedCategoryErrors.With(prometheus.Labels{
   849  			storedDataErrorLabel: string(labels.Error),
   850  		}).Inc()
   851  	case metrics.RequestDataType:
   852  		m.storedRequestErrors.With(prometheus.Labels{
   853  			storedDataErrorLabel: string(labels.Error),
   854  		}).Inc()
   855  	case metrics.VideoDataType:
   856  		m.storedVideoErrors.With(prometheus.Labels{
   857  			storedDataErrorLabel: string(labels.Error),
   858  		}).Inc()
   859  	case metrics.ResponseDataType:
   860  		m.storedResponsesErrors.With(prometheus.Labels{
   861  			storedDataErrorLabel: string(labels.Error),
   862  		}).Inc()
   863  	}
   864  }
   865  
   866  func (m *Metrics) RecordAdapterRequest(labels metrics.AdapterLabels) {
   867  	m.adapterRequests.With(prometheus.Labels{
   868  		adapterLabel: string(labels.Adapter),
   869  		cookieLabel:  string(labels.CookieFlag),
   870  		hasBidsLabel: strconv.FormatBool(labels.AdapterBids == metrics.AdapterBidPresent),
   871  	}).Inc()
   872  
   873  	for err := range labels.AdapterErrors {
   874  		m.adapterErrors.With(prometheus.Labels{
   875  			adapterLabel:      string(labels.Adapter),
   876  			adapterErrorLabel: string(err),
   877  		}).Inc()
   878  	}
   879  }
   880  
   881  // Keeps track of created and reused connections to adapter bidders and the time from the
   882  // connection request, to the connection creation, or reuse from the pool across all engines
   883  func (m *Metrics) RecordAdapterConnections(adapterName openrtb_ext.BidderName, connWasReused bool, connWaitTime time.Duration) {
   884  	if m.metricsDisabled.AdapterConnectionMetrics {
   885  		return
   886  	}
   887  
   888  	if connWasReused {
   889  		m.adapterReusedConnections.With(prometheus.Labels{
   890  			adapterLabel: string(adapterName),
   891  		}).Inc()
   892  	} else {
   893  		m.adapterCreatedConnections.With(prometheus.Labels{
   894  			adapterLabel: string(adapterName),
   895  		}).Inc()
   896  	}
   897  
   898  	m.adapterConnectionWaitTime.With(prometheus.Labels{
   899  		adapterLabel: string(adapterName),
   900  	}).Observe(connWaitTime.Seconds())
   901  }
   902  
   903  func (m *Metrics) RecordDNSTime(dnsLookupTime time.Duration) {
   904  	m.dnsLookupTimer.Observe(dnsLookupTime.Seconds())
   905  }
   906  
   907  func (m *Metrics) RecordTLSHandshakeTime(tlsHandshakeTime time.Duration) {
   908  	m.tlsHandhakeTimer.Observe(tlsHandshakeTime.Seconds())
   909  }
   910  
   911  func (m *Metrics) RecordBidderServerResponseTime(bidderServerResponseTime time.Duration) {
   912  	m.bidderServerResponseTimer.Observe(bidderServerResponseTime.Seconds())
   913  }
   914  
   915  func (m *Metrics) RecordAdapterPanic(labels metrics.AdapterLabels) {
   916  	m.adapterPanics.With(prometheus.Labels{
   917  		adapterLabel: string(labels.Adapter),
   918  	}).Inc()
   919  }
   920  
   921  func (m *Metrics) RecordAdapterBidReceived(labels metrics.AdapterLabels, bidType openrtb_ext.BidType, hasAdm bool) {
   922  	markupDelivery := markupDeliveryNurl
   923  	if hasAdm {
   924  		markupDelivery = markupDeliveryAdm
   925  	}
   926  
   927  	m.adapterBids.With(prometheus.Labels{
   928  		adapterLabel:        string(labels.Adapter),
   929  		markupDeliveryLabel: markupDelivery,
   930  	}).Inc()
   931  }
   932  
   933  func (m *Metrics) RecordAdapterPrice(labels metrics.AdapterLabels, cpm float64) {
   934  	m.adapterPrices.With(prometheus.Labels{
   935  		adapterLabel: string(labels.Adapter),
   936  	}).Observe(cpm)
   937  }
   938  
   939  func (m *Metrics) RecordOverheadTime(overhead metrics.OverheadType, duration time.Duration) {
   940  	m.overheadTimer.With(prometheus.Labels{
   941  		overheadTypeLabel: overhead.String(),
   942  	}).Observe(duration.Seconds())
   943  }
   944  
   945  func (m *Metrics) RecordAdapterTime(labels metrics.AdapterLabels, length time.Duration) {
   946  	if len(labels.AdapterErrors) == 0 {
   947  		m.adapterRequestsTimer.With(prometheus.Labels{
   948  			adapterLabel: string(labels.Adapter),
   949  		}).Observe(length.Seconds())
   950  	}
   951  }
   952  
   953  func (m *Metrics) RecordCookieSync(status metrics.CookieSyncStatus) {
   954  	m.cookieSync.With(prometheus.Labels{
   955  		statusLabel: string(status),
   956  	}).Inc()
   957  }
   958  
   959  func (m *Metrics) RecordSyncerRequest(key string, status metrics.SyncerCookieSyncStatus) {
   960  	m.syncerRequests.With(prometheus.Labels{
   961  		syncerLabel: key,
   962  		statusLabel: string(status),
   963  	}).Inc()
   964  }
   965  
   966  func (m *Metrics) RecordSetUid(status metrics.SetUidStatus) {
   967  	m.setUid.With(prometheus.Labels{
   968  		statusLabel: string(status),
   969  	}).Inc()
   970  }
   971  
   972  func (m *Metrics) RecordSyncerSet(key string, status metrics.SyncerSetUidStatus) {
   973  	m.syncerSets.With(prometheus.Labels{
   974  		syncerLabel: key,
   975  		statusLabel: string(status),
   976  	}).Inc()
   977  }
   978  
   979  func (m *Metrics) RecordStoredReqCacheResult(cacheResult metrics.CacheResult, inc int) {
   980  	m.storedRequestCacheResult.With(prometheus.Labels{
   981  		cacheResultLabel: string(cacheResult),
   982  	}).Add(float64(inc))
   983  }
   984  
   985  func (m *Metrics) RecordStoredImpCacheResult(cacheResult metrics.CacheResult, inc int) {
   986  	m.storedImpressionsCacheResult.With(prometheus.Labels{
   987  		cacheResultLabel: string(cacheResult),
   988  	}).Add(float64(inc))
   989  }
   990  
   991  func (m *Metrics) RecordAccountCacheResult(cacheResult metrics.CacheResult, inc int) {
   992  	m.accountCacheResult.With(prometheus.Labels{
   993  		cacheResultLabel: string(cacheResult),
   994  	}).Add(float64(inc))
   995  }
   996  
   997  func (m *Metrics) RecordPrebidCacheRequestTime(success bool, length time.Duration) {
   998  	m.prebidCacheWriteTimer.With(prometheus.Labels{
   999  		successLabel: strconv.FormatBool(success),
  1000  	}).Observe(length.Seconds())
  1001  }
  1002  
  1003  func (m *Metrics) RecordRequestQueueTime(success bool, requestType metrics.RequestType, length time.Duration) {
  1004  	successLabelFormatted := requestRejectLabel
  1005  	if success {
  1006  		successLabelFormatted = requestSuccessLabel
  1007  	}
  1008  	m.requestsQueueTimer.With(prometheus.Labels{
  1009  		requestTypeLabel:   string(requestType),
  1010  		requestStatusLabel: successLabelFormatted,
  1011  	}).Observe(length.Seconds())
  1012  }
  1013  
  1014  func (m *Metrics) RecordTimeoutNotice(success bool) {
  1015  	if success {
  1016  		m.timeoutNotifications.With(prometheus.Labels{
  1017  			successLabel: requestSuccessful,
  1018  		}).Inc()
  1019  	} else {
  1020  		m.timeoutNotifications.With(prometheus.Labels{
  1021  			successLabel: requestFailed,
  1022  		}).Inc()
  1023  	}
  1024  }
  1025  
  1026  func (m *Metrics) RecordRequestPrivacy(privacy metrics.PrivacyLabels) {
  1027  	if privacy.CCPAProvided {
  1028  		m.privacyCCPA.With(prometheus.Labels{
  1029  			sourceLabel: sourceRequest,
  1030  			optOutLabel: strconv.FormatBool(privacy.CCPAEnforced),
  1031  		}).Inc()
  1032  	}
  1033  
  1034  	if privacy.COPPAEnforced {
  1035  		m.privacyCOPPA.With(prometheus.Labels{
  1036  			sourceLabel: sourceRequest,
  1037  		}).Inc()
  1038  	}
  1039  
  1040  	if privacy.GDPREnforced {
  1041  		m.privacyTCF.With(prometheus.Labels{
  1042  			versionLabel: string(privacy.GDPRTCFVersion),
  1043  			sourceLabel:  sourceRequest,
  1044  		}).Inc()
  1045  	}
  1046  
  1047  	if privacy.LMTEnforced {
  1048  		m.privacyLMT.With(prometheus.Labels{
  1049  			sourceLabel: sourceRequest,
  1050  		}).Inc()
  1051  	}
  1052  }
  1053  
  1054  func (m *Metrics) RecordAdapterGDPRRequestBlocked(adapterName openrtb_ext.BidderName) {
  1055  	if m.metricsDisabled.AdapterGDPRRequestBlocked {
  1056  		return
  1057  	}
  1058  
  1059  	m.adapterGDPRBlockedRequests.With(prometheus.Labels{
  1060  		adapterLabel: string(adapterName),
  1061  	}).Inc()
  1062  }
  1063  
  1064  func (m *Metrics) RecordAdsCertReq(success bool) {
  1065  	if success {
  1066  		m.adsCertRequests.With(prometheus.Labels{
  1067  			successLabel: requestSuccessful,
  1068  		}).Inc()
  1069  	} else {
  1070  		m.adsCertRequests.With(prometheus.Labels{
  1071  			successLabel: requestFailed,
  1072  		}).Inc()
  1073  	}
  1074  }
  1075  func (m *Metrics) RecordAdsCertSignTime(adsCertSignTime time.Duration) {
  1076  	m.adsCertSignTimer.Observe(adsCertSignTime.Seconds())
  1077  }
  1078  
  1079  func (m *Metrics) RecordBidValidationCreativeSizeError(adapter openrtb_ext.BidderName, account string) {
  1080  	m.adapterBidResponseValidationSizeError.With(prometheus.Labels{
  1081  		adapterLabel: string(adapter), successLabel: successLabel,
  1082  	}).Inc()
  1083  
  1084  	if !m.metricsDisabled.AccountAdapterDetails && account != metrics.PublisherUnknown {
  1085  		m.accountBidResponseValidationSizeError.With(prometheus.Labels{
  1086  			accountLabel: account, successLabel: successLabel,
  1087  		}).Inc()
  1088  	}
  1089  }
  1090  
  1091  func (m *Metrics) RecordBidValidationCreativeSizeWarn(adapter openrtb_ext.BidderName, account string) {
  1092  	m.adapterBidResponseValidationSizeWarn.With(prometheus.Labels{
  1093  		adapterLabel: string(adapter), successLabel: successLabel,
  1094  	}).Inc()
  1095  
  1096  	if !m.metricsDisabled.AccountAdapterDetails && account != metrics.PublisherUnknown {
  1097  		m.accountBidResponseValidationSizeWarn.With(prometheus.Labels{
  1098  			accountLabel: account, successLabel: successLabel,
  1099  		}).Inc()
  1100  	}
  1101  }
  1102  
  1103  func (m *Metrics) RecordBidValidationSecureMarkupError(adapter openrtb_ext.BidderName, account string) {
  1104  	m.adapterBidResponseSecureMarkupError.With(prometheus.Labels{
  1105  		adapterLabel: string(adapter), successLabel: successLabel,
  1106  	}).Inc()
  1107  
  1108  	if !m.metricsDisabled.AccountAdapterDetails && account != metrics.PublisherUnknown {
  1109  		m.accountBidResponseSecureMarkupError.With(prometheus.Labels{
  1110  			accountLabel: account, successLabel: successLabel,
  1111  		}).Inc()
  1112  	}
  1113  }
  1114  
  1115  func (m *Metrics) RecordBidValidationSecureMarkupWarn(adapter openrtb_ext.BidderName, account string) {
  1116  	m.adapterBidResponseSecureMarkupWarn.With(prometheus.Labels{
  1117  		adapterLabel: string(adapter), successLabel: successLabel,
  1118  	}).Inc()
  1119  
  1120  	if !m.metricsDisabled.AccountAdapterDetails && account != metrics.PublisherUnknown {
  1121  		m.accountBidResponseSecureMarkupWarn.With(prometheus.Labels{
  1122  			accountLabel: account, successLabel: successLabel,
  1123  		}).Inc()
  1124  	}
  1125  }
  1126  
  1127  func (m *Metrics) RecordModuleCalled(labels metrics.ModuleLabels, duration time.Duration) {
  1128  	m.moduleCalls[labels.Module].With(prometheus.Labels{
  1129  		stageLabel: labels.Stage,
  1130  	}).Inc()
  1131  
  1132  	m.moduleDuration[labels.Module].With(prometheus.Labels{
  1133  		stageLabel: labels.Stage,
  1134  	}).Observe(duration.Seconds())
  1135  }
  1136  
  1137  func (m *Metrics) RecordModuleFailed(labels metrics.ModuleLabels) {
  1138  	m.moduleFailures[labels.Module].With(prometheus.Labels{
  1139  		stageLabel: labels.Stage,
  1140  	}).Inc()
  1141  }
  1142  
  1143  func (m *Metrics) RecordModuleSuccessNooped(labels metrics.ModuleLabels) {
  1144  	m.moduleSuccessNoops[labels.Module].With(prometheus.Labels{
  1145  		stageLabel: labels.Stage,
  1146  	}).Inc()
  1147  }
  1148  
  1149  func (m *Metrics) RecordModuleSuccessUpdated(labels metrics.ModuleLabels) {
  1150  	m.moduleSuccessUpdates[labels.Module].With(prometheus.Labels{
  1151  		stageLabel: labels.Stage,
  1152  	}).Inc()
  1153  }
  1154  
  1155  func (m *Metrics) RecordModuleSuccessRejected(labels metrics.ModuleLabels) {
  1156  	m.moduleSuccessRejects[labels.Module].With(prometheus.Labels{
  1157  		stageLabel: labels.Stage,
  1158  	}).Inc()
  1159  }
  1160  
  1161  func (m *Metrics) RecordModuleExecutionError(labels metrics.ModuleLabels) {
  1162  	m.moduleExecutionErrors[labels.Module].With(prometheus.Labels{
  1163  		stageLabel: labels.Stage,
  1164  	}).Inc()
  1165  }
  1166  
  1167  func (m *Metrics) RecordModuleTimeout(labels metrics.ModuleLabels) {
  1168  	m.moduleTimeouts[labels.Module].With(prometheus.Labels{
  1169  		stageLabel: labels.Stage,
  1170  	}).Inc()
  1171  }