Skip to content

bootstrap: allow exporters to add routes - #430

Merged
ArthurSens merged 6 commits into
prometheus:masterfrom
nicolastakashi:bootstrap-extra-routes
Aug 25, 2026
Merged

bootstrap: allow exporters to add routes#430
ArthurSens merged 6 commits into
prometheus:masterfrom
nicolastakashi:bootstrap-extra-routes

Conversation

@nicolastakashi

@nicolastakashi nicolastakashi commented Aug 18, 2026

Copy link
Copy Markdown
Contributor

Problem

bootstrap builds the exporter's HTTP mux itself: Run() registers the metrics handler at --web.telemetry-path and the landing page at /, and nothing else can be added to it.

That is enough for node_exporter, but it blocks exporters that serve more than those two endpoints. postgres_exporter is the immediate case:

  • it serves the multi-target /probe endpoint, which is the documented way to scrape remote instances via auth_modules
  • it exposes the net/http/pprof handlers

Adopting bootstrap as it stands would silently 404 both, so the exporter cannot move onto the shared startup path without a user-visible regression. Any exporter with a second endpoint hits the same wall, which pushes them back to hand-rolled main() blocks — the duplication bootstrap exists to remove.

A second constraint is when those handlers can be built. postgres_exporter's probe handler needs the logger and the loaded config file, neither of which exists until flags are parsed, so a static list of routes on Config is not sufficient.

Follow-up

Consumed by prometheus-community/postgres_exporter#1368, which moves postgres_exporter onto bootstrap while keeping /probe and pprof working. That PR needs a release of this one before it builds.

Note: an earlier revision of this PR also let exporters back --web.telemetry-path with a custom env var, to preserve postgres_exporter's PG_EXPORTER_WEB_TELEMETRY_PATH. Per @ArthurSens's review, that's dropped — new env-var-backed flags shouldn't be added, existing ones should be deprecated/removed instead. The follow-up postgres_exporter PR will need to handle that separately.

The bootstrap package builds its own mux, so an exporter that serves more
than /metrics and the landing page cannot adopt it. postgres_exporter, for
example, serves the multi-target /probe endpoint and the net/http/pprof
handlers, and node_exporter-style adoption would silently drop both.

Give Bootstrap a Handle/HandleFunc pair. Routes registered from the metrics
handler factory are applied to the mux next to the metrics endpoint, which
keeps them constructible from state that only exists after flags are
parsed, such as the logger and the loaded config.

Exporters that shipped --web.telemetry-path with an environment variable
also cannot keep that behavior once bootstrap owns the flag, so allow the
envar name to be configured.

Signed-off-by: Nicolas Takashi <nicolas.tcs@hotmail.com>
@nicolastakashi
nicolastakashi force-pushed the bootstrap-extra-routes branch from e9cdc36 to 1518a47 Compare August 18, 2026 20:00
@nicolastakashi
nicolastakashi marked this pull request as ready for review August 18, 2026 20:01

@ArthurSens ArthurSens left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think we want to continue using env vars in exporters. It would be better to deprecate and remove this functionality from existing exporters rather than continue building on top of it

nicolastakashi added a commit to nicolastakashi/exporter-toolkit that referenced this pull request Aug 21, 2026
Per review feedback on prometheus#430, exporters should not
gain new env-var-backed flags; existing env var support should be deprecated
and removed rather than extended.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01QwjFhjwbakiAgUbfnmfJLc
@nicolastakashi nicolastakashi changed the title bootstrap: allow exporters to add routes and a metrics path envar bootstrap: allow exporters to add routes Aug 21, 2026
@nicolastakashi

Copy link
Copy Markdown
Contributor Author

I don't think we want to continue using env vars in exporters. It would be better to deprecate and remove this functionality from existing exporters rather than continue building on top of it

Remove the env var support in here.

