mirror of
https://github.com/VictoriaMetrics/VictoriaMetrics.git
synced 2024-11-21 14:44:00 +00:00
lib/promscrape: Enable filters for endpoint and labels (#2466)
* lib/promscrape: Enable filters for endpoint and labels * lib/promscrape: cleanup * lib/promscrape: update template * lib/promscrape: move logic filter logic to backend * lib/promscrape: updated placeholder * lib/promscrape: updated placeholder * lib/promscrape: use two different fields for filters, updated form, added error on parsing queries * lib/promscrape: rename functions * lib/promscrape: removed unused values * wip * wip * wip Co-authored-by: Aliaksandr Valialkin <valyala@victoriametrics.com>
This commit is contained in:
parent
7a622a71ea
commit
17552dba8b
6 changed files with 795 additions and 424 deletions
|
@ -15,6 +15,7 @@ The following tip changes can be tested by building VictoriaMetrics components f
|
|||
|
||||
## tip
|
||||
|
||||
* FEATUREL [vmagent](https://docs.victoriametrics.com/vmagent.html): allow filtering targets by target url and by target labels with [time series selector](https://prometheus.io/docs/prometheus/latest/querying/basics/#time-series-selectors) on `http://vmagent:8429/targets` page. This may be useful when `vmagent` scrapes big number of targets. See [this feature request](https://github.com/VictoriaMetrics/VictoriaMetrics/issues/1796).
|
||||
* FEATURE: [vmagent](https://docs.victoriametrics.com/vmagent.html): reduce `-promscrape.config` reload duration when the config contains big number of jobs (aka [scrape_config](https://prometheus.io/docs/prometheus/latest/configuration/configuration/#scrape_config) sections) and only a few of them are changed. Previously all the jobs were restarted. Now only the jobs with changed configs are restarted. This should reduce the probability of data miss because of slow config reload. See [this issue](https://github.com/VictoriaMetrics/VictoriaMetrics/issues/2270).
|
||||
* FEATURE: [vmalert](https://docs.victoriametrics.com/vmalert.html): add support for DNS-based discovery for notifiers in the same way as Prometheus does. See [these docs](https://docs.victoriametrics.com/vmalert.html#notifier-configuration-file) and [this feature request](https://github.com/VictoriaMetrics/VictoriaMetrics/issues/2460).
|
||||
* FEATURE: allow specifying TLS cipher suites for incoming https requests via `-tlsCipherSuites` command-line flag. See [this feature request](https://github.com/VictoriaMetrics/VictoriaMetrics/issues/2404).
|
||||
|
|
|
@ -17,26 +17,34 @@ type IfExpression struct {
|
|||
lfs []*labelFilter
|
||||
}
|
||||
|
||||
// Parse parses `if` expression from s and stores it to ie.
|
||||
func (ie *IfExpression) Parse(s string) error {
|
||||
expr, err := metricsql.Parse(s)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
me, ok := expr.(*metricsql.MetricExpr)
|
||||
if !ok {
|
||||
return fmt.Errorf("expecting series selector; got %q", expr.AppendString(nil))
|
||||
}
|
||||
lfs, err := metricExprToLabelFilters(me)
|
||||
if err != nil {
|
||||
return fmt.Errorf("cannot parse series selector: %w", err)
|
||||
}
|
||||
ie.s = s
|
||||
ie.lfs = lfs
|
||||
return nil
|
||||
}
|
||||
|
||||
// UnmarshalYAML unmarshals ie from YAML passed to f.
|
||||
func (ie *IfExpression) UnmarshalYAML(f func(interface{}) error) error {
|
||||
var s string
|
||||
if err := f(&s); err != nil {
|
||||
return fmt.Errorf("cannot unmarshal `if` option: %w", err)
|
||||
}
|
||||
expr, err := metricsql.Parse(s)
|
||||
if err != nil {
|
||||
if err := ie.Parse(s); err != nil {
|
||||
return fmt.Errorf("cannot parse `if` series selector: %w", err)
|
||||
}
|
||||
me, ok := expr.(*metricsql.MetricExpr)
|
||||
if !ok {
|
||||
return fmt.Errorf("expecting `if` series selector; got %q", expr.AppendString(nil))
|
||||
}
|
||||
lfs, err := metricExprToLabelFilters(me)
|
||||
if err != nil {
|
||||
return fmt.Errorf("cannot parse `if` filters: %w", err)
|
||||
}
|
||||
ie.s = s
|
||||
ie.lfs = lfs
|
||||
return nil
|
||||
}
|
||||
|
||||
|
|
|
@ -10,6 +10,32 @@ import (
|
|||
"gopkg.in/yaml.v2"
|
||||
)
|
||||
|
||||
func TestIfExpressionParseFailure(t *testing.T) {
|
||||
f := func(s string) {
|
||||
t.Helper()
|
||||
var ie IfExpression
|
||||
if err := ie.Parse(s); err == nil {
|
||||
t.Fatalf("expecting non-nil error when parsing %q", s)
|
||||
}
|
||||
}
|
||||
f(`{`)
|
||||
f(`{foo`)
|
||||
f(`foo{`)
|
||||
}
|
||||
|
||||
func TestIfExpressionParseSuccess(t *testing.T) {
|
||||
f := func(s string) {
|
||||
t.Helper()
|
||||
var ie IfExpression
|
||||
if err := ie.Parse(s); err != nil {
|
||||
t.Fatalf("unexpected error: %s", err)
|
||||
}
|
||||
}
|
||||
f(`foo`)
|
||||
f(`{foo="bar"}`)
|
||||
f(`foo{bar=~"baz", x!="y"}`)
|
||||
}
|
||||
|
||||
func TestIfExpressionUnmarshalFailure(t *testing.T) {
|
||||
f := func(s string) {
|
||||
t.Helper()
|
||||
|
|
|
@ -5,6 +5,7 @@ import (
|
|||
"fmt"
|
||||
"io"
|
||||
"net/http"
|
||||
"regexp"
|
||||
"sort"
|
||||
"strconv"
|
||||
"strings"
|
||||
|
@ -45,12 +46,14 @@ func WriteTargetResponse(w http.ResponseWriter, r *http.Request) error {
|
|||
func WriteHumanReadableTargetsStatus(w http.ResponseWriter, r *http.Request) {
|
||||
showOriginalLabels, _ := strconv.ParseBool(r.FormValue("show_original_labels"))
|
||||
showOnlyUnhealthy, _ := strconv.ParseBool(r.FormValue("show_only_unhealthy"))
|
||||
endpointSearch := strings.TrimSpace(r.FormValue("endpoint_search"))
|
||||
labelSearch := strings.TrimSpace(r.FormValue("label_search"))
|
||||
if accept := r.Header.Get("Accept"); strings.Contains(accept, "text/html") {
|
||||
w.Header().Set("Content-Type", "text/html; charset=utf-8")
|
||||
tsmGlobal.WriteTargetsHTML(w, showOnlyUnhealthy)
|
||||
tsmGlobal.WriteTargetsHTML(w, showOnlyUnhealthy, endpointSearch, labelSearch)
|
||||
} else {
|
||||
w.Header().Set("Content-Type", "text/plain; charset=utf-8")
|
||||
tsmGlobal.WriteTargetsPlain(w, showOriginalLabels)
|
||||
tsmGlobal.WriteTargetsPlain(w, showOriginalLabels, showOnlyUnhealthy, endpointSearch, labelSearch)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -318,7 +321,7 @@ type jobTargetsStatuses struct {
|
|||
targetsStatus []targetStatus
|
||||
}
|
||||
|
||||
func (tsm *targetStatusMap) getTargetsStatusByJob() ([]jobTargetsStatuses, []string) {
|
||||
func (tsm *targetStatusMap) getTargetsStatusByJob(endpointSearch, labelSearch string) ([]jobTargetsStatuses, []string, error) {
|
||||
byJob := make(map[string][]targetStatus)
|
||||
tsm.mu.Lock()
|
||||
for _, st := range tsm.m {
|
||||
|
@ -352,7 +355,78 @@ func (tsm *targetStatusMap) getTargetsStatusByJob() ([]jobTargetsStatuses, []str
|
|||
return jts[i].job < jts[j].job
|
||||
})
|
||||
emptyJobs := getEmptyJobs(jts, jobNames)
|
||||
return jts, emptyJobs
|
||||
var err error
|
||||
jts, err = filterTargets(jts, endpointSearch, labelSearch)
|
||||
if len(endpointSearch) > 0 || len(labelSearch) > 0 {
|
||||
// Do not show empty jobs if target filters are set.
|
||||
emptyJobs = nil
|
||||
}
|
||||
return jts, emptyJobs, err
|
||||
}
|
||||
|
||||
func filterTargetsByEndpoint(jts []jobTargetsStatuses, searchQuery string) ([]jobTargetsStatuses, error) {
|
||||
if searchQuery == "" {
|
||||
return jts, nil
|
||||
}
|
||||
finder, err := regexp.Compile(searchQuery)
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("cannot parse %s: %w", searchQuery, err)
|
||||
}
|
||||
var jtsFiltered []jobTargetsStatuses
|
||||
for _, job := range jts {
|
||||
var tss []targetStatus
|
||||
for _, ts := range job.targetsStatus {
|
||||
if finder.MatchString(ts.sw.Config.ScrapeURL) {
|
||||
tss = append(tss, ts)
|
||||
}
|
||||
}
|
||||
if len(tss) == 0 {
|
||||
// Skip jobs with zero targets after filtering, so users could see only the requested targets
|
||||
continue
|
||||
}
|
||||
job.targetsStatus = tss
|
||||
jtsFiltered = append(jtsFiltered, job)
|
||||
}
|
||||
return jtsFiltered, nil
|
||||
}
|
||||
|
||||
func filterTargetsByLabels(jts []jobTargetsStatuses, searchQuery string) ([]jobTargetsStatuses, error) {
|
||||
if searchQuery == "" {
|
||||
return jts, nil
|
||||
}
|
||||
var ie promrelabel.IfExpression
|
||||
if err := ie.Parse(searchQuery); err != nil {
|
||||
return nil, fmt.Errorf("cannot parse %s: %w", searchQuery, err)
|
||||
}
|
||||
var jtsFiltered []jobTargetsStatuses
|
||||
for _, job := range jts {
|
||||
var tss []targetStatus
|
||||
for _, ts := range job.targetsStatus {
|
||||
if ie.Match(ts.sw.Config.Labels) {
|
||||
tss = append(tss, ts)
|
||||
}
|
||||
}
|
||||
if len(tss) == 0 {
|
||||
// Skip jobs with zero targets after filtering, so users could see only the requested targets
|
||||
continue
|
||||
}
|
||||
job.targetsStatus = tss
|
||||
jtsFiltered = append(jtsFiltered, job)
|
||||
}
|
||||
return jtsFiltered, nil
|
||||
}
|
||||
|
||||
func filterTargets(jts []jobTargetsStatuses, endpointQuery, labelQuery string) ([]jobTargetsStatuses, error) {
|
||||
var err error
|
||||
jts, err = filterTargetsByEndpoint(jts, endpointQuery)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
jts, err = filterTargetsByLabels(jts, labelQuery)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return jts, nil
|
||||
}
|
||||
|
||||
func getEmptyJobs(jts []jobTargetsStatuses, jobNames []string) []string {
|
||||
|
@ -373,14 +447,14 @@ func getEmptyJobs(jts []jobTargetsStatuses, jobNames []string) []string {
|
|||
|
||||
// WriteTargetsHTML writes targets status grouped by job into writer w in html table,
|
||||
// accepts filter to show only unhealthy targets.
|
||||
func (tsm *targetStatusMap) WriteTargetsHTML(w io.Writer, showOnlyUnhealthy bool) {
|
||||
jss, emptyJobs := tsm.getTargetsStatusByJob()
|
||||
WriteTargetsResponseHTML(w, jss, emptyJobs, showOnlyUnhealthy)
|
||||
func (tsm *targetStatusMap) WriteTargetsHTML(w io.Writer, showOnlyUnhealthy bool, endpointSearch, labelSearch string) {
|
||||
jss, emptyJobs, err := tsm.getTargetsStatusByJob(endpointSearch, labelSearch)
|
||||
WriteTargetsResponseHTML(w, jss, emptyJobs, showOnlyUnhealthy, endpointSearch, labelSearch, err)
|
||||
}
|
||||
|
||||
// WriteTargetsPlain writes targets grouped by job into writer w in plain text,
|
||||
// accept filter to show original labels.
|
||||
func (tsm *targetStatusMap) WriteTargetsPlain(w io.Writer, showOriginalLabels bool) {
|
||||
jss, emptyJobs := tsm.getTargetsStatusByJob()
|
||||
WriteTargetsResponsePlain(w, jss, emptyJobs, showOriginalLabels)
|
||||
func (tsm *targetStatusMap) WriteTargetsPlain(w io.Writer, showOriginalLabels, showOnlyUnhealthy bool, endpointSearch, labelSearch string) {
|
||||
jss, emptyJobs, err := tsm.getTargetsStatusByJob(endpointSearch, labelSearch)
|
||||
WriteTargetsResponsePlain(w, jss, emptyJobs, showOriginalLabels, showOnlyUnhealthy, err)
|
||||
}
|
||||
|
|
|
@ -1,4 +1,5 @@
|
|||
{% import (
|
||||
"net/url"
|
||||
"time"
|
||||
"github.com/VictoriaMetrics/VictoriaMetrics/lib/prompbmarshal"
|
||||
"github.com/VictoriaMetrics/VictoriaMetrics/lib/promrelabel"
|
||||
|
@ -6,25 +7,32 @@
|
|||
|
||||
{% stripspace %}
|
||||
|
||||
{% func TargetsResponsePlain(jts []jobTargetsStatuses, emptyJobs []string, showOriginLabels bool) %}
|
||||
{% func TargetsResponsePlain(jts []jobTargetsStatuses, emptyJobs []string, showOriginLabels, showOnlyUnhealthy bool, err error) %}
|
||||
|
||||
{% if err != nil %}
|
||||
{%s= err.Error() %}
|
||||
{% return %}
|
||||
{% endif %}
|
||||
|
||||
{% for _, js := range jts %}
|
||||
job={%q= js.job %} ({%d js.upCount %}/{%d js.targetsTotal %}{% space %}up)
|
||||
{% newline %}
|
||||
{% for _, ts := range js.targetsStatus %}
|
||||
{%s= "\t" %}
|
||||
state={% if ts.up %}up{% else %}down{% endif %},{% space %}
|
||||
endpoint={%s= ts.sw.Config.ScrapeURL %},{% space %}
|
||||
labels={%s= promLabelsString(promrelabel.FinalizeLabels(nil, ts.sw.Config.Labels)) %},{% space %}
|
||||
{% if showOriginLabels %}originalLabels={%s= promLabelsString(ts.sw.Config.OriginalLabels) %},{% space %}{% endif %}
|
||||
scrapes_total={%d ts.scrapesTotal %},{% space %}
|
||||
scrapes_failed={%d ts.scrapesFailed %},{% space %}
|
||||
last_scrape={%f.3 ts.getDurationFromLastScrape().Seconds() %}s ago,{% space %}
|
||||
scrape_duration={%d int(ts.scrapeDuration) %}ms,{% space %}
|
||||
samples_scraped={%d ts.samplesScraped %},{% space %}
|
||||
error={% if ts.err != nil %}{%s= ts.err.Error() %}{% endif %}
|
||||
{% newline %}
|
||||
{% endfor %}
|
||||
{% if showOnlyUnhealthy && js.upCount == js.targetsTotal %}{% continue %}{% endif %}
|
||||
job={%q= js.job %} ({%d js.upCount %}/{%d js.targetsTotal %}{% space %}up)
|
||||
{% newline %}
|
||||
{% for _, ts := range js.targetsStatus %}
|
||||
{% if showOnlyUnhealthy && ts.up %}{% continue %}{% endif %}
|
||||
{%s= "\t" %}
|
||||
state={% if ts.up %}up{% else %}down{% endif %},{% space %}
|
||||
endpoint={%s= ts.sw.Config.ScrapeURL %},{% space %}
|
||||
labels={%s= promLabelsString(promrelabel.FinalizeLabels(nil, ts.sw.Config.Labels)) %},{% space %}
|
||||
{% if showOriginLabels %}originalLabels={%s= promLabelsString(ts.sw.Config.OriginalLabels) %},{% space %}{% endif %}
|
||||
scrapes_total={%d ts.scrapesTotal %},{% space %}
|
||||
scrapes_failed={%d ts.scrapesFailed %},{% space %}
|
||||
last_scrape={%f.3 ts.getDurationFromLastScrape().Seconds() %}s ago,{% space %}
|
||||
scrape_duration={%d int(ts.scrapeDuration) %}ms,{% space %}
|
||||
samples_scraped={%d ts.samplesScraped %},{% space %}
|
||||
error={% if ts.err != nil %}{%s= ts.err.Error() %}{% endif %}
|
||||
{% newline %}
|
||||
{% endfor %}
|
||||
{% endfor %}
|
||||
|
||||
{% for _, jobName := range emptyJobs %}
|
||||
|
@ -34,7 +42,7 @@ job={%q= jobName %} (0/0 up)
|
|||
|
||||
{% endfunc %}
|
||||
|
||||
{% func TargetsResponseHTML(jts []jobTargetsStatuses, emptyJobs []string, onlyUnhealthy bool) %}
|
||||
{% func TargetsResponseHTML(jts []jobTargetsStatuses, emptyJobs []string, showOnlyUnhealthy bool, endpointSearch, labelSearch string, err error) %}
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
|
@ -63,109 +71,194 @@ function expand_all() {
|
|||
}
|
||||
</script>
|
||||
</head>
|
||||
<body class="m-3">
|
||||
<h1>Scrape targets</h1>
|
||||
<div style="padding: 3px">
|
||||
<button type="button" class="btn{% space %}{% if !onlyUnhealthy %}btn-primary{% else %}btn-secondary{% endif %}" onclick="location.href='targets'">
|
||||
All
|
||||
</button>
|
||||
<button type="button" class="btn{% space %}{% if onlyUnhealthy %}btn-primary{% else %}btn-secondary{% endif %}" onclick="location.href='targets?show_only_unhealthy=true'">
|
||||
Unhealthy
|
||||
</button>
|
||||
<button type="button" class="btn btn-primary" onclick="collapse_all()">
|
||||
Collapse all
|
||||
</button>
|
||||
<button type="button" class="btn btn-secondary" onclick="expand_all()">
|
||||
Expand all
|
||||
</button>
|
||||
</div>
|
||||
{% for i, js := range jts %}
|
||||
{% if onlyUnhealthy && js.upCount == js.targetsTotal %}{% continue %}{% endif %}
|
||||
<div>
|
||||
<h4>
|
||||
{%s js.job %}{% space %}({%d js.upCount %}/{%d js.targetsTotal %}{% space %}up)
|
||||
<button type="button" class="btn btn-primary" onclick="document.getElementById('table-{%d i %}').style.display='none'">collapse</button>
|
||||
<button type="button" class="btn btn-secondary" onclick="document.getElementById('table-{%d i %}').style.display='block'">expand</button>
|
||||
</h4>
|
||||
<div id="table-{%d i %}">
|
||||
<table class="table table-striped table-hover table-bordered table-sm">
|
||||
<thead>
|
||||
<tr>
|
||||
<th scope="col">Endpoint</th>
|
||||
<th scope="col">State</th>
|
||||
<th scope="col" title="scrape target labels">Labels</th>
|
||||
<th scope="col" title="total scrapes">Scrapes</th>
|
||||
<th scope="col" title="total scrape errors">Errors</th>
|
||||
<th scope="col" title="the time of the last scrape">Last Scrape</th>
|
||||
<th scope="col" title="the duration of the last scrape">Duration</th>
|
||||
<th scope="col" title="the number of metrics scraped during the last scrape">Samples</th>
|
||||
<th scope="col" title="error from the last scrape (if any)">Last error</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
{% for _, ts := range js.targetsStatus %}
|
||||
{% code
|
||||
endpoint := ts.sw.Config.ScrapeURL
|
||||
targetID := getTargetID(ts.sw)
|
||||
lastScrapeTime := ts.getDurationFromLastScrape()
|
||||
%}
|
||||
{% if onlyUnhealthy && ts.up %}{% continue %}{% endif %}
|
||||
<tr {% if !ts.up %}{%space%}class="alert alert-danger" role="alert"{% endif %}>
|
||||
<td><a href="{%s endpoint %}" target="_blank">{%s endpoint %}</a> (
|
||||
<a href="target_response?id={%s targetID %}" target="_blank" title="click to fetch target response on behalf of the scraper">response</a>
|
||||
)</td>
|
||||
<td>{% if ts.up %}UP{% else %}DOWN{% endif %}</td>
|
||||
<td>
|
||||
<div title="click to show original labels" onclick="document.getElementById('original_labels_{%s targetID %}').style.display='block'">
|
||||
{%= formatLabel(promrelabel.FinalizeLabels(nil, ts.sw.Config.Labels)) %}
|
||||
<body class="py-3">
|
||||
<div class="container-fluid">
|
||||
{% if err != nil %}
|
||||
{%= errorNotification(err) %}
|
||||
{% endif %}
|
||||
<div class="row">
|
||||
<main class="col-12">
|
||||
<h1>Scrape targets</h1>
|
||||
<hr />
|
||||
<div class="row g-3 align-items-center mb-3">
|
||||
<div class="col-auto">
|
||||
<button type="button" class="btn{% space %}{% if !showOnlyUnhealthy %}btn-primary{% else %}btn-secondary{% endif %}" onclick="location.href='?{%= queryArgs(map[string]string{
|
||||
"show_only_unhealthy": "false",
|
||||
"endpoint_search": endpointSearch,
|
||||
"label_search": labelSearch,
|
||||
}) %}'">
|
||||
All
|
||||
</button>
|
||||
</div>
|
||||
<div class="col-auto">
|
||||
<button type="button" class="btn{% space %}{% if showOnlyUnhealthy %}btn-primary{% else %}btn-secondary{% endif %}" onclick="location.href='?{%= queryArgs(map[string]string{
|
||||
"show_only_unhealthy": "true",
|
||||
"endpoint_search": endpointSearch,
|
||||
"label_search": labelSearch,
|
||||
}) %}'">
|
||||
Unhealthy
|
||||
</button>
|
||||
</div>
|
||||
<div class="col-auto">
|
||||
<button type="button" class="btn btn-primary" onclick="collapse_all()">
|
||||
Collapse all
|
||||
</button>
|
||||
</div>
|
||||
<div class="col-auto">
|
||||
<button type="button" class="btn btn-secondary" onclick="expand_all()">
|
||||
Expand all
|
||||
</button>
|
||||
</div>
|
||||
<div class="col-auto">
|
||||
{% if endpointSearch == "" && labelSearch == "" %}
|
||||
<button type="button" class="btn btn-primary" onclick="document.getElementById('filters').style.display='block'">
|
||||
Filter targets
|
||||
</button>
|
||||
{% else %}
|
||||
<button type="button" class="btn btn-primary" onclick="location.href='?'">
|
||||
Clear target filters
|
||||
</button>
|
||||
{% endif %}
|
||||
</div>
|
||||
</div>
|
||||
<div style="display:none" id="original_labels_{%s targetID %}">
|
||||
{%= formatLabel(ts.sw.Config.OriginalLabels) %}
|
||||
<div id="filters" {% if endpointSearch == "" && labelSearch == "" %}style="display:none"{% endif %}>
|
||||
<form class="form-horizontal">
|
||||
<div class="form-group mb-3">
|
||||
<label for="endpoint_search" class="col-sm-10 control-label">Endpoint filter (<a target="_blank" href="https://github.com/google/re2/wiki/Syntax">Regexp</a> is accepted)</label>
|
||||
<div class="col-sm-10">
|
||||
<input type="text" id="endpoint_search" name="endpoint_search"
|
||||
placeholder="For example, 127.0.0.1" class="form-control" value="{%s endpointSearch %}"/>
|
||||
</div>
|
||||
</div>
|
||||
<div class="form-group mb-3">
|
||||
<label for="label_search" class="col-sm-10 control-label">Labels filter (<a target="_blank" href="https://prometheus.io/docs/prometheus/latest/querying/basics/#time-series-selectors">Arbitrary time series selectors</a> are accepted)</label>
|
||||
<div class="col-sm-10">
|
||||
<input type="text" id="label_search" name="label_search"
|
||||
placeholder="For example, {instance=~'.+:9100'}" class="form-control" value="{%s labelSearch %}"/>
|
||||
</div>
|
||||
</div>
|
||||
<input type="hidden" name="show_only_unhealthy" value="{%v showOnlyUnhealthy %}"/>
|
||||
<button type="submit" class="btn btn-success mb-3">Submit</button>
|
||||
</form>
|
||||
</div>
|
||||
<hr />
|
||||
<div class="row">
|
||||
<div class="col-12">
|
||||
{% for i, js := range jts %}
|
||||
{% if showOnlyUnhealthy && js.upCount == js.targetsTotal %}{% continue %}{% endif %}
|
||||
<div class="row mb-4">
|
||||
<div class="col-12">
|
||||
<h4>
|
||||
{%s js.job %}{% space %}({%d js.upCount %}/{%d js.targetsTotal %}{% space %}up)
|
||||
</h4>
|
||||
<div class="row mb-2">
|
||||
<div class="col-12">
|
||||
<button type="button" class="btn btn-primary me-1"
|
||||
onclick="document.getElementById('table-{%d i %}').style.display='none'">collapse
|
||||
</button>
|
||||
<button type="button" class="btn btn-secondary me-1"
|
||||
onclick="document.getElementById('table-{%d i %}').style.display='block'">expand
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
<div id="table-{%d i %}" class="table-responsive">
|
||||
<table class="table table-striped table-hover table-bordered table-sm">
|
||||
<thead>
|
||||
<tr>
|
||||
<th scope="col">Endpoint</th>
|
||||
<th scope="col">State</th>
|
||||
<th scope="col" title="scrape target labels">Labels</th>
|
||||
<th scope="col" title="total scrapes">Scrapes</th>
|
||||
<th scope="col" title="total scrape errors">Errors</th>
|
||||
<th scope="col" title="the time of the last scrape">Last Scrape</th>
|
||||
<th scope="col" title="the duration of the last scrape">Duration</th>
|
||||
<th scope="col" title="the number of metrics scraped during the last scrape">Samples</th>
|
||||
<th scope="col" title="error from the last scrape (if any)">Last error</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody class="list-{%d i %}">
|
||||
{% for _, ts := range js.targetsStatus %}
|
||||
{% code
|
||||
endpoint := ts.sw.Config.ScrapeURL
|
||||
targetID := getTargetID(ts.sw)
|
||||
lastScrapeTime := ts.getDurationFromLastScrape()
|
||||
%}
|
||||
{% if showOnlyUnhealthy && ts.up %}{% continue %}{% endif %}
|
||||
<tr {% if !ts.up %}{%space%}class="alert alert-danger" role="alert" {% endif %}>
|
||||
<td class="endpoint"><a href="{%s endpoint %}" target="_blank">{%s endpoint %}</a> (
|
||||
<a href="target_response?id={%s targetID %}" target="_blank"
|
||||
title="click to fetch target response on behalf of the scraper">response</a>
|
||||
)
|
||||
</td>
|
||||
<td>{% if ts.up %}UP{% else %}DOWN{% endif %}</td>
|
||||
<td class="labels">
|
||||
<div title="click to show original labels"
|
||||
onclick="document.getElementById('original_labels_{%s targetID %}').style.display='block'">
|
||||
{%= formatLabel(promrelabel.FinalizeLabels(nil, ts.sw.Config.Labels)) %}
|
||||
</div>
|
||||
<div style="display:none" id="original_labels_{%s targetID %}">
|
||||
{%= formatLabel(ts.sw.Config.OriginalLabels) %}
|
||||
</div>
|
||||
</td>
|
||||
<td>{%d ts.scrapesTotal %}</td>
|
||||
<td>{%d ts.scrapesFailed %}</td>
|
||||
<td>
|
||||
{% if lastScrapeTime < 365*24*time.Hour %}
|
||||
{%f.3 lastScrapeTime.Seconds() %}s ago
|
||||
{% else %}
|
||||
none
|
||||
{% endif %}
|
||||
<td>{%d int(ts.scrapeDuration) %}ms</td>
|
||||
<td>{%d ts.samplesScraped %}</td>
|
||||
<td>{% if ts.err != nil %}{%s ts.err.Error() %}{% endif %}</td>
|
||||
</tr>
|
||||
{% endfor %}
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</div>
|
||||
</td>
|
||||
<td>{%d ts.scrapesTotal %}</td>
|
||||
<td>{%d ts.scrapesFailed %}</td>
|
||||
<td>
|
||||
{% if lastScrapeTime < 365*24*time.Hour %}
|
||||
{%f.3 lastScrapeTime.Seconds() %}s ago
|
||||
{% else %}
|
||||
none
|
||||
{% endif %}
|
||||
<td>{%d int(ts.scrapeDuration) %}ms</td>
|
||||
<td>{%d ts.samplesScraped %}</td>
|
||||
<td>{% if ts.err != nil %}{%s ts.err.Error() %}{% endif %}</td>
|
||||
</tr>
|
||||
{% endfor %}
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
</div>
|
||||
{% endfor %}
|
||||
|
||||
{% for _, jobName := range emptyJobs %}
|
||||
<div>
|
||||
<h4>
|
||||
<a>{%s jobName %} (0/0 up)</a>
|
||||
</h4>
|
||||
<table class="table table-striped table-hover table-bordered table-sm">
|
||||
<thead>
|
||||
<tr>
|
||||
<th scope="col">Endpoint</th>
|
||||
<th scope="col">State</th>
|
||||
<th scope="col">Labels</th>
|
||||
<th scope="col">Last Scrape</th>
|
||||
<th scope="col">Scrape Duration</th>
|
||||
<th scope="col">Samples Scraped</th>
|
||||
<th scope="col">Error</th>
|
||||
</tr>
|
||||
</thead>
|
||||
</table>
|
||||
{% for _, jobName := range emptyJobs %}
|
||||
<div>
|
||||
<h4>
|
||||
<a>{%s jobName %} (0/0 up)</a>
|
||||
</h4>
|
||||
<table class="table table-striped table-hover table-bordered table-sm">
|
||||
<thead>
|
||||
<tr>
|
||||
<th scope="col">Endpoint</th>
|
||||
<th scope="col">State</th>
|
||||
<th scope="col">Labels</th>
|
||||
<th scope="col">Last Scrape</th>
|
||||
<th scope="col">Scrape Duration</th>
|
||||
<th scope="col">Samples Scraped</th>
|
||||
<th scope="col">Error</th>
|
||||
</tr>
|
||||
</thead>
|
||||
</table>
|
||||
</div>
|
||||
{% endfor %}
|
||||
</main>
|
||||
</div>
|
||||
</div>
|
||||
{% endfor %}
|
||||
</body>
|
||||
</html>
|
||||
{% endfunc %}
|
||||
|
||||
{% func queryArgs(m map[string]string) %}
|
||||
{% code
|
||||
qa := make(url.Values, len(m))
|
||||
for k, v := range m {
|
||||
qa[k] = []string{v}
|
||||
}
|
||||
%}
|
||||
{%s qa.Encode() %}
|
||||
{% endfunc %}
|
||||
|
||||
{% func formatLabel(labels []prompbmarshal.Label) %}
|
||||
{
|
||||
{% for i, label := range labels %}
|
||||
|
@ -175,4 +268,14 @@ function expand_all() {
|
|||
}
|
||||
{% endfunc %}
|
||||
|
||||
{% func errorNotification(err error) %}
|
||||
<div class="alert alert-danger d-flex align-items-center" role="alert">
|
||||
<svg class="bi flex-shrink-0 me-2" width="24" height="24" role="img" aria-label="Danger:">
|
||||
<use xlink:href="#exclamation-triangle-fill"/></svg>
|
||||
<div>
|
||||
{%s err.Error() %}
|
||||
</div>
|
||||
</div>
|
||||
{% endfunc %}
|
||||
|
||||
{% endstripspace %}
|
||||
|
|
|
@ -8,467 +8,626 @@ package promscrape
|
|||
import (
|
||||
"github.com/VictoriaMetrics/VictoriaMetrics/lib/prompbmarshal"
|
||||
"github.com/VictoriaMetrics/VictoriaMetrics/lib/promrelabel"
|
||||
"net/url"
|
||||
"time"
|
||||
)
|
||||
|
||||
//line lib/promscrape/targetstatus.qtpl:9
|
||||
//line lib/promscrape/targetstatus.qtpl:10
|
||||
import (
|
||||
qtio422016 "io"
|
||||
|
||||
qt422016 "github.com/valyala/quicktemplate"
|
||||
)
|
||||
|
||||
//line lib/promscrape/targetstatus.qtpl:9
|
||||
//line lib/promscrape/targetstatus.qtpl:10
|
||||
var (
|
||||
_ = qtio422016.Copy
|
||||
_ = qt422016.AcquireByteBuffer
|
||||
)
|
||||
|
||||
//line lib/promscrape/targetstatus.qtpl:9
|
||||
func StreamTargetsResponsePlain(qw422016 *qt422016.Writer, jts []jobTargetsStatuses, emptyJobs []string, showOriginLabels bool) {
|
||||
//line lib/promscrape/targetstatus.qtpl:11
|
||||
for _, js := range jts {
|
||||
//line lib/promscrape/targetstatus.qtpl:11
|
||||
qw422016.N().S(`job=`)
|
||||
//line lib/promscrape/targetstatus.qtpl:10
|
||||
func StreamTargetsResponsePlain(qw422016 *qt422016.Writer, jts []jobTargetsStatuses, emptyJobs []string, showOriginLabels, showOnlyUnhealthy bool, err error) {
|
||||
//line lib/promscrape/targetstatus.qtpl:12
|
||||
qw422016.N().Q(js.job)
|
||||
//line lib/promscrape/targetstatus.qtpl:12
|
||||
qw422016.N().S(`(`)
|
||||
//line lib/promscrape/targetstatus.qtpl:12
|
||||
qw422016.N().D(js.upCount)
|
||||
//line lib/promscrape/targetstatus.qtpl:12
|
||||
qw422016.N().S(`/`)
|
||||
//line lib/promscrape/targetstatus.qtpl:12
|
||||
qw422016.N().D(js.targetsTotal)
|
||||
//line lib/promscrape/targetstatus.qtpl:12
|
||||
qw422016.N().S(` `)
|
||||
//line lib/promscrape/targetstatus.qtpl:12
|
||||
qw422016.N().S(`up)`)
|
||||
if err != nil {
|
||||
//line lib/promscrape/targetstatus.qtpl:13
|
||||
qw422016.N().S(err.Error())
|
||||
//line lib/promscrape/targetstatus.qtpl:14
|
||||
return
|
||||
//line lib/promscrape/targetstatus.qtpl:15
|
||||
}
|
||||
//line lib/promscrape/targetstatus.qtpl:17
|
||||
for _, js := range jts {
|
||||
//line lib/promscrape/targetstatus.qtpl:18
|
||||
if showOnlyUnhealthy && js.upCount == js.targetsTotal {
|
||||
//line lib/promscrape/targetstatus.qtpl:18
|
||||
continue
|
||||
//line lib/promscrape/targetstatus.qtpl:18
|
||||
}
|
||||
//line lib/promscrape/targetstatus.qtpl:18
|
||||
qw422016.N().S(`job=`)
|
||||
//line lib/promscrape/targetstatus.qtpl:19
|
||||
qw422016.N().Q(js.job)
|
||||
//line lib/promscrape/targetstatus.qtpl:19
|
||||
qw422016.N().S(`(`)
|
||||
//line lib/promscrape/targetstatus.qtpl:19
|
||||
qw422016.N().D(js.upCount)
|
||||
//line lib/promscrape/targetstatus.qtpl:19
|
||||
qw422016.N().S(`/`)
|
||||
//line lib/promscrape/targetstatus.qtpl:19
|
||||
qw422016.N().D(js.targetsTotal)
|
||||
//line lib/promscrape/targetstatus.qtpl:19
|
||||
qw422016.N().S(` `)
|
||||
//line lib/promscrape/targetstatus.qtpl:19
|
||||
qw422016.N().S(`up)`)
|
||||
//line lib/promscrape/targetstatus.qtpl:20
|
||||
qw422016.N().S(`
|
||||
`)
|
||||
//line lib/promscrape/targetstatus.qtpl:14
|
||||
//line lib/promscrape/targetstatus.qtpl:21
|
||||
for _, ts := range js.targetsStatus {
|
||||
//line lib/promscrape/targetstatus.qtpl:15
|
||||
//line lib/promscrape/targetstatus.qtpl:22
|
||||
if showOnlyUnhealthy && ts.up {
|
||||
//line lib/promscrape/targetstatus.qtpl:22
|
||||
continue
|
||||
//line lib/promscrape/targetstatus.qtpl:22
|
||||
}
|
||||
//line lib/promscrape/targetstatus.qtpl:23
|
||||
qw422016.N().S("\t")
|
||||
//line lib/promscrape/targetstatus.qtpl:15
|
||||
//line lib/promscrape/targetstatus.qtpl:23
|
||||
qw422016.N().S(`state=`)
|
||||
//line lib/promscrape/targetstatus.qtpl:16
|
||||
//line lib/promscrape/targetstatus.qtpl:24
|
||||
if ts.up {
|
||||
//line lib/promscrape/targetstatus.qtpl:16
|
||||
//line lib/promscrape/targetstatus.qtpl:24
|
||||
qw422016.N().S(`up`)
|
||||
//line lib/promscrape/targetstatus.qtpl:16
|
||||
//line lib/promscrape/targetstatus.qtpl:24
|
||||
} else {
|
||||
//line lib/promscrape/targetstatus.qtpl:16
|
||||
//line lib/promscrape/targetstatus.qtpl:24
|
||||
qw422016.N().S(`down`)
|
||||
//line lib/promscrape/targetstatus.qtpl:16
|
||||
//line lib/promscrape/targetstatus.qtpl:24
|
||||
}
|
||||
//line lib/promscrape/targetstatus.qtpl:16
|
||||
//line lib/promscrape/targetstatus.qtpl:24
|
||||
qw422016.N().S(`,`)
|
||||
//line lib/promscrape/targetstatus.qtpl:16
|
||||
//line lib/promscrape/targetstatus.qtpl:24
|
||||
qw422016.N().S(` `)
|
||||
//line lib/promscrape/targetstatus.qtpl:16
|
||||
//line lib/promscrape/targetstatus.qtpl:24
|
||||
qw422016.N().S(`endpoint=`)
|
||||
//line lib/promscrape/targetstatus.qtpl:17
|
||||
//line lib/promscrape/targetstatus.qtpl:25
|
||||
qw422016.N().S(ts.sw.Config.ScrapeURL)
|
||||
//line lib/promscrape/targetstatus.qtpl:17
|
||||
//line lib/promscrape/targetstatus.qtpl:25
|
||||
qw422016.N().S(`,`)
|
||||
//line lib/promscrape/targetstatus.qtpl:17
|
||||
//line lib/promscrape/targetstatus.qtpl:25
|
||||
qw422016.N().S(` `)
|
||||
//line lib/promscrape/targetstatus.qtpl:17
|
||||
//line lib/promscrape/targetstatus.qtpl:25
|
||||
qw422016.N().S(`labels=`)
|
||||
//line lib/promscrape/targetstatus.qtpl:18
|
||||
qw422016.N().S(promLabelsString(promrelabel.FinalizeLabels(nil, ts.sw.Config.Labels)))
|
||||
//line lib/promscrape/targetstatus.qtpl:18
|
||||
qw422016.N().S(`,`)
|
||||
//line lib/promscrape/targetstatus.qtpl:18
|
||||
qw422016.N().S(` `)
|
||||
//line lib/promscrape/targetstatus.qtpl:19
|
||||
if showOriginLabels {
|
||||
//line lib/promscrape/targetstatus.qtpl:19
|
||||
qw422016.N().S(`originalLabels=`)
|
||||
//line lib/promscrape/targetstatus.qtpl:19
|
||||
qw422016.N().S(promLabelsString(ts.sw.Config.OriginalLabels))
|
||||
//line lib/promscrape/targetstatus.qtpl:19
|
||||
qw422016.N().S(`,`)
|
||||
//line lib/promscrape/targetstatus.qtpl:19
|
||||
qw422016.N().S(` `)
|
||||
//line lib/promscrape/targetstatus.qtpl:19
|
||||
}
|
||||
//line lib/promscrape/targetstatus.qtpl:19
|
||||
qw422016.N().S(`scrapes_total=`)
|
||||
//line lib/promscrape/targetstatus.qtpl:20
|
||||
qw422016.N().D(ts.scrapesTotal)
|
||||
//line lib/promscrape/targetstatus.qtpl:20
|
||||
qw422016.N().S(`,`)
|
||||
//line lib/promscrape/targetstatus.qtpl:20
|
||||
qw422016.N().S(` `)
|
||||
//line lib/promscrape/targetstatus.qtpl:20
|
||||
qw422016.N().S(`scrapes_failed=`)
|
||||
//line lib/promscrape/targetstatus.qtpl:21
|
||||
qw422016.N().D(ts.scrapesFailed)
|
||||
//line lib/promscrape/targetstatus.qtpl:21
|
||||
qw422016.N().S(`,`)
|
||||
//line lib/promscrape/targetstatus.qtpl:21
|
||||
qw422016.N().S(` `)
|
||||
//line lib/promscrape/targetstatus.qtpl:21
|
||||
qw422016.N().S(`last_scrape=`)
|
||||
//line lib/promscrape/targetstatus.qtpl:22
|
||||
qw422016.N().FPrec(ts.getDurationFromLastScrape().Seconds(), 3)
|
||||
//line lib/promscrape/targetstatus.qtpl:22
|
||||
qw422016.N().S(`s ago,`)
|
||||
//line lib/promscrape/targetstatus.qtpl:22
|
||||
qw422016.N().S(` `)
|
||||
//line lib/promscrape/targetstatus.qtpl:22
|
||||
qw422016.N().S(`scrape_duration=`)
|
||||
//line lib/promscrape/targetstatus.qtpl:23
|
||||
qw422016.N().D(int(ts.scrapeDuration))
|
||||
//line lib/promscrape/targetstatus.qtpl:23
|
||||
qw422016.N().S(`ms,`)
|
||||
//line lib/promscrape/targetstatus.qtpl:23
|
||||
qw422016.N().S(` `)
|
||||
//line lib/promscrape/targetstatus.qtpl:23
|
||||
qw422016.N().S(`samples_scraped=`)
|
||||
//line lib/promscrape/targetstatus.qtpl:24
|
||||
qw422016.N().D(ts.samplesScraped)
|
||||
//line lib/promscrape/targetstatus.qtpl:24
|
||||
qw422016.N().S(`,`)
|
||||
//line lib/promscrape/targetstatus.qtpl:24
|
||||
qw422016.N().S(` `)
|
||||
//line lib/promscrape/targetstatus.qtpl:24
|
||||
qw422016.N().S(`error=`)
|
||||
//line lib/promscrape/targetstatus.qtpl:25
|
||||
if ts.err != nil {
|
||||
//line lib/promscrape/targetstatus.qtpl:25
|
||||
qw422016.N().S(ts.err.Error())
|
||||
//line lib/promscrape/targetstatus.qtpl:25
|
||||
}
|
||||
//line lib/promscrape/targetstatus.qtpl:26
|
||||
qw422016.N().S(promLabelsString(promrelabel.FinalizeLabels(nil, ts.sw.Config.Labels)))
|
||||
//line lib/promscrape/targetstatus.qtpl:26
|
||||
qw422016.N().S(`,`)
|
||||
//line lib/promscrape/targetstatus.qtpl:26
|
||||
qw422016.N().S(` `)
|
||||
//line lib/promscrape/targetstatus.qtpl:27
|
||||
if showOriginLabels {
|
||||
//line lib/promscrape/targetstatus.qtpl:27
|
||||
qw422016.N().S(`originalLabels=`)
|
||||
//line lib/promscrape/targetstatus.qtpl:27
|
||||
qw422016.N().S(promLabelsString(ts.sw.Config.OriginalLabels))
|
||||
//line lib/promscrape/targetstatus.qtpl:27
|
||||
qw422016.N().S(`,`)
|
||||
//line lib/promscrape/targetstatus.qtpl:27
|
||||
qw422016.N().S(` `)
|
||||
//line lib/promscrape/targetstatus.qtpl:27
|
||||
}
|
||||
//line lib/promscrape/targetstatus.qtpl:27
|
||||
qw422016.N().S(`scrapes_total=`)
|
||||
//line lib/promscrape/targetstatus.qtpl:28
|
||||
qw422016.N().D(ts.scrapesTotal)
|
||||
//line lib/promscrape/targetstatus.qtpl:28
|
||||
qw422016.N().S(`,`)
|
||||
//line lib/promscrape/targetstatus.qtpl:28
|
||||
qw422016.N().S(` `)
|
||||
//line lib/promscrape/targetstatus.qtpl:28
|
||||
qw422016.N().S(`scrapes_failed=`)
|
||||
//line lib/promscrape/targetstatus.qtpl:29
|
||||
qw422016.N().D(ts.scrapesFailed)
|
||||
//line lib/promscrape/targetstatus.qtpl:29
|
||||
qw422016.N().S(`,`)
|
||||
//line lib/promscrape/targetstatus.qtpl:29
|
||||
qw422016.N().S(` `)
|
||||
//line lib/promscrape/targetstatus.qtpl:29
|
||||
qw422016.N().S(`last_scrape=`)
|
||||
//line lib/promscrape/targetstatus.qtpl:30
|
||||
qw422016.N().FPrec(ts.getDurationFromLastScrape().Seconds(), 3)
|
||||
//line lib/promscrape/targetstatus.qtpl:30
|
||||
qw422016.N().S(`s ago,`)
|
||||
//line lib/promscrape/targetstatus.qtpl:30
|
||||
qw422016.N().S(` `)
|
||||
//line lib/promscrape/targetstatus.qtpl:30
|
||||
qw422016.N().S(`scrape_duration=`)
|
||||
//line lib/promscrape/targetstatus.qtpl:31
|
||||
qw422016.N().D(int(ts.scrapeDuration))
|
||||
//line lib/promscrape/targetstatus.qtpl:31
|
||||
qw422016.N().S(`ms,`)
|
||||
//line lib/promscrape/targetstatus.qtpl:31
|
||||
qw422016.N().S(` `)
|
||||
//line lib/promscrape/targetstatus.qtpl:31
|
||||
qw422016.N().S(`samples_scraped=`)
|
||||
//line lib/promscrape/targetstatus.qtpl:32
|
||||
qw422016.N().D(ts.samplesScraped)
|
||||
//line lib/promscrape/targetstatus.qtpl:32
|
||||
qw422016.N().S(`,`)
|
||||
//line lib/promscrape/targetstatus.qtpl:32
|
||||
qw422016.N().S(` `)
|
||||
//line lib/promscrape/targetstatus.qtpl:32
|
||||
qw422016.N().S(`error=`)
|
||||
//line lib/promscrape/targetstatus.qtpl:33
|
||||
if ts.err != nil {
|
||||
//line lib/promscrape/targetstatus.qtpl:33
|
||||
qw422016.N().S(ts.err.Error())
|
||||
//line lib/promscrape/targetstatus.qtpl:33
|
||||
}
|
||||
//line lib/promscrape/targetstatus.qtpl:34
|
||||
qw422016.N().S(`
|
||||
`)
|
||||
//line lib/promscrape/targetstatus.qtpl:27
|
||||
//line lib/promscrape/targetstatus.qtpl:35
|
||||
}
|
||||
//line lib/promscrape/targetstatus.qtpl:28
|
||||
//line lib/promscrape/targetstatus.qtpl:36
|
||||
}
|
||||
//line lib/promscrape/targetstatus.qtpl:30
|
||||
//line lib/promscrape/targetstatus.qtpl:38
|
||||
for _, jobName := range emptyJobs {
|
||||
//line lib/promscrape/targetstatus.qtpl:30
|
||||
//line lib/promscrape/targetstatus.qtpl:38
|
||||
qw422016.N().S(`job=`)
|
||||
//line lib/promscrape/targetstatus.qtpl:31
|
||||
//line lib/promscrape/targetstatus.qtpl:39
|
||||
qw422016.N().Q(jobName)
|
||||
//line lib/promscrape/targetstatus.qtpl:31
|
||||
//line lib/promscrape/targetstatus.qtpl:39
|
||||
qw422016.N().S(`(0/0 up)`)
|
||||
//line lib/promscrape/targetstatus.qtpl:32
|
||||
//line lib/promscrape/targetstatus.qtpl:40
|
||||
qw422016.N().S(`
|
||||
`)
|
||||
//line lib/promscrape/targetstatus.qtpl:33
|
||||
//line lib/promscrape/targetstatus.qtpl:41
|
||||
}
|
||||
//line lib/promscrape/targetstatus.qtpl:35
|
||||
//line lib/promscrape/targetstatus.qtpl:43
|
||||
}
|
||||
|
||||
//line lib/promscrape/targetstatus.qtpl:35
|
||||
func WriteTargetsResponsePlain(qq422016 qtio422016.Writer, jts []jobTargetsStatuses, emptyJobs []string, showOriginLabels bool) {
|
||||
//line lib/promscrape/targetstatus.qtpl:35
|
||||
//line lib/promscrape/targetstatus.qtpl:43
|
||||
func WriteTargetsResponsePlain(qq422016 qtio422016.Writer, jts []jobTargetsStatuses, emptyJobs []string, showOriginLabels, showOnlyUnhealthy bool, err error) {
|
||||
//line lib/promscrape/targetstatus.qtpl:43
|
||||
qw422016 := qt422016.AcquireWriter(qq422016)
|
||||
//line lib/promscrape/targetstatus.qtpl:35
|
||||
StreamTargetsResponsePlain(qw422016, jts, emptyJobs, showOriginLabels)
|
||||
//line lib/promscrape/targetstatus.qtpl:35
|
||||
//line lib/promscrape/targetstatus.qtpl:43
|
||||
StreamTargetsResponsePlain(qw422016, jts, emptyJobs, showOriginLabels, showOnlyUnhealthy, err)
|
||||
//line lib/promscrape/targetstatus.qtpl:43
|
||||
qt422016.ReleaseWriter(qw422016)
|
||||
//line lib/promscrape/targetstatus.qtpl:35
|
||||
//line lib/promscrape/targetstatus.qtpl:43
|
||||
}
|
||||
|
||||
//line lib/promscrape/targetstatus.qtpl:35
|
||||
func TargetsResponsePlain(jts []jobTargetsStatuses, emptyJobs []string, showOriginLabels bool) string {
|
||||
//line lib/promscrape/targetstatus.qtpl:35
|
||||
//line lib/promscrape/targetstatus.qtpl:43
|
||||
func TargetsResponsePlain(jts []jobTargetsStatuses, emptyJobs []string, showOriginLabels, showOnlyUnhealthy bool, err error) string {
|
||||
//line lib/promscrape/targetstatus.qtpl:43
|
||||
qb422016 := qt422016.AcquireByteBuffer()
|
||||
//line lib/promscrape/targetstatus.qtpl:35
|
||||
WriteTargetsResponsePlain(qb422016, jts, emptyJobs, showOriginLabels)
|
||||
//line lib/promscrape/targetstatus.qtpl:35
|
||||
//line lib/promscrape/targetstatus.qtpl:43
|
||||
WriteTargetsResponsePlain(qb422016, jts, emptyJobs, showOriginLabels, showOnlyUnhealthy, err)
|
||||
//line lib/promscrape/targetstatus.qtpl:43
|
||||
qs422016 := string(qb422016.B)
|
||||
//line lib/promscrape/targetstatus.qtpl:35
|
||||
//line lib/promscrape/targetstatus.qtpl:43
|
||||
qt422016.ReleaseByteBuffer(qb422016)
|
||||
//line lib/promscrape/targetstatus.qtpl:35
|
||||
//line lib/promscrape/targetstatus.qtpl:43
|
||||
return qs422016
|
||||
//line lib/promscrape/targetstatus.qtpl:35
|
||||
//line lib/promscrape/targetstatus.qtpl:43
|
||||
}
|
||||
|
||||
//line lib/promscrape/targetstatus.qtpl:37
|
||||
func StreamTargetsResponseHTML(qw422016 *qt422016.Writer, jts []jobTargetsStatuses, emptyJobs []string, onlyUnhealthy bool) {
|
||||
//line lib/promscrape/targetstatus.qtpl:37
|
||||
//line lib/promscrape/targetstatus.qtpl:45
|
||||
func StreamTargetsResponseHTML(qw422016 *qt422016.Writer, jts []jobTargetsStatuses, emptyJobs []string, showOnlyUnhealthy bool, endpointSearch, labelSearch string, err error) {
|
||||
//line lib/promscrape/targetstatus.qtpl:45
|
||||
qw422016.N().S(`<!DOCTYPE html><html lang="en"><head><meta charset="utf-8"><meta name="viewport" content="width=device-width, initial-scale=1"><link href="https://cdn.jsdelivr.net/npm/bootstrap@5.0.2/dist/css/bootstrap.min.css" rel="stylesheet" integrity="sha384-EVSTQN3/azprG1Anm3QDgpJLIm9Nao0Yz1ztcQTwFspd3yD65VohhpuuCOmLASjC" crossorigin="anonymous"><title>Scrape targets</title><script>function collapse_all() {for (var i = 0; i <`)
|
||||
//line lib/promscrape/targetstatus.qtpl:47
|
||||
//line lib/promscrape/targetstatus.qtpl:55
|
||||
qw422016.N().D(len(jts))
|
||||
//line lib/promscrape/targetstatus.qtpl:47
|
||||
//line lib/promscrape/targetstatus.qtpl:55
|
||||
qw422016.N().S(`; i++) {let el = document.getElementById("table-" + i);if (!el) {continue;}el.style.display = 'none';}}function expand_all() {for (var i = 0; i <`)
|
||||
//line lib/promscrape/targetstatus.qtpl:56
|
||||
//line lib/promscrape/targetstatus.qtpl:64
|
||||
qw422016.N().D(len(jts))
|
||||
//line lib/promscrape/targetstatus.qtpl:56
|
||||
qw422016.N().S(`; i++) {let el = document.getElementById("table-" + i);if (!el) {continue;}el.style.display = 'block';}}</script></head><body class="m-3"><h1>Scrape targets</h1><div style="padding: 3px"><button type="button" class="btn`)
|
||||
//line lib/promscrape/targetstatus.qtpl:69
|
||||
qw422016.N().S(` `)
|
||||
//line lib/promscrape/targetstatus.qtpl:69
|
||||
if !onlyUnhealthy {
|
||||
//line lib/promscrape/targetstatus.qtpl:69
|
||||
qw422016.N().S(`btn-primary`)
|
||||
//line lib/promscrape/targetstatus.qtpl:69
|
||||
} else {
|
||||
//line lib/promscrape/targetstatus.qtpl:69
|
||||
qw422016.N().S(`btn-secondary`)
|
||||
//line lib/promscrape/targetstatus.qtpl:69
|
||||
//line lib/promscrape/targetstatus.qtpl:64
|
||||
qw422016.N().S(`; i++) {let el = document.getElementById("table-" + i);if (!el) {continue;}el.style.display = 'block';}}</script></head><body class="py-3"><div class="container-fluid">`)
|
||||
//line lib/promscrape/targetstatus.qtpl:76
|
||||
if err != nil {
|
||||
//line lib/promscrape/targetstatus.qtpl:77
|
||||
streamerrorNotification(qw422016, err)
|
||||
//line lib/promscrape/targetstatus.qtpl:78
|
||||
}
|
||||
//line lib/promscrape/targetstatus.qtpl:69
|
||||
qw422016.N().S(`" onclick="location.href='targets'">All</button><button type="button" class="btn`)
|
||||
//line lib/promscrape/targetstatus.qtpl:72
|
||||
//line lib/promscrape/targetstatus.qtpl:78
|
||||
qw422016.N().S(`<div class="row"><main class="col-12"><h1>Scrape targets</h1><hr /><div class="row g-3 align-items-center mb-3"><div class="col-auto"><button type="button" class="btn`)
|
||||
//line lib/promscrape/targetstatus.qtpl:85
|
||||
qw422016.N().S(` `)
|
||||
//line lib/promscrape/targetstatus.qtpl:72
|
||||
if onlyUnhealthy {
|
||||
//line lib/promscrape/targetstatus.qtpl:72
|
||||
//line lib/promscrape/targetstatus.qtpl:85
|
||||
if !showOnlyUnhealthy {
|
||||
//line lib/promscrape/targetstatus.qtpl:85
|
||||
qw422016.N().S(`btn-primary`)
|
||||
//line lib/promscrape/targetstatus.qtpl:72
|
||||
//line lib/promscrape/targetstatus.qtpl:85
|
||||
} else {
|
||||
//line lib/promscrape/targetstatus.qtpl:72
|
||||
//line lib/promscrape/targetstatus.qtpl:85
|
||||
qw422016.N().S(`btn-secondary`)
|
||||
//line lib/promscrape/targetstatus.qtpl:72
|
||||
//line lib/promscrape/targetstatus.qtpl:85
|
||||
}
|
||||
//line lib/promscrape/targetstatus.qtpl:72
|
||||
qw422016.N().S(`" onclick="location.href='targets?show_only_unhealthy=true'">Unhealthy</button><button type="button" class="btn btn-primary" onclick="collapse_all()">Collapse all</button><button type="button" class="btn btn-secondary" onclick="expand_all()">Expand all</button></div>`)
|
||||
//line lib/promscrape/targetstatus.qtpl:82
|
||||
//line lib/promscrape/targetstatus.qtpl:85
|
||||
qw422016.N().S(`" onclick="location.href='?`)
|
||||
//line lib/promscrape/targetstatus.qtpl:85
|
||||
streamqueryArgs(qw422016, map[string]string{
|
||||
"show_only_unhealthy": "false",
|
||||
"endpoint_search": endpointSearch,
|
||||
"label_search": labelSearch,
|
||||
})
|
||||
//line lib/promscrape/targetstatus.qtpl:89
|
||||
qw422016.N().S(`'">All</button></div><div class="col-auto"><button type="button" class="btn`)
|
||||
//line lib/promscrape/targetstatus.qtpl:94
|
||||
qw422016.N().S(` `)
|
||||
//line lib/promscrape/targetstatus.qtpl:94
|
||||
if showOnlyUnhealthy {
|
||||
//line lib/promscrape/targetstatus.qtpl:94
|
||||
qw422016.N().S(`btn-primary`)
|
||||
//line lib/promscrape/targetstatus.qtpl:94
|
||||
} else {
|
||||
//line lib/promscrape/targetstatus.qtpl:94
|
||||
qw422016.N().S(`btn-secondary`)
|
||||
//line lib/promscrape/targetstatus.qtpl:94
|
||||
}
|
||||
//line lib/promscrape/targetstatus.qtpl:94
|
||||
qw422016.N().S(`" onclick="location.href='?`)
|
||||
//line lib/promscrape/targetstatus.qtpl:94
|
||||
streamqueryArgs(qw422016, map[string]string{
|
||||
"show_only_unhealthy": "true",
|
||||
"endpoint_search": endpointSearch,
|
||||
"label_search": labelSearch,
|
||||
})
|
||||
//line lib/promscrape/targetstatus.qtpl:98
|
||||
qw422016.N().S(`'">Unhealthy</button></div><div class="col-auto"><button type="button" class="btn btn-primary" onclick="collapse_all()">Collapse all</button></div><div class="col-auto"><button type="button" class="btn btn-secondary" onclick="expand_all()">Expand all</button></div><div class="col-auto">`)
|
||||
//line lib/promscrape/targetstatus.qtpl:113
|
||||
if endpointSearch == "" && labelSearch == "" {
|
||||
//line lib/promscrape/targetstatus.qtpl:113
|
||||
qw422016.N().S(`<button type="button" class="btn btn-primary" onclick="document.getElementById('filters').style.display='block'">Filter targets</button>`)
|
||||
//line lib/promscrape/targetstatus.qtpl:117
|
||||
} else {
|
||||
//line lib/promscrape/targetstatus.qtpl:117
|
||||
qw422016.N().S(`<button type="button" class="btn btn-primary" onclick="location.href='?'">Clear target filters</button>`)
|
||||
//line lib/promscrape/targetstatus.qtpl:121
|
||||
}
|
||||
//line lib/promscrape/targetstatus.qtpl:121
|
||||
qw422016.N().S(`</div></div><div id="filters"`)
|
||||
//line lib/promscrape/targetstatus.qtpl:124
|
||||
if endpointSearch == "" && labelSearch == "" {
|
||||
//line lib/promscrape/targetstatus.qtpl:124
|
||||
qw422016.N().S(`style="display:none"`)
|
||||
//line lib/promscrape/targetstatus.qtpl:124
|
||||
}
|
||||
//line lib/promscrape/targetstatus.qtpl:124
|
||||
qw422016.N().S(`><form class="form-horizontal"><div class="form-group mb-3"><label for="endpoint_search" class="col-sm-10 control-label">Endpoint filter (<a target="_blank" href="https://github.com/google/re2/wiki/Syntax">Regexp</a> is accepted)</label><div class="col-sm-10"><input type="text" id="endpoint_search" name="endpoint_search"placeholder="For example, 127.0.0.1" class="form-control" value="`)
|
||||
//line lib/promscrape/targetstatus.qtpl:130
|
||||
qw422016.E().S(endpointSearch)
|
||||
//line lib/promscrape/targetstatus.qtpl:130
|
||||
qw422016.N().S(`"/></div></div><div class="form-group mb-3"><label for="label_search" class="col-sm-10 control-label">Labels filter (<a target="_blank" href="https://prometheus.io/docs/prometheus/latest/querying/basics/#time-series-selectors">Arbitrary time series selectors</a> are accepted)</label><div class="col-sm-10"><input type="text" id="label_search" name="label_search"placeholder="For example, {instance=~'.+:9100'}" class="form-control" value="`)
|
||||
//line lib/promscrape/targetstatus.qtpl:137
|
||||
qw422016.E().S(labelSearch)
|
||||
//line lib/promscrape/targetstatus.qtpl:137
|
||||
qw422016.N().S(`"/></div></div><input type="hidden" name="show_only_unhealthy" value="`)
|
||||
//line lib/promscrape/targetstatus.qtpl:140
|
||||
qw422016.E().V(showOnlyUnhealthy)
|
||||
//line lib/promscrape/targetstatus.qtpl:140
|
||||
qw422016.N().S(`"/><button type="submit" class="btn btn-success mb-3">Submit</button></form></div><hr /><div class="row"><div class="col-12">`)
|
||||
//line lib/promscrape/targetstatus.qtpl:147
|
||||
for i, js := range jts {
|
||||
//line lib/promscrape/targetstatus.qtpl:83
|
||||
if onlyUnhealthy && js.upCount == js.targetsTotal {
|
||||
//line lib/promscrape/targetstatus.qtpl:83
|
||||
//line lib/promscrape/targetstatus.qtpl:148
|
||||
if showOnlyUnhealthy && js.upCount == js.targetsTotal {
|
||||
//line lib/promscrape/targetstatus.qtpl:148
|
||||
continue
|
||||
//line lib/promscrape/targetstatus.qtpl:83
|
||||
//line lib/promscrape/targetstatus.qtpl:148
|
||||
}
|
||||
//line lib/promscrape/targetstatus.qtpl:83
|
||||
qw422016.N().S(`<div><h4>`)
|
||||
//line lib/promscrape/targetstatus.qtpl:86
|
||||
//line lib/promscrape/targetstatus.qtpl:148
|
||||
qw422016.N().S(`<div class="row mb-4"><div class="col-12"><h4>`)
|
||||
//line lib/promscrape/targetstatus.qtpl:152
|
||||
qw422016.E().S(js.job)
|
||||
//line lib/promscrape/targetstatus.qtpl:86
|
||||
//line lib/promscrape/targetstatus.qtpl:152
|
||||
qw422016.N().S(` `)
|
||||
//line lib/promscrape/targetstatus.qtpl:86
|
||||
//line lib/promscrape/targetstatus.qtpl:152
|
||||
qw422016.N().S(`(`)
|
||||
//line lib/promscrape/targetstatus.qtpl:86
|
||||
//line lib/promscrape/targetstatus.qtpl:152
|
||||
qw422016.N().D(js.upCount)
|
||||
//line lib/promscrape/targetstatus.qtpl:86
|
||||
//line lib/promscrape/targetstatus.qtpl:152
|
||||
qw422016.N().S(`/`)
|
||||
//line lib/promscrape/targetstatus.qtpl:86
|
||||
//line lib/promscrape/targetstatus.qtpl:152
|
||||
qw422016.N().D(js.targetsTotal)
|
||||
//line lib/promscrape/targetstatus.qtpl:86
|
||||
//line lib/promscrape/targetstatus.qtpl:152
|
||||
qw422016.N().S(` `)
|
||||
//line lib/promscrape/targetstatus.qtpl:86
|
||||
qw422016.N().S(`up)<button type="button" class="btn btn-primary" onclick="document.getElementById('table-`)
|
||||
//line lib/promscrape/targetstatus.qtpl:87
|
||||
//line lib/promscrape/targetstatus.qtpl:152
|
||||
qw422016.N().S(`up)</h4><div class="row mb-2"><div class="col-12"><button type="button" class="btn btn-primary me-1"onclick="document.getElementById('table-`)
|
||||
//line lib/promscrape/targetstatus.qtpl:157
|
||||
qw422016.N().D(i)
|
||||
//line lib/promscrape/targetstatus.qtpl:87
|
||||
qw422016.N().S(`').style.display='none'">collapse</button><button type="button" class="btn btn-secondary" onclick="document.getElementById('table-`)
|
||||
//line lib/promscrape/targetstatus.qtpl:88
|
||||
//line lib/promscrape/targetstatus.qtpl:157
|
||||
qw422016.N().S(`').style.display='none'">collapse</button><button type="button" class="btn btn-secondary me-1"onclick="document.getElementById('table-`)
|
||||
//line lib/promscrape/targetstatus.qtpl:160
|
||||
qw422016.N().D(i)
|
||||
//line lib/promscrape/targetstatus.qtpl:88
|
||||
qw422016.N().S(`').style.display='block'">expand</button></h4><div id="table-`)
|
||||
//line lib/promscrape/targetstatus.qtpl:90
|
||||
//line lib/promscrape/targetstatus.qtpl:160
|
||||
qw422016.N().S(`').style.display='block'">expand</button></div></div><div id="table-`)
|
||||
//line lib/promscrape/targetstatus.qtpl:164
|
||||
qw422016.N().D(i)
|
||||
//line lib/promscrape/targetstatus.qtpl:90
|
||||
qw422016.N().S(`"><table class="table table-striped table-hover table-bordered table-sm"><thead><tr><th scope="col">Endpoint</th><th scope="col">State</th><th scope="col" title="scrape target labels">Labels</th><th scope="col" title="total scrapes">Scrapes</th><th scope="col" title="total scrape errors">Errors</th><th scope="col" title="the time of the last scrape">Last Scrape</th><th scope="col" title="the duration of the last scrape">Duration</th><th scope="col" title="the number of metrics scraped during the last scrape">Samples</th><th scope="col" title="error from the last scrape (if any)">Last error</th></tr></thead><tbody>`)
|
||||
//line lib/promscrape/targetstatus.qtpl:106
|
||||
//line lib/promscrape/targetstatus.qtpl:164
|
||||
qw422016.N().S(`" class="table-responsive"><table class="table table-striped table-hover table-bordered table-sm"><thead><tr><th scope="col">Endpoint</th><th scope="col">State</th><th scope="col" title="scrape target labels">Labels</th><th scope="col" title="total scrapes">Scrapes</th><th scope="col" title="total scrape errors">Errors</th><th scope="col" title="the time of the last scrape">Last Scrape</th><th scope="col" title="the duration of the last scrape">Duration</th><th scope="col" title="the number of metrics scraped during the last scrape">Samples</th><th scope="col" title="error from the last scrape (if any)">Last error</th></tr></thead><tbody class="list-`)
|
||||
//line lib/promscrape/targetstatus.qtpl:179
|
||||
qw422016.N().D(i)
|
||||
//line lib/promscrape/targetstatus.qtpl:179
|
||||
qw422016.N().S(`">`)
|
||||
//line lib/promscrape/targetstatus.qtpl:180
|
||||
for _, ts := range js.targetsStatus {
|
||||
//line lib/promscrape/targetstatus.qtpl:108
|
||||
//line lib/promscrape/targetstatus.qtpl:182
|
||||
endpoint := ts.sw.Config.ScrapeURL
|
||||
targetID := getTargetID(ts.sw)
|
||||
lastScrapeTime := ts.getDurationFromLastScrape()
|
||||
|
||||
//line lib/promscrape/targetstatus.qtpl:112
|
||||
if onlyUnhealthy && ts.up {
|
||||
//line lib/promscrape/targetstatus.qtpl:112
|
||||
//line lib/promscrape/targetstatus.qtpl:186
|
||||
if showOnlyUnhealthy && ts.up {
|
||||
//line lib/promscrape/targetstatus.qtpl:186
|
||||
continue
|
||||
//line lib/promscrape/targetstatus.qtpl:112
|
||||
//line lib/promscrape/targetstatus.qtpl:186
|
||||
}
|
||||
//line lib/promscrape/targetstatus.qtpl:112
|
||||
//line lib/promscrape/targetstatus.qtpl:186
|
||||
qw422016.N().S(`<tr`)
|
||||
//line lib/promscrape/targetstatus.qtpl:113
|
||||
//line lib/promscrape/targetstatus.qtpl:187
|
||||
if !ts.up {
|
||||
//line lib/promscrape/targetstatus.qtpl:113
|
||||
//line lib/promscrape/targetstatus.qtpl:187
|
||||
qw422016.N().S(` `)
|
||||
//line lib/promscrape/targetstatus.qtpl:113
|
||||
//line lib/promscrape/targetstatus.qtpl:187
|
||||
qw422016.N().S(`class="alert alert-danger" role="alert"`)
|
||||
//line lib/promscrape/targetstatus.qtpl:113
|
||||
//line lib/promscrape/targetstatus.qtpl:187
|
||||
}
|
||||
//line lib/promscrape/targetstatus.qtpl:113
|
||||
qw422016.N().S(`><td><a href="`)
|
||||
//line lib/promscrape/targetstatus.qtpl:114
|
||||
//line lib/promscrape/targetstatus.qtpl:187
|
||||
qw422016.N().S(`><td class="endpoint"><a href="`)
|
||||
//line lib/promscrape/targetstatus.qtpl:188
|
||||
qw422016.E().S(endpoint)
|
||||
//line lib/promscrape/targetstatus.qtpl:114
|
||||
//line lib/promscrape/targetstatus.qtpl:188
|
||||
qw422016.N().S(`" target="_blank">`)
|
||||
//line lib/promscrape/targetstatus.qtpl:114
|
||||
//line lib/promscrape/targetstatus.qtpl:188
|
||||
qw422016.E().S(endpoint)
|
||||
//line lib/promscrape/targetstatus.qtpl:114
|
||||
//line lib/promscrape/targetstatus.qtpl:188
|
||||
qw422016.N().S(`</a> (<a href="target_response?id=`)
|
||||
//line lib/promscrape/targetstatus.qtpl:115
|
||||
//line lib/promscrape/targetstatus.qtpl:189
|
||||
qw422016.E().S(targetID)
|
||||
//line lib/promscrape/targetstatus.qtpl:115
|
||||
qw422016.N().S(`" target="_blank" title="click to fetch target response on behalf of the scraper">response</a>)</td><td>`)
|
||||
//line lib/promscrape/targetstatus.qtpl:117
|
||||
//line lib/promscrape/targetstatus.qtpl:189
|
||||
qw422016.N().S(`" target="_blank"title="click to fetch target response on behalf of the scraper">response</a>)</td><td>`)
|
||||
//line lib/promscrape/targetstatus.qtpl:193
|
||||
if ts.up {
|
||||
//line lib/promscrape/targetstatus.qtpl:117
|
||||
//line lib/promscrape/targetstatus.qtpl:193
|
||||
qw422016.N().S(`UP`)
|
||||
//line lib/promscrape/targetstatus.qtpl:117
|
||||
//line lib/promscrape/targetstatus.qtpl:193
|
||||
} else {
|
||||
//line lib/promscrape/targetstatus.qtpl:117
|
||||
//line lib/promscrape/targetstatus.qtpl:193
|
||||
qw422016.N().S(`DOWN`)
|
||||
//line lib/promscrape/targetstatus.qtpl:117
|
||||
//line lib/promscrape/targetstatus.qtpl:193
|
||||
}
|
||||
//line lib/promscrape/targetstatus.qtpl:117
|
||||
qw422016.N().S(`</td><td><div title="click to show original labels" onclick="document.getElementById('original_labels_`)
|
||||
//line lib/promscrape/targetstatus.qtpl:119
|
||||
//line lib/promscrape/targetstatus.qtpl:193
|
||||
qw422016.N().S(`</td><td class="labels"><div title="click to show original labels"onclick="document.getElementById('original_labels_`)
|
||||
//line lib/promscrape/targetstatus.qtpl:196
|
||||
qw422016.E().S(targetID)
|
||||
//line lib/promscrape/targetstatus.qtpl:119
|
||||
//line lib/promscrape/targetstatus.qtpl:196
|
||||
qw422016.N().S(`').style.display='block'">`)
|
||||
//line lib/promscrape/targetstatus.qtpl:120
|
||||
//line lib/promscrape/targetstatus.qtpl:197
|
||||
streamformatLabel(qw422016, promrelabel.FinalizeLabels(nil, ts.sw.Config.Labels))
|
||||
//line lib/promscrape/targetstatus.qtpl:120
|
||||
//line lib/promscrape/targetstatus.qtpl:197
|
||||
qw422016.N().S(`</div><div style="display:none" id="original_labels_`)
|
||||
//line lib/promscrape/targetstatus.qtpl:122
|
||||
//line lib/promscrape/targetstatus.qtpl:199
|
||||
qw422016.E().S(targetID)
|
||||
//line lib/promscrape/targetstatus.qtpl:122
|
||||
//line lib/promscrape/targetstatus.qtpl:199
|
||||
qw422016.N().S(`">`)
|
||||
//line lib/promscrape/targetstatus.qtpl:123
|
||||
//line lib/promscrape/targetstatus.qtpl:200
|
||||
streamformatLabel(qw422016, ts.sw.Config.OriginalLabels)
|
||||
//line lib/promscrape/targetstatus.qtpl:123
|
||||
//line lib/promscrape/targetstatus.qtpl:200
|
||||
qw422016.N().S(`</div></td><td>`)
|
||||
//line lib/promscrape/targetstatus.qtpl:126
|
||||
//line lib/promscrape/targetstatus.qtpl:203
|
||||
qw422016.N().D(ts.scrapesTotal)
|
||||
//line lib/promscrape/targetstatus.qtpl:126
|
||||
//line lib/promscrape/targetstatus.qtpl:203
|
||||
qw422016.N().S(`</td><td>`)
|
||||
//line lib/promscrape/targetstatus.qtpl:127
|
||||
//line lib/promscrape/targetstatus.qtpl:204
|
||||
qw422016.N().D(ts.scrapesFailed)
|
||||
//line lib/promscrape/targetstatus.qtpl:127
|
||||
//line lib/promscrape/targetstatus.qtpl:204
|
||||
qw422016.N().S(`</td><td>`)
|
||||
//line lib/promscrape/targetstatus.qtpl:129
|
||||
//line lib/promscrape/targetstatus.qtpl:206
|
||||
if lastScrapeTime < 365*24*time.Hour {
|
||||
//line lib/promscrape/targetstatus.qtpl:130
|
||||
//line lib/promscrape/targetstatus.qtpl:207
|
||||
qw422016.N().FPrec(lastScrapeTime.Seconds(), 3)
|
||||
//line lib/promscrape/targetstatus.qtpl:130
|
||||
//line lib/promscrape/targetstatus.qtpl:207
|
||||
qw422016.N().S(`s ago`)
|
||||
//line lib/promscrape/targetstatus.qtpl:131
|
||||
//line lib/promscrape/targetstatus.qtpl:208
|
||||
} else {
|
||||
//line lib/promscrape/targetstatus.qtpl:131
|
||||
//line lib/promscrape/targetstatus.qtpl:208
|
||||
qw422016.N().S(`none`)
|
||||
//line lib/promscrape/targetstatus.qtpl:133
|
||||
//line lib/promscrape/targetstatus.qtpl:210
|
||||
}
|
||||
//line lib/promscrape/targetstatus.qtpl:133
|
||||
//line lib/promscrape/targetstatus.qtpl:210
|
||||
qw422016.N().S(`<td>`)
|
||||
//line lib/promscrape/targetstatus.qtpl:134
|
||||
//line lib/promscrape/targetstatus.qtpl:211
|
||||
qw422016.N().D(int(ts.scrapeDuration))
|
||||
//line lib/promscrape/targetstatus.qtpl:134
|
||||
//line lib/promscrape/targetstatus.qtpl:211
|
||||
qw422016.N().S(`ms</td><td>`)
|
||||
//line lib/promscrape/targetstatus.qtpl:135
|
||||
//line lib/promscrape/targetstatus.qtpl:212
|
||||
qw422016.N().D(ts.samplesScraped)
|
||||
//line lib/promscrape/targetstatus.qtpl:135
|
||||
//line lib/promscrape/targetstatus.qtpl:212
|
||||
qw422016.N().S(`</td><td>`)
|
||||
//line lib/promscrape/targetstatus.qtpl:136
|
||||
//line lib/promscrape/targetstatus.qtpl:213
|
||||
if ts.err != nil {
|
||||
//line lib/promscrape/targetstatus.qtpl:136
|
||||
//line lib/promscrape/targetstatus.qtpl:213
|
||||
qw422016.E().S(ts.err.Error())
|
||||
//line lib/promscrape/targetstatus.qtpl:136
|
||||
//line lib/promscrape/targetstatus.qtpl:213
|
||||
}
|
||||
//line lib/promscrape/targetstatus.qtpl:136
|
||||
//line lib/promscrape/targetstatus.qtpl:213
|
||||
qw422016.N().S(`</td></tr>`)
|
||||
//line lib/promscrape/targetstatus.qtpl:138
|
||||
//line lib/promscrape/targetstatus.qtpl:215
|
||||
}
|
||||
//line lib/promscrape/targetstatus.qtpl:138
|
||||
qw422016.N().S(`</tbody></table></div></div>`)
|
||||
//line lib/promscrape/targetstatus.qtpl:143
|
||||
//line lib/promscrape/targetstatus.qtpl:215
|
||||
qw422016.N().S(`</tbody></table></div></div></div>`)
|
||||
//line lib/promscrape/targetstatus.qtpl:221
|
||||
}
|
||||
//line lib/promscrape/targetstatus.qtpl:145
|
||||
//line lib/promscrape/targetstatus.qtpl:221
|
||||
qw422016.N().S(`</div></div>`)
|
||||
//line lib/promscrape/targetstatus.qtpl:225
|
||||
for _, jobName := range emptyJobs {
|
||||
//line lib/promscrape/targetstatus.qtpl:145
|
||||
//line lib/promscrape/targetstatus.qtpl:225
|
||||
qw422016.N().S(`<div><h4><a>`)
|
||||
//line lib/promscrape/targetstatus.qtpl:148
|
||||
//line lib/promscrape/targetstatus.qtpl:228
|
||||
qw422016.E().S(jobName)
|
||||
//line lib/promscrape/targetstatus.qtpl:148
|
||||
//line lib/promscrape/targetstatus.qtpl:228
|
||||
qw422016.N().S(`(0/0 up)</a></h4><table class="table table-striped table-hover table-bordered table-sm"><thead><tr><th scope="col">Endpoint</th><th scope="col">State</th><th scope="col">Labels</th><th scope="col">Last Scrape</th><th scope="col">Scrape Duration</th><th scope="col">Samples Scraped</th><th scope="col">Error</th></tr></thead></table></div>`)
|
||||
//line lib/promscrape/targetstatus.qtpl:164
|
||||
//line lib/promscrape/targetstatus.qtpl:244
|
||||
}
|
||||
//line lib/promscrape/targetstatus.qtpl:164
|
||||
qw422016.N().S(`</body></html>`)
|
||||
//line lib/promscrape/targetstatus.qtpl:167
|
||||
//line lib/promscrape/targetstatus.qtpl:244
|
||||
qw422016.N().S(`</main></div></div></body></html>`)
|
||||
//line lib/promscrape/targetstatus.qtpl:250
|
||||
}
|
||||
|
||||
//line lib/promscrape/targetstatus.qtpl:167
|
||||
func WriteTargetsResponseHTML(qq422016 qtio422016.Writer, jts []jobTargetsStatuses, emptyJobs []string, onlyUnhealthy bool) {
|
||||
//line lib/promscrape/targetstatus.qtpl:167
|
||||
//line lib/promscrape/targetstatus.qtpl:250
|
||||
func WriteTargetsResponseHTML(qq422016 qtio422016.Writer, jts []jobTargetsStatuses, emptyJobs []string, showOnlyUnhealthy bool, endpointSearch, labelSearch string, err error) {
|
||||
//line lib/promscrape/targetstatus.qtpl:250
|
||||
qw422016 := qt422016.AcquireWriter(qq422016)
|
||||
//line lib/promscrape/targetstatus.qtpl:167
|
||||
StreamTargetsResponseHTML(qw422016, jts, emptyJobs, onlyUnhealthy)
|
||||
//line lib/promscrape/targetstatus.qtpl:167
|
||||
//line lib/promscrape/targetstatus.qtpl:250
|
||||
StreamTargetsResponseHTML(qw422016, jts, emptyJobs, showOnlyUnhealthy, endpointSearch, labelSearch, err)
|
||||
//line lib/promscrape/targetstatus.qtpl:250
|
||||
qt422016.ReleaseWriter(qw422016)
|
||||
//line lib/promscrape/targetstatus.qtpl:167
|
||||
//line lib/promscrape/targetstatus.qtpl:250
|
||||
}
|
||||
|
||||
//line lib/promscrape/targetstatus.qtpl:167
|
||||
func TargetsResponseHTML(jts []jobTargetsStatuses, emptyJobs []string, onlyUnhealthy bool) string {
|
||||
//line lib/promscrape/targetstatus.qtpl:167
|
||||
//line lib/promscrape/targetstatus.qtpl:250
|
||||
func TargetsResponseHTML(jts []jobTargetsStatuses, emptyJobs []string, showOnlyUnhealthy bool, endpointSearch, labelSearch string, err error) string {
|
||||
//line lib/promscrape/targetstatus.qtpl:250
|
||||
qb422016 := qt422016.AcquireByteBuffer()
|
||||
//line lib/promscrape/targetstatus.qtpl:167
|
||||
WriteTargetsResponseHTML(qb422016, jts, emptyJobs, onlyUnhealthy)
|
||||
//line lib/promscrape/targetstatus.qtpl:167
|
||||
//line lib/promscrape/targetstatus.qtpl:250
|
||||
WriteTargetsResponseHTML(qb422016, jts, emptyJobs, showOnlyUnhealthy, endpointSearch, labelSearch, err)
|
||||
//line lib/promscrape/targetstatus.qtpl:250
|
||||
qs422016 := string(qb422016.B)
|
||||
//line lib/promscrape/targetstatus.qtpl:167
|
||||
//line lib/promscrape/targetstatus.qtpl:250
|
||||
qt422016.ReleaseByteBuffer(qb422016)
|
||||
//line lib/promscrape/targetstatus.qtpl:167
|
||||
//line lib/promscrape/targetstatus.qtpl:250
|
||||
return qs422016
|
||||
//line lib/promscrape/targetstatus.qtpl:167
|
||||
//line lib/promscrape/targetstatus.qtpl:250
|
||||
}
|
||||
|
||||
//line lib/promscrape/targetstatus.qtpl:169
|
||||
//line lib/promscrape/targetstatus.qtpl:252
|
||||
func streamqueryArgs(qw422016 *qt422016.Writer, m map[string]string) {
|
||||
//line lib/promscrape/targetstatus.qtpl:254
|
||||
qa := make(url.Values, len(m))
|
||||
for k, v := range m {
|
||||
qa[k] = []string{v}
|
||||
}
|
||||
|
||||
//line lib/promscrape/targetstatus.qtpl:259
|
||||
qw422016.E().S(qa.Encode())
|
||||
//line lib/promscrape/targetstatus.qtpl:260
|
||||
}
|
||||
|
||||
//line lib/promscrape/targetstatus.qtpl:260
|
||||
func writequeryArgs(qq422016 qtio422016.Writer, m map[string]string) {
|
||||
//line lib/promscrape/targetstatus.qtpl:260
|
||||
qw422016 := qt422016.AcquireWriter(qq422016)
|
||||
//line lib/promscrape/targetstatus.qtpl:260
|
||||
streamqueryArgs(qw422016, m)
|
||||
//line lib/promscrape/targetstatus.qtpl:260
|
||||
qt422016.ReleaseWriter(qw422016)
|
||||
//line lib/promscrape/targetstatus.qtpl:260
|
||||
}
|
||||
|
||||
//line lib/promscrape/targetstatus.qtpl:260
|
||||
func queryArgs(m map[string]string) string {
|
||||
//line lib/promscrape/targetstatus.qtpl:260
|
||||
qb422016 := qt422016.AcquireByteBuffer()
|
||||
//line lib/promscrape/targetstatus.qtpl:260
|
||||
writequeryArgs(qb422016, m)
|
||||
//line lib/promscrape/targetstatus.qtpl:260
|
||||
qs422016 := string(qb422016.B)
|
||||
//line lib/promscrape/targetstatus.qtpl:260
|
||||
qt422016.ReleaseByteBuffer(qb422016)
|
||||
//line lib/promscrape/targetstatus.qtpl:260
|
||||
return qs422016
|
||||
//line lib/promscrape/targetstatus.qtpl:260
|
||||
}
|
||||
|
||||
//line lib/promscrape/targetstatus.qtpl:262
|
||||
func streamformatLabel(qw422016 *qt422016.Writer, labels []prompbmarshal.Label) {
|
||||
//line lib/promscrape/targetstatus.qtpl:169
|
||||
//line lib/promscrape/targetstatus.qtpl:262
|
||||
qw422016.N().S(`{`)
|
||||
//line lib/promscrape/targetstatus.qtpl:171
|
||||
//line lib/promscrape/targetstatus.qtpl:264
|
||||
for i, label := range labels {
|
||||
//line lib/promscrape/targetstatus.qtpl:172
|
||||
//line lib/promscrape/targetstatus.qtpl:265
|
||||
qw422016.E().S(label.Name)
|
||||
//line lib/promscrape/targetstatus.qtpl:172
|
||||
//line lib/promscrape/targetstatus.qtpl:265
|
||||
qw422016.N().S(`=`)
|
||||
//line lib/promscrape/targetstatus.qtpl:172
|
||||
//line lib/promscrape/targetstatus.qtpl:265
|
||||
qw422016.E().Q(label.Value)
|
||||
//line lib/promscrape/targetstatus.qtpl:173
|
||||
//line lib/promscrape/targetstatus.qtpl:266
|
||||
if i+1 < len(labels) {
|
||||
//line lib/promscrape/targetstatus.qtpl:173
|
||||
//line lib/promscrape/targetstatus.qtpl:266
|
||||
qw422016.N().S(`,`)
|
||||
//line lib/promscrape/targetstatus.qtpl:173
|
||||
//line lib/promscrape/targetstatus.qtpl:266
|
||||
qw422016.N().S(` `)
|
||||
//line lib/promscrape/targetstatus.qtpl:173
|
||||
//line lib/promscrape/targetstatus.qtpl:266
|
||||
}
|
||||
//line lib/promscrape/targetstatus.qtpl:174
|
||||
//line lib/promscrape/targetstatus.qtpl:267
|
||||
}
|
||||
//line lib/promscrape/targetstatus.qtpl:174
|
||||
//line lib/promscrape/targetstatus.qtpl:267
|
||||
qw422016.N().S(`}`)
|
||||
//line lib/promscrape/targetstatus.qtpl:176
|
||||
//line lib/promscrape/targetstatus.qtpl:269
|
||||
}
|
||||
|
||||
//line lib/promscrape/targetstatus.qtpl:176
|
||||
//line lib/promscrape/targetstatus.qtpl:269
|
||||
func writeformatLabel(qq422016 qtio422016.Writer, labels []prompbmarshal.Label) {
|
||||
//line lib/promscrape/targetstatus.qtpl:176
|
||||
//line lib/promscrape/targetstatus.qtpl:269
|
||||
qw422016 := qt422016.AcquireWriter(qq422016)
|
||||
//line lib/promscrape/targetstatus.qtpl:176
|
||||
//line lib/promscrape/targetstatus.qtpl:269
|
||||
streamformatLabel(qw422016, labels)
|
||||
//line lib/promscrape/targetstatus.qtpl:176
|
||||
//line lib/promscrape/targetstatus.qtpl:269
|
||||
qt422016.ReleaseWriter(qw422016)
|
||||
//line lib/promscrape/targetstatus.qtpl:176
|
||||
//line lib/promscrape/targetstatus.qtpl:269
|
||||
}
|
||||
|
||||
//line lib/promscrape/targetstatus.qtpl:176
|
||||
//line lib/promscrape/targetstatus.qtpl:269
|
||||
func formatLabel(labels []prompbmarshal.Label) string {
|
||||
//line lib/promscrape/targetstatus.qtpl:176
|
||||
//line lib/promscrape/targetstatus.qtpl:269
|
||||
qb422016 := qt422016.AcquireByteBuffer()
|
||||
//line lib/promscrape/targetstatus.qtpl:176
|
||||
//line lib/promscrape/targetstatus.qtpl:269
|
||||
writeformatLabel(qb422016, labels)
|
||||
//line lib/promscrape/targetstatus.qtpl:176
|
||||
//line lib/promscrape/targetstatus.qtpl:269
|
||||
qs422016 := string(qb422016.B)
|
||||
//line lib/promscrape/targetstatus.qtpl:176
|
||||
//line lib/promscrape/targetstatus.qtpl:269
|
||||
qt422016.ReleaseByteBuffer(qb422016)
|
||||
//line lib/promscrape/targetstatus.qtpl:176
|
||||
//line lib/promscrape/targetstatus.qtpl:269
|
||||
return qs422016
|
||||
//line lib/promscrape/targetstatus.qtpl:176
|
||||
//line lib/promscrape/targetstatus.qtpl:269
|
||||
}
|
||||
|
||||
//line lib/promscrape/targetstatus.qtpl:271
|
||||
func streamerrorNotification(qw422016 *qt422016.Writer, err error) {
|
||||
//line lib/promscrape/targetstatus.qtpl:271
|
||||
qw422016.N().S(`<div class="alert alert-danger d-flex align-items-center" role="alert"><svg class="bi flex-shrink-0 me-2" width="24" height="24" role="img" aria-label="Danger:"><use xlink:href="#exclamation-triangle-fill"/></svg><div>`)
|
||||
//line lib/promscrape/targetstatus.qtpl:276
|
||||
qw422016.E().S(err.Error())
|
||||
//line lib/promscrape/targetstatus.qtpl:276
|
||||
qw422016.N().S(`</div></div>`)
|
||||
//line lib/promscrape/targetstatus.qtpl:279
|
||||
}
|
||||
|
||||
//line lib/promscrape/targetstatus.qtpl:279
|
||||
func writeerrorNotification(qq422016 qtio422016.Writer, err error) {
|
||||
//line lib/promscrape/targetstatus.qtpl:279
|
||||
qw422016 := qt422016.AcquireWriter(qq422016)
|
||||
//line lib/promscrape/targetstatus.qtpl:279
|
||||
streamerrorNotification(qw422016, err)
|
||||
//line lib/promscrape/targetstatus.qtpl:279
|
||||
qt422016.ReleaseWriter(qw422016)
|
||||
//line lib/promscrape/targetstatus.qtpl:279
|
||||
}
|
||||
|
||||
//line lib/promscrape/targetstatus.qtpl:279
|
||||
func errorNotification(err error) string {
|
||||
//line lib/promscrape/targetstatus.qtpl:279
|
||||
qb422016 := qt422016.AcquireByteBuffer()
|
||||
//line lib/promscrape/targetstatus.qtpl:279
|
||||
writeerrorNotification(qb422016, err)
|
||||
//line lib/promscrape/targetstatus.qtpl:279
|
||||
qs422016 := string(qb422016.B)
|
||||
//line lib/promscrape/targetstatus.qtpl:279
|
||||
qt422016.ReleaseByteBuffer(qb422016)
|
||||
//line lib/promscrape/targetstatus.qtpl:279
|
||||
return qs422016
|
||||
//line lib/promscrape/targetstatus.qtpl:279
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue