# Docker Permission Denied: Complete Troubleshooting Guide

Permission denied errors in Docker can occur at multiple levels—the Docker daemon socket, volume mounts, container processes, and file operations. Each requires a different fix. The error message "permission denied" doesn't tell you which layer is blocking access, so systematic diagnosis is essential.

Common error messages:

bash
docker: Got permission denied while trying to connect to the Docker daemon socket at unix:///var/run/docker.sock
bash
Error: permission denied while trying to connect to the Docker daemon socket
bash
mkdir: cannot create directory '/data': Permission denied

Level 1: Docker Daemon Socket Permission

The Problem

Your user doesn't have permission to access the Docker socket, typically at /var/run/docker.sock.

Symptoms: `` docker: Got permission denied while trying to connect to the Docker daemon socket

Diagnosis: ```bash # Check socket permissions ls -la /var/run/docker.sock # Output: srw-rw---- 1 root docker 0 Apr 1 10:00 /var/run/docker.sock

# Check your groups groups # Output: user adm cdrom sudo dip plugdev

# Check if you're in docker group groups | grep docker ```

Fix 1: Add User to Docker Group (Recommended)

```bash # Add your user to the docker group sudo usermod -aG docker $USER

# Log out and log back in for changes to take effect # Or run: newgrp docker

# Verify docker ps ```

Security Note: Adding a user to the docker group grants root-equivalent privileges. Only add trusted users.

Fix 2: Use sudo (Temporary)

```bash # Run docker commands with sudo sudo docker ps

# Or add alias echo 'alias docker="sudo docker"' >> ~/.bashrc source ~/.bashrc ```

Fix 3: Change Socket Permissions (Not Recommended)

bash
# This is a security risk - anyone can access Docker
sudo chmod 666 /var/run/docker.sock

Fix 4: Start Docker Service

If the socket doesn't exist:

```bash # Check if Docker is running sudo systemctl status docker

# Start Docker sudo systemctl start docker

# Enable at boot sudo systemctl enable docker ```

Level 2: Volume Mount Permission Denied

The Problem

Container processes can't read or write to mounted volumes.

Symptoms: `` mkdir: cannot create directory '/data': Permission denied

bash
touch: cannot touch '/data/file.txt': Permission denied

Diagnosis: ```bash # Check host directory permissions ls -la /host/path/to/mount

# Check container user docker run --rm <image> whoami

# Check container user ID docker run --rm <image> id ```

Fix 1: Adjust Host Permissions

```bash # Make directory writable by everyone (quick fix, not secure) chmod 777 /host/path/to/mount

# Better: Change ownership to container user ID chown -R 1000:1000 /host/path/to/mount ```

Fix 2: Run Container as Root

bash
# Temporary fix
docker run --user root -v /host/path:/container/path <image>

In Docker Compose: ``yaml services: myapp: image: myimage:latest user: root volumes: - /host/path:/container/path

Fix 3: Fix Dockerfile User

If your Dockerfile sets a non-root user but doesn't handle permissions:

```dockerfile FROM alpine:3.18

# Create directory with proper permissions before switching user RUN mkdir -p /data && chown -R appuser:appuser /data

USER appuser

VOLUME /data ```

Fix 4: Use Named Volumes

Named volumes are managed by Docker and handle permissions automatically:

bash
docker run -v mydata:/data <image>

Fix 5: SELinux Context (RHEL/CentOS/Fedora)

On SELinux-enabled systems:

```bash # Check SELinux status getenforce

# Use :z flag for shared volumes docker run -v /host/path:/container/path:z <image>

# Use :Z flag for private volumes docker run -v /host/path:/container/path:Z <image> ```

In Docker Compose: ``yaml services: myapp: image: myimage:latest volumes: - /host/path:/container/path:z

Level 3: Container Process Permission

The Problem

The process running inside the container lacks permissions.

Symptoms: `` Permission denied

bash
bash: /app/script.sh: Permission denied

