Safely inspect and maintain Docker Swarm nodes
You will use docker node to identify Swarm nodes, inspect their state, temporarily stop one receiving service tasks, and make a controlled membership change. Allow about 15 minutes for inspection and a maintenance drain. Removing a node or changing a manager role needs a maintenance plan and a recovery path.
The route
Jump straight to the step you need, or tick off Done means at the end.
This guide uses Docker CE CLI 29.8.1, installed here as package docker-ce-cli version 5:29.8.1-1~ubuntu.24.04~noble. The local docker-node(1) page is the umbrella entry for the command; its subcommand help provides the installed option set. Run these commands from a Swarm manager. Most Docker commands use the current Docker context, so confirm that context before you affect a real cluster.
1. Confirm the target context and command set
Start with read-only checks. Do not add sudo automatically: use it only if your local Docker socket policy requires elevated access, and understand that it changes which Docker configuration and context may be used.
$ docker version --format '{{.Client.Version}}'
29.8.1
$ docker node --help
Usage: docker node COMMAND
Manage Swarm nodes
The available subcommands are ls, inspect, ps, update, promote, demote and rm. If Docker reports that the node is not a manager, stop here. A worker can run workloads, but node administration is a manager operation.
Checkpoint
You have confirmed the Docker context and are connected to the intended manager. If you use named contexts, run docker context show and record the result before continuing.
2. List nodes and filter the view
List the nodes the manager knows about. The command prints a table containing the node ID, hostname, readiness, availability and manager status.
$ docker node ls
ID HOSTNAME STATUS AVAILABILITY MANAGER STATUS
MANAGER-ID * manager-1 Ready Active Leader
WORKER-ID worker-1 Ready Active
$ docker node ls --filter role=worker
$ docker node ls --quiet
MANAGER-ID
WORKER-ID
The asterisk identifies the node used by the current Docker daemon. It does not mean that the node is the leader. The supported filters include id, label, node.label, membership, name and role. Quote a filter containing shell punctuation, such as --filter "role=manager".
For scripts, request JSON records or a small template rather than parsing aligned columns:
$ docker node ls --format json
{"Availability":"Active","EngineVersion":"ENGINE-VERSION","Hostname":"HOSTNAME","ID":"NODE-ID","ManagerStatus":"Leader","Self":true,"Status":"Ready","TLSStatus":"Ready"}
3. Inspect one node before changing it
Use inspect when the summary is not enough. The default result is a JSON array, which is useful for retaining the exact state before maintenance. The --pretty option gives a human-readable view instead.
$ docker node inspect --pretty NODE-NAME-OR-ID
ID: NODE-ID
Hostname: HOSTNAME
Status:
State: Ready
Availability: Active
Manager Status: Reachable
Exact fields and manager status vary with the node, so treat the values above as a shape, not a promised transcript. Save a read-only record when you need an audit trail:
$ docker node inspect NODE-NAME-OR-ID > node-before.json
Do not publish that file casually. Node inspection can expose infrastructure details. Keep it in a suitably protected directory and remove it according to your organisation's retention rules when it is no longer needed.
4. See the tasks before planned maintenance
Before draining a node, find the Swarm tasks assigned to it:
$ docker node ps NODE-NAME-OR-ID
ID NAME IMAGE NODE DESIRED STATE CURRENT STATE
TASK-ID SERVICE.1 IMAGE HOSTNAME Running Running
$ docker node ps NODE-NAME-OR-ID --no-trunc
docker node ps defaults to the current node if you omit the node argument. That default is a common distraction trap: an apparently empty result may describe the manager you are connected to, not the worker you meant to maintain. Use the explicit node name or ID in operational notes and scripts.
5. Drain a node for maintenance
Warning
Draining changes scheduling and can stop running Swarm service tasks on that node. The manager attempts to replace them on available nodes. Check capacity, replicas and any placement constraints first. Standalone containers created with docker run or Compose are not moved by this setting.
Change the node's availability from active to drain:
$ docker node update --availability drain NODE-NAME-OR-ID
NODE-NAME-OR-ID
Verify the change and watch service placement:
$ docker node inspect --pretty NODE-NAME-OR-ID
Availability: Drain
$ docker node ps NODE-NAME-OR-ID
$ docker service ps SERVICE-NAME
When maintenance is complete, restore scheduling explicitly:
$ docker node update --availability active NODE-NAME-OR-ID
NODE-NAME-OR-ID
Checkpoint
The node is Drain while it is being serviced, and returns to Active only after you have checked the host. Drain is reversible, but it is not a harmless label: service tasks may be recreated elsewhere.
6. Add labels or change a role carefully
Node labels are Swarm metadata used by service placement constraints. They are not the same as Docker daemon labels:
$ docker node update --label-add type=queue NODE-NAME-OR-ID
$ docker node inspect NODE-NAME-OR-ID --pretty
Remove a label only when you have checked that no service constraint depends on it:
$ docker node update --label-rm type NODE-NAME-OR-ID
Warning
Promotion and demotion alter the control plane, not just workload placement. A worker can be promoted with docker node promote; a manager can be demoted with docker node demote. Keep manager quorum in mind, and do not demote the last viable manager as a routine maintenance step.
7. Remove a node only after membership is settled
Removal is a membership change, not a way to tidy a display. First inspect the node and confirm that it is down or that you have deliberately accepted the consequences of force removal.
$ docker node inspect --pretty NODE-NAME-OR-ID
$ docker node rm NODE-NAME-OR-ID
Normal removal is intended for a stopped or down node. If an inaccessible worker must be removed, --force exists, but it can interrupt tasks and should be treated as an incident action:
$ docker node rm --force UNREACHABLE-WORKER-ID
A manager must be demoted before removal. There is no undo command that restores the old node membership and workload state automatically. To recover, rebuild or rejoin the machine using your swarm's join procedure, then verify it with docker node ls.
Done means
- You confirmed the Docker context, CLI version and manager connection.
- You used
docker node ls,inspectand, where relevant,psto identify the real target. - Maintenance nodes are
Drain, service tasks have been checked, and completed nodes are restored toActive. - Labels, promotions and demotions were checked against placement and manager-quorum needs.
- Removal was reserved for a settled node, with a rejoin plan recorded before any force action.