Skip to content

Commit

Permalink
Merge pull request #57 from jolicode/registry
Browse files Browse the repository at this point in the history
Use a registry for storing docker frontend image
  • Loading branch information
lyrixx authored Jul 4, 2023
2 parents 66167bd + a33b2bd commit 61cc359
Show file tree
Hide file tree
Showing 15 changed files with 126 additions and 37 deletions.
30 changes: 21 additions & 9 deletions .castor/infra.php
Original file line number Diff line number Diff line change
Expand Up @@ -79,32 +79,44 @@ function destroy(

docker_compose(['down', '--remove-orphans', '--volumes', '--rmi=local'], withBuilder: true);
$files = finder()
->in(variable('root_dir') . '/infrastructure/docker/services/router/etc/ssl/certs/')
->in(variable('root_dir') . '/infrastructure/docker/services/router/certs/')
->name('*.pem')
->files()
;
fs()->remove($files);
}

#[AsTask(description: 'Push images to the registry')]
function push(): void
{
docker_compose(['push'], withBuilder: true);
}

#[AsTask(description: 'Pull images from the registry')]
function pull(): void
{
docker_compose(['pull', '-q'], withBuilder: true);
}

#[AsTask(description: 'Generates SSL certificates (with mkcert if available or self-signed if not)')]
function generate_certificates(
#[AsOption(description: 'Force the certificates re-generation without confirmation', shortcut: 'f')]
bool $force = false,
): void {
if (file_exists(variable('root_dir') . '/infrastructure/docker/services/router/etc/ssl/certs/cert.pem') && !$force) {
if (file_exists(variable('root_dir') . '/infrastructure/docker/services/router/certs/cert.pem') && !$force) {
io()->comment('SSL certificates already exists.');
io()->note('Run "castor infra:generate-certificates --force" to generate new certificates.');

return;
}

if ($force) {
if (file_exists($f = variable('root_dir') . '/infrastructure/docker/services/router/etc/ssl/certs/cert.pem')) {
io()->comment('Removing existing certificates in infrastructure/docker/services/router/etc/ssl/certs/*.pem.');
if (file_exists($f = variable('root_dir') . '/infrastructure/docker/services/router/certs/cert.pem')) {
io()->comment('Removing existing certificates in infrastructure/docker/services/router/certs/*.pem.');
unlink($f);
}

if (file_exists($f = variable('root_dir') . '/infrastructure/docker/services/router/etc/ssl/certs/key.pem')) {
if (file_exists($f = variable('root_dir') . '/infrastructure/docker/services/router/certs/key.pem')) {
unlink($f);
}
}
Expand All @@ -125,8 +137,8 @@ function generate_certificates(

run([
'mkcert',
'-cert-file', 'infrastructure/docker/services/router/etc/ssl/certs/cert.pem',
'-key-file', 'infrastructure/docker/services/router/etc/ssl/certs/key.pem',
'-cert-file', 'infrastructure/docker/services/router/certs/cert.pem',
'-key-file', 'infrastructure/docker/services/router/certs/key.pem',
$rootDomain,
"*.{$rootDomain}",
...variable('extra_domains'),
Expand All @@ -141,9 +153,9 @@ function generate_certificates(
return;
}

run(['infrastructure/docker/services/router/generate-ssl.sh']);
run(['infrastructure/docker/services/router/generate-ssl.sh'], quiet: true);

io()->success('Successfully generated self-signed SSL certificates in infrastructure/docker/services/router/etc/ssl/certs/*.pem.');
io()->success('Successfully generated self-signed SSL certificates in infrastructure/docker/services/router/certs/*.pem.');
io()->comment('Consider installing mkcert to generate locally trusted SSL certificates and run "castor infra:generate-certificates --force".');

if ($force) {
Expand Down
17 changes: 10 additions & 7 deletions .castor/utils.php
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,7 @@ function about(): void
}

#[AsTask(description: 'Opens a shell (bash) into a builder container')]
function builder(string $user = 'app'): void
function builder(): void
{
$c = get_context()
->withTimeout(null)
Expand All @@ -56,7 +56,7 @@ function builder(string $user = 'app'): void
->withQuiet()
->withAllowFailure()
;
docker_compose_run('bash', c: $c, user: $user);
docker_compose_run('bash', c: $c);
}

#[AsContext(default: true)]
Expand Down Expand Up @@ -98,15 +98,18 @@ function create_default_context(): Context
$data['user_id'] = 1000;
}

// @phpstan-ignore-next-line
return new Context($data, pty: 'dev' === $data['env']);
return new Context(
// @phpstan-ignore-next-line
$data,
pty: 'dev' === $data['env'],
environment: create_default_environment(),
);
}

function docker_compose_run(
string $runCommand,
Context $c = null,
string $service = 'builder',
string $user = 'app',
bool $noDeps = true,
string $workDir = null,
bool $portMapping = false,
Expand All @@ -115,7 +118,6 @@ function docker_compose_run(
$command = [
'run',
'--rm',
'-u', $user,
];

if ($noDeps) {
Expand Down Expand Up @@ -156,9 +158,10 @@ function docker_compose(array $subCommand, Context $c = null, bool $withBuilder
'PROJECT_DIRECTORY' => variable('project_directory'),
'PROJECT_ROOT_DOMAIN' => variable('root_domain'),
'PROJECT_DOMAINS' => $domains,
'USER_ID' => variable('user_id'),
'COMPOSER_CACHE_DIR' => variable('composer_cache_dir'),
'PHP_VERSION' => variable('php_version'),
], false)
], true)
;

$command = [
Expand Down
10 changes: 10 additions & 0 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -10,15 +10,25 @@ name: Continuous Integration

permissions:
contents: read
packages: read

jobs:
ci:
name: Continuous Integration
runs-on: ubuntu-latest
env:
BUILDKIT_PROGRESS: plain
DOCKER_BUILDKIT: 1
CI: 1
steps:
-
name: Log in to the Container registry
uses: docker/login-action@v2
with:
registry: 'ghcr.io'
username: ${{ github.actor }}
password: ${{ secrets.GITHUB_TOKEN }}

-
uses: actions/checkout@v3

Expand Down
2 changes: 1 addition & 1 deletion .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -26,4 +26,4 @@
/.castor.stub.php
/infrastructure/docker/.env
/infrastructure/docker/docker-compose.override.yml
/infrastructure/docker/services/router/etc/ssl/certs/*
/infrastructure/docker/services/router/certs/*
20 changes: 18 additions & 2 deletions castor.php
Original file line number Diff line number Diff line change
Expand Up @@ -24,11 +24,27 @@ function create_default_variables(): array
];
}

/**
* @return array<string, mixed>
*/
function create_default_environment(): array
{
return [
'BUILDER_VERSION' => 'latest',
'FRONTEND_VERSION' => 'latest',
'ROUTER_VERSION' => 'latest',
];
}

#[AsTask(description: 'Builds and starts the infrastructure, then install the application (composer, yarn, ...)')]
function start(): void
function start(bool $build = false): void
{
infra\generate_certificates(false);
infra\build();
if ($build) {
infra\build();
} else {
infra\pull();
}
infra\up();
cache_clear();
install();
Expand Down
11 changes: 6 additions & 5 deletions infrastructure/docker/docker-compose.builder.yml
Original file line number Diff line number Diff line change
Expand Up @@ -5,19 +5,20 @@ volumes:

services:
builder:
image: "ghcr.io/jolicode/monologue/builder:${BUILDER_VERSION:-latest}"
build:
context: services/php
target: builder
# cache_to:
# - "ghcr.io/jolicode/monologue/builder:${BUILDER_VERSION:-latest}"
# cache_from:
# - "ghcr.io/jolicode/monologue/builder:${BUILDER_VERSION:-latest}"
depends_on:
- postgres
environment:
- COMPOSER_MEMORY_LIMIT=-1
# The following list contains the common environment variables exposed by CI platforms
- UID=${USER_ID}
- GITHUB_ACTIONS
- CI # Travis CI, CircleCI, Cirrus CI, Gitlab CI, Appveyor, CodeShip, dsari
- CONTINUOUS_INTEGRATION # Travis CI, Cirrus CI
- BUILD_NUMBER # Jenkins, TeamCity
- RUN_ID # TaskCluster, dsari
volumes:
- "../../${PROJECT_DIRECTORY}:/home/app/application:cached"
- "${COMPOSER_CACHE_DIR}:/home/app/.composer/cache"
Expand Down
16 changes: 14 additions & 2 deletions infrastructure/docker/docker-compose.yml
Original file line number Diff line number Diff line change
Expand Up @@ -5,15 +5,27 @@ volumes:

services:
router:
build: services/router
image: "ghcr.io/jolicode/monologue/router:${ROUTER_VERSION:-latest}"
build:
context: services/router
# cache_to:
# - "ghcr.io/jolicode/monologue/router:${ROUTER__VERSION:-latest}"
# cache_from:
# - "ghcr.io/jolicode/monologue/router:${ROUTER__VERSION:-latest}"
volumes:
- "/var/run/docker.sock:/var/run/docker.sock"
- "./services/router/certs:/etc/ssl/certs"
network_mode: host

frontend:
image: "ghcr.io/jolicode/monologue/frontend:${FRONTEND_VERSION:-latest}"
build:
context: services/php
target: frontend
# cache_to:
# - "ghcr.io/jolicode/monologue/frontend:${FRONTEND_VERSION:-latest}"
# cache_from:
# - "ghcr.io/jolicode/monologue/frontend:${FRONTEND_VERSION:-latest}"
depends_on:
- postgres
volumes:
Expand All @@ -29,7 +41,7 @@ services:
- "traefik.http.routers.${PROJECT_NAME}-frontend-unsecure.middlewares=redirect-to-https@file"

postgres:
build: services/postgres
image: postgres:15.2
environment:
POSTGRES_PASSWORD: monologue
POSTGRES_USER: monologue
Expand Down
17 changes: 12 additions & 5 deletions infrastructure/docker/services/php/Dockerfile
Original file line number Diff line number Diff line change
@@ -1,12 +1,16 @@
FROM debian:11.7-slim as php-base

LABEL org.opencontainers.image.source https://github.com/jolicode/monologue

RUN apt-get update \
&& apt install -y --no-install-recommends \
curl \
ca-certificates \
gnupg \
&& curl -s https://packages.sury.org/php/apt.gpg | gpg --dearmor > /usr/share/keyrings/deb.sury.org-php.gpg \
&& echo "deb [signed-by=/usr/share/keyrings/deb.sury.org-php.gpg] https://packages.sury.org/php bullseye main" > /etc/apt/sources.list.d/sury.list
&& echo "deb [signed-by=/usr/share/keyrings/deb.sury.org-php.gpg] https://packages.sury.org/php bullseye main" > /etc/apt/sources.list.d/sury.list \
&& apt-get clean \
&& rm -rf /var/lib/apt/lists/* /tmp/* /var/tmp/* /usr/share/doc/*

RUN apt-get update \
&& apt-get install -y --no-install-recommends \
Expand All @@ -33,14 +37,19 @@ RUN apt-get update \
&& rm -rf /var/lib/apt/lists/* /tmp/* /var/tmp/* /usr/share/doc/*

# Fake user to maps with the one on the host
COPY entrypoint /
ARG USER_ID
RUN addgroup --gid 1000 app && \
adduser --system --uid $USER_ID --home /home/app --shell /bin/bash app
RUN addgroup --gid $USER_ID app && \
adduser --system --uid $USER_ID --home /home/app --shell /bin/bash app && \
curl -Ls https://github.com/tianon/gosu/releases/download/1.16/gosu-amd64 | \
install /dev/stdin /usr/local/bin/gosu && \
sed "s/{{ application_user }}/app/g" -i /entrypoint

# Configuration
COPY base/php-configuration /etc/php/${PHP_VERSION}

WORKDIR /home/app/application
ENTRYPOINT [ "/entrypoint" ]

FROM php-base as frontend

Expand Down Expand Up @@ -94,5 +103,3 @@ RUN mkdir -p "/home/app/.composer/cache" \

ENV PATH="$PATH:/home/app/application/tools/php-cs-fixer/vendor/bin"
ENV PATH="$PATH:/home/app/application/tools/phpstan/vendor/bin"

USER app
26 changes: 26 additions & 0 deletions infrastructure/docker/services/php/entrypoint
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
#!/bin/sh

set -e
set -u

if [ $(id -u) != 0 ]; then
echo "Running this image as non root is not allowed"
exit 1
fi

: "${UID:=0}"
: "${GID:=${UID}}"

if [ "$#" = 0 ]; then
set -- "$(command -v bash 2>/dev/null || command -v sh)" -l
fi

if [ "$UID" != 0 ]; then
usermod -u "$UID" "{{ application_user }}" >/dev/null 2>/dev/null && {
groupmod -g "$GID" "{{ application_user }}" >/dev/null 2>/dev/null ||
usermod -a -G "$GID" "{{ application_user }}" >/dev/null 2>/dev/null
}
set -- gosu "${UID}:${GID}" "${@}"
fi

exec "$@"
3 changes: 0 additions & 3 deletions infrastructure/docker/services/postgres/Dockerfile

This file was deleted.

6 changes: 5 additions & 1 deletion infrastructure/docker/services/router/Dockerfile
Original file line number Diff line number Diff line change
@@ -1,3 +1,7 @@
FROM traefik:v2.7

COPY etc/. /etc/
LABEL org.opencontainers.image.source https://github.com/jolicode/monologue

COPY traefik /etc/traefik

VOLUME [ "/etc/ssl/certs" ]
Empty file.
5 changes: 3 additions & 2 deletions infrastructure/docker/services/router/generate-ssl.sh
Original file line number Diff line number Diff line change
Expand Up @@ -4,9 +4,10 @@

BASE=$(dirname $0)

rm -rf mkdir $BASE/certs/

CERTS_DIR=$BASE/etc/ssl/certs
CERTS_DIR=$BASE/certs

rm -rf mkdir $CERTS_DIR

mkdir -p $CERTS_DIR

Expand Down

0 comments on commit 61cc359

Please sign in to comment.