Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
80 commits
Select commit Hold shift + click to select a range
f07ffcc
Added Dockerfile and docker-compose.yaml
RicardoJeronimo Oct 21, 2024
3b242b9
Added necessary packages to allow realtime processing with Celery
RicardoJeronimo Nov 28, 2024
fc9bdc6
Added entrypoint script to start Apache httpd and Celery worker simul…
RicardoJeronimo Nov 28, 2024
2bf1974
Added patchman-email installation
RicardoJeronimo Nov 28, 2024
66e2616
Added patchman-email dependencies
RicardoJeronimo Nov 28, 2024
613950e
Added Redis container for Celery realtime processing
RicardoJeronimo Nov 28, 2024
4ba672f
Adjusted build context
RicardoJeronimo Nov 28, 2024
565c5ee
Changed Dockerfile to install from source instead of repository
RicardoJeronimo Jan 21, 2025
0e56a1f
Fixed django-bootstrap3 installation and some file origins
RicardoJeronimo Jan 21, 2025
529b9b6
Entrypoint only starts Celery worker if an environment varible exists
RicardoJeronimo Jan 21, 2025
5efeccb
Changed entrypoint interpreter to Bash
RicardoJeronimo Jan 21, 2025
4c0e74e
Fixed httpd virtualhost location
RicardoJeronimo Jan 21, 2025
53b237f
Added httpd service reload
RicardoJeronimo Jan 21, 2025
0511255
Reverted change made in 787f257
RicardoJeronimo Jan 21, 2025
d04fb15
Created missing directory and optimized instructions
RicardoJeronimo Jan 21, 2025
119468a
Fixed COPY instruction and made Python scripts executable
RicardoJeronimo Jan 21, 2025
edba541
Fixed COPY instruction
RicardoJeronimo Jan 21, 2025
40d67b8
Fixed COPY instruction for the full project tree to be copied into /srv
RicardoJeronimo Jan 21, 2025
7dc4b59
Changed ENTRYPOINT to meet JSONArgsRecommended check
RicardoJeronimo Jan 21, 2025
df805be
Exposed port 443
RicardoJeronimo Jan 21, 2025
981ec28
Reverted changes made in 3178c02
RicardoJeronimo Jan 21, 2025
4d7b537
Fixed entrypoint
RicardoJeronimo Jan 21, 2025
64caeee
Entrypoint script configures SECRET_KEY if not set
RicardoJeronimo Jan 30, 2025
d9d1eb1
Added to do items
RicardoJeronimo Jan 30, 2025
5695f75
Entrypoint now configures Memcached
RicardoJeronimo Jan 30, 2025
930d17d
Entrypoint now configures ADMINS and TIME_ZONE
RicardoJeronimo Jan 30, 2025
c70e52e
Entrypoint now starts httpd after celery broker
RicardoJeronimo Jan 30, 2025
bbee6ae
Fixed TIMEZONE sed where a slash needs to be escaped
RicardoJeronimo Jan 30, 2025
a11f447
Entrypoint now configures USE_ASYNC_PROCESSING
RicardoJeronimo Jan 30, 2025
a6e10a9
Minor bugfix
RicardoJeronimo Jan 30, 2025
6472e16
Entrypoint now configures DATABASES
RicardoJeronimo Jan 30, 2025
8cb178b
Minor bugfix
RicardoJeronimo Jan 30, 2025
6d460f6
Minor bugfixes
RicardoJeronimo Jan 30, 2025
5e60b6b
Minor bugfixes
RicardoJeronimo Jan 30, 2025
4266367
Minor indentation fixes
RicardoJeronimo Jan 30, 2025
6ff4a4b
Minor indentation fixes
RicardoJeronimo Jan 30, 2025
929772a
Sed commands that comment lines don't do it again on container restarts
RicardoJeronimo Jan 30, 2025
c7f2d09
Entrypoint now checks if a MySQL or PostgreSQL database is already co…
RicardoJeronimo Jan 30, 2025
ac22d4d
Minor bugfix
RicardoJeronimo Jan 30, 2025
fbd377c
Binary files are now symlinked instead of copied
RicardoJeronimo Jan 30, 2025
64d7491
Added build step via setup.py
RicardoJeronimo Apr 3, 2025
d3e3120
Entrypoint syncs database on container first start
RicardoJeronimo Apr 3, 2025
098a683
Added PostgreSQL dependency
RicardoJeronimo Apr 3, 2025
e7acfab
Fixed COPY instruction
RicardoJeronimo Apr 3, 2025
c5bba1a
Added GitHub Action to build container
RicardoJeronimo Apr 4, 2025
744cace
Latest tag is now used for container versioning during builds
RicardoJeronimo Apr 4, 2025
a6fa2e6
Removed build steps for branch integrity
RicardoJeronimo Apr 4, 2025
9acf354
Removed build dependencies for branch integrity
RicardoJeronimo Apr 4, 2025
d0abc9d
Fixed minor bug and removed build on pull requests
RicardoJeronimo Apr 4, 2025
d164c82
Minor bugfix
RicardoJeronimo Apr 4, 2025
838dcf7
Improved Docker Compose example
RicardoJeronimo Apr 4, 2025
459fa28
Environment variable DB_PORT is now optional
RicardoJeronimo Apr 4, 2025
32454bb
Minor improvements
RicardoJeronimo Apr 4, 2025
06e81ec
Moved local_settings.py path to a variable
RicardoJeronimo Apr 4, 2025
ebcc531
Improved Docker Compose example
RicardoJeronimo Apr 4, 2025
c23385f
Adjusted entrypoint script to reflect changes made to local_settings.…
RicardoJeronimo Apr 7, 2025
3040e6b
Minor bugfix
RicardoJeronimo Apr 7, 2025
b2a6013
Added git dependency to Dockerfile
RicardoJeronimo Apr 7, 2025
caf0b44
Minor bugfix
RicardoJeronimo Apr 7, 2025
8b1d997
Added CACHE_TIMEOUT environment variable to entrypoint script
RicardoJeronimo Apr 7, 2025
66cf8dc
Improved Docker Compose example
RicardoJeronimo Apr 7, 2025
f06c6ec
Changed Redis environment variable name
RicardoJeronimo Apr 7, 2025
ea045e8
Adjusted entrypoint script to reflect changes made to local_settings.…
RicardoJeronimo Apr 7, 2025
8ed49c6
Minor bugfix
RicardoJeronimo Apr 7, 2025
965350f
Merge remote-tracking branch 'upstream/main' into docker
RicardoJeronimo Apr 24, 2025
57284bd
Adjusted entrypoint script to reflect changes made to local_settings.…
RicardoJeronimo Apr 24, 2025
eaacc12
Merge remote-tracking branch 'upstream/main' into docker
RicardoJeronimo Jun 23, 2025
e6f5b9d
CACHES and CELERY_BROKER_URL configuration can now be set to false wh…
RicardoJeronimo Jun 25, 2025
8b90eca
Fixed if statements when checking if variables are TRUE or FALSE
RicardoJeronimo Jun 25, 2025
d7b3406
Merge remote-tracking branch 'upstream/main' into docker
RicardoJeronimo Sep 10, 2025
72d1c2e
Added README
RicardoJeronimo Sep 10, 2025
102ed5a
Changed build action to update Docker Hub description with README.md …
RicardoJeronimo Sep 10, 2025
d95e71c
Fixed README.md file location
RicardoJeronimo Sep 10, 2025
68ee20d
Fixed README.md file location
RicardoJeronimo Sep 10, 2025
6944d4d
Fixed README.md file location
RicardoJeronimo Sep 10, 2025
54c8cfa
Fixed README.md file location
RicardoJeronimo Sep 10, 2025
f5b51c6
Fixed README.md file location
RicardoJeronimo Sep 10, 2025
463b76a
Fixed checkout job on build action
RicardoJeronimo Sep 10, 2025
6416977
Changed README
RicardoJeronimo Sep 10, 2025
8956889
Changed README
RicardoJeronimo Sep 10, 2025
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
42 changes: 42 additions & 0 deletions .github/workflows/docker-build.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
name: Docker Image CI

on:
push:
branches: [ "main" ]

jobs:
docker:
runs-on: ubuntu-latest
steps:
- name: Login to Docker Hub
uses: docker/login-action@v3
with:
username: ${{ vars.DOCKERHUB_USERNAME }}
password: ${{ secrets.DOCKERHUB_TOKEN }}

- name: Set up QEMU
uses: docker/setup-qemu-action@v3

- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v3

- name: Build and push
uses: docker/build-push-action@v6
with:
file: docker/Dockerfile
platforms: linux/amd64,linux/arm64
push: true
tags: ${{vars.DOCKERHUB_USERNAME}}/${{vars.DOCKERHUB_CONTAINER}}:latest,${{vars.DOCKERHUB_USERNAME}}/${{vars.DOCKERHUB_CONTAINER}}:${{github.ref_name}}
cache-from: type=gha
cache-to: type=gha,mode=max

- name: Checkout for next job
uses: actions/checkout@v4

- name: Docker Hub Description
uses: peter-evans/dockerhub-description@v4
with:
username: ${{ vars.DOCKERHUB_USERNAME }}
password: ${{ secrets.DOCKERHUB_TOKEN }}
repository: ${{vars.DOCKERHUB_USERNAME}}/${{vars.DOCKERHUB_CONTAINER}}
readme-filepath: docker/README.md
22 changes: 22 additions & 0 deletions docker/Dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
FROM debian:bookworm-slim

RUN apt -y update && apt -y upgrade
RUN apt install -y apache2 git libapache2-mod-wsgi-py3 mariadb-client python-celery-common python3-celery python3-debian python3-defusedxml python3-lxml python3-mysqldb python3-pip python3-progressbar python3-psycopg2 python3-redis python3-rpm

WORKDIR /srv/patchman

COPY . /srv/patchman/
COPY ./etc/patchman/apache.conf.example /etc/apache2/sites-available/patchman.conf

RUN /srv/patchman/setup.py install

RUN a2enmod wsgi
RUN a2ensite patchman

RUN mkdir -p /var/lib/patchman/db
RUN chown :www-data /var/lib/patchman/db && chmod 2770 /var/lib/patchman/db

EXPOSE 80

COPY ./docker/docker-entrypoint.sh docker-entrypoint.sh
ENTRYPOINT ["./docker-entrypoint.sh"]
89 changes: 89 additions & 0 deletions docker/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,89 @@
Source: https://github.com/ricardojeronimo/patchman

Upstream: https://github.com/furlongm/patchman


## Getting Started

To get started, pull the latest image from Docker Hub and run it.
```
docker pull ricardojeronim0/patchman:latest
docker run -d -p 80:80 --name patchman ricardojeronim0/patchman
```

This container will run migrations on first startup, but you still need to create a superuser before being able to log in on the web interface.

```
docker exec -it patchman patchman-manage createsuperuser
```

## Configuration

This container is configured using environment variables. The following variables are available to customize the container's behavior.

| Variable | Default Value | Description |
| :--- | :--- | :--- |
| `ADMIN_NAME` | `Your Name` | Your name |
| `ADMIN_EMAIL` | `[email protected]` | Your e-mail address |
| `TIMEZONE` | `America/New_York` | Your timezone |
| `DB_ENGINE` | `SQLite` | Database engine to be used. Choose between `MySQL` or `PostgreSQL`, leave empty to use default `SQLite` |
| `DB_HOST` | | Database hostname, IP or container name |
| `DB_PORT` |` | Database port |
| `DB_DATABASE` | | Database name |
| `DB_USER` | | Database user |
| `DB_PASSWORD` | | Database password |
| `REDIS_HOST` | `127.0.0.1` | Redis hostname, IP or container name |
| `REDIS_PORT` | `6379` | Redis port |
| `USE_CELERY` | `False` | Change to `True` for realtime processing of reports from clients |
| `USE_CACHE` | `False` | Change to `True` cache contents and reduce the load on the server |
| `CACHE_TIMEOUT` | `30` | Cache time in seconds. Be aware that the UI results may be out of date for this amount of time |


## Docker Compose Example

For more complex deployments, `docker-compose` is the recommended approach. Below is an example `docker-compose.yaml` file that demonstrates how to configure the container and connect it to a separate MySQL service, and Redis for async processing and/or caching.

```yaml
---
services:
patchman:
container_name: patchman
image: ricardojeronim0/patchman:latest
restart: unless-stopped
environment:
ADMIN_NAME: admin_name
ADMIN_EMAIL: [email protected]
TIMEZONE: America/New_York
DB_ENGINE: MySQL
DB_HOST: patchman-db
DB_PORT: 3306
DB_DATABASE: patchman
DB_USER: user
DB_PASSWORD: changeme
REDIS_HOST: redis
REDIS_PORT: 6379
USE_CELERY: True
USE_CACHE: True
CACHE_TIMEOUT: 20
ports:
- 80:80/tcp
depends_on:
- patchman-db
- redis

patchman-db:
container_name: patchman-db
image: mysql:latest
restart: unless-stopped
command: ["mysqld", "--character-set-server=utf8", "--collation-server=utf8_general_ci"]
environment:
MYSQL_ROOT_PASSWORD: changeme
MYSQL_DATABASE: patchman
MYSQL_USER: user
MYSQL_PASSWORD: changeme

