# HashiCorp Vault Failing to Bind Port 8200 in Docker Compose — Port Appears Free on Host

**URL:** <https://discuss.hashicorp.com/t/hashicorp-vault-failing-to-bind-port-8200-in-docker-compose-port-appears-free-on-host/77476>\
**Category:** Vault\
**Tags:** hashiconf, ports, vault, consul-vault, consul-api-gateway\
**Created:** [June 7, 2026, 9:29am UTC](https://discuss.hashicorp.com/t/hashicorp-vault-failing-to-bind-port-8200-in-docker-compose-port-appears-free-on-host/77476 "2026-06-07T09:29:51Z")\
**Posts on this page:** 2\
**Page:** 1

<div class="post-metadata">

**Author:** ![Katt](https://sea2.discourse-cdn.com/hashicorp/user_avatar/discuss.hashicorp.com/katt/32/47419_2.png) [@Katt](https://discuss.hashicorp.com/u/Katt)\
**Post date:** [June 7, 2026, 9:29am UTC](https://discuss.hashicorp.com/t/hashicorp-vault-failing-to-bind-port-8200-in-docker-compose-port-appears-free-on-host/77476/1 "2026-06-07T09:29:51Z")

</div>

## Environment

- **Docker:** 29.5.2
- **Docker Compose:** v5.1.4
- **OS:** Ubuntu 26.04 LTS (ARM64)
- **Kernel:** 7.0.0-15-generic
- **Vault Image:** hashicorp/vault:1.15.0

## The Problem

My Vault container starts but immediately exits with the following error:

```auto
Error initializing listener of type tcp: listen tcp4 0.0.0.0:8200: bind: address already in use

```

The puzzling part: **nothing is actually using port 8200 on the host**. I’ve verified this with:

```bash
sudo lsof -i :8200 # No output
sudo ss -tlnp | grep 8200 # No output
sudo netstat -tulpn | grep 8200 # No output

```

Yet Docker insists the port is occupied. This has persisted even after:

- Stopping all containers
- Restarting the Docker daemon
- Clearing Docker networks and volumes
- Changing to different ports (8201, 8202, etc.)
- Removing orphaned containers
- Restarting the entire system

## What I’ve Tried

### 1. Basic Cleanup

```bash
docker container prune -f
docker network prune -f
sudo systemctl restart docker
docker system prune -a --volumes -f

```

### 2. Configuration Validation

**vault.hcl**

```hcl
storage "file" {
  path = "/vault/data"
}

listener "tcp" {
  address = "0.0.0.0:8200"
  tls_disable = true
  tls_min_version = "tls12"
}

api_addr = "http://vault:8200"
cluster_addr = "http://vault:8201"

ui = true
disable_mlock = true

```

**Docker Compose Service**

```yaml
services:
  vault:
    image: hashicorp/vault:1.15.0
    cap_add:
      - IPC_LOCK
    ports:
      - "8200:8200"
      - "8201:8201"
    environment:
      VAULT_ADDR: "http://127.0.0.1:8200"
      VAULT_API_ADDR: "http://127.0.0.1:8200"
    volumes:
      - ./vault-data:/vault/data
      - ./vault-config:/vault/config
      - ./vault-logs:/vault/logs
    command:
      - server
      - "-config=/vault/config/vault.hcl"
    healthcheck:
      test: ["CMD", "vault", "operator", "status"]
      interval: 10s
      timeout: 10s
      retries: 5
      start_period: 30s
    networks:
      - girl-network

```

### 3. Port Diagnostics

```bash
# Check for any process binding 8200
sudo lsof -i TCP:8200
sudo ss -ltnp '( sport = :8200 )'
sudo netstat -tlnp | grep :8200

# Force kill any process on 8200
sudo fuser -k 8200/tcp

# Flush ARP cache
sudo ip neigh flush all

```

All commands return empty or show nothing using the port.

### 4. YAML Command Structure

I changed from:

```yaml
command: server -config=/vault/config/vault.hcl

```

To:

```yaml
command:
  - server
  - "-config=/vault/config/vault.hcl"

```

The YAML string format passes the entire command as a single argument `$1`, which causes Vault’s entrypoint script to not recognize it as the `server` subcommand. The list format correctly splits the arguments.

## The Actual Error in Logs

```auto
Error parsing listener configuration.
Error initializing listener of type tcp: listen tcp4 0.0.0.0:8200: bind: address already in use
2026-06-07T04:59:30.994Z [INFO] proxy environment: http_proxy="" https_proxy="" no_proxy=""

```

The `Error parsing listener configuration` appears **before** the bind error, suggesting something is wrong with how the listener is being read even before it attempts to bind.

## What I’ve Learned

1. **Port binding error occurs inside the container** , not on the host. Docker’s internal port allocation table can be out of sync with the OS network namespace.

2. **The IPC\_LOCK capability** was a red herring. Adding `cap_add: - IPC_LOCK` fixed the IPC\_LOCK warning but didn’t resolve the binding error.

3. **The vault.hcl syntax validation passed** , with `cat -A` confirming no trailing whitespace or hidden characters after fixing with:

4. **Docker maintains its own port allocation state** that persists even after containers stop and networks are pruned. The `docker.sock` itself can hold allocations.

## Where I’m Stuck Now

The container still exits immediately on startup despite:

- Port 8200 appearing completely free on the host
- No process actually listening on that port
- All cleanup commands showing nothing
- Config files appearing valid
- Command structure properly formatted as a list

The error message says the port is in use, but **all system level tools confirm it’s free**. This points to either:

1. Docker’s network driver caching old allocations
2. A zombie container holding the namespace
3. An issue with how Vault is reading the config inside the container

## My Goal

I’m trying to run HashiCorp Vault for secrets management to store API credentials (Twitch tokens, database credentials, etc.) for an Airflow based analytics pipeline. Once Vault is running, I need to execute an initialization script to set up policies and store secrets.

Any insight on why Docker would report a port as “already in use” when the entire system shows it’s free would be greatly appreciated. This has been driving me in circles for days.

_Thanks in advance for any help. I’m happy to provide additional logs, configs, or debugging output._

---

<div class="post-metadata">

**Author:** ![jonathanfrappier](https://sea2.discourse-cdn.com/hashicorp/user_avatar/discuss.hashicorp.com/jonathanfrappier/32/28004_2.png) [@jonathanfrappier](https://discuss.hashicorp.com/u/jonathanfrappier)\
**Post date:** [June 11, 2026, 8:35pm UTC](https://discuss.hashicorp.com/t/hashicorp-vault-failing-to-bind-port-8200-in-docker-compose-port-appears-free-on-host/77476/2 "2026-06-11T20:35:16Z")

</div>

Noticed you said you’re using 1.15. Do you get the same problem if you use a newer/supported version like 1.21?

What if you just run Vault via `docker run` and not from compose file?

```auto
   $ docker run \
         --name=learn-vault \
         --hostname=learn-vault \\
         --publish 8200:8200 \
         --env VAULT_ADDR="http://localhost:8200" \
         --env VAULT_CLUSTER_ADDR="http://learn-vault:8201" \
         --env VAULT_API_ADDR="http://learn-vault:8200" \
         --cap-add=IPC_LOCK \
         --detach \
         --rm \
         hashicorp/vault:1.21 vault server -dev -dev-listen-address 0.0.0.0:8200 -dev-root-token-id root

```

Can’t say i’ve run into this before but can try to replicate based on whether a newer version works and/or just docker run works.
