Nginx Docker-Compose root-less read-only

You can run Nginx as a non-root user inside of Docker

The era of website defacement is long gone, but it’s worth mentioning that read-only config and mounts are also viable.

 

Docker-Compose file and quick documentation

version: '3' services: nginx: image: nginx:stable-alpine user: '1042:1042' volumes: - ./html/www:/var/www/html/www/:ro - ./conf:/etc/nginx/conf.d:ro - ./nginx.conf:/etc/nginx/nginx.conf:ro ports: - "0.0.0.0:6666:80" networks: - default command: ["nginx", "-g", "daemon off;"] networks: default: driver: bridge

 

https://hub.docker.com/_/nginx

 

  • This starts a stable Nginx docker (Alpine)

  • user is not root, but 1042, same for the group (ID)

  • volumes get mapped as read-only

    • web root

    • config

  • listener is on 6666

 

Relevant parts on nginx.conf

 

# user www; #error_log logs/error.log; #error_log logs/error.log notice; #error_log logs/error.log info; #error_log syslog:server=unix:/dev/log,severity=notice; pid /tmp/nginx.pid; worker_rlimit_nofile 1024; ...
  • No user definition here in the .conf

  • Error logging not via Syslog or file

  • pid to tmp

http { include mime.types; default_type application/octet-stream; client_max_body_size 100M; #log_format main '$remote_addr - $remote_user [$time_local] "$request" ' # '$status $body_bytes_sent "$http_referer" ' # '"$http_user_agent" "$http_x_forwarded_for"'; #access_log logs/access.log main; #access_log syslog:server=unix:/dev/log,severity=notice main; tcp_nopush on; # keepalive_timeout 0; # keepalive_timeout 65; gzip on; server_tokens off; # include "/usr/local/share/nginx/naxsi_core.rules"; client_body_temp_path /tmp/client_temp; proxy_temp_path /tmp/proxy_temp_path; fastcgi_temp_path /tmp/fastcgi_temp; uwsgi_temp_path /tmp/uwsgi_temp; scgi_temp_path /tmp/scgi_temp;
  • mostly a standard config

  • several paths go to /tmp/

 

  • again: different error logging needed

  • root is defined: the read-only mount

Â