Secure Docker Postgres

Purpose

The purpose of this post is to learn how to secure a PostgreSQL Docker installation against unauthorized access following steps:

1. Check OS firewall

(On debian-based Linux distros) Check ufw is installed, enabled and denies 5432 input connections:

$ sudo ufw enable

$ sudo ufw status
> Status: active

$ sudo ufw deny 5432/tcp
$ sudo ufw status
> 5432/tcp                   DENY        Anywhere
> 5432/tcp (v6)              DENY        Anywhere (v6)

If PostreSQL needs to be accessed from another server we can allow only a specific [EXTERNAL_IP] address:

sudo ufw allow from [EXTERNAL_IP] to any port 5432
$ sudo ufw deny 5432/tcp
$ sudo ufw status
Status: active

To                         Action      From
--                         ------      ----
5432/tcp                   DENY        Anywhere
5432                       ALLOW       [EXTERNAL_IP]
5432/tcp (v6)              DENY        Anywhere (v6)

As an alternative of ufw, selinux or other OS firewalls you can also use iptables rules directly to achieve the same result:

# Listing current iptables rules
$ iptables -S

# Block input connections to 5432
$ iptables -A INPUT -p tcp --destination-port 5432 -j DROP

# Searching previous rule is updated
$ iptables -S  | grep 5432
> -A INPUT -p tcp -m tcp --dport 5432 -j DROP

2. Check port is not published to the host machine

Display Postgres running container:

$ docker ps | grep [POSTGRES_CONTAINER_NAME]

Check Docker Postgres port is not published to the host (0.0.0.0) like 0.0.0.0:5432->5432/tcp. Otherwise rerun container without publishing ports at all.

3. Check pg_hba.conf configuration

Postgres accessed internally

If Postgres has to be accessed by other containers on the same network (or on the same cluster) you should create an internal Postgres user with password and just add the following command at the end of the pg_hba.conf file.

host [INTERNAL_USER] all samenet md5

PostgreSQL accessed externally

If we need to enable a PostgreSQL remote connection, we can restrict which external IP address has the right to access it with an external user with password. Finally, at the following line at the end of the pg_hba.conf file:

host [EXTERNAL_USER] all [EXTERNAL_IP] md5

In previous cases, make sure that doesn’t exist a line like host all all all trust or host all all 0.0.0.0/0 trust opening Postgres for everybody.



Recommended books to expand your PostgreSQL knowledge:

Finally, you should definitely take a look at these books to fuel your Docker knowledge: