Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Make Docker setup less memory-intensive & build deps at container start #736

Merged
merged 116 commits into from
Feb 3, 2025
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
116 commits
Select commit Hold shift + click to select a range
72c4638
Try out to mount local gems to docker container
Splines Jan 21, 2025
4b7b37f
Install dependencies in initialize & use volume for bundle_cache
Splines Jan 21, 2025
9d2f463
Use bundle cache also for webpacker in dev
Splines Jan 21, 2025
98601a4
Remove prometheus exporter statements from entrypoint
Splines Jan 21, 2025
63a566f
Remove old comments from entrypoint
Splines Jan 21, 2025
8e8fdbb
Readd accidentally deleted rails statement
Splines Jan 21, 2025
ba6e01e
Don't start prometheus exporter in dev environment
Splines Jan 21, 2025
ff9ae19
Also use the volume for gems in test environment
Splines Jan 21, 2025
15236e8
Make test env closer to dev & don't rebuild entire mampf
Splines Jan 21, 2025
306cd83
Move entrypoint and init to docker folder
Splines Jan 21, 2025
2e0dbbf
Also install Node.js modules at container start
Splines Jan 21, 2025
40e0d75
Remove webpacker from justfile rebuild script
Splines Jan 21, 2025
825e016
Init commands to download latest database dump & reseed db from file …
Splines Jan 22, 2025
828006f
Merge branch 'release/1.15.2' into deps/bundle-local-gems
Splines Jan 22, 2025
cf011cb
Change user name to localroot in test db
Splines Jan 22, 2025
827983c
Improve docstring of rebuild docker command
Splines Jan 22, 2025
70ec02f
Use localroot user also in test db
Splines Jan 22, 2025
66b2476
Remove pull policy (defaults to 'missing')
Splines Jan 22, 2025
fc1b108
Bake dependencies into image on CI/CD (for better caching)
Splines Jan 23, 2025
f484c87
Fail build on check violations
Splines Jan 23, 2025
99d69f8
Use mode max and set output type to registry (to trigger a push)
Splines Jan 23, 2025
0a4307d
Use `--push` as shorthand option
Splines Jan 23, 2025
359ad77
Set output to type=registry again
Splines Jan 23, 2025
8ba42c6
Build mampf image in test environment on CI/CD
Splines Jan 23, 2025
fe7f604
Use `run: >` to avoid manual multi-line breaking
Splines Jan 23, 2025
88e4d23
Overwrite mampf.build in CI/CD
Splines Jan 23, 2025
eecee56
Use additional compose file to overwrite build section in CI/CD
Splines Jan 23, 2025
e2112de
Add fs.read entitlements for buildx
Splines Jan 23, 2025
ccf2245
Use type=docker again & overwrite image name
Splines Jan 23, 2025
5d4b832
Pass IN_CI_CD via docker compose file
Splines Jan 23, 2025
10484bc
Create empty mampf database
Splines Jan 23, 2025
55d140b
Let waiting for MaMpf timeout after 1m
Splines Jan 23, 2025
54a4f6d
Fix wrong indentation & make entrypoint-ci script executable
Splines Jan 23, 2025
3c6c84c
Use postgres init script to always create empty mampf db
Splines Jan 24, 2025
4ddf15b
Remove entrypoint-ci from docker dev setup
Splines Jan 24, 2025
595cf8d
Outsource cypress entrypoint script
Splines Jan 24, 2025
7162a91
Remove entrypoint-ci entrypoint overwrite from CI/CD
Splines Jan 24, 2025
7cdc083
Make db-tear-down more reliable by removing the entire volume
Splines Jan 24, 2025
e012b10
Redirecting webpacker output to run in background on GitHub Actions
Splines Jan 24, 2025
7312421
Use shorter syntax for volumes
Splines Jan 26, 2025
d4c9234
Use cypress run instead of cypress open in CI
Splines Jan 26, 2025
cd3eaa9
Remove entrypoint for dev setup in CI
Splines Jan 26, 2025
d37889e
Split deps installing into two RUN commands
Splines Jan 26, 2025
bb1b8f0
Fix spelling mistake
Splines Jan 26, 2025
11365ce
Simplify webpack dev server calling
Splines Jan 26, 2025
84310da
Precompile assets in CI/CD
Splines Jan 26, 2025
13ffb40
Explicitly use a bind mount
Splines Jan 26, 2025
92a9b24
Use ";" instead of "&&" in if statement
Splines Jan 26, 2025
f0a8308
Print folder contents for debugging
Splines Jan 26, 2025
04b3c08
Use shorter volume syntax again & fix wrong volume name
Splines Jan 26, 2025
e92238d
Additionally print working directory for debugging
Splines Jan 26, 2025
7af730f
Use github.workspace variable for volume bind mount
Splines Jan 26, 2025
2ea37e1
Add dummy echos to trigger cache miss
Splines Jan 26, 2025
8068824
Try to only use github workspace bind (to test)
Splines Jan 27, 2025
00e4b66
Make dummy commit to trigger no caching
Splines Jan 27, 2025
d92ff83
Move env variable declaration to build step
Splines Jan 27, 2025
68e742e
Copy app files to docker container to precompile assets
Splines Jan 27, 2025
be90572
Use Docker copy statement
Splines Jan 27, 2025
a24bf0b
Try to manually set compile to false in webpacker test config
Splines Jan 28, 2025
73e5b19
Set new CI env variable in GitHub Actions
Splines Jan 28, 2025
46ac47c
Set compile to false manually
Splines Jan 28, 2025
473f4df
Specify separate ci webpacker config
Splines Jan 28, 2025
be94e2a
Set NODE_ENV instead of RAILS_ENV
Splines Jan 28, 2025
92c0a94
Add missing test-ci config file
Splines Jan 28, 2025
0596ef5
Don't compile test packs to a separate directory
Splines Jan 28, 2025
9b216c5
Call NODE_ENV for webpacker config to be available during runtime
Splines Jan 28, 2025
1895e75
Pass NODE_ENV to docker containers in CI/CD
Splines Jan 28, 2025
2d929a6
Remove custom filename for test-ci & specify NODE_ENV correctly
Splines Jan 28, 2025
eebf375
Try setting compile back to true
Splines Jan 28, 2025
dd00505
Try to set env variables before `bundle exec rspec`
Splines Jan 28, 2025
9d50fc2
Add dependent build mampf step to avoid building twice
Splines Jan 28, 2025
020aa58
Use docker image pull to pull from GHCR
Splines Jan 28, 2025
aa4cf13
Pull image with debug flag
Splines Jan 31, 2025
7785597
Set cache manually, rename url & make permissions more granular
Splines Jan 31, 2025
0b8555a
Use correct flags
Splines Jan 31, 2025
9787468
Set target pattern for cache
Splines Jan 31, 2025
2a9d6b2
Set target output option to registry
Splines Jan 31, 2025
354fac1
Specify ref as name in target.output
Splines Jan 31, 2025
c7453e3
Explicitly set tag & use registry as output type (shortcut)
Splines Jan 31, 2025
9e41c39
Use `tags` instead of `tag`
Splines Jan 31, 2025
eac905e
Comment out build step and remove -f flag
Splines Jan 31, 2025
1353f76
Try to pull only mampf service
Splines Feb 1, 2025
2832134
Embed build cache into image
Splines Feb 1, 2025
cdccd8c
Only build image in build job
Splines Feb 1, 2025
9f6ac2c
Use full URL to reference mampf image when running test
Splines Feb 1, 2025
9130881
Explicitly set node env for mampf service
Splines Feb 1, 2025
25cebc2
Unify test-ci and test
Splines Feb 1, 2025
26a3d8e
Set RAILS_ENV to test during assets precompiling
Splines Feb 1, 2025
03af6f7
Use [name]-[hash] pattern also in CI and set NODE_ENV
Splines Feb 1, 2025
c75624a
Try to remove hash for filenames in test env
Splines Feb 1, 2025
04f8a10
Compile tests to separate directory
Splines Feb 1, 2025
c9937e1
Add back rails env to assets:precompile
Splines Feb 1, 2025
51739a7
Use test database adapter instead
Splines Feb 1, 2025
c8b9fa5
Temporarily use previous webpacker test config
Splines Feb 1, 2025
157751a
Use anonymous volume for /usr/src/app/public
Splines Feb 1, 2025
75615d4
Remove unnecessary variable setting on cypress tests
Splines Feb 1, 2025
9562d63
Add another link for a great guide to webpacker.yml
Splines Feb 1, 2025
1e63a41
Revert "Temporarily use previous webpacker test config"
Splines Feb 1, 2025
ad0f107
Also require testing environment for mampf build
Splines Feb 1, 2025
0c73e48
Extract CSS file in CI/CD
Splines Feb 1, 2025
3971a6c
Rename buildcache to cache
Splines Feb 1, 2025
1be0564
Use registry cache exporter to allow for max-mode caching
Splines Feb 1, 2025
1cf9ade
Don't require another approval for subsequent jobs (after build)
Splines Feb 1, 2025
10d36de
Generate OCI-compatible image manifest
Splines Feb 1, 2025
e254e18
Push image & buildcache separately, then import image later
Splines Feb 1, 2025
56c0487
Try to specify tag for mampftest:image
Splines Feb 1, 2025
dca4d24
Add new environment (testing-review)
Splines Feb 1, 2025
4f162de
Specify webpack-dev-server as dev dependency
Splines Feb 1, 2025
2cd120e
Only install production Node.js packages in CI/CD tests
Splines Feb 1, 2025
024f9fe
Never pull mampf image automatically
Splines Feb 1, 2025
cf90581
Merge branch 'release/1.15.3' into deps/bundle-local-gems
Splines Feb 1, 2025
9bea9cd
Add recipe to run rspec via just
Splines Feb 1, 2025
adb17a9
Also install bundle dependencies when invoked via VSCode
Splines Feb 1, 2025
78c2b88
Remove unnecessary test dependencies
Splines Feb 3, 2025
db7d1ce
Add install dependencies in test container command
Splines Feb 3, 2025
bba3b8c
Increase timeout to 2min in Cypress entrypoint
Splines Feb 3, 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
176 changes: 162 additions & 14 deletions .config/commands/docker.justfile
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
help:
@just --list --justfile {{source_file()}}

# Starts the dev docker containers
# Starts the dev containers (assumes a valid database)
@up *args:
#!/usr/bin/env bash
cd {{justfile_directory()}}/docker/development/
Expand All @@ -11,8 +11,9 @@ help:
# Starts the dev docker containers (detached) & shows MaMpf logs
up-logs *args:
#!/usr/bin/env bash
just docker up -d {{args}}

cd {{justfile_directory()}}/docker/development/
docker compose up -d {{args}}
docker compose logs -f mampf

# Shows the log of the specified container
Expand All @@ -25,10 +26,100 @@ up-logs *args:
[confirm("This will reset all your data in the database locally. Continue? (y/n)")]
up-reseed *args:
#!/usr/bin/env bash
# (pgadmin issue: https://github.com/pgadmin-org/pgadmin4/issues/8071)

set -e
just --yes docker db-tear-down

cd {{justfile_directory()}}/docker/development/
export DB_SQL_PRESEED_URL="https://github.com/MaMpf-HD/mampf-init-data/raw/main/data/20220923120841_mampf.sql"
export UPLOADS_PRESEED_URL="https://github.com/MaMpf-HD/mampf-init-data/raw/main/data/uploads.zip"
docker compose rm --stop --force mampf && docker compose up {{args}}
docker compose rm --stop --force mampf && just docker up {{args}}

# Starts the dev docker containers and preseeds the database from an .sql file
[confirm("This will reset all your data in the database locally. Continue? (y/n)")]
up-reseed-from-file preseed_file *args:
#!/usr/bin/env bash
if [[ {{preseed_file}} != *.sql ]]; then
echo "The file must be an .sql file."
exit 1
fi

cd {{justfile_directory()}}/docker/development/
export DB_SQL_PRESEED_URL="{{preseed_file}}"
export UPLOADS_PRESEED_URL=""
docker compose rm --stop --force mampf && just docker up {{args}}

# Restores a postgres backup file that was made using pg_dump or pg_dumpall
[no-cd]
up-reseed-from-dump preseed_file:
#!/usr/bin/env bash
set -e
just docker db-tear-down

# If file is gzipped, unzip it
if [[ {{preseed_file}} == *.gz ]]; then
unzipped=$(echo {{preseed_file}} | sed 's/\.gz$//')
if [[ -f $unzipped ]]; then
echo "Using already existing unzipped file $unzipped"
else
echo "Unzipping {{preseed_file}}"
gunzip {{preseed_file}}
fi
else
unzipped={{preseed_file}}
fi

if [[ $unzipped != *.pg_dump ]]; then
echo "The file must be a .pg_dump file."
exit 1
fi

file=$(realpath ${unzipped})
echo "Will restore database from $file"
echo -n "Is this correct? (y/n) "
read confirmation
if [ "$confirmation" != "y" ]; then
exit 1
fi

just docker ensure-db-container-running-and-postgres-ready
cd {{justfile_directory()}}/docker/development/

echo "Copy file over to docker container"
docker compose cp ${file} db:/tmp/backup.pg_dump

# This is necessary because somehow the last line is not properly read,
# probably due to some missing newline character
# As the last line is really not that important, we just get rid of it
echo "Removing last line from dump"
docker compose exec -T db bash -c "head -n -1 /tmp/backup.pg_dump > /tmp/backup.pg_dump.tmp && mv /tmp/backup.pg_dump.tmp /tmp/backup.pg_dump"

echo "Restoring database from dump"
# Should you experience "\N" errors, see https://stackoverflow.com/questions/20427689/psql-invalid-command-n-while-restore-sql#comment38644877_20428547
# i.e. add `-v ON_ERROR_STOP=1` to the psql command below.
# However, this will error immediately with "mampf db already exists".
# This is because we mount an init .sql script into the db container
# (see directory /docker-entrypoint-initdb.d/) and this script is called
# immediately upon startup. So in case you really get the "\N" errors,
# add the `-v ON_ERROR_STOP=1` flag to the psql command below and additionally
# remove the init script from the db container, e.g. by exec'ing into it
# and removing the file manually.
docker compose exec -T db bash -c "psql -h localhost -p 5432 -U localroot -f /tmp/backup.pg_dump"

echo "Restarting containers"
just docker stop
just docker up -d

# Removes all database data in the db docker container
[confirm("This will completely destroy your local database, including all tables and users. Continue? (y/n)")]
db-tear-down:
#!/usr/bin/env bash
echo -e "\033[33mIgnore the error 'Resource is still in use' for the development_default network\033[0m"
cd {{justfile_directory()}}/docker/development/
docker compose down db --volumes
docker-compose up -d --force-recreate db
just docker wait-for-postgres

# Removes the development docker containers
@down:
Expand All @@ -55,26 +146,83 @@ up-reseed *args:
docker compose exec -it {{name}} {{shell}}

# Puts you into the rails console of the dev docker mampf container
@rails-c:
@rails-c *args:
#!/usr/bin/env bash
cd {{justfile_directory()}}/docker/development/
docker compose exec mampf bundle exec rails c
docker compose exec mampf bundle exec rails c {{args}}

# Rebuilds the most essential containers in the dev or test environment
# Rebuilds the MaMpf container (in the dev or test environment)
rebuild env="dev":
#!/usr/bin/env bash
environment={{ if env == "test" {"test"} else {"development"} }}
echo "Rebuilding in env: ${environment}"
cd {{justfile_directory()}}/docker/${environment}

# Remove
docker compose rm -s mampf
if [ "$environment" = "development" ]; then
docker compose rm -s webpacker
docker compose build mampf


# Creates an empty mampf db (assumes that the db container is running)
[private]
create-empty-mampf-db-if-not-exists:
#!/usr/bin/env bash
# This is just left as reference for now. We don't actually use this recipe
# anywhere. Instead, to create an empty mampf db, we put an .sql file into
# the special initialization directory in the db container
# (`/docker-entrypoint-initdb.d/`).
# See https://docs.docker.com/guides/pre-seeding/#pre-seed-the-database-by-bind-mounting-a-sql-script
set -e

just docker ensure-db-container-running-and-postgres-ready

cd {{justfile_directory()}}/docker/development/

# Early return if mampf db already exists
if [ "$(docker compose exec -T db bash -c "psql -h localhost -U localroot -XtA -c \"SELECT 1 FROM pg_database WHERE datname='mampf'\"")" == "1" ]; then
exit 0
fi

# Rebuild
docker compose build mampf
if [ "$environment" = "development" ]; then
docker compose build webpacker
# Create an empty mampf database. This is necessary since the default user
# is called localroot and not mampf. (It it were called mampf, postgresql
# would created the mampf db automatically.)
# see also https://stackoverflow.com/a/68091072/
docker compose exec -T db bash -c "psql -v ON_ERROR_STOP=1 -h localhost -p 5432 -U localroot -c 'CREATE DATABASE mampf;'"

# Make sure mampf db exists now
if [ "$(docker compose exec -T db bash -c "psql -h localhost -U localroot -XtA -c \"SELECT 1 FROM pg_database WHERE datname='mampf'\"")" != "1" ]; then
echo "Could not create the empty mampf database. Exiting."
exit 1
fi

# Waits for postgres to be available (assumes that the db container is running)
[private]
wait-for-postgres:
#!/usr/bin/env bash
set -e
cd {{justfile_directory()}}/docker/development/

# https://stackoverflow.com/a/77582897/
# Wait for the db container to be up
until docker compose exec -T db bash -c "pg_isready -h localhost -U localroot"; do
>&2 echo "Postgres is unavailable (waiting...)"
sleep 1
done
>&2 echo "Postgres is up, will continue"

# Ensures that the db container is running (does not wait for postgres; starts the db container if not running)
[private]
ensure-db-container-running:
#!/usr/bin/env bash
cd {{justfile_directory()}}/docker/development/

# If the db container is not running, start it first
if [ -z "$(docker compose ps --services --filter 'status=running' | grep db)" ]; then
docker compose up -d db
fi


# Ensures that the db container is running and postgres is ready (if not, starts the db container and waits for postgres)
[private]
ensure-db-container-running-and-postgres-ready:
#!/usr/bin/env bash
just docker ensure-db-container-running
just docker wait-for-postgres
40 changes: 40 additions & 0 deletions .config/commands/prod.justfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
[private]
help:
@just --list --justfile {{source_file()}}

# Downloads the latest database dump from the production server
download-db-dump:
#!/usr/bin/env bash
set -e

# User input: proxy jump
echo "To connect to the remote server you might need a proxy jump. Enter the host name (or leave empty):"
read proxy_jump_destination
proxy_jump_cmd="-J $proxy_jump_destination"

# User input for remote server & dump folder
echo "Enter the remote user and host in the format user@host "
read remote_user_host
echo "Enter the path to the folder that contains the database dumps on the remote server, e.g. /a/b/db"
read remote_dump_folder

# Latest file
latest_file=$(ssh $proxy_jump_cmd "$remote_user_host" "ls -t $remote_dump_folder | head -n 1")
if [ -z "$latest_file" ]; then
echo "No files found in the remote folder."
exit 1
fi
echo ""
echo "Latest file found: $latest_file"

# Download file
echo "We will now download this file to the local machine into the folder db/backups/prod/"
echo -n "Are you sure you want to continue? (y/n) "
read confirmation
if [ "$confirmation" != "y" ]; then
echo "Operation cancelled."
exit 1
fi
local_dir={{justfile_directory()}}/db/backups/prod/
mkdir -p "$local_dir"
scp -C $proxy_jump_cmd "$remote_user_host:$remote_dump_folder/$latest_file" "$local_dir"
12 changes: 12 additions & 0 deletions .config/commands/test.justfile
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,18 @@
help:
@just --list --justfile {{source_file()}}

# Installs the dependencies for the test environment (bundle install, yarn install)
install-dependencies:
#!/usr/bin/env bash
cd {{justfile_directory()}}/docker/test
docker compose run --entrypoint="" mampf sh -c "bundle install && yarn install"

# Runs the RSpec tests (you should rather use the VSCode test runner)
rspec:
#!/usr/bin/env bash
cd {{justfile_directory()}}/docker/test
docker compose run --entrypoint="" mampf sh -c "bundle install && RAILS_ENV=test bundle exec rspec --format documentation"

# Starts the interactive Cypress test runner UI
cypress:
#!/usr/bin/env bash
Expand Down
15 changes: 0 additions & 15 deletions .github/workflows/docker-compose-cache.json

This file was deleted.

Loading