Running docker config inspect and getting a wall of base64 back is a good way to leak a secret into your scrollback. You will finish with a repeatable way to inspect one or more Swarm configs, pick out useful fields with a Go template, and recognise the error that means you are talking to a non-manager. The examples use Docker 29.8.1 and the locally installed docker-config-inspect(1) interface.
Allow about ten minutes. You need the Docker CLI, access to the intended Docker Engine, and a config name or ID. The command is read-only, but its default result can include the config payload as base64 text.
Warning: treat terminal output, saved output and shell history as sensitive if the config contains credentials, certificates or other private material. No example in this guide creates, updates or removes a config.
Start with read-only checks so you know which binary and option set you are using:
$ docker --version
Docker version 29.8.1, build 4a63305
$ docker config inspect --help
Usage: docker config inspect [OPTIONS] CONFIG [CONFIG...]
Display detailed information on one or more configs
The version string will differ on another machine. The syntax that matters is docker config inspect [OPTIONS] CONFIG [CONFIG...]. A config can be addressed by name or ID, and the trailing argument form accepts more than one target.
Checkpoint: confirm that you are using the Docker context and Engine you intended before inspecting a similarly named config. The inspect command follows the current Docker connection; it does not search every host in an estate.
docker config inspect is a Swarm cluster-management command. It must run against a Swarm manager. Adding sudo to an ordinary client connected to the wrong Engine will not fix that.
Run the command with the exact name or ID you were given:
$ docker config inspect CONFIG_NAME
Error response from daemon: This node is not a Swarm manager. Use "docker swarm init" or "docker swarm join" to connect to a Swarm cluster.
That wording is the result from this machine when the daemon is not a manager. Docker may instead report that the target does not exist, or return an authentication or connection error. Read the first failure literally: establish the correct Engine and manager connection before changing the target name.
Warning: do not run docker swarm init as a diagnostic shortcut. Initialising a standalone Engine changes its role and can affect how workloads are operated. Joining a cluster also changes node membership and needs an operator-approved maintenance procedure. Stop here if you do not already have the correct manager context.
On the correct manager, the default output is a JSON array, even when you inspect one config:
$ docker config inspect CONFIG_NAME
[
{
"ID": "CONFIG_ID",
"Version": { "Index": 17 },
"CreatedAt": "TIMESTAMP",
"UpdatedAt": "TIMESTAMP",
"Spec": {
"Name": "CONFIG_NAME",
"Labels": { "environment": "staging" },
"Data": "BASE64_PAYLOAD"
}
}
]
The IDs, timestamps, labels and payload show the shape of the response, not values to copy. Spec.Data is encoded for transport and display, and base64 is not encryption. Avoid pasting the full response into an issue, chat message or shell transcript. If you need an audit record, protect it with the same controls as the original secret.
Checkpoint: if you only need identity, labels or timestamps, stop using the full response and switch to a field-specific template in the next step.
The --format option executes a Go template for each result. This keeps routine checks away from the payload:
$ docker config inspect --format='{{.ID}} {{.Spec.Name}} {{.CreatedAt}} {{.UpdatedAt}}' CONFIG_NAME
CONFIG_ID CONFIG_NAME CREATED_TIMESTAMP UPDATED_TIMESTAMP
Use the actual field paths shown by the inspect result. Labels are a map, so select a known label key only when you know its spelling:
$ docker config inspect --format='{{.Spec.Labels.environment}}' CONFIG_NAME
staging
These outputs are illustrative. A missing label can produce an empty value, and the Docker Engine supplies the timestamp format. Keep the command quoted so the shell passes the braces to Docker rather than trying to interpret them.
For machine-readable processing, the manpage also documents the special json format:
$ docker config inspect --format=json CONFIG_NAME
[{"ID":"CONFIG_ID","Spec":{"Name":"CONFIG_NAME"}}]
Do not assume the compact example contains every field. The point of this mode is valid JSON output; the returned object still represents the config and may contain sensitive data. Pipe it only to a tool and destination approved for that data.
Pass multiple names or IDs after the options. A template is executed for each result, so add a stable identifier to every line:
$ docker config inspect --format='{{.Spec.Name}} {{.Spec.Labels.environment}} {{.UpdatedAt}}' CONFIG_A CONFIG_B
CONFIG_A staging UPDATED_TIMESTAMP_A
CONFIG_B production UPDATED_TIMESTAMP_B
A blank label does not mean the configs are identical. It can mean the key is absent. Compare the names, update times and labels you actually care about, then inspect the full record for one selected config only if a change investigation requires it.
If one target is misspelled or unavailable, the command fails rather than silently proving that the configs match. Keep the target list short enough that you can spot the failing name, and rerun each candidate separately when the error does not identify it clearly.
The --pretty option requests human-friendly information:
$ docker config inspect --pretty CONFIG_NAME
CONFIG_NAME
ID: CONFIG_ID
Created at: CREATED_TIMESTAMP
Updated at: UPDATED_TIMESTAMP
Exact spacing and the fields shown can vary with the Docker CLI and Engine version. Use this mode for a person reading the result, not for a script. For automation, prefer --format or --format=json and validate the data before acting on it.
Recovery: nothing in the commands above changes Docker state, so there is no undo command. Stop using the wrong context or target and rerun the read-only inspection against the approved manager.
--pretty is for people; formatted JSON or templates are for controlled automation.