diff --git a/.gitignore b/.gitignore index aafda3a..33f2691 100644 --- a/.gitignore +++ b/.gitignore @@ -1,2 +1,3 @@ .vscode .idea +**/.DS_Store \ No newline at end of file diff --git a/Dockerfile b/Dockerfile index b1910e4..702f1c7 100644 --- a/Dockerfile +++ b/Dockerfile @@ -3,9 +3,6 @@ ARG PHP_VERSION=8.2 ARG COMPOSER_VERSION=latest -# Accepted values: swoole - roadrunner -ARG OCTANE_SERVER="swoole" - ########################################### # Build frontend assets with PNPM ########################################### @@ -16,58 +13,30 @@ FROM node:${NODE_VERSION} as build ENV ROOT=/var/www/html -WORKDIR $ROOT +WORKDIR ${ROOT} RUN npm install -g pnpm COPY package.json pnpm-lock.yaml* ./ -RUN if [ -f $ROOT/pnpm-lock.yaml ]; \ +RUN if [ -f ${ROOT}/pnpm-lock.yaml ]; \ then \ pnpm install --frozen-lockfile --no-optional --prefer-offline; \ - elif [ -f $ROOT/package.json ]; \ + elif [ -f ${ROOT}/package.json ]; \ then \ pnpm install --no-optional --prefer-offline; \ fi COPY . . -RUN if [ -f $ROOT/package.json ] || [ -f $ROOT/pnpm-lock.yaml ]; \ +RUN if [ -f ${ROOT}/package.json ] || [ -f ${ROOT}/pnpm-lock.yaml ]; \ then \ pnpm run build; \ fi ########################################### -# PHP dependencies -########################################### FROM composer:${COMPOSER_VERSION} AS vendor -ARG OCTANE_SERVER -WORKDIR /var/www/html -COPY composer* ./ -RUN composer install \ - --no-dev \ - --no-interaction \ - --prefer-dist \ - --ignore-platform-reqs \ - --optimize-autoloader \ - --apcu-autoloader \ - --ansi \ - --no-scripts \ - --audit - -########################################### -# RoadRunner binary -########################################### - -RUN if [ ${OCTANE_SERVER} = "roadrunner" ]; then \ - if composer show | grep spiral/roadrunner-cli >/dev/null; then \ - ./vendor/bin/rr get-binary; else \ - echo "spiral/roadrunner-cli package is not installed. exiting..."; exit 1; \ - fi \ - fi - -########################################### FROM php:${PHP_VERSION}-cli-bookworm @@ -77,7 +46,8 @@ ARG WWWUSER=1000 ARG WWWGROUP=1000 ARG TZ=UTC -ARG OCTANE_SERVER +# Accepted values: swoole - roadrunner +ARG OCTANE_SERVER="swoole" # Accepted values: app - horizon - scheduler ARG CONTAINER_MODE=app @@ -94,12 +64,12 @@ ENV DEBIAN_FRONTEND=noninteractive \ NON_ROOT_USER=octane ENV ROOT=/var/www/html -WORKDIR $ROOT +WORKDIR ${ROOT} SHELL ["/bin/bash", "-eou", "pipefail", "-c"] -RUN ln -snf /usr/share/zoneinfo/$TZ /etc/localtime \ - && echo $TZ > /etc/timezone +RUN ln -snf /usr/share/zoneinfo/${TZ} /etc/localtime \ + && echo ${TZ} > /etc/timezone RUN apt-get update; \ apt-get upgrade -yqq; \ @@ -107,11 +77,12 @@ RUN apt-get update; \ apt-get install -yqq --no-install-recommends --show-progress \ apt-utils \ gnupg \ - gosu \ git \ curl \ wget \ nano \ + rsync \ + sqlite3 \ libcurl4-openssl-dev \ ca-certificates \ supervisor \ @@ -121,194 +92,68 @@ RUN apt-get update; \ libpq-dev \ libjpeg-dev \ libpng-dev \ + librsvg2-bin \ libfreetype6-dev \ libssl-dev \ libwebp-dev \ libmcrypt-dev \ + libldap2-dev \ libonig-dev \ + libmagickwand-dev \ libzip-dev zip unzip \ libargon2-1 \ libidn2-0 \ libpcre2-8-0 \ + librdkafka-dev \ libpcre3 \ libxml2 \ + libxslt-dev \ libzstd1 \ + libc-ares-dev \ procps \ - libbz2-dev - - -########################################### -# bzip2 -########################################### - -RUN docker-php-ext-install bz2; - -########################################### -# pdo_mysql -########################################### - -RUN docker-php-ext-install pdo_mysql; - -########################################### -# zip -########################################### - -RUN docker-php-ext-configure zip && docker-php-ext-install zip; - -########################################### -# mbstring -########################################### - -RUN docker-php-ext-install mbstring; - -########################################### -# GD -########################################### - -RUN docker-php-ext-configure gd \ + postgresql-client \ + postgis \ + default-mysql-client \ + libbz2-dev \ + zlib1g-dev \ + libicu-dev \ + g++ \ + # Install PHP extensions + && docker-php-ext-install \ + bz2 \ + pcntl \ + mbstring \ + bcmath \ + sockets \ + pgsql \ + pdo_pgsql \ + opcache \ + && docker-php-ext-configure pdo_mysql --with-pdo-mysql=mysqlnd && docker-php-ext-install pdo_mysql \ + && docker-php-ext-configure zip && docker-php-ext-install zip \ + && docker-php-ext-configure intl && docker-php-ext-install intl \ + && docker-php-ext-configure gd \ --prefix=/usr \ --with-jpeg \ --with-webp \ - --with-freetype \ - && docker-php-ext-install gd; - -########################################### -# OPcache -########################################### - -ARG INSTALL_OPCACHE=true - -RUN if [ ${INSTALL_OPCACHE} = true ]; then \ - docker-php-ext-install opcache; \ - fi - -########################################### -# PHP Redis -########################################### - -ARG INSTALL_PHPREDIS=true - -RUN if [ ${INSTALL_PHPREDIS} = true ]; then \ - pecl -q install -o -f redis \ - && rm -rf /tmp/pear \ - && docker-php-ext-enable redis; \ - fi - -########################################### -# PCNTL -########################################### - -ARG INSTALL_PCNTL=true - -RUN if [ ${INSTALL_PCNTL} = true ]; then \ - docker-php-ext-install pcntl; \ - fi - -########################################### -# BCMath -########################################### - -ARG INSTALL_BCMATH=true - -RUN if [ ${INSTALL_BCMATH} = true ]; then \ - docker-php-ext-install bcmath; \ - fi - -########################################### -# RDKAFKA -########################################### - -ARG INSTALL_RDKAFKA=true - -RUN if [ ${INSTALL_RDKAFKA} = true ]; then \ - apt-get install -yqq --no-install-recommends --show-progress librdkafka-dev \ - && pecl -q install -o -f rdkafka \ - && docker-php-ext-enable rdkafka; \ - fi - -########################################### -# OpenSwoole/Swoole extension -########################################### - -ARG SERVER=swoole - -RUN if [ ${OCTANE_SERVER} = "swoole" ]; then \ - apt-get install -yqq --no-install-recommends --show-progress libc-ares-dev \ - && printf "\n" | pecl -q install -o -f -D 'enable-openssl="yes" enable-http2="yes" enable-swoole-curl="yes" enable-mysqlnd="yes" enable-cares="yes"' ${SERVER} \ - && docker-php-ext-enable ${SERVER}; \ - fi - -########################################################################### -# Human Language and Character Encoding Support -########################################################################### - -ARG INSTALL_INTL=true - -RUN if [ ${INSTALL_INTL} = true ]; then \ - apt-get install -yqq --no-install-recommends --show-progress zlib1g-dev libicu-dev g++ \ - && docker-php-ext-configure intl \ - && docker-php-ext-install intl; \ - fi - -########################################### -# Memcached -########################################### - -ARG INSTALL_MEMCACHED=false - -RUN if [ ${INSTALL_MEMCACHED} = true ]; then \ - pecl -q install -o -f memcached && docker-php-ext-enable memcached; \ - fi - -########################################### -# MySQL Client -########################################### - -ARG INSTALL_MYSQL_CLIENT=true - -RUN if [ ${INSTALL_MYSQL_CLIENT} = true ]; then \ - apt-get install -yqq --no-install-recommends --show-progress default-mysql-client; \ - fi - -########################################### -# pdo_pgsql -########################################### - -ARG INSTALL_PDO_PGSQL=false - -RUN if [ ${INSTALL_PDO_PGSQL} = true ]; then \ - docker-php-ext-install pdo_pgsql; \ - fi - -########################################### -# pgsql -########################################### - -ARG INSTALL_PGSQL=false - -RUN if [ ${INSTALL_PGSQL} = true ]; then \ - docker-php-ext-install pgsql; \ - fi - -########################################### -# pgsql client and postgis -########################################### - -ARG INSTALL_PG_CLIENT=false -ARG INSTALL_POSTGIS=false - -RUN if [ ${INSTALL_PG_CLIENT} = true ]; then \ - apt-get install -yqq gnupg \ - && . /etc/os-release \ - && echo "deb http://apt.postgresql.org/pub/repos/apt $VERSION_CODENAME-pgdg main" > /etc/apt/sources.list.d/pgdg.list \ - && curl -sL https://www.postgresql.org/media/keys/ACCC4CF8.asc | apt-key add - \ - && apt-get update -yqq \ - && apt-get install -yqq --no-install-recommends --show-progress postgresql-client-12 postgis; \ - if [ ${INSTALL_POSTGIS} = true ]; then \ - apt-get install -yqq --no-install-recommends --show-progress postgis; \ + --with-freetype && docker-php-ext-install gd \ + && pecl -q install -o -f redis && docker-php-ext-enable redis \ + && pecl -q install -o -f imagick && docker-php-ext-enable imagick \ + && pecl -q install -o -f rdkafka && docker-php-ext-enable rdkafka \ + && pecl -q install -o -f memcached && docker-php-ext-enable memcached \ + && pecl -q install -o -f igbinary && docker-php-ext-enable igbinary \ + && docker-php-ext-configure ldap --with-libdir=lib/$(gcc -dumpmachine) && docker-php-ext-install ldap \ + && if [ ${OCTANE_SERVER} = "swoole" ]; then \ + printf "\n" | pecl -q install -o -f -D 'enable-openssl="yes" enable-http2="yes" enable-swoole-curl="yes" enable-mysqlnd="yes" enable-cares="yes"' swoole \ + && docker-php-ext-enable swoole; \ fi \ - && apt-get purge -yqq gnupg; \ - fi + && apt-get -y autoremove \ + && apt-get clean \ + && docker-php-source delete \ + && pecl clear-cache \ + && rm -R /tmp/pear \ + && rm -rf /var/lib/apt/lists/* /tmp/* /var/tmp/* \ + && rm /var/log/lastlog /var/log/faillog + ########################################### # Laravel scheduler @@ -324,43 +169,62 @@ RUN if [ ${CONTAINER_MODE} = 'scheduler' ] || [ ${APP_WITH_SCHEDULER} = true ]; ########################################### -RUN apt-get clean \ - && docker-php-source delete \ - && pecl clear-cache \ - && rm -R /tmp/pear \ - && rm -rf /var/lib/apt/lists/* /tmp/* /var/tmp/* \ - && rm /var/log/lastlog /var/log/faillog +RUN userdel --remove --force www-data \ + && groupadd --force -g ${WWWGROUP} ${NON_ROOT_USER} \ + && useradd -ms /bin/bash --no-log-init --no-user-group -g ${WWWGROUP} -u ${WWWUSER} ${NON_ROOT_USER} -RUN groupadd --force -g $WWWGROUP $NON_ROOT_USER \ - && useradd -ms /bin/bash --no-log-init --no-user-group -g $WWWGROUP -u $WWWUSER $NON_ROOT_USER - -RUN chown -R $NON_ROOT_USER:$NON_ROOT_USER $ROOT /var/log/ +RUN chown -R ${NON_ROOT_USER}:${NON_ROOT_USER} ${ROOT} /var/log/ RUN chmod -R ug+rw /var/log/ -USER $NON_ROOT_USER +USER ${NON_ROOT_USER} -COPY --chown=$NON_ROOT_USER:$NON_ROOT_USER . . -COPY --chown=$NON_ROOT_USER:$NON_ROOT_USER --from=build ${ROOT}/public public -COPY --chown=$NON_ROOT_USER:$NON_ROOT_USER --from=vendor ${ROOT}/vendor vendor -COPY --chown=$NON_ROOT_USER:$NON_ROOT_USER --from=vendor ${ROOT}/rr* ${ROOT}/composer.json ./ +COPY --chown=${NON_ROOT_USER}:${NON_ROOT_USER} --from=vendor /usr/bin/composer /usr/bin/composer +COPY --chown=${NON_ROOT_USER}:${NON_ROOT_USER} composer* ./ + +RUN composer install \ + --no-dev \ + --no-interaction \ + --prefer-dist \ + --no-autoloader \ + --ansi \ + --no-scripts \ + --audit + +COPY --chown=${NON_ROOT_USER}:${NON_ROOT_USER} . . +COPY --chown=${NON_ROOT_USER}:${NON_ROOT_USER} --from=build ${ROOT}/public public RUN mkdir -p \ storage/framework/{sessions,views,cache} \ storage/logs \ bootstrap/cache -COPY --chown=$NON_ROOT_USER:$NON_ROOT_USER deployment/octane/supervisord* /etc/supervisor/conf.d/ -COPY --chown=$NON_ROOT_USER:$NON_ROOT_USER deployment/octane/php.ini /usr/local/etc/php/conf.d/99-octane.ini -COPY --chown=$NON_ROOT_USER:$NON_ROOT_USER deployment/octane/.rr.prod.yaml ./.rr.yaml -COPY --chown=$NON_ROOT_USER:$NON_ROOT_USER deployment/octane/start-container /usr/local/bin/start-container +COPY --chown=${NON_ROOT_USER}:${NON_ROOT_USER} deployment/octane/supervisord* /etc/supervisor/conf.d/ +COPY --chown=${NON_ROOT_USER}:${NON_ROOT_USER} deployment/octane/php.ini /usr/local/etc/php/conf.d/99-octane.ini +COPY --chown=${NON_ROOT_USER}:${NON_ROOT_USER} deployment/octane/.rr.prod.yaml ./.rr.yaml +COPY --chown=${NON_ROOT_USER}:${NON_ROOT_USER} deployment/octane/start-container /usr/local/bin/start-container -RUN chmod +x /usr/local/bin/start-container +RUN composer dump-autoload \ + --optimize \ + --apcu \ + --no-dev \ + --no-interaction \ + && composer clear-cache \ + && php artisan storage:link + +RUN if [ ${OCTANE_SERVER} = "roadrunner" ]; then \ + if composer show | grep spiral/roadrunner-cli >/dev/null; then \ + ./vendor/bin/rr get-binary; else \ + echo "spiral/roadrunner-cli package is not installed. exiting..."; exit 1; \ + fi \ + fi RUN if [ -f "rr" ]; then \ chmod +x rr; \ fi +RUN chmod +x /usr/local/bin/start-container + RUN cat deployment/octane/utilities.sh >> ~/.bashrc EXPOSE 9000 diff --git a/README.md b/README.md index af16345..37ba3e3 100644 --- a/README.md +++ b/README.md @@ -25,27 +25,6 @@ You can build the Docker image in different modes: > If you want to run Scheduler in the Octane container, then you should set `APP_WITH_SCHEDULER` build argument `true`. -## PHP extensions - -And the following PHP extensions are included: - -- [x] OpenSwoole/Swoole with support of OpenSSL, HTTP/2, Native cURL hook for coroutines, `mysqlnd`, and asynchronous DNS. -- [x] OPcache -- [x] Redis -- [x] PCNTL -- [x] BCMath -- [x] RDKAFKA -- [x] INTL -- [x] pdo_mysql -- [x] pdo_pgsql (disabled by default) -- [x] pgsql (disabled by default) -- [x] Memcached (disabled by default) -- [x] zip -- [x] cURL -- [x] GD -- [x] mbstring -- [x] bz2 - ## Usage 1. Clone this repository: diff --git a/deployment/octane/php.ini b/deployment/octane/php.ini index fcb99d9..15e3282 100644 --- a/deployment/octane/php.ini +++ b/deployment/octane/php.ini @@ -7,7 +7,6 @@ realpath_cache_size = 16M realpath_cache_ttl = 360 [Opcache] -opcache.enable = 1 opcache.enable_cli = 1 opcache.memory_consumption = 512M opcache.use_cwd = 0 diff --git a/deployment/octane/start-container b/deployment/octane/start-container index 71b6fe7..bd694f0 100644 --- a/deployment/octane/start-container +++ b/deployment/octane/start-container @@ -7,7 +7,6 @@ echo "Container mode: $container_mode" initialStuff() { php artisan optimize:clear; \ - php artisan package:discover --ansi; \ php artisan event:cache; \ php artisan config:cache; \ php artisan route:cache;