skip to content

How do you change the Actuator base path and move endpoints onto a separate management port?

level: seniorimportance: should knowfreq 48%

answer

  1. default base path /actuator
  2. management.endpoints.web.base-path
  3. path-mapping.<id> per-endpoint
  4. management.server.port = separate connector
  5. management.server.address loopback; port=-1 disables

basics

~10 s

The default web base path is /actuator (e.g. /actuator/health). Change it with management.endpoints.web.base-path. Move Actuator to its own port with management.server.port (a different value from server.port).

solid answer

~40 s

By default Actuator web endpoints live under `/actuator`, so health is `/actuator/health`. You can rename the base path with `management.endpoints.web.base-path=/manage`, and remap an individual endpoint's sub-path with `management.endpoints.web.path-mapping.<id>` (e.g. map `health` to `/healthcheck`). To isolate management traffic from application traffic, set `management.server.port` to a port different from `server.port`; Actuator then binds its own connector (you can also restrict the bind address with `management.server.address=127.0.0.1` so it's only reachable internally). Setting `management.server.port=-1` disables the HTTP management server entirely. When on a separate port, the base path defaults to `/` unless overridden, and Actuator no longer inherits the main app's servlet context path. This separation is a common production hardening: expose more endpoints, but only on an internal port behind the LB.

code

java · 10 lines
java
// application.properties — production-style split
server.port=8080                                  // user-facing app
management.server.port=8081                        // Actuator on its own connector
management.server.address=127.0.0.1                // reachable only from the host/sidecar
management.endpoints.web.base-path=/manage         // /manage/... instead of /actuator/...
management.endpoints.web.path-mapping.health=healthcheck  // /manage/healthcheck
management.endpoints.web.exposure.include=health,info,metrics,prometheus

// Reachable: http://127.0.0.1:8081/manage/healthcheck
// NOT reachable from the public 8080 connector.

go deeper

for a junior

Knows the default /actuator prefix; may not know the port/base-path knobs.

for a middle

Can change base-path and expose extra endpoints, aware a separate port exists.

for a senior

Configures separate port + loopback bind as deliberate hardening and updates probes/scrapers accordingly.

for a principal

Bakes the management-port/network topology into platform standards and coordinates it with LB, security, and probe conventions.

## Default base path: `/actuator` Over the web, all exposed Actuator endpoints are grouped under a **base path**, default `/actuator`. So the health endpoint (ID `health`) is served at `GET /actuator/health`, metrics at `/actuator/metrics`, and so on. A discovery/index document is served at `/actuator` itself listing the exposed endpoints. ## Changing the base path ```properties management.endpoints.web.base-path=/manage # -> /manage/health, /manage/metrics ... ``` The base path is applied relative to the server's context path (or to `management.server.base-path` when a separate management port is used). ## Remapping individual endpoint paths `management.endpoints.web.path-mapping.<id>` changes the last path segment for one endpoint: ```properties management.endpoints.web.path-mapping.health=healthcheck # -> /actuator/healthcheck (others unchanged) ``` This is useful when an orchestrator (e.g. Kubernetes probes) expects a specific path. ## Separate management port By default Actuator shares the main application connector (`server.port`, e.g. 8080). Set a distinct port to isolate it: ```properties server.port=8080 management.server.port=8081 ``` Effects when a separate port is active: - Actuator gets its **own** HTTP connector on 8081. - The management server does **not** inherit the app's servlet context path; its base path defaults to `/` (so health is `http://host:8081/actuator/health`, or `/health` if you also set `management.endpoints.web.base-path=/`). You can set `management.server.base-path`. - `management.server.address=127.0.0.1` binds the connector only to loopback, so endpoints are reachable from the host/sidecar but not externally. - `management.server.port=-1` (or `management.server.port=0` for a random port) — `-1` disables the HTTP management server; `0` picks an ephemeral port. ## Why separate the port Production hardening pattern: keep the app port (8080) behind the load balancer for user traffic, and put Actuator on 8081 bound to an internal interface. You can then expose richer endpoints (metrics, prometheus, loggers) without exposing them to the internet, complementing Spring Security rules. ## Gotchas - Moving to a separate port **resets the base path context** — URLs change; update your probes/scrapers. - The management port needs its own security config if you rely on `WebSecurity`/`SecurityFilterChain` — an `EndpointRequest` matcher helps target Actuator. - `base-path` change affects the discovery index URL too (`/manage`). - Separate port + reactive/servlet mismatch can surprise; both stacks support it but config differs.

  • After setting a separate management port, why did `/actuator/health` stop working on the app port?
    With `management.server.port` set, Actuator binds its own connector and is no longer served on the application port — you must hit it on the management port, and its base path context resets.
  • How would you make Actuator reachable only from inside the host?
    Set `management.server.port` to a separate port and `management.server.address=127.0.0.1` so the connector binds to loopback only, invisible to external clients.

saying these in an interview costs you the question

  • Thinking Actuator is still on the app port after setting management.server.port
  • Assuming the separate management port inherits the app's context path / base path
  • Believing base-path controls which endpoints are exposed (it only controls the URL prefix)

context