cloudflare/pint
Publicmirrored from https://github.com/cloudflare/pintAvailable
docs/CONFIGURATION.md
801lines · modecode
| 1 | # Configuration syntax |
| 2 | |
| 3 | **NOTE** all regex pattern are anchored. |
| 4 | |
| 5 | ## CI |
| 6 | |
| 7 | Configure continuous integration environments. |
| 8 | |
| 9 | Syntax: |
| 10 | |
| 11 | ```JS |
| 12 | ci { |
| 13 | include = [ "(.*)", ... ] |
| 14 | maxCommits = 20 |
| 15 | baseBranch = "master" |
| 16 | } |
| 17 | ``` |
| 18 | |
| 19 | - `include` - list of file patters to checks when running checks. Only files |
| 20 | matching those regex rules will be checked, other modified files will be ignored. |
| 21 | - `maxCommits` - by default pint will try to find all commits on current branch, |
| 22 | this requires full git history to be present, if we have a shallow clone this |
| 23 | might fail to find only current branch commits and give us a huge list. |
| 24 | If the number of commits returned by branch discovery is more than `maxCommits` |
| 25 | then pint will fail to run. |
| 26 | - `baseBranch` - base branch to compare `HEAD` commit with when calculating the list |
| 27 | of commits to check. |
| 28 | |
| 29 | ## Repository |
| 30 | |
| 31 | Configure supported code hosting repository, used for reporting PR checks from CI |
| 32 | back to the repository, to be displayed in the PR UI. |
| 33 | Currently only supports [BitBucket](https://bitbucket.org/) and [GitHub](https://github.com/). |
| 34 | |
| 35 | **NOTE**: BitBucket integration requires `BITBUCKET_AUTH_TOKEN` environment variable |
| 36 | to be set. It should contain a personal access token used to authenticate with the API. |
| 37 | |
| 38 | **NOTE**: GitHub integration requires `GITHUB_AUTH_TOKEN` environment variable |
| 39 | to be set to a personal access key that can access your repository. Also, `GITHUB_PULL_REQUEST_NUMBER` |
| 40 | environment variable needs to point to the pull request number which will be used whilst |
| 41 | submitting comments. |
| 42 | |
| 43 | Syntax: |
| 44 | |
| 45 | ```JS |
| 46 | repository { |
| 47 | bitbucket { |
| 48 | uri = "https://..." |
| 49 | timeout = "30s" |
| 50 | project = "..." |
| 51 | repository = "..." |
| 52 | } |
| 53 | } |
| 54 | ``` |
| 55 | |
| 56 | - `bitbucket:uri` - base URI of this repository, will be used for HTTP |
| 57 | requests to the BitBucket API. |
| 58 | - `bitbucket:timeout` - timeout to be used for API requests. |
| 59 | - `bitbucket:project` - name of the BitBucket project for this repository. |
| 60 | - `bitbucket:repository` - name of the BitBucket repository. |
| 61 | |
| 62 | ```JS |
| 63 | repository { |
| 64 | github { |
| 65 | uri = "https://..." |
| 66 | timeout = "30s" |
| 67 | owner = "..." |
| 68 | repo = "..." |
| 69 | } |
| 70 | } |
| 71 | ``` |
| 72 | |
| 73 | - `github:baseuri` - base URI of GitHub or GitHub enterprise, will be used for HTTP requests to the GitHub API. |
| 74 | - `github:uploaduri` - upload URI of GitHub or GitHub enterprise, will be used for HTTP requests to the GitHub API. |
| 75 | |
| 76 | If `github:baseuri` _or_ `github:uploaduri` are not specified then [GitHub](https://github.com) will be used. |
| 77 | |
| 78 | - `github:timeout` - timeout to be used for API requests; |
| 79 | - `github:owner` - name of the GitHub owner i.e. the first part that comes before the repository's name in the URI; |
| 80 | - `github:repo` - name of the GitHub repository (e.g. `monitoring`). |
| 81 | |
| 82 | ## Prometheus servers |
| 83 | |
| 84 | Some checks work by querying a running Prometheus instance to verify if |
| 85 | metrics used in rules are present. If you want to use those checks then you |
| 86 | first need to define one or more Prometheus servers. |
| 87 | |
| 88 | Syntax: |
| 89 | |
| 90 | ```JS |
| 91 | prometheus "$name" { |
| 92 | uri = "https://..." |
| 93 | timeout = "60s" |
| 94 | paths = ["...", ...] |
| 95 | } |
| 96 | ``` |
| 97 | |
| 98 | - `$name` - each defined server should have a unique name that can be used in check |
| 99 | definitions. |
| 100 | - `uri` - base URI of this Prometheus server, used for API requests and queries. |
| 101 | - `timeout` - timeout to be used for API requests. |
| 102 | - `paths` - optional path filter, if specified only paths matching one of listed regex |
| 103 | patterns will use this Prometheus server for checks. |
| 104 | |
| 105 | Example: |
| 106 | |
| 107 | ```JS |
| 108 | prometheus "prod" { |
| 109 | uri = "https://prometheus-prod.example.com" |
| 110 | timeout = "60s" |
| 111 | } |
| 112 | |
| 113 | prometheus "dev" { |
| 114 | uri = "https://prometheus-dev.example.com" |
| 115 | timeout = "30s" |
| 116 | paths = [ "alerts/test/.*" ] |
| 117 | } |
| 118 | ``` |
| 119 | |
| 120 | ## Matching rules to checks |
| 121 | |
| 122 | Most checks, except basic syntax verification, requires some configuration to decide |
| 123 | which checks to run against which files and rules. |
| 124 | |
| 125 | Syntax: |
| 126 | |
| 127 | ```JS |
| 128 | rule { |
| 129 | match { |
| 130 | path = "(.+)" |
| 131 | name = "(.+)" |
| 132 | kind = "alerting|recording" |
| 133 | annotation "(.*)" { |
| 134 | value = "(.*)" |
| 135 | } |
| 136 | label "(.*)" { |
| 137 | value = "(.*)" |
| 138 | } |
| 139 | } |
| 140 | ignore { |
| 141 | path = "(.+)" |
| 142 | name = "(.+)" |
| 143 | kind = "alerting|recording" |
| 144 | annotation "(.*)" { |
| 145 | value = "(.*)" |
| 146 | } |
| 147 | label "(.*)" { |
| 148 | value = "(.*)" |
| 149 | } |
| 150 | } |
| 151 | |
| 152 | [ check definition ] |
| 153 | ... |
| 154 | [ check definition ] |
| 155 | } |
| 156 | ``` |
| 157 | |
| 158 | - `match:path` - only files matching this pattern will be checked by this rule |
| 159 | - `match:name` - only rules with names (`record` for recording rules and `alert` for alerting |
| 160 | rules) matching this pattern will be checked rule |
| 161 | - `match:kind` - optional rule type filter, only rule of this type will be checked |
| 162 | - `match:annotation` - optional annotation filter, only alert rules with at least one |
| 163 | annotation matching this pattern will be checked by this rule. |
| 164 | - `match:label` - optional annotation filter, only rules with at least one label |
| 165 | matching this pattern will be checked by this rule. For recording rules only static |
| 166 | labels set on the recording rule are considered. |
| 167 | - `ignore` - works exactly like `match` but does the opposite - any alerting or recording rule |
| 168 | matching all conditions defined on `ignore` will not be checked by this `rule` block. |
| 169 | |
| 170 | Example: |
| 171 | |
| 172 | ```JS |
| 173 | rule { |
| 174 | match { |
| 175 | path = "rules/.*" |
| 176 | kind = "alerting" |
| 177 | label "severity" { |
| 178 | value = "(warning|critical)" |
| 179 | } |
| 180 | [ check applied only to severity="critical" and severity="warning" alerts ] |
| 181 | } |
| 182 | } |
| 183 | ``` |
| 184 | |
| 185 | # Check definitions |
| 186 | |
| 187 | ## Aggregation |
| 188 | |
| 189 | This check is used to inspect promql expressions and ensure that specific labels |
| 190 | are kept or stripped away when aggregating results. It's mostly useful in recording |
| 191 | rules. |
| 192 | |
| 193 | Syntax: |
| 194 | |
| 195 | ```JS |
| 196 | aggregate "(.*)" { |
| 197 | severity = "bug|warning|info" |
| 198 | keep = [ "...", ... ] |
| 199 | strip = [ "...", ... ] |
| 200 | } |
| 201 | ``` |
| 202 | |
| 203 | - `severity` - set custom severity for reported issues, defaults to a warning |
| 204 | - `keep` - list of label names that must be preserved |
| 205 | - `strip` - list of label names that must be stripped |
| 206 | |
| 207 | Examples: |
| 208 | |
| 209 | Ensure that all series generated from recording rules have `job` labels preserved: |
| 210 | |
| 211 | ```JS |
| 212 | rule { |
| 213 | match { |
| 214 | kind = "recording" |
| 215 | } |
| 216 | aggregate ".+" { |
| 217 | keep = ["job"] |
| 218 | } |
| 219 | } |
| 220 | ``` |
| 221 | |
| 222 | In some cases you might want to ensure that specific labels are removed in aggregations. |
| 223 | For example in recording rules that are producing series consumed by federation, where |
| 224 | only aggregated results (not per instance) are allowed: |
| 225 | |
| 226 | ```JS |
| 227 | rule { |
| 228 | match { |
| 229 | kind = "recording" |
| 230 | } |
| 231 | aggregate "cluster:.+" { |
| 232 | strip = ["instance"] |
| 233 | } |
| 234 | } |
| 235 | ``` |
| 236 | |
| 237 | By default all issues found by this check will be reported as warnings. To adjust |
| 238 | severity set a custom `severity` key: |
| 239 | |
| 240 | ```JS |
| 241 | aggregate ".+" { |
| 242 | ... |
| 243 | severity = "bug" |
| 244 | } |
| 245 | ``` |
| 246 | |
| 247 | ## Annotations |
| 248 | |
| 249 | This check is used to ensure that all required annotations are set on alerts and that |
| 250 | they have correct values. |
| 251 | |
| 252 | Syntax: |
| 253 | |
| 254 | ```JS |
| 255 | annotation "(.*)" { |
| 256 | severity = "bug|warning|info" |
| 257 | value = "(.*)" |
| 258 | required = true|false |
| 259 | } |
| 260 | ``` |
| 261 | |
| 262 | - `severity` - set custom severity for reported issues, defaults to a warning |
| 263 | - `value` - optional value pattern to enforce |
| 264 | - `required` - if `true` pint will require every alert to have this annotation set, |
| 265 | if `false` it will only check values where annotation is set |
| 266 | |
| 267 | Examples: |
| 268 | |
| 269 | This set of rules will: |
| 270 | - require `summary` annotation to be present, if missing it will be reported as a warning |
| 271 | - if a `dashboard` annotation is provided it must match `https://grafana\.example\.com/.+` |
| 272 | pattern, if it doesn't match that pattern it will be reported as a bug |
| 273 | |
| 274 | ```JS |
| 275 | rule { |
| 276 | match { |
| 277 | kind = "alerting" |
| 278 | } |
| 279 | |
| 280 | annotation "summary" { |
| 281 | required = true |
| 282 | } |
| 283 | |
| 284 | annotation "dashboard" { |
| 285 | severity = "bug" |
| 286 | value = "https://grafana\.example\.com/.+" |
| 287 | } |
| 288 | } |
| 289 | ``` |
| 290 | |
| 291 | ## Labels |
| 292 | |
| 293 | This check works the same way as `annotation` check, but it operates on |
| 294 | labels instead. |
| 295 | It uses static labels set on alerting or recording rule. It doesn't use |
| 296 | labels on time series used in those rules. |
| 297 | |
| 298 | Syntax: |
| 299 | |
| 300 | ```JS |
| 301 | label "(.*)" { |
| 302 | severity = "bug|warning|info" |
| 303 | value = "..." |
| 304 | required = true|false |
| 305 | } |
| 306 | ``` |
| 307 | |
| 308 | Example: |
| 309 | |
| 310 | Require `severity` label to be set on alert rules with two all possible values: |
| 311 | |
| 312 | ```JS |
| 313 | rule { |
| 314 | match { |
| 315 | kind = "alerting" |
| 316 | } |
| 317 | |
| 318 | label "severity" { |
| 319 | value = "(warning|critical)" |
| 320 | required = true |
| 321 | } |
| 322 | } |
| 323 | ``` |
| 324 | |
| 325 | ## Rate |
| 326 | |
| 327 | This check inspects `rate()` and `irate()` functions and warns if used duration |
| 328 | is too low. It does so by first getting global `scrape_interval` value for selected |
| 329 | Prometheus servers and comparing duration to it. |
| 330 | Reported issue depends on a few factors: |
| 331 | |
| 332 | For `rate()` function: |
| 333 | - If duration is less than 2x `scrape_interval` it will report a bug. |
| 334 | - If duration is between 2x and 4x `scrape_interval` it will report a warning. |
| 335 | |
| 336 | For `irate()` function: |
| 337 | - If duration is less than 2x `scrape_interval` it will report a bug. |
| 338 | - If duration is between 2x and 3x `scrape_interval` it will report a warning. |
| 339 | |
| 340 | Syntax: |
| 341 | |
| 342 | ```JS |
| 343 | rate {} |
| 344 | ``` |
| 345 | |
| 346 | Example: |
| 347 | |
| 348 | ```JS |
| 349 | prometheus "prod" { |
| 350 | uri = "https://prometheus-prod.example.com" |
| 351 | timeout = "60s" |
| 352 | } |
| 353 | |
| 354 | prometheus "dev" { |
| 355 | uri = "https://prometheus-dev.example.com" |
| 356 | timeout = "30s" |
| 357 | } |
| 358 | |
| 359 | rule { |
| 360 | match { |
| 361 | kind = "recording" |
| 362 | } |
| 363 | |
| 364 | rate {} |
| 365 | } |
| 366 | ``` |
| 367 | |
| 368 | ## Alerts |
| 369 | |
| 370 | This check is used to estimate how many times given alert would fire. |
| 371 | It will run `expr` query from every alert rule against selected Prometheus |
| 372 | servers and report how many unique alerts it would generate. |
| 373 | If `for` is set on alerts it will be used to adjust results. |
| 374 | |
| 375 | Syntax: |
| 376 | |
| 377 | ```JS |
| 378 | alerts { |
| 379 | range = "1h" |
| 380 | step = "1m" |
| 381 | resolve = "5m" |
| 382 | } |
| 383 | ``` |
| 384 | |
| 385 | - `range` - query range, how far to look back, `1h` would mean that pint will |
| 386 | query last 1h of metrics. If a query results in a timeout pint will retry it |
| 387 | with 50% smaller range until it succeeds. |
| 388 | Defaults to `1d`. |
| 389 | - `step` - query resolution, for most accurate result use step equal |
| 390 | to `scrape_interval`, try to reduce it if that would load too many samples. |
| 391 | Defaults to `1m`. |
| 392 | - `resolve` - duration after which stale alerts are resolved. Defaults to `5m`. |
| 393 | |
| 394 | Example: |
| 395 | |
| 396 | ```JS |
| 397 | prometheus "prod" { |
| 398 | uri = "https://prometheus-prod.example.com" |
| 399 | timeout = "60s" |
| 400 | } |
| 401 | |
| 402 | rule { |
| 403 | match { |
| 404 | kind = "recording" |
| 405 | } |
| 406 | alerts { |
| 407 | range = "1d" |
| 408 | step = "1m" |
| 409 | resolve = "5m" |
| 410 | } |
| 411 | } |
| 412 | ``` |
| 413 | |
| 414 | ## Comparison |
| 415 | |
| 416 | This check enforces use of a comparison operator in alert queries. |
| 417 | Since any query result triggers an alert usual query would be something |
| 418 | like `error_count > 10`, so we only get `error_count` series if the value |
| 419 | is above 10. If we would remove `> 10` part query would always return `error_count` |
| 420 | and so it would always trigger an alert. |
| 421 | |
| 422 | Syntax: |
| 423 | |
| 424 | ```JS |
| 425 | comparison { |
| 426 | severity = "bug|warning|info" |
| 427 | } |
| 428 | ``` |
| 429 | |
| 430 | - `severity` - set custom severity for reported issues, defaults to a bug. |
| 431 | |
| 432 | Example: |
| 433 | |
| 434 | ``` |
| 435 | rule { |
| 436 | match { |
| 437 | kind = "alerting" |
| 438 | } |
| 439 | comparison {} |
| 440 | } |
| 441 | ``` |
| 442 | |
| 443 | |
| 444 | ## Cost |
| 445 | |
| 446 | This check is used to calculate cost of a query and optionally report an issue |
| 447 | if that cost is too high. It will run `expr` query from every rule against |
| 448 | selected Prometheus servers and report results. |
| 449 | This check can be used for both recording and alerting rules, but is most |
| 450 | useful for recording rules. |
| 451 | |
| 452 | Syntax: |
| 453 | |
| 454 | ```JS |
| 455 | cost { |
| 456 | severity = "bug|warning|info" |
| 457 | bytesPerSample = 1024 |
| 458 | maxSeries = 5000 |
| 459 | } |
| 460 | ``` |
| 461 | |
| 462 | - `severity` - set custom severity for reported issues, defaults to a warning. |
| 463 | This is only used when query result series exceed `maxSeries` value (if set). |
| 464 | If `maxSeries` is not set or when results count is below it pint will still |
| 465 | report it as information. |
| 466 | - `bytesPerSample` - if set results will use this to calculate estimated memory |
| 467 | required to store returned series in Prometheus. |
| 468 | - `maxSeries` - if set and number of results for given query exceeds this value |
| 469 | it will be reported as a bug (or custom severity if `severity` is set). |
| 470 | |
| 471 | Examples: |
| 472 | |
| 473 | All rules from files matching `rules/dev/.+` pattern will be tested against |
| 474 | `dev` server. Results will be reported as information regardless of results. |
| 475 | |
| 476 | ```JS |
| 477 | prometheus "dev" { |
| 478 | uri = "https://prometheus-dev.example.com" |
| 479 | timeout = "30s" |
| 480 | paths = ["rules/dev/.+"] |
| 481 | } |
| 482 | |
| 483 | rule { |
| 484 | cost {} |
| 485 | } |
| 486 | ``` |
| 487 | |
| 488 | To add memory usage estimate we first need to get average bytes per sample. |
| 489 | This can be be estimated using two different queries: |
| 490 | |
| 491 | - for RSS usage: `process_resident_memory_bytes / prometheus_tsdb_head_series` |
| 492 | - for Go allocations: `go_memstats_alloc_bytes / prometheus_tsdb_head_series` |
| 493 | |
| 494 | Since Go uses garbage collector RSS memory will be more than the sum of all |
| 495 | memory allocations. RSS usage will be "worst case" while "Go alloc" best case, |
| 496 | while real memory usage will be somewhere in between, depending on many factors |
| 497 | like memory pressure, Go version, GOGC settings etc. |
| 498 | |
| 499 | ```JS |
| 500 | ... |
| 501 | cost { |
| 502 | bytesPerSample = 4096 |
| 503 | } |
| 504 | } |
| 505 | ``` |
| 506 | |
| 507 | ## Series |
| 508 | |
| 509 | This check will also query Prometheus servers, it is used to warn about queries |
| 510 | that are using metrics not currently present in Prometheus. |
| 511 | It parses `expr` query from every rule, finds individual metric selectors and |
| 512 | checks if they return any values. |
| 513 | |
| 514 | Let's say we have a rule this query: `sum(my_metric{foo="bar"}) > 10`. |
| 515 | This checks would query all configured server for the existence of |
| 516 | `my_metric{foo="bar"}` series and report a warning if it's missing. |
| 517 | |
| 518 | Syntax: |
| 519 | |
| 520 | ```JS |
| 521 | series { |
| 522 | severity = "bug|warning|info" |
| 523 | } |
| 524 | ``` |
| 525 | |
| 526 | - `severity` - set custom severity for reported issues, defaults to a warning. |
| 527 | |
| 528 | Example: |
| 529 | |
| 530 | ```JS |
| 531 | prometheus "dev" { |
| 532 | uri = "https://prometheus-dev.example.com" |
| 533 | timeout = "30s" |
| 534 | } |
| 535 | |
| 536 | prometheus "prod" { |
| 537 | uri = "https://prometheus-prod.example.com" |
| 538 | timeout = "30s" |
| 539 | } |
| 540 | |
| 541 | rule { |
| 542 | match { |
| 543 | kind = "recording" |
| 544 | } |
| 545 | |
| 546 | series {} |
| 547 | } |
| 548 | ``` |
| 549 | |
| 550 | ## Reject |
| 551 | |
| 552 | This check allows rejecting label or annotations keys and values |
| 553 | using regexp rules. |
| 554 | |
| 555 | Syntax: |
| 556 | |
| 557 | ```JS |
| 558 | reject "(.*)" { |
| 559 | severity = "bug|warning|info" |
| 560 | label_keys = true|false |
| 561 | label_values = true|false |
| 562 | annotation_keys = true|false |
| 563 | annotation_values = true|false |
| 564 | } |
| 565 | ``` |
| 566 | |
| 567 | - `severity` - set custom severity for reported issues, defaults to a bug. |
| 568 | - `label_keys` - if true label keys for recording and alerting rules will |
| 569 | be checked. |
| 570 | - `label_values` - if true label values for recording and alerting rules will |
| 571 | be checked. |
| 572 | - `annotation_keys` - if true annotation keys for alerting rules will be checked. |
| 573 | - `annotation_values` - if true label values for alerting rules will be checked. |
| 574 | |
| 575 | Example: |
| 576 | |
| 577 | Disallow using URLs as label keys or values: |
| 578 | |
| 579 | ```JS |
| 580 | rule { |
| 581 | match { |
| 582 | kind = "alerting" |
| 583 | } |
| 584 | |
| 585 | reject "https?://.+" { |
| 586 | label_keys = true |
| 587 | label_values = true |
| 588 | } |
| 589 | } |
| 590 | ``` |
| 591 | |
| 592 | Disallow spaces in label and annotation keys: |
| 593 | |
| 594 | ```JS |
| 595 | rule { |
| 596 | reject ".* +.*" { |
| 597 | annotation_keys = true |
| 598 | label_keys = true |
| 599 | } |
| 600 | } |
| 601 | ``` |
| 602 | |
| 603 | ## Template |
| 604 | |
| 605 | This check validates templating used in annotations and labels for alerting rules. |
| 606 | See [Prometheus docs](https://prometheus.io/docs/prometheus/latest/configuration/template_reference/) |
| 607 | for details of supported templating syntax. |
| 608 | |
| 609 | This check will also inspect all alert rules and warn if any of them |
| 610 | uses query return values inside alert labels. |
| 611 | Two alerts are identical if they have identical labels, so using |
| 612 | query value will generate a new unique alert every time it changes. |
| 613 | If alerting rule is using `for` it might prevent it from ever firing |
| 614 | if the value keeps changing before `for` is satisfied, because |
| 615 | Prometheus will consider it to be a new alert and start `for` tracking |
| 616 | from zero. |
| 617 | |
| 618 | If you want to include query value in the alert then use annotations |
| 619 | for that. Annotations are not used to compare alerts identity and so |
| 620 | the value of any annotation can change between alert evaluations. |
| 621 | |
| 622 | See [this blog post](https://www.robustperception.io/dont-put-the-value-in-alert-labels) |
| 623 | for more details. |
| 624 | |
| 625 | Syntax: |
| 626 | |
| 627 | ```JS |
| 628 | template { |
| 629 | severity = "bug|warning|info" |
| 630 | } |
| 631 | ``` |
| 632 | |
| 633 | - `severity` - set custom severity for reported issues, defaults to a bug. |
| 634 | |
| 635 | Example: |
| 636 | |
| 637 | ```JS |
| 638 | rule { |
| 639 | match { |
| 640 | kind = "alerting" |
| 641 | } |
| 642 | |
| 643 | template { |
| 644 | severity = "fatal" |
| 645 | } |
| 646 | } |
| 647 | ``` |
| 648 | |
| 649 | ## Vector Matching |
| 650 | |
| 651 | This check will try to find queries that try to |
| 652 | [match vectors](https://prometheus.io/docs/prometheus/latest/querying/operators/#vector-matching) |
| 653 | but have different sets of labels on both side of the query. |
| 654 | |
| 655 | Consider these two time series: |
| 656 | |
| 657 | ``` |
| 658 | http_errors{job="node-exporter", cluster="prod", instance="server1"} |
| 659 | ``` |
| 660 | |
| 661 | and |
| 662 | |
| 663 | ``` |
| 664 | cluster:http_errors{job="node-exporter", cluster="prod"} |
| 665 | ``` |
| 666 | |
| 667 | One of them tracks specific instance and one aggregates series for the whole cluster. |
| 668 | Because they have different set of labels if we want to calculate some value using both |
| 669 | of them, for example: |
| 670 | |
| 671 | ``` |
| 672 | http_errors / cluster:http_errors |
| 673 | ``` |
| 674 | |
| 675 | we wouldn't get any results. To fix that we need ignore extra labels: |
| 676 | |
| 677 | ``` |
| 678 | http_errors / ignoring(instance) cluster:http_errors |
| 679 | ``` |
| 680 | |
| 681 | This check aims to find all queries that using vector matching where both sides |
| 682 | of the query have different sets of labels causing no results to be returned. |
| 683 | |
| 684 | Syntax: |
| 685 | |
| 686 | ```JS |
| 687 | vector_matching { |
| 688 | severity = "bug|warning|info" |
| 689 | } |
| 690 | ``` |
| 691 | |
| 692 | - `severity` - set custom severity for reported issues, defaults to a warning. |
| 693 | |
| 694 | Example: |
| 695 | |
| 696 | ```JS |
| 697 | prometheus "dev" { |
| 698 | uri = "https://prometheus-dev.example.com" |
| 699 | timeout = "30s" |
| 700 | } |
| 701 | |
| 702 | prometheus "prod" { |
| 703 | uri = "https://prometheus-prod.example.com" |
| 704 | timeout = "30s" |
| 705 | } |
| 706 | |
| 707 | rule { |
| 708 | vector_matching {} |
| 709 | } |
| 710 | ``` |
| 711 | |
| 712 | # Ignoring selected lines or files |
| 713 | |
| 714 | While parsing files pint will look for special comment blocks and use them to |
| 715 | exclude some parts all whole files from checks. |
| 716 | |
| 717 | ## Ignoring whole files |
| 718 | |
| 719 | Add a `# pint ignore/file` comment on top of the file, everything below that line |
| 720 | will be ignored. |
| 721 | |
| 722 | Example: |
| 723 | |
| 724 | ```YAML |
| 725 | # pint ignore/file |
| 726 | |
| 727 | groups: |
| 728 | - name: example |
| 729 | rules: |
| 730 | - record: job:http_inprogress_requests:sum |
| 731 | expr: sum by (job) (http_inprogress_requests) |
| 732 | ``` |
| 733 | |
| 734 | ## Ignoring individual lines |
| 735 | |
| 736 | To ignore just one line use `# pint ignore/line` at the end of that line or |
| 737 | `# ignore/next-line` on the line before. |
| 738 | This is useful if you're linting templates used to generate Prometheus |
| 739 | configuration and it contains some extra lines that are not valid YAML. |
| 740 | |
| 741 | Example: |
| 742 | |
| 743 | ```YAML |
| 744 | {% set some_jinja_var1 = "bar" } # pint ignore/line |
| 745 | groups: |
| 746 | - name: example |
| 747 | rules: |
| 748 | - record: job:http_inprogress_requests:sum |
| 749 | expr: sum by (job) (http_inprogress_requests) |
| 750 | |
| 751 | # pint ignore/next-line |
| 752 | {% set some_jinja_var2 = "foo" } |
| 753 | ``` |
| 754 | |
| 755 | ## Ignoring a range of lines |
| 756 | |
| 757 | To ignore a part of a file wrap it with `# pint ignore/begin` and |
| 758 | `# pint ignore/end` comments. |
| 759 | |
| 760 | Example: |
| 761 | |
| 762 | ```YAML |
| 763 | # pint ignore/begin |
| 764 | {% set some_jinja_var1 = "bar" } |
| 765 | {% set some_jinja_var2 = "foo" } |
| 766 | # pint ignore/end |
| 767 | |
| 768 | groups: |
| 769 | - name: example |
| 770 | rules: |
| 771 | - record: job:http_inprogress_requests:sum |
| 772 | expr: sum by (job) (http_inprogress_requests) |
| 773 | ``` |
| 774 | |
| 775 | ## Disabling individual checks for specific rules |
| 776 | |
| 777 | To disable individual check for a specific rule use `# pint disable ...` comments. |
| 778 | A single comment can only disable one check, so repeat it for every check you wish |
| 779 | to disable. |
| 780 | |
| 781 | To disable `query/cost` check add `# pint disable query/cost` comment anywhere in |
| 782 | the rule. |
| 783 | |
| 784 | Example: |
| 785 | |
| 786 | ```YAML |
| 787 | groups: |
| 788 | - name: example |
| 789 | rules: |
| 790 | - record: instance:http_requests_total:avg_over_time:1w |
| 791 | # pint disable query/cost |
| 792 | expr: avg_over_time(http_requests_total[1w]) by (instance) |
| 793 | ``` |
| 794 | |
| 795 | ```YAML |
| 796 | groups: |
| 797 | - name: example |
| 798 | rules: |
| 799 | - record: instance:http_requests_total:avg_over_time:1w |
| 800 | expr: avg_over_time(http_requests_total[1w]) by (instance) # pint disable query/cost |
| 801 | ``` |
| 802 | |