nicolastakashi added a commit to nicolastakashi/exporter-toolkit that referenced this pull request Aug 21, 2026
Per review feedback on prometheus#430, exporters should not
gain new env-var-backed flags; existing env var support should be deprecated
and removed rather than extended.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01QwjFhjwbakiAgUbfnmfJLc
Signed-off-by: Nicolas Takashi <nicolas.tcs@hotmail.com>
@nicolastakashi
nicolastakashi force-pushed the bootstrap-extra-routes branch from 8ed863e to 58bf611 Compare August 21, 2026 19:50

@ArthurSens ArthurSens left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What happens if someone adds a new route that conflicts with / or /metrics? Should we provide guardrails against that?

What ever we decide, it would also be nice to have a test that confirms the behavior we want

@ArthurSens

Copy link
Copy Markdown
Member

Could update your node/postgres PRs with a replace in go mod, just so we can see how these changes look like downstream before we merge?

@nicolastakashi

Copy link
Copy Markdown
Contributor Author

What happens if someone adds a new route that conflicts with / or /metrics? Should we provide guardrails against that?

What ever we decide, it would also be nice to have a test that confirms the behavior we want

Good suggestion, I'll take it.

Per review feedback on prometheus#430, exporters should not
gain new env-var-backed flags; existing env var support should be deprecated
and removed rather than extended.

Signed-off-by: Nicolas Takashi <nicolas.tcs@hotmail.com>
The metricsPathFlag helper only existed to branch on MetricsPathEnvar,
which was dropped in a3566c1. With no branching left, the extraction
added nothing.

Signed-off-by: Nicolas Takashi <nicolas.tcs@hotmail.com>
Handle/HandleFunc let callers register any pattern, including the metrics
path or root, which the mux would otherwise reject with a raw ServeMux
panic at startup. Validate against the protected set (--web.telemetry-path
and /) in newServer and return a normal error instead.

Signed-off-by: Nicolas Takashi <nicolas.tcs@hotmail.com>
@nicolastakashi
nicolastakashi force-pushed the bootstrap-extra-routes branch from aed14d2 to c5b079e Compare August 23, 2026 18:46
nicolastakashi added a commit to nicolastakashi/postgres_exporter that referenced this pull request Aug 23, 2026
…a-routes fork

Lets CI show how prometheus/exporter-toolkit#430 lands downstream before
that PR merges. Drop this replace once prometheus-community#430 ships in a tagged release.

Signed-off-by: Nicolas Takashi <nicolas.tcs@hotmail.com>
nicolastakashi added a commit to nicolastakashi/postgres_exporter that referenced this pull request Aug 23, 2026
exporter-toolkit's bootstrap.Config dropped MetricsPathEnvar (see
prometheus/exporter-toolkit#430) rather than grow env-var-backed flag
support further. Use --web.telemetry-path instead.

Signed-off-by: Nicolas Takashi <nicolas.tcs@hotmail.com>
@ArthurSens

ArthurSens commented Aug 24, 2026

Copy link
Copy Markdown
Member

Sorry for the back-and-forth here, but after thinking a bit more, it feels like we shouldn't reserve the bootstrap routes. I can imagine that tons of exporters already have something running at the / route, for example. Prometheus is one example, where the landing page redirects to /query.

Maybe we should allow overrides, and our test would focus on making sure the override takes precedence over the routes that bootstrap creates?

@ArthurSens

Copy link
Copy Markdown
Member

Hey @nicolastakashi, not sure if you requested my review by mistake, but my last comment is still unaddressed 😅

…erved

Per review on prometheus#430: reserving / blocks exporters
that already serve something there (Prometheus itself redirects / to
/query). A caller-registered route at / now takes precedence over the
generated landing page. The metrics path stays reserved, since silently
losing the scrape endpoint to a route collision is a much worse failure
mode than losing the landing page.

Signed-off-by: Nicolas Takashi <nicolas.tcs@hotmail.com>
nicolastakashi added a commit to nicolastakashi/postgres_exporter that referenced this pull request Aug 25, 2026
Picks up prometheus/exporter-toolkit#430's latest revision, which allows
overriding the root route while keeping the metrics path reserved.

Signed-off-by: Nicolas Takashi <nicolas.tcs@hotmail.com>
…outes

Signed-off-by: Nicolas Takashi <nicolas.tcs@hotmail.com>

# Conflicts:
#	bootstrap/bootstrap_test.go
@nicolastakashi

Copy link
Copy Markdown
Contributor Author

Sorry for the back-and-forth here, but after thinking a bit more, it feels like we shouldn't reserve the bootstrap routes. I can imagine that tons of exporters already have something running at the / route, for example. Prometheus is one example, where the landing page redirects to /query.

Maybe we should allow overrides, and our test would focus on making sure the override takes precedence over the routes that bootstrap creates?

/metrics stays reserved (errors on conflict), but a caller route at / now overrides the landing page.

@ArthurSens PTAL 🙏🏽

@ArthurSens ArthurSens left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM

@ArthurSens
ArthurSens merged commit 007f1cd into prometheus:master Aug 25, 2026
6 checks passed
nicolastakashi added a commit to nicolastakashi/postgres_exporter that referenced this pull request Aug 27, 2026
…a-routes fork

Lets CI show how prometheus/exporter-toolkit#430 lands downstream before
that PR merges. Drop this replace once prometheus-community#430 ships in a tagged release.

Signed-off-by: Nicolas Takashi <nicolas.tcs@hotmail.com>
nicolastakashi added a commit to nicolastakashi/postgres_exporter that referenced this pull request Aug 27, 2026
exporter-toolkit's bootstrap.Config dropped MetricsPathEnvar (see
prometheus/exporter-toolkit#430) rather than grow env-var-backed flag
support further. Use --web.telemetry-path instead.

Signed-off-by: Nicolas Takashi <nicolas.tcs@hotmail.com>
nicolastakashi added a commit to nicolastakashi/postgres_exporter that referenced this pull request Aug 27, 2026
Picks up prometheus/exporter-toolkit#430's latest revision, which allows
overriding the root route while keeping the metrics path reserved.

Signed-off-by: Nicolas Takashi <nicolas.tcs@hotmail.com>
nicolastakashi added a commit to nicolastakashi/postgres_exporter that referenced this pull request Aug 27, 2026
prometheus/exporter-toolkit#430 shipped in v0.19.0, so the temporary
replace directive pointing at the bootstrap-extra-routes fork is no
longer needed.

Signed-off-by: Nicolas Takashi <nicolas.tcs@hotmail.com>
nicolastakashi added a commit to nicolastakashi/postgres_exporter that referenced this pull request Aug 27, 2026
The entrypoint hand-rolls what exporter-toolkit/bootstrap now provides:
the web.telemetry-path / web.listen-address flags, promslog flag wiring,
version output, the landing page, and the ListenAndServe call. Keeping a
private copy is how exporters drift apart in flags and startup behavior.

Move exporter construction into a metrics handler factory, which runs
after flags are parsed, and register the multi-target /probe endpoint
and the net/http/pprof and expvar (/debug/) handlers as bootstrap
routes so they keep working on the mux bootstrap owns.

Two flags come with bootstrap and are wired to real behavior here:
--web.max-requests limits in-flight scrapes, and
--web.disable-exporter-metrics drops the Go and process collectors.

exporter-toolkit is bumped to v0.19.0, which ships the route-registration
support this depends on (prometheus/exporter-toolkit#430).
PG_EXPORTER_WEB_TELEMETRY_PATH keeps working, but bootstrap dropped
env-var support for --web.telemetry-path, so instead of relocating the
metrics endpoint the handler is additionally served at the env var's
path (with a deprecation warning) for a compatibility window.

Fatal startup errors are logged through the configured logger once one
exists, falling back to stderr only for pre-parse failures. --dumpmaps
and runtime shutdown are handled from main rather than exiting from
inside the bootstrap callback.

Signed-off-by: Nicolas Takashi <nicolas.tcs@hotmail.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants