diff --git a/nezha-fronted/src/assets/css/components/page/dashboard/explore/explore.scss b/nezha-fronted/src/assets/css/components/page/dashboard/explore/explore.scss index 52636689c..fba99f49b 100644 --- a/nezha-fronted/src/assets/css/components/page/dashboard/explore/explore.scss +++ b/nezha-fronted/src/assets/css/components/page/dashboard/explore/explore.scss @@ -54,15 +54,6 @@ } .el-collapse-item__content { padding: 0 30px 20px; - //.chart-body { - // div:nth-of-type(2) { - // background-color: $--chart-background-color !important; - // border-color: $--chart-border-color !important; - // div { - // color: $--color-text-regular; - // } - // } - //} } } .explore { @@ -214,118 +205,122 @@ border-color: $--button-icon-border-color; } } + .binary-operator-precedence{ + ul li{ + list-style: decimal !important; + } + } } /*外部引用 样式start*/ -.doc-content { - font-size: 16px; -} +// .doc-content { +// font-size: 16px; +// } -.doc-content p, -.doc-content.ul, -.doc-content .alert { - margin: 15px 0 15px 0; - line-height: 1.5; - color: $--color-text-primary; -} +// .doc-content p, +// .doc-content.ul, +// .doc-content .alert { +// margin: 15px 0 15px 0; +// line-height: 1.5; +// color: $--color-text-primary; +// } -.doc-content .content-divider { - height: 1px; - width: 100%; - border-bottom: 2px solid $--explore-border-color-bottom; - margin: 5px 0; -} +// .doc-content .content-divider { +// height: 1px; +// width: 100%; +// border-bottom: 2px solid $--explore-border-color-bottom; +// margin: 5px 0; +// } -.doc-content > h1 { - color: #e6522c; - font-size: 30px; - text-transform: uppercase; -} +// .doc-content > h1 { +// color: #e6522c; +// font-size: 30px; +// text-transform: uppercase; +// } -.doc-content > h1 a { - color: #000 !important; -} +// .doc-content > h1 a { +// color: #000 !important; +// } -.doc-content.blog > h1 { - text-transform: none; -} +// .doc-content.blog > h1 { +// text-transform: none; +// } -.doc-content.blog .sponsor-logos > a > img { - width: 250px; - display: inline-block !important; - margin: 15px 55px; -} -.doc-content > h1 { - color: #e6522c; - font-size: 24px; -} +// .doc-content.blog .sponsor-logos > a > img { +// width: 250px; +// display: inline-block !important; +// margin: 15px 55px; +// } +// .doc-content > h1 { +// color: #e6522c; +// font-size: 24px; +// } -.doc-content > h2 { - color: #e6522c; - font-size: 18px; -} +// .doc-content > h2 { +// color: #e6522c; +// font-size: 18px; +// } -.doc-content > h2 code { - color: #e6522c; - background: none; -} +// .doc-content > h2 code { +// color: #e6522c; +// background: none; +// } -.doc-content > h3 { - font-size: 20px; - font-weight: bold; -} +// .doc-content > h3 { +// font-size: 20px; +// font-weight: bold; +// } -.doc-content > h4 { - font-weight: bold; - font-size: 18px; - margin-top: 20px; -} +// .doc-content > h4 { +// font-weight: bold; +// font-size: 18px; +// margin-top: 20px; +// } -.doc-content a.header-anchor { - padding-left: 15px; - color: gray; - text-decoration: none; -} +// .doc-content a.header-anchor { +// padding-left: 15px; +// color: gray; +// text-decoration: none; +// } -.doc-content img { - width: 90%; - margin-left: auto; - margin-right: auto; - display: block; -} +// .doc-content img { +// width: 90%; +// margin-left: auto; +// margin-right: auto; +// display: block; +// } -.doc-content img.orig-size { - width: auto; - margin-left: 0; -} +// .doc-content img.orig-size { +// width: auto; +// margin-left: 0; +// } -.doc-content .open-source-notice { - color: $--color-text-regular; - background-color: $--background-color-base; - text-align: center; - padding: 0.8em; - margin-top: 1.5em; -} +// .doc-content .open-source-notice { +// color: $--color-text-regular; +// background-color: $--background-color-base; +// text-align: center; +// padding: 0.8em; +// margin-top: 1.5em; +// } -.toc { - padding: 1em; - background-color: $--background-color-base; -} +// .toc { +// padding: 1em; +// background-color: $--background-color-base; +// } +// .toc-right { +// float: right; +// width: 40%; +// margin: 0 0 0.5em 0.5em; +// } -.toc-right { - float: right; - width: 40%; - margin: 0 0 0.5em 0.5em; -} +// .toc ul { +// padding: 0 0 0 1.5em; +// margin: 0; +// } -.toc ul { - padding: 0 0 0 1.5em; - margin: 0; -} - -.toc a code { - color: #337ab7; - background-color: transparent; -} +// .toc a code { +// color: #337ab7; +// background-color: transparent; +// } code { color: $--color-text-primary; @@ -340,7 +335,6 @@ aside { article { margin: 10px 0 60px 0; } -/*外部引用 样式end*/ .explore .introduce-view .title-heard.info-room{ position: relative; @@ -440,6 +434,7 @@ article { } } .catalog{ + width: 360px; position: absolute; top: 75px; right: 25px; @@ -450,9 +445,18 @@ article { list-style: circle; color: #3C92F1; } + ul.catalog-square>li{ + list-style: square; + } + ul.catalog-disc>li{ + list-style: disc; + } span:hover{ cursor: pointer; border-bottom: 1px solid #3C92F1; } } + .box-w-auto{ + width: calc(100% - 390px) !important; + } } diff --git a/nezha-fronted/src/components/page/dashboard/explore/exploreItem.vue b/nezha-fronted/src/components/page/dashboard/explore/exploreItem.vue index 5a26831e6..d2fb8e321 100644 --- a/nezha-fronted/src/components/page/dashboard/explore/exploreItem.vue +++ b/nezha-fronted/src/components/page/dashboard/explore/exploreItem.vue @@ -198,110 +198,1050 @@ +
Return all time series with the metric http_requests_total:
Prometheus provides a functional query language called PromQL (Prometheus Query Language) that lets the user select and aggregate time series data in real time. The result of an expression can either be shown as a graph, viewed as tabular data in Prometheus's expression browser, or consumed by external systems via the HTTP API.
+This document is meant as a reference. For learning, it might be easier to start with a couple of examples.
+In Prometheus's expression language, an expression or sub-expression can evaluate to one of four types:
+Depending on the use-case (e.g. when graphing vs. displaying the output of an expression), only some of these types are legal as the result from a user-specified expression. For example, an expression that returns an instant vector is the only type that can be directly graphed.
+Strings may be specified as literals in single quotes, double quotes or backticks.
+PromQL follows the same escaping rules as Go. In single or double quotes a backslash begins an escape sequence, which may be followed by a, b, f, n, r, t, v or \. Specific characters can be provided using octal (\nnn) or hexadecimal (\xnn, \unnnn and \Unnnnnnnn).
No escaping is processed inside backticks. Unlike Go, Prometheus does not discard newlines inside backticks.
+Example:
+"this is a string" +'these are unescaped: \n \\ \t' +`these are not unescaped: \n ' " \t`+
Scalar float values can be written as literal integer or floating-point numbers in the format (whitespace only included for better readability):
+[-+]?( + [0-9]*\.?[0-9]+([eE][-+]?[0-9]+)? + | 0[xX][0-9a-fA-F]+ + | [nN][aA][nN] + | [iI][nN][fF] +)+
Examples:
+23 +-2.43 +3.4e-9 +0x8f +-Inf +NaN+
Instant vector selectors allow the selection of a set of time series and a single sample value for each at a given timestamp (instant): in the simplest form, only a metric name is specified. This results in an instant vector containing elements for all time series that have this metric name.
+This example selects all time series that have the http_requests_total metric name:
http_requests_total+
It is possible to filter these time series further by appending a comma separated list of label matchers in curly braces ({}).
This example selects only those time series with the http_requests_total metric name that also have the job label set to prometheus and their group label set to canary:
http_requests_total{job="prometheus",group="canary"}
+ It is also possible to negatively match a label value, or to match label values against regular expressions. The following label matching operators exist:
+=: Select labels that are exactly equal to the provided string.!=: Select labels that are not equal to the provided string.=~: Select labels that regex-match the provided string.!~: Select labels that do not regex-match the provided string.Regex matches are fully anchored. A match of env=~"foo" is treated as env=~"^foo$".
For example, this selects all http_requests_total time series for staging, testing, and development environments and HTTP methods other than GET.
http_requests_total{environment=~"staging|testing|development",method!="GET"}
+ Label matchers that match empty label values also select all time series that do not have the specific label set at all. It is possible to have multiple matchers for the same label name.
+Vector selectors must either specify a name or at least one label matcher that does not match the empty string. The following expression is illegal:
+{job=~".*"} # Bad!
+ In contrast, these expressions are valid as they both have a selector that does not match empty label values.
+{job=~".+"} # Good!
+{job=~".*",method="get"} # Good!
+ Label matchers can also be applied to metric names by matching against the internal __name__ label. For example, the expression http_requests_total is equivalent to {__name__="http_requests_total"}. Matchers other than = (!=, =~, !~) may also be used. The following expression selects all metrics that have a name starting with job::
{__name__=~"job:.*"}
+ The metric name must not be one of the keywords bool, on, ignoring, group_left and group_right. The following expression is illegal:
on{} # Bad!
+ A workaround for this restriction is to use the __name__ label:
{__name__="on"} # Good!
+ All regular expressions in Prometheus use RE2 syntax.
+Range vector literals work like instant vector literals, except that they select a range of samples back from the current instant. Syntactically, a time duration is appended in square brackets ([]) at the end of a vector selector to specify how far back in time values should be fetched for each resulting range vector element.
In this example, we select all the values we have recorded within the last 5 minutes for all time series that have the metric name http_requests_total and a job label set to prometheus:
http_requests_total{job="prometheus"}[5m]
+ Time durations are specified as a number, followed immediately by one of the following units:
+ms - millisecondss - secondsm - minutesh - hoursd - days - assuming a day has always 24hw - weeks - assuming a week has always 7dy - years - assuming a year has always 365dTime durations can be combined, by concatenation. Units must be ordered from the longest to the shortest. A given unit must only appear once in a time duration.
+Here are some examples of valid time durations:
+5h +1h30m +5m +10s+
The offset modifier allows changing the time offset for individual instant and range vectors in a query.
For example, the following expression returns the value of http_requests_total 5 minutes in the past relative to the current query evaluation time:
http_requests_total offset 5m+
Note that the offset modifier always needs to follow the selector immediately, i.e. the following would be correct:
sum(http_requests_total{method="GET"} offset 5m) // GOOD.
+ While the following would be incorrect:
+sum(http_requests_total{method="GET"}) offset 5m // INVALID.
+ The same works for range vectors. This returns the 5-minute rate that http_requests_total had a week ago:
rate(http_requests_total[5m] offset 1w)+
For comparisons with temporal shifts forward in time, a negative offset can be specified:
+rate(http_requests_total[5m] offset -1w)+
Note that this allows a query to look ahead of its evaluation time.
+The @ modifier allows changing the evaluation time for individual instant and range vectors in a query. The time supplied to the @ modifier is a unix timestamp and described with a float literal.
For example, the following expression returns the value of http_requests_total at 2021-01-04T07:40:00+00:00:
http_requests_total @ 1609746000+
Note that the @ modifier always needs to follow the selector immediately, i.e. the following would be correct:
sum(http_requests_total{method="GET"} @ 1609746000) // GOOD.
+ While the following would be incorrect:
+sum(http_requests_total{method="GET"}) @ 1609746000 // INVALID.
+ The same works for range vectors. This returns the 5-minute rate that http_requests_total had at 2021-01-04T07:40:00+00:00:
rate(http_requests_total[5m] @ 1609746000)+
The @ modifier supports all representation of float literals described above within the limits of int64. It can also be used along with the offset modifier where the offset is applied relative to the @ modifier time irrespective of which modifier is written first. These 2 queries will produce the same result.
# offset after @ +http_requests_total @ 1609746000 offset 5m +# offset before @ +http_requests_total offset 5m @ 1609746000+
Additionally, start() and end() can also be used as values for the @ modifier as special values.
For a range query, they resolve to the start and end of the range query respectively and remain the same for all steps.
+For an instant query, start() and end() both resolve to the evaluation time.
http_requests_total @ start() +rate(http_requests_total[5m] @ end())+
Note that the @ modifier allows a query to look ahead of its evaluation time.
Subquery allows you to run an instant query for a given range and resolution. The result of a subquery is a range vector.
+Syntax: <instant_query> '[' <range> ':' [<resolution>] ']' [ @ <float_literal> ] [ offset <duration> ]
<resolution> is optional. Default is the global evaluation interval.Prometheus supports many binary and aggregation operators. These are described in detail in the expression language operators page.
+Prometheus supports several functions to operate on data. These are described in detail in the expression language functions page.
+PromQL supports line comments that start with #. Example:
# This is a comment+
When queries are run, timestamps at which to sample data are selected independently of the actual present time series data. This is mainly to support cases like aggregation (sum, avg, and so on), where multiple aggregated time series do not exactly align in time. Because of their independence, Prometheus needs to assign a value at those timestamps for each relevant time series. It does so by simply taking the newest sample before this timestamp.
If a target scrape or rule evaluation no longer returns a sample for a time series that was previously present, that time series will be marked as stale. If a target is removed, its previously returned time series will be marked as stale soon afterwards.
+If a query is evaluated at a sampling timestamp after a time series is marked stale, then no value is returned for that time series. If new samples are subsequently ingested for that time series, they will be returned as normal.
+If no sample is found (by default) 5 minutes before a sampling timestamp, no value is returned for that time series at this point in time. This effectively means that time series "disappear" from graphs at times where their latest collected sample is older than 5 minutes or after they are marked stale.
+Staleness will not be marked for time series that have timestamps included in their scrapes. Only the 5 minute threshold will be applied in that case.
+If a query needs to operate on a very large amount of data, graphing it might time out or overload the server or browser. Thus, when constructing queries over unknown data, always start building the query in the tabular view of Prometheus's expression browser until the result set seems reasonable (hundreds, not thousands, of time series at most). Only when you have filtered or aggregated your data sufficiently, switch to graph mode. If the expression still takes too long to graph ad-hoc, pre-record it via a recording rule.
+This is especially relevant for Prometheus's query language, where a bare metric name selector like api_http_requests_total could expand to thousands of time series with different labels. Also keep in mind that expressions which aggregate over many time series will generate load on the server even if the output is only a small number of time series. This is similar to how it would be slow to sum all values of a column in a relational database, even if the output value is only a single number.
Prometheus's query language supports basic logical and arithmetic operators. For operations between two instant vectors, the matching behavior can be modified.
+The following binary arithmetic operators exist in Prometheus:
++ (addition)- (subtraction)* (multiplication)/ (division)% (modulo)^ (power/exponentiation)Binary arithmetic operators are defined between scalar/scalar, vector/scalar, and vector/vector value pairs.
+Between two scalars, the behavior is obvious: they evaluate to another scalar that is the result of the operator applied to both scalar operands.
+Between an instant vector and a scalar, the operator is applied to the value of every data sample in the vector. E.g. if a time series instant vector is multiplied by 2, the result is another vector in which every sample value of the original vector is multiplied by 2. The metric name is dropped.
+Between two instant vectors, a binary arithmetic operator is applied to each entry in the left-hand side vector and its matching element in the right-hand vector. The result is propagated into the result vector with the grouping labels becoming the output label set. The metric name is dropped. Entries for which no matching entry in the right-hand vector can be found are not part of the result.
+The following trigonometric binary operators, which work in radians, exist in Prometheus:
+atan2 (based on https://pkg.go.dev/math#Atan2)Trigonometric operators allow trigonometric functions to be executed on two vectors using vector matching, which isn't available with normal functions. They act in the same manner as arithmetic operators.
+The following binary comparison operators exist in Prometheus:
+== (equal)!= (not-equal)> (greater-than)< (less-than)>= (greater-or-equal)<= (less-or-equal)Comparison operators are defined between scalar/scalar, vector/scalar, and vector/vector value pairs. By default they filter. Their behavior can be modified by providing bool after the operator, which will return 0 or 1 for the value rather than filtering.
Between two scalars, the bool modifier must be provided and these operators result in another scalar that is either 0 (false) or 1 (true), depending on the comparison result.
Between an instant vector and a scalar, these operators are applied to the value of every data sample in the vector, and vector elements between which the comparison result is false get dropped from the result vector. If the bool modifier is provided, vector elements that would be dropped instead have the value 0 and vector elements that would be kept have the value 1. The metric name is dropped if the bool modifier is provided.
Between two instant vectors, these operators behave as a filter by default, applied to matching entries. Vector elements for which the expression is not true or which do not find a match on the other side of the expression get dropped from the result, while the others are propagated into a result vector with the grouping labels becoming the output label set. If the bool modifier is provided, vector elements that would have been dropped instead have the value 0 and vector elements that would be kept have the value 1, with the grouping labels again becoming the output label set. The metric name is dropped if the bool modifier is provided.
These logical/set binary operators are only defined between instant vectors:
+and (intersection)or (union)unless (complement)vector1 and vector2 results in a vector consisting of the elements of vector1 for which there are elements in vector2 with exactly matching label sets. Other elements are dropped. The metric name and values are carried over from the left-hand side vector.
vector1 or vector2 results in a vector that contains all original elements (label sets + values) of vector1 and additionally all elements of vector2 which do not have matching label sets in vector1.
vector1 unless vector2 results in a vector consisting of the elements of vector1 for which there are no elements in vector2 with exactly matching label sets. All matching elements in both vectors are dropped.
Operations between vectors attempt to find a matching element in the right-hand side vector for each entry in the left-hand side. There are two basic types of matching behavior: One-to-one and many-to-one/one-to-many.
+These vector matching keywords allow for matching between series with different label sets providing:
+onignoringLabel lists provided to matching keywords will determine how vectors are combined. Examples can be found in One-to-one vector matches and in Many-to-one and one-to-many vector matches
+These group modifiers enable many-to-one/one-to-many vector matching:
+group_leftgroup_rightLabel lists can be provided to the group modifier which contain labels from the "one"-side to be included in the result metrics.
+Many-to-one and one-to-many matching are advanced use cases that should be carefully considered. Often a proper use of ignoring(<labels>) provides the desired outcome.
Grouping modifiers can only be used for comparison and arithmetic. Operations as and, unless and or operations match with all possible entries in the right vector by default.
One-to-one finds a unique pair of entries from each side of the operation. In the default case, that is an operation following the format vector1 <operator> vector2. Two entries match if they have the exact same set of labels and corresponding values. The ignoring keyword allows ignoring certain labels when matching, while the on keyword allows reducing the set of considered labels to a provided list:
<vector expr> <bin-op> ignoring(<label list>) <vector expr> +<vector expr> <bin-op> on(<label list>) <vector expr>+
Example input:
+method_code:http_errors:rate5m{method="get", code="500"} 24
+method_code:http_errors:rate5m{method="get", code="404"} 30
+method_code:http_errors:rate5m{method="put", code="501"} 3
+method_code:http_errors:rate5m{method="post", code="500"} 6
+method_code:http_errors:rate5m{method="post", code="404"} 21
- http_requests_total
+method:http_requests:rate5m{method="get"} 600
+method:http_requests:rate5m{method="del"} 34
+method:http_requests:rate5m{method="post"} 120
+ Example query:
+method_code:http_errors:rate5m{code="500"} / ignoring(code) method:http_requests:rate5m
+ This returns a result vector containing the fraction of HTTP requests with status code of 500 for each method, as measured over the last 5 minutes. Without ignoring(code) there would have been no match as the metrics do not share the same set of labels. The entries with methods put and del have no match and will not show up in the result:
{method="get"} 0.04 // 24 / 600
+{method="post"} 0.05 // 6 / 120
+ Many-to-one and one-to-many matchings refer to the case where each vector element on the "one"-side can match with multiple elements on the "many"-side. This has to be explicitly requested using the group_left or group_right modifiers, where left/right determines which vector has the higher cardinality.
<vector expr> <bin-op> ignoring(<label list>) group_left(<label list>) <vector expr> +<vector expr> <bin-op> ignoring(<label list>) group_right(<label list>) <vector expr> +<vector expr> <bin-op> on(<label list>) group_left(<label list>) <vector expr> +<vector expr> <bin-op> on(<label list>) group_right(<label list>) <vector expr>+
The label list provided with the group modifier contains additional labels from the "one"-side to be included in the result metrics. For on a label can only appear in one of the lists. Every time series of the result vector must be uniquely identifiable.
Example query:
+method_code:http_errors:rate5m / ignoring(code) group_left method:http_requests:rate5m+
In this case the left vector contains more than one entry per method label value. Thus, we indicate this using group_left. The elements from the right side are now matched with multiple elements with the same method label on the left:
{method="get", code="500"} 0.04 // 24 / 600
+{method="get", code="404"} 0.05 // 30 / 600
+{method="post", code="500"} 0.05 // 6 / 120
+{method="post", code="404"} 0.175 // 21 / 120
+ Prometheus supports the following built-in aggregation operators that can be used to aggregate the elements of a single instant vector, resulting in a new vector of fewer elements with aggregated values:
+sum (calculate sum over dimensions)min (select minimum over dimensions)max (select maximum over dimensions)avg (calculate the average over dimensions)group (all values in the resulting vector are 1)stddev (calculate population standard deviation over dimensions)stdvar (calculate population standard variance over dimensions)count (count number of elements in the vector)count_values (count number of elements with the same value)bottomk (smallest k elements by sample value)topk (largest k elements by sample value)quantile (calculate φ-quantile (0 ≤ φ ≤ 1) over dimensions)These operators can either be used to aggregate over all label dimensions or preserve distinct dimensions by including a without or by clause. These clauses may be used before or after the expression.
<aggr-op> [without|by (<label list>)] ([parameter,] <vector expression>)+
or
+<aggr-op>([parameter,] <vector expression>) [without|by (<label list>)]+
label list is a list of unquoted labels that may include a trailing comma, i.e. both (label1, label2) and (label1, label2,) are valid syntax.
without removes the listed labels from the result vector, while all other labels are preserved in the output. by does the opposite and drops labels that are not listed in the by clause, even if their label values are identical between all elements of the vector.
parameter is only required for count_values, quantile, topk and bottomk.
count_values outputs one time series per unique sample value. Each series has an additional label. The name of that label is given by the aggregation parameter, and the label value is the unique sample value. The value of each time series is the number of times that sample value was present.
topk and bottomk are different from other aggregators in that a subset of the input samples, including the original labels, are returned in the result vector. by and without are only used to bucket the input vector.
quantile calculates the φ-quantile, the value that ranks at number φ*N among the N metric values of the dimensions aggregated over. φ is provided as the aggregation parameter. For example, quantile(0.5, ...) calculates the median, quantile(0.95, ...) the 95th percentile. For φ = NaN, NaN is returned. For φ < 0, -Inf is returned. For φ > 1, +Inf is returned.
Example:
+If the metric http_requests_total had time series that fan out by application, instance, and group labels, we could calculate the total number of seen HTTP requests per application and group over all instances via:
sum without (instance) (http_requests_total)+
Which is equivalent to:
+sum by (application, group) (http_requests_total)+
If we are just interested in the total of HTTP requests we have seen in all applications, we could simply write:
+sum(http_requests_total)+
To count the number of binaries running each build version we could write:
+count_values("version", build_version)
+ To get the 5 largest HTTP requests counts across all instances we could write:
+topk(5, http_requests_total)+
The following list shows the precedence of binary operators in Prometheus, from highest to lowest.
+^*, /, %, atan2+, -==, !=, <=, <, >=, >and, unlessorOperators on the same precedence level are left-associative. For example, 2 * 3 % 2 is equivalent to (2 * 3) % 2. However ^ is right associative, so 2 ^ 3 ^ 2 is equivalent to 2 ^ (3 ^ 2).
Some functions have default arguments, e.g. year(v=vector(time()) instant-vector). This means that there is one argument v which is an instant vector, which if not provided it will default to the value of the expression vector(time()).
abs(v instant-vector) returns the input vector with all sample values converted to their absolute value.
absent(v instant-vector) returns an empty vector if the vector passed to it has any elements and a 1-element vector with the value 1 if the vector passed to it has no elements.
This is useful for alerting on when no time series exist for a given metric name and label combination.
+absent(nonexistent{job="myjob"})
+# => {job="myjob"}
- Return all time series with the metric http_requests_total and the givenjob and handler labels:
+absent(nonexistent{job="myjob",instance=~".*"})
+# => {job="myjob"}
- http_requests_total{job="apiserver", handler="/api/comments"}
+absent(sum(nonexistent{job="myjob"}))
+# => {}
+ In the first two examples, absent() tries to be smart about deriving labels of the 1-element output vector from the input vector.
absent_over_time(v range-vector) returns an empty vector if the range vector passed to it has any elements and a 1-element vector with the value 1 if the range vector passed to it has no elements.
This is useful for alerting on when no time series exist for a given metric name and label combination for a certain amount of time.
+absent_over_time(nonexistent{job="myjob"}[1h])
+# => {job="myjob"}
- Return a whole range of time (in this case 5 minutes) for the same vector,
- making it a range vector:
+absent_over_time(nonexistent{job="myjob",instance=~".*"}[1h])
+# => {job="myjob"}
- http_requests_total{job="apiserver", handler="/api/comments"}[5m]
-
- Note that an expression resulting in a range vector cannot be graphed directly,
- but viewed in the tabular ("Console") view of the expression browser.
-
- Using regular expressions, you could select time series only for jobs whose
- name match a certain pattern, in this case, all jobs that end with server:
-
- http_requests_total{job=~".*server"}
-
- All regular expressions in Prometheus use RE2 syntax.
-
- To select all HTTP status codes except 4xx ones, you could run:
-
- http_requests_total{status!~"4.."}
-
-
- Subquery
-
-
- Return the 5-minute rate of the http_requests_total metric for the past 30 minutes, with a resolution of 1 minute.
-
- rate(http_requests_total[5m])[30m:1m]
-
- This is an example of a nested subquery. The subquery for the deriv function uses the default resolution. Note that using subqueries unnecessarily is unwise.
-
- max_over_time(deriv(rate(distance_covered_total[5s])[30s:5s])[10m:])
-
-
- Using functions, operators, etc.
-
-
- Return the per-second rate for all time series with the http_requests_total
- metric name, as measured over the last 5 minutes:
-
- rate(http_requests_total[5m])
-
- Assuming that the http_requests_total time series all have the labels job
- (fanout by job name) and instance (fanout by instance of the job), we might
- want to sum over the rate of all instances, so we get fewer output time series,
- but still preserve the job dimension:
-
- sum by (job) (rate(http_requests_total[5m]))
-
- If we have two different metrics with the same dimensional labels, we can apply
- binary operators to them and elements on both sides with the same label set
- will get matched and propagated to the output. For example, this expression
- returns the unused memory in MiB for every instance (on a fictional cluster
- scheduler exposing these metrics about the instances it runs):
-
- (instance_memory_limit_bytes - instance_memory_usage_bytes) / 1024 / 1024
-
- The same expression, but summed by application, could be written like this:
-
- sum by (app, proc) (instance_memory_limit_bytes - instance_memory_usage_bytes) / 1024 / 1024
-
- If the same fictional cluster scheduler exposed CPU usage metrics like the following for every instance:
-
- instance_cpu_time_ns{app="lion", proc="web", rev="34d0f99", env="prod", job="cluster-manager"}
+absent_over_time(sum(nonexistent{job="myjob"})[1h:])
+# => {}
+ In the first two examples, absent_over_time() tries to be smart about deriving labels of the 1-element output vector from the input vector.
+ ceil(v instant-vector) rounds the sample values of all elements in v up to the nearest integer.
For each input time series, changes(v range-vector) returns the number of times its value has changed within the provided time range as an instant vector.
clamp(v instant-vector, min scalar, max scalar) clamps the sample values of all elements in v to have a lower limit of min and an upper limit of max.
Special cases: - Return an empty vector if min > max - Return NaN if min or max is NaN
clamp_max(v instant-vector, max scalar) clamps the sample values of all elements in v to have an upper limit of max.
clamp_min(v instant-vector, min scalar) clamps the sample values of all elements in v to have a lower limit of min.
day_of_month(v=vector(time()) instant-vector) returns the day of the month for each of the given times in UTC. Returned values are from 1 to 31.
day_of_week(v=vector(time()) instant-vector) returns the day of the week for each of the given times in UTC. Returned values are from 0 to 6, where 0 means Sunday etc.
day_of_year(v=vector(time()) instant-vector) returns the day of the year for each of the given times in UTC. Returned values are from 1 to 365 for non-leap years, and 1 to 366 in leap years.
days_in_month(v=vector(time()) instant-vector) returns number of days in the month for each of the given times in UTC. Returned values are from 28 to 31.
delta(v range-vector) calculates the difference between the first and last value of each time series element in a range vector v, returning an instant vector with the given deltas and equivalent labels. The delta is extrapolated to cover the full time range as specified in the range vector selector, so that it is possible to get a non-integer result even if the sample values are all integers.
The following example expression returns the difference in CPU temperature between now and 2 hours ago:
+delta(cpu_temp_celsius{host="zeus"}[2h])
+ delta should only be used with gauges.
deriv(v range-vector) calculates the per-second derivative of the time series in a range vector v, using simple linear regression. The range vector must have at least two samples in order to perform the calculation. When +Inf or -Inf are found in the range vector, the slope and offset value calculated will be NaN.
deriv should only be used with gauges.
exp(v instant-vector) calculates the exponential function for all elements in v. Special cases are:
Exp(+Inf) = +InfExp(NaN) = NaNfloor(v instant-vector) rounds the sample values of all elements in v down to the nearest integer.
histogram_quantile(φ scalar, b instant-vector) calculates the φ-quantile (0 ≤ φ ≤ 1) from the buckets b of a histogram. (See histograms and summaries for a detailed explanation of φ-quantiles and the usage of the histogram metric type in general.) The samples in b are the counts of observations in each bucket. Each sample must have a label le where the label value denotes the inclusive upper bound of the bucket. (Samples without such a label are silently ignored.) The histogram metric type automatically provides time series with the _bucket suffix and the appropriate labels.
Use the rate() function to specify the time window for the quantile calculation.
Example: A histogram metric is called http_request_duration_seconds. To calculate the 90th percentile of request durations over the last 10m, use the following expression:
histogram_quantile(0.9, rate(http_request_duration_seconds_bucket[10m]))+
The quantile is calculated for each label combination in http_request_duration_seconds. To aggregate, use the sum() aggregator around the rate() function. Since the le label is required by histogram_quantile(), it has to be included in the by clause. The following expression aggregates the 90th percentile by job:
histogram_quantile(0.9, sum by (job, le) (rate(http_request_duration_seconds_bucket[10m])))+
To aggregate everything, specify only the le label:
histogram_quantile(0.9, sum by (le) (rate(http_request_duration_seconds_bucket[10m])))+
The histogram_quantile() function interpolates quantile values by assuming a linear distribution within a bucket. The highest bucket must have an upper bound of +Inf. (Otherwise, NaN is returned.) If a quantile is located in the highest bucket, the upper bound of the second highest bucket is returned. A lower limit of the lowest bucket is assumed to be 0 if the upper bound of that bucket is greater than 0. In that case, the usual linear interpolation is applied within that bucket. Otherwise, the upper bound of the lowest bucket is returned for quantiles located in the lowest bucket.
If b has 0 observations, NaN is returned. If b contains fewer than two buckets, NaN is returned. For φ < 0, -Inf is returned. For φ > 1, +Inf is returned. For φ = NaN, NaN is returned.
holt_winters(v range-vector, sf scalar, tf scalar) produces a smoothed value for time series based on the range in v. The lower the smoothing factor sf, the more importance is given to old data. The higher the trend factor tf, the more trends in the data is considered. Both sf and tf must be between 0 and 1.
holt_winters should only be used with gauges.
hour(v=vector(time()) instant-vector) returns the hour of the day for each of the given times in UTC. Returned values are from 0 to 23.
idelta(v range-vector) calculates the difference between the last two samples in the range vector v, returning an instant vector with the given deltas and equivalent labels.
idelta should only be used with gauges.
increase(v range-vector) calculates the increase in the time series in the range vector. Breaks in monotonicity (such as counter resets due to target restarts) are automatically adjusted for. The increase is extrapolated to cover the full time range as specified in the range vector selector, so that it is possible to get a non-integer result even if a counter increases only by integer increments.
The following example expression returns the number of HTTP requests as measured over the last 5 minutes, per time series in the range vector:
+increase(http_requests_total{job="api-server"}[5m])
+ increase should only be used with counters. It is syntactic sugar for rate(v) multiplied by the number of seconds under the specified time range window, and should be used primarily for human readability. Use rate in recording rules so that increases are tracked consistently on a per-second basis.
irate(v range-vector) calculates the per-second instant rate of increase of the time series in the range vector. This is based on the last two data points. Breaks in monotonicity (such as counter resets due to target restarts) are automatically adjusted for.
The following example expression returns the per-second rate of HTTP requests looking up to 5 minutes back for the two most recent data points, per time series in the range vector:
+irate(http_requests_total{job="api-server"}[5m])
+ irate should only be used when graphing volatile, fast-moving counters. Use rate for alerts and slow-moving counters, as brief changes in the rate can reset the FOR clause and graphs consisting entirely of rare spikes are hard to read.
Note that when combining irate() with an aggregation operator (e.g. sum()) or a function aggregating over time (any function ending in _over_time), always take a irate() first, then aggregate. Otherwise irate() cannot detect counter resets when your target restarts.
For each timeseries in v, label_join(v instant-vector, dst_label string, separator string, src_label_1 string, src_label_2 string, ...) joins all the values of all the src_labels using separator and returns the timeseries with the label dst_label containing the joined value. There can be any number of src_labels in this function.
This example will return a vector with each time series having a foo label with the value a,b,c added to it:
label_join(up{job="api-server",src1="a",src2="b",src3="c"}, "foo", ",", "src1", "src2", "src3")
+ For each timeseries in v, label_replace(v instant-vector, dst_label string, replacement string, src_label string, regex string) matches the regular expression regex against the value of the label src_label. If it matches, the value of the label dst_label in the returned timeseries will be the expansion of replacement, together with the original labels in the input. Capturing groups in the regular expression can be referenced with $1, $2, etc. If the regular expression doesn't match then the timeseries is returned unchanged.
This example will return timeseries with the values a:c at label service and a at label foo:
label_replace(up{job="api-server",service="a:c"}, "foo", "$1", "service", "(.*):.*")
+ ln(v instant-vector) calculates the natural logarithm for all elements in v. Special cases are:
ln(+Inf) = +Infln(0) = -Infln(x < 0) = NaNln(NaN) = NaNlog2(v instant-vector) calculates the binary logarithm for all elements in v. The special cases are equivalent to those in ln.
log10(v instant-vector) calculates the decimal logarithm for all elements in v. The special cases are equivalent to those in ln.
minute(v=vector(time()) instant-vector) returns the minute of the hour for each of the given times in UTC. Returned values are from 0 to 59.
month(v=vector(time()) instant-vector) returns the month of the year for each of the given times in UTC. Returned values are from 1 to 12, where 1 means January etc.
predict_linear(v range-vector, t scalar) predicts the value of time series t seconds from now, based on the range vector v, using simple linear regression. The range vector must have at least two samples in order to perform the calculation. When +Inf or -Inf are found in the range vector, the slope and offset value calculated will be NaN.
predict_linear should only be used with gauges.
rate(v range-vector) calculates the per-second average rate of increase of the time series in the range vector. Breaks in monotonicity (such as counter resets due to target restarts) are automatically adjusted for. Also, the calculation extrapolates to the ends of the time range, allowing for missed scrapes or imperfect alignment of scrape cycles with the range's time period.
The following example expression returns the per-second rate of HTTP requests as measured over the last 5 minutes, per time series in the range vector:
+rate(http_requests_total{job="api-server"}[5m])
+ rate should only be used with counters. It is best suited for alerting, and for graphing of slow-moving counters.
Note that when combining rate() with an aggregation operator (e.g. sum()) or a function aggregating over time (any function ending in _over_time), always take a rate() first, then aggregate. Otherwise rate() cannot detect counter resets when your target restarts.
For each input time series, resets(v range-vector) returns the number of counter resets within the provided time range as an instant vector. Any decrease in the value between two consecutive samples is interpreted as a counter reset.
resets should only be used with counters.
round(v instant-vector, to_nearest=1 scalar) rounds the sample values of all elements in v to the nearest integer. Ties are resolved by rounding up. The optional to_nearest argument allows specifying the nearest multiple to which the sample values should be rounded. This multiple may also be a fraction.
Given a single-element input vector, scalar(v instant-vector) returns the sample value of that single element as a scalar. If the input vector does not have exactly one element, scalar will return NaN.
sgn(v instant-vector) returns a vector with all sample values converted to their sign, defined as this: 1 if v is positive, -1 if v is negative and 0 if v is equal to zero.
sort(v instant-vector) returns vector elements sorted by their sample values, in ascending order.
Same as sort, but sorts in descending order.
sqrt(v instant-vector) calculates the square root of all elements in v.
time() returns the number of seconds since January 1, 1970 UTC. Note that this does not actually return the current time, but the time at which the expression is to be evaluated.
timestamp(v instant-vector) returns the timestamp of each of the samples of the given vector as the number of seconds since January 1, 1970 UTC.
vector(s scalar) returns the scalar s as a vector with no labels.
year(v=vector(time()) instant-vector) returns the year for each of the given times in UTC.
The following functions allow aggregating each series of a given range vector over time and return an instant vector with per-series aggregation results:
+avg_over_time(range-vector): the average value of all points in the specified interval.min_over_time(range-vector): the minimum value of all points in the specified interval.max_over_time(range-vector): the maximum value of all points in the specified interval.sum_over_time(range-vector): the sum of all values in the specified interval.count_over_time(range-vector): the count of all values in the specified interval.quantile_over_time(scalar, range-vector): the φ-quantile (0 ≤ φ ≤ 1) of the values in the specified interval.stddev_over_time(range-vector): the population standard deviation of the values in the specified interval.stdvar_over_time(range-vector): the population standard variance of the values in the specified interval.last_over_time(range-vector): the most recent point value in specified interval.present_over_time(range-vector): the value 1 for any series in the specified interval.Note that all values in the specified interval have the same weight in the aggregation even if the values are not equally spaced throughout the interval.
+The trigonometric functions work in radians:
+acos(v instant-vector): calculates the arccosine of all elements in v (special cases).acosh(v instant-vector): calculates the inverse hyperbolic cosine of all elements in v (special cases).asin(v instant-vector): calculates the arcsine of all elements in v (special cases).asinh(v instant-vector): calculates the inverse hyperbolic sine of all elements in v (special cases).atan(v instant-vector): calculates the arctangent of all elements in v (special cases).atanh(v instant-vector): calculates the inverse hyperbolic tangent of all elements in v (special cases).cos(v instant-vector): calculates the cosine of all elements in v (special cases).cosh(v instant-vector): calculates the hyperbolic cosine of all elements in v (special cases).sin(v instant-vector): calculates the sine of all elements in v (special cases).sinh(v instant-vector): calculates the hyperbolic sine of all elements in v (special cases).tan(v instant-vector): calculates the tangent of all elements in v (special cases).tanh(v instant-vector): calculates the hyperbolic tangent of all elements in v (special cases).The following are useful for converting between degrees and radians:
+deg(v instant-vector): converts radians to degrees for all elements in v.pi(): returns pi.rad(v instant-vector): converts degrees to radians for all elements in v.Return all time series with the metric http_requests_total:
http_requests_total+
Return all time series with the metric http_requests_total and the given job and handler labels:
http_requests_total{job="apiserver", handler="/api/comments"}
+ Return a whole range of time (in this case 5 minutes up to the query time) for the same vector, making it a range vector:
+http_requests_total{job="apiserver", handler="/api/comments"}[5m]
+ Note that an expression resulting in a range vector cannot be graphed directly, but viewed in the tabular ("Console") view of the expression browser.
+Using regular expressions, you could select time series only for jobs whose name match a certain pattern, in this case, all jobs that end with server:
http_requests_total{job=~".*server"}
+ All regular expressions in Prometheus use RE2 syntax.
+To select all HTTP status codes except 4xx ones, you could run:
+http_requests_total{status!~"4.."}
+ Return the 5-minute rate of the http_requests_total metric for the past 30 minutes, with a resolution of 1 minute.
rate(http_requests_total[5m])[30m:1m]+
This is an example of a nested subquery. The subquery for the deriv function uses the default resolution. Note that using subqueries unnecessarily is unwise.
max_over_time(deriv(rate(distance_covered_total[5s])[30s:5s])[10m:])+
Return the per-second rate for all time series with the http_requests_total metric name, as measured over the last 5 minutes:
rate(http_requests_total[5m])+
Assuming that the http_requests_total time series all have the labels job (fanout by job name) and instance (fanout by instance of the job), we might want to sum over the rate of all instances, so we get fewer output time series, but still preserve the job dimension:
sum by (job) ( + rate(http_requests_total[5m]) +)+
If we have two different metrics with the same dimensional labels, we can apply binary operators to them and elements on both sides with the same label set will get matched and propagated to the output. For example, this expression returns the unused memory in MiB for every instance (on a fictional cluster scheduler exposing these metrics about the instances it runs):
+(instance_memory_limit_bytes - instance_memory_usage_bytes) / 1024 / 1024+
The same expression, but summed by application, could be written like this:
+sum by (app, proc) ( + instance_memory_limit_bytes - instance_memory_usage_bytes +) / 1024 / 1024+
If the same fictional cluster scheduler exposed CPU usage metrics like the following for every instance:
+instance_cpu_time_ns{app="lion", proc="web", rev="34d0f99", env="prod", job="cluster-manager"}
instance_cpu_time_ns{app="elephant", proc="worker", rev="34d0f99", env="prod", job="cluster-manager"}
instance_cpu_time_ns{app="turtle", proc="api", rev="4d3a513", env="prod", job="cluster-manager"}
instance_cpu_time_ns{app="fox", proc="widget", rev="4d3a513", env="prod", job="cluster-manager"}
-...
-
-
- ...we could get the top 3 CPU users grouped by application (app) and process type (proc) like this:
topk(3, sum by (app, proc) (rate(instance_cpu_time_ns[5m])))
-
- Assuming this metric contains one time series per running instance, you could count the number of running instances per application like this:
- -count by (app) (instance_cpu_time_ns)
-
+...
+ ...we could get the top 3 CPU users grouped by application (app) and process type (proc) like this:
topk(3, sum by (app, proc) (rate(instance_cpu_time_ns[5m])))+
Assuming this metric contains one time series per running instance, you could count the number of running instances per application like this:
+count by (app) (instance_cpu_time_ns)+
LogQL is Grafana Loki’s PromQL-inspired query language. Queries act as if they are a distributed grep to aggregate log sources. LogQL uses labels and operators for filtering.
+LogQL is Grafana Loki’s PromQL-inspired query language. Queries act as if they are a distributed grep to aggregate log sources. LogQL uses labels and operators for filtering.
There are two types of LogQL queries:
All LogQL queries contain a log stream selector.
+All LogQL queries contain a log stream selector.
Optionally, the log stream selector can be followed by a log pipeline. A log pipeline is a set of stage expressions that are chained together and applied to the selected log streams. Each expression can filter out, parse, or mutate log lines and their respective labels.
The following example shows a full log query in action:
@@ -835,12 +1775,12 @@ level=info ts=2020-10-23T20:32:18.068866235Z caller=metrics.go:81 org_id=29 trac