diff --git a/Dockerfile b/Dockerfile deleted file mode 100644 index 783f521f9..000000000 --- a/Dockerfile +++ /dev/null @@ -1,118 +0,0 @@ -FROM alpine:latest - -# Build-time metadata as defined at http://label-schema.org -ARG BUILD_DATE -ARG VCS_REF -ARG COMMIT -ARG VERSION -LABEL org.label-schema.build-date=$BUILD_DATE \ - org.label-schema.name="MonicaHQ, the Personal Relationship Manager" \ - org.label-schema.description="This is MonicaHQ, your personal memory! MonicaHQ is like a CRM but for the friends, family, and acquaintances around you." \ - org.label-schema.url="https://monicahq.com" \ - org.label-schema.vcs-ref=$VCS_REF \ - org.label-schema.vcs-url="https://github.com/monicahq/monica" \ - org.label-schema.vendor="Monica" \ - org.label-schema.version=$VERSION \ - org.label-schema.schema-version="1.0" - -EXPOSE 80:80 - -RUN apk update && apk upgrade -RUN apk add --virtual .build-deps \ - curl openssl bash -RUN apk add apache2 make netcat-openbsd \ - #- base - php7 php7-apache2 php7-intl php7-openssl php7-ctype \ - php7-zip php7-zlib \ - php7-redis \ - #- Authentication Guards - php7-session php7-tokenizer \ - #- laravel/cashier sabre/vobject sabre/xml - php7-dom \ - #- intervention/image - php7-fileinfo \ - #- laravel/cashier - php7-gd \ - #- composer - php7-phar php7-json php7-iconv \ - #- laravel/framework sabre/vobject - php7-mbstring \ - #- league/flysystem-aws-s3-v3 - php7-simplexml \ - #- sabre/vobject sabre/xml - php7-xml php7-xmlreader php7-xmlwriter \ - #- mysql - php7-mysqli php7-pdo_mysql \ - #- pgsql - php7-pgsql php7-pdo_pgsql \ - #- vinkla/hashids - php7-bcmath \ - #- sentry/sentry - php7-curl \ - #- cbor-php (webauthn) - php7-gmp -# Create apache2 dir needed for httpd -RUN mkdir -p /run/apache2 - -# Create a user to own all the code and assets and give them a working -# directory -RUN adduser -D monica apache -h /var/www/monica -WORKDIR /var/www/monica - -# Copy the local (outside Docker) source into the working directory, -# copy system files into their proper homes, and set file ownership -# correctly -COPY readme.md \ - CONTRIBUTING.md \ - CHANGELOG \ - CONTRIBUTORS \ - LICENSE \ - .env.example \ - artisan \ - composer.json \ - composer.lock \ - package.json \ - app.json \ - nginx_app.conf \ - webpack.mix.js \ - yarn.lock \ - ./ -COPY app ./app -COPY bootstrap ./bootstrap -COPY config ./config -COPY database ./database -COPY public ./public -COPY resources ./resources -COPY routes ./routes -COPY scripts ./scripts - -RUN echo $VCS_REF > .sentry-release -RUN echo $COMMIT > .sentry-commit -RUN mkdir -p bootstrap/cache -RUN mkdir -p storage -COPY .env.example .env -RUN chown -R monica:monica . -RUN chgrp -R apache bootstrap/cache storage -RUN chmod -R g+w bootstrap/cache storage - -# Sentry -RUN mkdir -p /root/.local/bin -RUN curl -sL https://sentry.io/get-cli/ | INSTALL_DIR=/root/.local/bin bash - -# Apache2 conf -COPY scripts/docker/000-default.conf /etc/apache2/conf.d/ -# Composer installation -RUN scripts/docker/install-composer.sh -# Set crontab for schedules -RUN echo '* * * * * /usr/bin/php /var/www/monica/artisan schedule:run' | crontab -u monica - -# Cleanup -RUN apk del .build-deps && rm -rf /var/cache/apk/* - -# Install composer dependencies and prepare permissions for Apache -USER monica -RUN composer install --no-interaction --no-suggest --no-dev -RUN composer clear-cache -USER root - -# This is the command that the container will run by default -ENTRYPOINT ["make", "-f", "/var/www/monica/scripts/docker/Makefile"] diff --git a/Dockerfile b/Dockerfile new file mode 120000 index 000000000..b021e899f --- /dev/null +++ b/Dockerfile @@ -0,0 +1 @@ +scripts/docker/apache/Dockerfile \ No newline at end of file diff --git a/Makefile b/Makefile index 1d81bac3e..64b24eea2 100644 --- a/Makefile +++ b/Makefile @@ -72,29 +72,51 @@ docker: $(MAKE) docker_tag $(MAKE) docker_push -docker_build: +docker_build: docker_build_apache docker_build_fpm + +docker_build_apache: docker build \ --build-arg BUILD_DATE=$(shell date -u +"%Y-%m-%dT%H:%M:%SZ") \ --build-arg VCS_REF=$(GIT_REF) \ --build-arg COMMIT=$(GIT_COMMIT) \ --build-arg VERSION=$(BUILD) \ + -f scripts/docker/apache/Dockerfile \ -t $(DOCKER_IMAGE) . docker images +docker_build_fpm: + docker build \ + --build-arg BUILD_DATE=$(shell date -u +"%Y-%m-%dT%H:%M:%SZ") \ + --build-arg VCS_REF=$(GIT_REF) \ + --build-arg COMMIT=$(GIT_COMMIT) \ + --build-arg VERSION=$(BUILD) \ + -f scripts/docker/fpm/Dockerfile \ + -t $(DOCKER_IMAGE):fpm . + docker images + DOCKER_SQUASH := $(shell which docker-squash) ifeq ($(DOCKER_SQUASH),) DOCKER_SQUASH := ~/.local/bin/docker-squash endif docker_squash: - $(DOCKER_SQUASH) -f $(shell docker image ls -q `head -n 1 Dockerfile | cut -d ' ' -f 2`) -t $(DOCKER_IMAGE):latest $(DOCKER_IMAGE):latest + $(DOCKER_SQUASH) -f $(shell docker image ls -q `head -n 1 scripts/docker/apache/Dockerfile | cut -d ' ' -f 2`) -t $(DOCKER_IMAGE):latest $(DOCKER_IMAGE):latest + $(DOCKER_SQUASH) -f $(shell docker image ls -q `head -n 1 scripts/docker/fpm/Dockerfile | cut -d ' ' -f 2`) -t $(DOCKER_IMAGE):fpm $(DOCKER_IMAGE):fpm docker images docker_tag: - docker tag $(DOCKER_IMAGE) $(DOCKER_IMAGE):$(BUILD) + docker tag $(DOCKER_IMAGE):latest $(DOCKER_IMAGE):$(BUILD) + docker tag $(DOCKER_IMAGE):latest $(DOCKER_IMAGE):apache + docker tag $(DOCKER_IMAGE):latest $(DOCKER_IMAGE):$(BUILD)-apache + docker tag $(DOCKER_IMAGE):fpm $(DOCKER_IMAGE):$(BUILD)-fpm + docker images docker_push: docker_tag docker push $(DOCKER_IMAGE):$(BUILD) + docker push $(DOCKER_IMAGE):$(BUILD)-apache + docker push $(DOCKER_IMAGE):apache + docker push $(DOCKER_IMAGE):$(BUILD)-fpm + docker push $(DOCKER_IMAGE):fpm docker push $(DOCKER_IMAGE):latest docker_push_bintray: .deploy.json @@ -102,7 +124,7 @@ docker_push_bintray: .deploy.json docker push monicahq-docker-docker.bintray.io/$(DOCKER_IMAGE):$(BUILD) BUILD=$(BUILD) scripts/tests/fix-bintray.sh -.PHONY: docker docker_build docker_tag docker_push docker_push_bintray +.PHONY: docker docker_build docker_build_apache docker_build_fpm docker_tag docker_push docker_push_bintray build: composer install --no-interaction --no-suggest --ignore-platform-reqs diff --git a/scripts/docker/000-default.conf b/scripts/docker/000-default.conf index ac19843ad..31065d252 100644 --- a/scripts/docker/000-default.conf +++ b/scripts/docker/000-default.conf @@ -1,44 +1,30 @@ LoadModule rewrite_module modules/mod_rewrite.so - - # The ServerName directive sets the request scheme, hostname and port that - # the server uses to identify itself. This is used when creating - # redirection URLs. In the context of virtual hosts, the ServerName - # specifies what hostname must appear in the request's Host: header to - # match this virtual host. For the default virtual host (this file) this - # value is not decisive as it is used as a last resort host regardless. - # However, you must set it for any further virtual host explicitly. - #ServerName www.example.com +ServerName localhost + ServerAdmin webmaster@localhost DocumentRoot /var/www/monica/public - - # Available loglevels: trace8, ..., trace1, debug, info, notice, warn, - # error, crit, alert, emerg. - # It is also possible to configure the loglevel for particular - # modules, e.g. - #LogLevel info ssl:warn - - ErrorLog logs/error.log - CustomLog logs/access.log combined - - ErrorLog /proc/self/fd/2 - CustomLog /proc/self/fd/1 combined - - - # For most configuration files from conf-available/, which are - # enabled or disabled at a global level, it is possible to - # include a line for only one particular virtual host. For example the - # following line enables the CGI configuration for this host only - # after it has been globally disabled with "a2disconf". - #Include conf-available/serve-cgi-bin.conf - Options Indexes FollowSymLinks AllowOverride All Require all granted + + + ProxyPassMatch ^/(.*\.php(/.*)?)$ fcgi://127.0.0.1:9000/var/www/monica/public/$1 + DirectoryIndex index.php + + + + ErrorLog logs/error.log + CustomLog logs/access.log combined + + ErrorLog /dev/stderr + CustomLog /dev/stdout combined + + # vim: syntax=apache ts=4 sw=4 sts=4 sr noet \ No newline at end of file diff --git a/scripts/docker/Makefile b/scripts/docker/Makefile deleted file mode 100644 index f4f448772..000000000 --- a/scripts/docker/Makefile +++ /dev/null @@ -1,10 +0,0 @@ -ROOT_DIR:=$(shell dirname $(realpath $(lastword $(MAKEFILE_LIST)))) - -test_server: waitfordb - $(ROOT_DIR)/test-server.sh - -shell: - /bin/sh - -waitfordb: - $(ROOT_DIR)/waitfordb.sh diff --git a/scripts/docker/apache-arm/Dockerfile b/scripts/docker/apache-arm/Dockerfile new file mode 100644 index 000000000..a89c01f6c --- /dev/null +++ b/scripts/docker/apache-arm/Dockerfile @@ -0,0 +1,124 @@ +FROM arm32v6/alpine:latest + +# Build-time metadata as defined at http://label-schema.org +ARG BUILD_DATE +ARG VCS_REF +ARG COMMIT +ARG VERSION +LABEL org.label-schema.build-date=$BUILD_DATE \ + org.label-schema.name="MonicaHQ, the Personal Relationship Manager" \ + org.label-schema.description="This is MonicaHQ, your personal memory! MonicaHQ is like a CRM but for the friends, family, and acquaintances around you." \ + org.label-schema.url="https://monicahq.com" \ + org.label-schema.vcs-ref=$VCS_REF \ + org.label-schema.vcs-url="https://github.com/monicahq/monica" \ + org.label-schema.vendor="Monica" \ + org.label-schema.version=$VERSION \ + org.label-schema.schema-version="1.0" + +RUN apk update && apk upgrade +RUN apk add --virtual .build-deps \ + curl openssl bash +RUN apk add netcat-openbsd \ + #- base + php7 php7-intl php7-openssl php7-ctype \ + php7-zip php7-zlib \ + php7-redis \ + #- Authentication Guards + php7-session php7-tokenizer \ + #- laravel/cashier sabre/vobject sabre/xml + php7-dom \ + #- intervention/image + php7-fileinfo \ + #- laravel/cashier + php7-gd \ + #- composer + php7-phar php7-json php7-iconv \ + #- laravel/framework sabre/vobject + php7-mbstring \ + #- league/flysystem-aws-s3-v3 + php7-simplexml \ + #- sabre/vobject sabre/xml + php7-xml php7-xmlreader php7-xmlwriter \ + #- mysql + php7-mysqli php7-pdo_mysql \ + #- pgsql + php7-pgsql php7-pdo_pgsql \ + #- vinkla/hashids + php7-bcmath \ + #- sentry/sentry + php7-curl \ + #- cbor-php (webauthn) + php7-gmp + +RUN apk add apache2 php7-apache2 + +# Create a user to own all the code and assets and give them a working +# directory +RUN mkdir -p /var/www/monica +RUN grep -q apache /etc/group || addgroup -S apache +RUN adduser -D monica apache -h /var/www/monica +WORKDIR /var/www/monica + +# Copy the local (outside Docker) source into the working directory, +# copy system files into their proper homes, and set file ownership +# correctly +COPY readme.md \ + CONTRIBUTING.md \ + CHANGELOG \ + CONTRIBUTORS \ + LICENSE \ + .env.example \ + artisan \ + composer.json \ + composer.lock \ + ./ +COPY app ./app +COPY bootstrap ./bootstrap +COPY config ./config +COPY database ./database +COPY public ./public +COPY resources ./resources +COPY routes ./routes + +RUN mkdir -p bootstrap/cache +RUN mkdir -p storage +COPY .env.example .env + +# Sentry +RUN echo $VCS_REF > .sentry-release +RUN echo $COMMIT > .sentry-commit +RUN mkdir -p /root/.local/bin +RUN curl -sL https://sentry.io/get-cli/ | INSTALL_DIR=/root/.local/bin bash + +RUN chown -R monica:monica . +RUN chgrp -R apache bootstrap/cache storage +RUN chmod -R g+w bootstrap/cache storage + +# Apache2 +COPY scripts/docker/apache2-foreground \ + /usr/local/bin/ +COPY scripts/docker/000-default.conf /etc/apache2/conf.d/ + +# Composer installation +COPY scripts/docker/install-composer.sh /usr/local/bin/ +RUN install-composer.sh + +# Set crontab for schedules +RUN echo -e "#!/bin/sh\n/usr/bin/php /var/www/monica/artisan schedule:run -v" > /etc/periodic/hourly/monica && \ + chmod a+x /etc/periodic/hourly/monica + +# Cleanup +RUN apk del .build-deps && \ + rm -rf /var/cache/apk/* + +# Install composer dependencies and prepare permissions for Apache +USER monica +RUN composer install --no-interaction --no-suggest --no-dev +RUN composer clear-cache +USER root + +COPY scripts/docker/entrypoint.sh / +ENTRYPOINT ["/entrypoint.sh"] + +EXPOSE 80 +CMD ["apache2-foreground"] diff --git a/scripts/docker/apache/Dockerfile b/scripts/docker/apache/Dockerfile new file mode 100644 index 000000000..749aad327 --- /dev/null +++ b/scripts/docker/apache/Dockerfile @@ -0,0 +1,127 @@ +FROM alpine:latest + +# Build-time metadata as defined at http://label-schema.org +ARG BUILD_DATE +ARG VCS_REF +ARG COMMIT +ARG VERSION +LABEL org.label-schema.build-date=$BUILD_DATE \ + org.label-schema.name="MonicaHQ, the Personal Relationship Manager" \ + org.label-schema.description="This is MonicaHQ, your personal memory! MonicaHQ is like a CRM but for the friends, family, and acquaintances around you." \ + org.label-schema.url="https://monicahq.com" \ + org.label-schema.vcs-ref=$VCS_REF \ + org.label-schema.vcs-url="https://github.com/monicahq/monica" \ + org.label-schema.vendor="Monica" \ + org.label-schema.version=$VERSION \ + org.label-schema.schema-version="1.0" + +RUN apk update && apk upgrade +RUN apk add --virtual .build-deps \ + curl openssl bash +RUN apk add netcat-openbsd \ + #- base + php7 php7-intl php7-openssl php7-ctype \ + php7-zip php7-zlib \ + php7-redis \ + #- Authentication Guards + php7-session php7-tokenizer \ + #- laravel/cashier sabre/vobject sabre/xml + php7-dom \ + #- intervention/image + php7-fileinfo \ + #- laravel/cashier + php7-gd \ + #- composer + php7-phar php7-json php7-iconv \ + #- laravel/framework sabre/vobject + php7-mbstring \ + #- league/flysystem-aws-s3-v3 + php7-simplexml \ + #- sabre/vobject sabre/xml + php7-xml php7-xmlreader php7-xmlwriter \ + #- mysql + php7-mysqli php7-pdo_mysql \ + #- pgsql + php7-pgsql php7-pdo_pgsql \ + #- vinkla/hashids + php7-bcmath \ + #- sentry/sentry + php7-curl \ + #- cbor-php (webauthn) + php7-gmp \ +# apache variant + apache2 php7-apache2 + +# Create a user to own all the code and assets and give them a working +# directory +RUN mkdir -p /var/www/monica +RUN grep -q apache /etc/group || addgroup -S apache +RUN adduser -D monica apache -h /var/www/monica +WORKDIR /var/www/monica + +# Copy the local (outside Docker) source into the working directory, +# copy system files into their proper homes, and set file ownership +# correctly +COPY readme.md \ + CONTRIBUTING.md \ + CHANGELOG \ + CONTRIBUTORS \ + LICENSE \ + artisan \ + composer.json \ + composer.lock \ + ./ +COPY app ./app +COPY bootstrap ./bootstrap +COPY config ./config +COPY database ./database +COPY public ./public +COPY resources ./resources +COPY routes ./routes + +RUN mkdir -p bootstrap/cache && \ + mkdir -p storage +COPY .env.example .env + +RUN chown -R monica:monica . +RUN chgrp -R apache bootstrap/cache storage +RUN chmod -R g+w bootstrap/cache storage + +# Sentry +RUN echo $VCS_REF > .sentry-release +RUN echo $COMMIT > .sentry-commit +RUN mkdir -p /root/.local/bin && \ + curl -sL https://sentry.io/get-cli/ | INSTALL_DIR=/root/.local/bin bash + +# Composer installation +COPY scripts/docker/install-composer.sh /usr/local/sbin/ +RUN install-composer.sh + +# Install composer dependencies +USER monica +RUN composer install --no-interaction --no-suggest --no-dev +RUN composer clear-cache +USER root + +# Set crontab for schedules +RUN set -ex && \ + cd /etc/periodic/hourly/ && \ + { \ + echo '#!/bin/sh'; \ + echo '/usr/bin/php /var/www/monica/artisan schedule:run -v'; \ + } | tee monica && \ + chmod a+x monica + +# Cleanup +RUN apk del .build-deps && \ + rm -rf /var/cache/apk/* + +COPY scripts/docker/entrypoint.sh . +ENTRYPOINT ["entrypoint.sh"] + +# Apache2 +COPY scripts/docker/apache2-foreground /usr/local/sbin/ +COPY scripts/docker/000-default.conf /etc/apache2/conf.d/ + +EXPOSE 80 +CMD ["apache2-foreground"] diff --git a/scripts/docker/apache2-foreground b/scripts/docker/apache2-foreground new file mode 100755 index 000000000..549977483 --- /dev/null +++ b/scripts/docker/apache2-foreground @@ -0,0 +1,6 @@ +#!/bin/sh + +# Run apache2 +mkdir -p /run/apache2 +rm -f /run/apache2/httpd.pid +httpd -DFOREGROUND "$@" diff --git a/scripts/docker/entrypoint.sh b/scripts/docker/entrypoint.sh new file mode 100755 index 000000000..58cce2bd8 --- /dev/null +++ b/scripts/docker/entrypoint.sh @@ -0,0 +1,60 @@ +#!/bin/sh + +waitfordb() { + echo "Connecting to ${DB_HOST}:${DB_PORT}" + + attempts=0 + max_attempts=30 + while [ $attempts -lt $max_attempts ]; do + nc -z "${DB_HOST}" "${DB_PORT}" && break + echo "Waiting for ${DB_HOST}:${DB_PORT} ..." + sleep 1 + let "attempts=attempts+1" + done + + if [ $attempts -eq $max_attempts ]; then + echo "Unable to contact your database at ${DB_HOST}:${DB_PORT}" + exit 1 + fi + + echo "Waiting for database to settle ..." + sleep 3 +} + +if expr "$1" : "apache" 1>/dev/null || [ "$1" = "php-fpm7" ]; then + + MONICADIR=/var/www/monica + ARTISAN="php ${MONICADIR}/artisan" + + # Ensure storage directories are present + STORAGE=${MONICADIR}/storage + mkdir -p ${STORAGE}/logs + mkdir -p ${STORAGE}/app/public + mkdir -p ${STORAGE}/framework/views + mkdir -p ${STORAGE}/framework/cache + mkdir -p ${STORAGE}/framework/sessions + chown -R monica:apache ${STORAGE} + chmod -R g+rw ${STORAGE} + + if [[ -z "${APP_KEY:-}" || "$APP_KEY" == "ChangeMeBy32KeyLengthOrGenerated" ]]; then + ${ARTISAN} key:generate --no-interaction + else + echo "APP_KEY already set" + fi + + # Run migrations + waitfordb + ${ARTISAN} monica:update --force -v + + if [[ -n "${SENTRY_SUPPORT:-}" && "$SENTRY_SUPPORT" == "true" && -z "${SENTRY_NORELEASE:-}" && -n "${SENTRY_ENV:-}" ]]; then + commit=$(cat .sentry-commit) + release=$(cat .sentry-release) + ${ARTISAN} sentry:release --release="$release" --commit="$commit" --environment="$SENTRY_ENV" -v || true + fi + + # Run cron + crond -b -l 0 -L /dev/stdout + +fi + +exec "$@" diff --git a/scripts/docker/fpm/Dockerfile b/scripts/docker/fpm/Dockerfile new file mode 100644 index 000000000..16fed1d98 --- /dev/null +++ b/scripts/docker/fpm/Dockerfile @@ -0,0 +1,147 @@ +FROM alpine:latest + +# Build-time metadata as defined at http://label-schema.org +ARG BUILD_DATE +ARG VCS_REF +ARG COMMIT +ARG VERSION +LABEL org.label-schema.build-date=$BUILD_DATE \ + org.label-schema.name="MonicaHQ, the Personal Relationship Manager" \ + org.label-schema.description="This is MonicaHQ, your personal memory! MonicaHQ is like a CRM but for the friends, family, and acquaintances around you." \ + org.label-schema.url="https://monicahq.com" \ + org.label-schema.vcs-ref=$VCS_REF \ + org.label-schema.vcs-url="https://github.com/monicahq/monica" \ + org.label-schema.vendor="Monica" \ + org.label-schema.version=$VERSION \ + org.label-schema.schema-version="1.0" + +RUN apk update && apk upgrade +RUN apk add --virtual .build-deps \ + curl openssl bash +RUN apk add netcat-openbsd \ + #- base + php7 php7-intl php7-openssl php7-ctype \ + php7-zip php7-zlib \ + php7-redis \ + #- Authentication Guards + php7-session php7-tokenizer \ + #- laravel/cashier sabre/vobject sabre/xml + php7-dom \ + #- intervention/image + php7-fileinfo \ + #- laravel/cashier + php7-gd \ + #- composer + php7-phar php7-json php7-iconv \ + #- laravel/framework sabre/vobject + php7-mbstring \ + #- league/flysystem-aws-s3-v3 + php7-simplexml \ + #- sabre/vobject sabre/xml + php7-xml php7-xmlreader php7-xmlwriter \ + #- mysql + php7-mysqli php7-pdo_mysql \ + #- pgsql + php7-pgsql php7-pdo_pgsql \ + #- vinkla/hashids + php7-bcmath \ + #- sentry/sentry + php7-curl \ + #- cbor-php (webauthn) + php7-gmp \ +# fpm variant + php7-fpm + +# Create a user to own all the code and assets and give them a working +# directory +RUN mkdir -p /var/www/monica +RUN grep -q apache /etc/group || addgroup -S apache +RUN adduser -D monica apache -h /var/www/monica +WORKDIR /var/www/monica + +# Copy the local (outside Docker) source into the working directory, +# copy system files into their proper homes, and set file ownership +# correctly +COPY readme.md \ + CONTRIBUTING.md \ + CHANGELOG \ + CONTRIBUTORS \ + LICENSE \ + artisan \ + composer.json \ + composer.lock \ + ./ +COPY app ./app +COPY bootstrap ./bootstrap +COPY config ./config +COPY database ./database +COPY public ./public +COPY resources ./resources +COPY routes ./routes + +RUN mkdir -p bootstrap/cache && \ + mkdir -p storage +COPY .env.example .env + +RUN chown -R monica:monica . +RUN chgrp -R apache bootstrap/cache storage +RUN chmod -R g+w bootstrap/cache storage + +# Sentry +RUN echo $VCS_REF > .sentry-release +RUN echo $COMMIT > .sentry-commit +RUN mkdir -p /root/.local/bin && \ + curl -sL https://sentry.io/get-cli/ | INSTALL_DIR=/root/.local/bin bash + +# Composer installation +COPY scripts/docker/install-composer.sh /usr/local/sbin/ +RUN install-composer.sh + +# Install composer dependencies +USER monica +RUN composer install --no-interaction --no-suggest --no-dev +RUN composer clear-cache +USER root + +# Set crontab for schedules +RUN set -ex && \ + cd /etc/periodic/hourly/ && \ + { \ + echo '#!/bin/sh'; \ + echo '/usr/bin/php /var/www/monica/artisan schedule:run -v'; \ + } | tee monica && \ + chmod a+x monica + +# Cleanup +RUN apk del .build-deps && \ + rm -rf /var/cache/apk/* + +COPY scripts/docker/entrypoint.sh . +ENTRYPOINT ["entrypoint.sh"] + +# FPM +RUN set -ex && \ + cd /etc/php7/php-fpm.d && \ + { \ + echo '[global]'; \ + echo 'error_log = /dev/stderr'; \ + echo; \ + echo '[www]'; \ + echo 'access.log = /dev/stdout'; \ + echo 'catch_workers_output = yes'; \ + } | tee docker.conf && \ + { \ + echo '[global]'; \ + echo 'daemonize = no'; \ + echo; \ + echo '[www]'; \ + echo 'group = apache'; \ + echo 'listen = 9000'; \ + } | tee zz-docker.conf + +# Override stop signal to stop process gracefully +# https://github.com/php/php-src/blob/17baa87faddc2550def3ae7314236826bc1b1398/sapi/fpm/php-fpm.8.in#L163 +STOPSIGNAL SIGQUIT + +EXPOSE 9000 +CMD ["php-fpm7"] diff --git a/scripts/docker/fpm/examples/nginx/docker-compose.yml b/scripts/docker/fpm/examples/nginx/docker-compose.yml new file mode 100644 index 000000000..f6372ba23 --- /dev/null +++ b/scripts/docker/fpm/examples/nginx/docker-compose.yml @@ -0,0 +1,42 @@ +version: "3.4" + +services: + app: + build: . + image: monicahq/monicahq:fpm + depends_on: + - mysql + env_file: .env + volumes: + - monica_data:/var/www/monica/storage + - monica_www:/var/www/monica + restart: always + + web: + build: ./web + restart: always + ports: + - 80:80 + volumes: + - monica_www:/var/www/monica:ro + depends_on: + - app + + mysql: + image: mysql:5.7 + environment: + - MYSQL_ROOT_PASSWORD=sekret_root_password + - MYSQL_DATABASE=monica + - MYSQL_USER=homestead + - MYSQL_PASSWORD=secret + volumes: + - monica_mysql:/var/lib/mysql + restart: always + +volumes: + monica_data: + name: monica_data + monica_www: + name: monica_www + monica_mysql: + name: monica_mysql diff --git a/scripts/docker/fpm/examples/nginx/web/Dockerfile b/scripts/docker/fpm/examples/nginx/web/Dockerfile new file mode 100644 index 000000000..9e620aff0 --- /dev/null +++ b/scripts/docker/fpm/examples/nginx/web/Dockerfile @@ -0,0 +1,3 @@ +FROM nginx:alpine + +COPY nginx.conf /etc/nginx/nginx.conf diff --git a/scripts/docker/fpm/examples/nginx/web/nginx.conf b/scripts/docker/fpm/examples/nginx/web/nginx.conf new file mode 100644 index 000000000..42bb6c89d --- /dev/null +++ b/scripts/docker/fpm/examples/nginx/web/nginx.conf @@ -0,0 +1,140 @@ +worker_processes 1; + +error_log /var/log/nginx/error.log warn; +pid /var/run/nginx.pid; + + +events { + worker_connections 1024; +} + + +http { + include /etc/nginx/mime.types; + default_type application/octet-stream; + + 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 /var/log/nginx/access.log main; + + sendfile on; + #tcp_nopush on; + + keepalive_timeout 65; + + #gzip on; + + upstream php-handler { + server app:9000; + } + + server { + listen 80; + + # Add headers to serve security related headers + # Before enabling Strict-Transport-Security headers please read into this + # topic first. + # add_header Strict-Transport-Security "max-age=15768000; + # includeSubDomains; preload;"; + # + # WARNING: Only add the preload option once you read about + # the consequences in https://hstspreload.org/. This option + # will add the domain to a hardcoded list that is shipped + # in all major browsers and getting removed from this list + # could take several months. + add_header X-Content-Type-Options nosniff; + add_header X-XSS-Protection "1; mode=block"; + add_header X-Robots-Tag none; + add_header X-Download-Options noopen; + add_header X-Permitted-Cross-Domain-Policies none; + add_header Referrer-Policy no-referrer; + + root /var/www/monica/public; + + location ~ ^/(?:robots.txt|security.txt) { + allow all; + log_not_found off; + access_log off; + } + + location = /.well-known/carddav { + return 301 $scheme://$host/dav; + } + location = /.well-known/caldav { + return 301 $scheme://$host/dav; + } + location = /.well-known/security.txt { + return 301 $scheme://$host/security.txt; + } + + # set max upload size + client_max_body_size 10G; + fastcgi_buffers 64 4K; + + # Enable gzip but do not remove ETag headers + gzip on; + gzip_vary on; + gzip_comp_level 4; + gzip_min_length 256; + gzip_proxied expired no-cache no-store private no_last_modified no_etag auth; + gzip_types application/atom+xml application/javascript application/json application/ld+json application/manifest+json application/rss+xml application/vnd.geo+json application/vnd.ms-fontobject application/x-font-ttf application/x-web-app-manifest+json application/xhtml+xml application/xml font/opentype image/bmp image/svg+xml image/x-icon text/cache-manifest text/css text/plain text/vcard text/vnd.rim.location.xloc text/vtt text/x-component text/x-cross-domain-policy; + + # Uncomment if your server is build with the ngx_pagespeed module + # This module is currently not supported. + #pagespeed off; + + location / { + rewrite ^ /index.php$request_uri; + } + + location ~ ^/(?:index)\.php(?:$|/) { + fastcgi_split_path_info ^(.+\.php)(/.*)$; + include fastcgi_params; + fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name; + fastcgi_param PATH_INFO $fastcgi_path_info; + # fastcgi_param HTTPS on; + #Avoid sending the security headers twice + fastcgi_param modHeadersAvailable true; + fastcgi_param front_controller_active true; + fastcgi_pass php-handler; + fastcgi_intercept_errors on; + fastcgi_request_buffering off; + } + + # Adding the cache control header for js and css files + # Make sure it is BELOW the PHP block + location ~ \.(?:css|js|woff2?|svg|gif|json)$ { + try_files $uri /index.php$request_uri; + add_header Cache-Control "public, max-age=15778463"; + # Add headers to serve security related headers (It is intended to + # have those duplicated to the ones above) + # Before enabling Strict-Transport-Security headers please read into + # this topic first. + # add_header Strict-Transport-Security "max-age=15768000; + # includeSubDomains; preload;"; + # + # WARNING: Only add the preload option once you read about + # the consequences in https://hstspreload.org/. This option + # will add the domain to a hardcoded list that is shipped + # in all major browsers and getting removed from this list + # could take several months. + add_header X-Content-Type-Options nosniff; + add_header X-XSS-Protection "1; mode=block"; + add_header X-Robots-Tag none; + add_header X-Download-Options noopen; + add_header X-Permitted-Cross-Domain-Policies none; + add_header Referrer-Policy no-referrer; + + # Optional: Don't log access to assets + access_log off; + } + + location ~ \.(?:png|html|ttf|ico|jpg|jpeg)$ { + try_files $uri /index.php$request_uri; + # Optional: Don't log access to assets + access_log off; + } + } +} diff --git a/scripts/docker/install-composer.sh b/scripts/docker/install-composer.sh index ed1a21e8a..a3a17dea9 100755 --- a/scripts/docker/install-composer.sh +++ b/scripts/docker/install-composer.sh @@ -1,5 +1,7 @@ #!/bin/sh +set -v + SETUP=composer-setup.php cd /tmp diff --git a/scripts/docker/test-server.sh b/scripts/docker/test-server.sh deleted file mode 100755 index 5ebe703df..000000000 --- a/scripts/docker/test-server.sh +++ /dev/null @@ -1,36 +0,0 @@ -#!/bin/sh - -MONICADIR=/var/www/monica -ARTISAN="php ${MONICADIR}/artisan" - -# Ensure storage directories are present -STORAGE=${MONICADIR}/storage -mkdir -p ${STORAGE}/logs -mkdir -p ${STORAGE}/app/public -mkdir -p ${STORAGE}/framework/views -mkdir -p ${STORAGE}/framework/cache -mkdir -p ${STORAGE}/framework/sessions -chown -R monica:apache ${STORAGE} -chmod -R g+rw ${STORAGE} - -if [[ -z ${APP_KEY:-} || "$APP_KEY" == "ChangeMeBy32KeyLengthOrGenerated" ]]; then - ${ARTISAN} key:generate --no-interaction -else - echo "APP_KEY already set" -fi - -# Run migrations -${ARTISAN} monica:update --force -v - -if [[ -n ${SENTRY_SUPPORT:-} && $SENTRY_SUPPORT && -z ${SENTRY_NORELEASE:-} ]]; then - commit=$(cat .sentry-commit) - release=$(cat .sentry-release) - ${ARTISAN} sentry:release --release=$release --commit=$commit --environment=$SENTRY_ENV -v || true -fi - -# Run cron -crond -b & - -# Run apache2 -rm -f /run/apache2/httpd.pid -httpd -DFOREGROUND diff --git a/scripts/docker/waitfordb.sh b/scripts/docker/waitfordb.sh deleted file mode 100755 index 14e6ad54c..000000000 --- a/scripts/docker/waitfordb.sh +++ /dev/null @@ -1,20 +0,0 @@ -#!/bin/sh - -echo "Connecting to ${DB_HOST}:${DB_PORT}" - -attempts=0 -max_attempts=30 -while [ $attempts -lt $max_attempts ]; do - nc -z "${DB_HOST}" "${DB_PORT}" && break - echo "Waiting for ${DB_HOST}:${DB_PORT} ..." - sleep 1 - let "attempts=attempts+1" -done - -if [ $attempts -eq $max_attempts ]; then - echo "Unable to contact your database at ${DB_HOST}:${DB_PORT}" - exit 1 -fi - -echo "Waiting for database to settle ..." -sleep 3