redis:
container_name: redis
image: redis:latest
restart: unless-stopped
```
42 changes: 42 additions & 0 deletions docker/docker-compose.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
---
services:
patchman:
container_name: patchman
image: furlongm/patchman:latest
restart: unless-stopped
environment:
ADMIN_NAME: admin_name
ADMIN_EMAIL: [email protected]
TIMEZONE: America/New_York
DB_ENGINE: MySQL
DB_HOST: patchman-db
DB_PORT: 3306
DB_DATABASE: patchman
DB_USER: user
DB_PASSWORD: changeme
REDIS_HOST: redis
REDIS_PORT: 6379
USE_CELERY: True
USE_CACHE: True
CACHE_TIMEOUT: 20
ports:
- 80:80/tcp
depends_on:
- patchman-db
- redis

patchman-db:
container_name: patchman-db
image: mysql:latest
restart: unless-stopped
command: ["mysqld", "--character-set-server=utf8", "--collation-server=utf8_general_ci"]
environment:
MYSQL_ROOT_PASSWORD: changeme
MYSQL_DATABASE: patchman
MYSQL_USER: user
MYSQL_PASSWORD: changeme

redis:
container_name: redis
image: redis:latest
restart: unless-stopped
155 changes: 155 additions & 0 deletions docker/docker-entrypoint.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,155 @@
#!/bin/bash

conf="/etc/patchman/local_settings.py"

# Configure ADMINS
if [ -n "${ADMIN_NAME}" ]; then
sed -i '6 {s/Your Name/'"${ADMIN_NAME}"'/}' "$conf"
fi

if [ -n "${ADMIN_EMAIL}" ]; then
sed -i '6 {s/[email protected]/'"${ADMIN_EMAIL}"'/}' "$conf"
fi

# Configure DATABASES
if [ -n "${DB_ENGINE}" ]; then
sed -i '9,18 {/^#/ ! s/\(.*\)/#\1/}' "$conf"

if [[ $(grep -v "#" "$conf" | grep -c "ENGINE") -lt 2 ]]; then
if [ "${DB_ENGINE}" == "MySQL" ]; then
if [ -n "${DB_PORT}" ]; then
dbPort="${DB_PORT}"
else
dbPort="3306"
fi

cat <<-EOF >> "$conf"

DATABASES = {
'default': {
'ENGINE': 'django.db.backends.mysql',
'NAME': '${DB_DATABASE}',
'USER': '${DB_USER}',
'PASSWORD': '${DB_PASSWORD}',
'HOST': '${DB_HOST}',
'PORT': '$dbPort',
'STORAGE_ENGINE': 'INNODB',
'CHARSET' : 'utf8'
}
}
EOF

elif [ "${DB_ENGINE}" == "PostgreSQL" ]; then
if [ -n "${DB_PORT}" ]; then
dbPort="${DB_PORT}"
else
dbPort="5432"
fi

cat <<-EOF >> "$conf"

DATABASES = {
'default': {
'ENGINE': 'django.db.backends.postgresql_psycopg2',
'NAME': '${DB_DATABASE}',
'USER': '${DB_USER}',
'PASSWORD': '${DB_PASSWORD}',
'HOST': '${DB_HOST}',
'PORT': '$dbPort',
'CHARSET' : 'utf8'
}
}
EOF
fi
fi
fi

# Configure TIME_ZONE
if [ -n "${TIMEZONE}" ]; then
sed -i '22 {s/America\/New_York/'"${TIMEZONE/\//\\/}"'/}' "$conf"
fi

# Configure SECRET_KEY
if [ -z "$(grep "SECRET_KEY" "$conf" | cut -d " " -f 3 | tr -d "'")" ]; then
if [ -n "${SECRET_KEY}" ]; then
sed -i "s/SECRET_KEY = ''/SECRET_KEY = '"${SECRET_KEY}"'/g" "$conf"
else
patchman-set-secret-key
fi
fi

# Configure CACHES
if "${USE_CACHE}"; then
if [ -n "${REDIS_HOST}" ]; then
redisHost="${REDIS_HOST}"
else
redisHost="127.0.0.1"
fi

if [ -n "${REDIS_PORT}" ]; then
redisPort="${REDIS_PORT}"
else
redisPort="6379"
fi

# Comment DummyCache Block
sed -i '47,51 {/^#/ ! s/\(.*\)/#\1/}' "$conf"

# Uncomment RedisCache Block
sed -i '55,61 {s/^# //}' "$conf"

sed -i "58 {s/127.0.0.1:6379/$redisHost:$redisPort/}" "$conf"

if [ -n "${CACHE_TIMEOUT}" ]; then
sed -i "59 {s/30/${CACHE_TIMEOUT}/}" "$conf"
fi
fi

# Sync database on container first start
if [ ! -f /var/lib/patchman/.firstrun ]; then
patchman-manage makemigrations
patchman-manage migrate --run-syncdb --fake-initial
patchman-manage collectstatic

# If SQLite is being used, allow httpd to write
if [ -z "${DB_ENGINE}" ]; then
chmod 660 /var/lib/patchman/db/patchman.db
fi

touch /var/lib/patchman/.firstrun
fi

# Starts Celery for for realtime processing of reports from clients
if "${USE_CELERY}"; then
if [ -n "${REDIS_HOST}" ]; then
redisHost="${REDIS_HOST}"
else
redisHost="127.0.0.1"
fi

if [ -n "${REDIS_PORT}" ]; then
redisPort="${REDIS_PORT}"
else
redisPort=6379
fi

if [ -z "$(grep "USE_ASYNC_PROCESSING" "$conf" | cut -d " " -f 3 | tr -d "'")" ]; then
echo "" >> "$conf"
echo "USE_ASYNC_PROCESSING = True" >> "$conf"
fi

if [ -z "$(grep "CELERY_BROKER_URL" "$conf" | cut -d " " -f 3 | tr -d "'")" ]; then
echo "CELERY_BROKER_URL = 'redis://$redisHost:$redisPort/0'" >> "$conf"
fi

C_FORCE_ROOT=1 celery -b redis://"$redisHost":"$redisPort"/0 -A patchman worker -l INFO -E &
fi

# Starts Apache httpd process
/usr/sbin/apache2ctl -DFOREGROUND

# Wait for any process to exit
wait -n

# Exit with status of process that exited first
exit $?