Diagnosis: ```bash # Check file permissions inside container docker exec <container> ls -la /app/script.sh

# Check if file is executable docker exec <container> test -x /app/script.sh && echo "executable" || echo "not executable" ```

Fix 1: Make Scripts Executable

In Dockerfile: ``dockerfile COPY script.sh /app/script.sh RUN chmod +x /app/script.sh

Or at runtime: ``bash docker exec <container> chmod +x /app/script.sh

Fix 2: Fix COPY Permissions

Files copied with COPY inherit permissions:

```dockerfile # Copy with executable permission COPY --chmod=755 script.sh /app/script.sh

# Or copy and chmod COPY script.sh /app/ RUN chmod +x /app/script.sh ```

Fix 3: Use Entrypoint Script

dockerfile
COPY entrypoint.sh /entrypoint.sh
RUN chmod +x /entrypoint.sh
ENTRYPOINT ["/entrypoint.sh"]

Level 4: Permission Issues in Mounted Files

The Problem

Host files have different UID/GID than container expects.

Symptoms: - Configuration files can't be read - Can't write to mounted files - "Permission denied" on specific files

Diagnosis: ```bash # Check host file ownership ls -la /host/config/file.conf

# Check container user ID docker run --rm <image> id

# Enter container and check docker exec -it <container> sh ls -la /mount/path ```

Fix 1: Match UID/GID

Find the container user's UID:

bash
docker run --rm <image> cat /etc/passwd | grep appuser

Then set host ownership:

bash
sudo chown -R 1000:1000 /host/path

Fix 2: Use User Namespace Mapping

Enable user namespaces in /etc/docker/daemon.json:

json
{
  "userns-remap": "default"
}

Then restart Docker:

bash
sudo systemctl restart docker

Fix 3: Pass UID/GID as Environment Variables

dockerfile
FROM alpine:3.18
ARG USER_ID=1000
ARG GROUP_ID=1000
RUN adduser -D -u ${USER_ID} appuser
USER appuser

Build and run:

bash
docker build --build-arg USER_ID=$(id -u) --build-arg GROUP_ID=$(id -g) -t myapp .

Level 5: Network Permission Issues

The Problem

Container can't bind to privileged ports (< 1024).

Symptoms: `` Error: Permission denied (bind failed)

Fix 1: Use Higher Ports

yaml
services:
  web:
    image: nginx
    ports:
      - "8080:80"  # Map to unprivileged port on host

Fix 2: Allow Unprivileged Ports

Allow binding to privileged ports:

bash
sudo setcap 'cap_net_bind_service=+ep' /usr/bin/docker-proxy

Or enable in kernel:

bash
sudo sysctl net.ipv4.ip_unprivileged_port_start=80

Quick Reference

ErrorCauseFix
Cannot connect to Docker daemonNot in docker groupusermod -aG docker $USER
mkdir: Permission deniedVolume mount permissionschown -R 1000:1000 /path
touch: Permission deniedRead-only mountRemove :ro flag
bash: ./script.sh: Permission deniedScript not executablechmod +x script.sh
Permission denied on port 80Privileged portUse port > 1024
Permission denied (SELinux)SELinux contextAdd :z or :Z flag

Verification Steps

  1. 1.Test Docker daemon access:
  2. 2.```bash
  3. 3.docker ps
  4. 4.docker run --rm hello-world
  5. 5.`
  6. 6.Test volume write:
  7. 7.```bash
  8. 8.docker run --rm -v /host/path:/data alpine sh -c "echo test > /data/test.txt && cat /data/test.txt"
  9. 9.`
  10. 10.Test as correct user:
  11. 11.```bash
  12. 12.docker exec <container> whoami
  13. 13.docker exec <container> id
  14. 14.`
  15. 15.Test file execution:
  16. 16.```bash
  17. 17.docker exec <container> /app/script.sh
  18. 18.`

Permission issues in Docker are usually straightforward once you identify which layer is blocking access. Start with the daemon socket, then work through volumes and container users systematically.