mirror of
https://github.com/solidtime-io/solidtime.git
synced 2026-06-15 13:32:43 +01:00
Moved from swoole to frankenphp
This commit is contained in:
committed by
Constantin Graf
parent
2e8b088c59
commit
7b467807d9
@@ -4,7 +4,7 @@ APP_ENV=production
|
|||||||
APP_DEBUG=false
|
APP_DEBUG=false
|
||||||
APP_FORCE_HTTPS=true
|
APP_FORCE_HTTPS=true
|
||||||
SESSION_SECURE_COOKIE=true
|
SESSION_SECURE_COOKIE=true
|
||||||
OCTANE_SERVER=swoole
|
OCTANE_SERVER=frankenphp
|
||||||
PAGINATION_PER_PAGE_DEFAULT=500
|
PAGINATION_PER_PAGE_DEFAULT=500
|
||||||
|
|
||||||
LOG_CHANNEL=stack
|
LOG_CHANNEL=stack
|
||||||
|
|||||||
4
.github/workflows/build-private.yml
vendored
4
.github/workflows/build-private.yml
vendored
@@ -69,7 +69,7 @@ jobs:
|
|||||||
uses: shivammathur/setup-php@v2
|
uses: shivammathur/setup-php@v2
|
||||||
with:
|
with:
|
||||||
php-version: '8.3'
|
php-version: '8.3'
|
||||||
extensions: mbstring, dom, fileinfo, pgsql, swoole
|
extensions: mbstring, dom, fileinfo, pgsql
|
||||||
|
|
||||||
- name: "Install dependencies"
|
- name: "Install dependencies"
|
||||||
uses: php-actions/composer@v6
|
uses: php-actions/composer@v6
|
||||||
@@ -119,6 +119,8 @@ jobs:
|
|||||||
uses: docker/build-push-action@v6
|
uses: docker/build-push-action@v6
|
||||||
with:
|
with:
|
||||||
context: .
|
context: .
|
||||||
|
build-args: |
|
||||||
|
DOCKER_FILES_BASE_PATH=docker/prod/
|
||||||
file: docker/prod/Dockerfile
|
file: docker/prod/Dockerfile
|
||||||
push: true
|
push: true
|
||||||
tags: ${{ steps.meta.outputs.tags }}
|
tags: ${{ steps.meta.outputs.tags }}
|
||||||
|
|||||||
2
.github/workflows/build-public.yml
vendored
2
.github/workflows/build-public.yml
vendored
@@ -66,6 +66,8 @@ jobs:
|
|||||||
with:
|
with:
|
||||||
context: .
|
context: .
|
||||||
file: docker/prod/Dockerfile
|
file: docker/prod/Dockerfile
|
||||||
|
build-args: |
|
||||||
|
DOCKER_FILES_BASE_PATH=docker/prod/
|
||||||
platforms: linux/amd64
|
platforms: linux/amd64
|
||||||
push: true
|
push: true
|
||||||
tags: ${{ steps.meta.outputs.tags }}
|
tags: ${{ steps.meta.outputs.tags }}
|
||||||
|
|||||||
6
.gitignore
vendored
6
.gitignore
vendored
@@ -34,3 +34,9 @@ yarn-error.log
|
|||||||
/_ide_helper.php
|
/_ide_helper.php
|
||||||
/.phpstorm.meta.php
|
/.phpstorm.meta.php
|
||||||
/.rnd
|
/.rnd
|
||||||
|
|
||||||
|
/caddy
|
||||||
|
/frankenphp
|
||||||
|
/public/frankenphp-worker.php
|
||||||
|
/data
|
||||||
|
/confif/caddy
|
||||||
|
|||||||
@@ -14,10 +14,13 @@ use Laravel\Octane\Events\WorkerErrorOccurred;
|
|||||||
use Laravel\Octane\Events\WorkerStarting;
|
use Laravel\Octane\Events\WorkerStarting;
|
||||||
use Laravel\Octane\Events\WorkerStopping;
|
use Laravel\Octane\Events\WorkerStopping;
|
||||||
use Laravel\Octane\Listeners\CloseMonologHandlers;
|
use Laravel\Octane\Listeners\CloseMonologHandlers;
|
||||||
|
use Laravel\Octane\Listeners\CollectGarbage;
|
||||||
|
use Laravel\Octane\Listeners\DisconnectFromDatabases;
|
||||||
use Laravel\Octane\Listeners\EnsureUploadedFilesAreValid;
|
use Laravel\Octane\Listeners\EnsureUploadedFilesAreValid;
|
||||||
use Laravel\Octane\Listeners\EnsureUploadedFilesCanBeMoved;
|
use Laravel\Octane\Listeners\EnsureUploadedFilesCanBeMoved;
|
||||||
use Laravel\Octane\Listeners\FlushOnce;
|
use Laravel\Octane\Listeners\FlushOnce;
|
||||||
use Laravel\Octane\Listeners\FlushTemporaryContainerInstances;
|
use Laravel\Octane\Listeners\FlushTemporaryContainerInstances;
|
||||||
|
use Laravel\Octane\Listeners\FlushUploadedFiles;
|
||||||
use Laravel\Octane\Listeners\ReportException;
|
use Laravel\Octane\Listeners\ReportException;
|
||||||
use Laravel\Octane\Listeners\StopWorkerIfNecessary;
|
use Laravel\Octane\Listeners\StopWorkerIfNecessary;
|
||||||
use Laravel\Octane\Octane;
|
use Laravel\Octane\Octane;
|
||||||
@@ -37,7 +40,7 @@ return [
|
|||||||
|
|
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
'server' => env('OCTANE_SERVER', 'swoole'),
|
'server' => env('OCTANE_SERVER', 'frankenphp'),
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|--------------------------------------------------------------------------
|
|--------------------------------------------------------------------------
|
||||||
|
|||||||
@@ -28,7 +28,9 @@ services:
|
|||||||
extra_hosts:
|
extra_hosts:
|
||||||
- 'host.docker.internal:host-gateway'
|
- 'host.docker.internal:host-gateway'
|
||||||
environment:
|
environment:
|
||||||
SUPERVISOR_PHP_COMMAND: "/usr/bin/php -d variables_order=EGPCS /var/www/html/artisan octane:start --server=swoole --watch --host=0.0.0.0 --port=80"
|
SUPERVISOR_PHP_COMMAND: "/usr/bin/php -d variables_order=EGPCS /var/www/html/artisan octane:start --server=frankenphp --host=0.0.0.0 --admin-port=2019 --port=80 --watch"
|
||||||
|
XDG_CONFIG_HOME: /var/www/html/config
|
||||||
|
XDG_DATA_HOME: /var/www/html/data
|
||||||
WWWUSER: '${WWWUSER}'
|
WWWUSER: '${WWWUSER}'
|
||||||
LARAVEL_SAIL: 1
|
LARAVEL_SAIL: 1
|
||||||
XDEBUG_MODE: '${SAIL_XDEBUG_MODE:-off}'
|
XDEBUG_MODE: '${SAIL_XDEBUG_MODE:-off}'
|
||||||
|
|||||||
@@ -1,120 +1,178 @@
|
|||||||
# Accepted values: 8.3 - 8.2
|
# Accepted values: 8.3 - 8.2
|
||||||
ARG PHP_VERSION=8.3
|
ARG PHP_VERSION=8.3
|
||||||
|
|
||||||
ARG DOCKER_FILES_BASE_PATH="docker/prod"
|
ARG FRANKENPHP_VERSION=latest
|
||||||
|
|
||||||
ARG COMPOSER_VERSION=latest
|
ARG COMPOSER_VERSION=latest
|
||||||
|
|
||||||
|
ARG DOCKER_FILES_BASE_PATH="docker/prod/"
|
||||||
|
|
||||||
|
###########################################
|
||||||
|
# Build frontend assets with NPM
|
||||||
|
###########################################
|
||||||
|
|
||||||
|
#ARG NODE_VERSION=20-alpine
|
||||||
|
#
|
||||||
|
#FROM node:${NODE_VERSION} AS build
|
||||||
|
#
|
||||||
|
#ENV ROOT=/var/www/html
|
||||||
|
#
|
||||||
|
#WORKDIR ${ROOT}
|
||||||
|
#
|
||||||
|
#RUN npm config set update-notifier false && npm set progress=false
|
||||||
|
#
|
||||||
|
#COPY package*.json ./
|
||||||
|
#
|
||||||
|
#RUN if [ -f $ROOT/package-lock.json ]; \
|
||||||
|
# then \
|
||||||
|
# npm ci --loglevel=error --no-audit; \
|
||||||
|
# else \
|
||||||
|
# npm install --loglevel=error --no-audit; \
|
||||||
|
# fi
|
||||||
|
#
|
||||||
|
#COPY . .
|
||||||
|
#
|
||||||
|
#RUN npm run build
|
||||||
|
|
||||||
###########################################
|
###########################################
|
||||||
|
|
||||||
FROM composer:${COMPOSER_VERSION} AS vendor
|
FROM composer:${COMPOSER_VERSION} AS vendor
|
||||||
|
|
||||||
FROM php:${PHP_VERSION}-cli-bookworm AS base
|
FROM dunglas/frankenphp:${FRANKENPHP_VERSION}-php${PHP_VERSION}
|
||||||
|
|
||||||
|
ARG DOCKER_FILES_BASE_PATH
|
||||||
|
|
||||||
LABEL maintainer="solidtime <hello@solidtime.io>"
|
LABEL maintainer="solidtime <hello@solidtime.io>"
|
||||||
LABEL org.opencontainers.image.title="solidtime"
|
LABEL org.opencontainers.image.title="solidtime"
|
||||||
LABEL org.opencontainers.image.description="solidtime is a modern open source timetracker for Freelancers and Agencies"
|
LABEL org.opencontainers.image.description="solidtime is a modern open source timetracker for freelancers and agencies"
|
||||||
LABEL org.opencontainers.image.source="https://github.com/solidtime-io/solidtime"
|
LABEL org.opencontainers.image.source="https://github.com/solidtime-io/solidtime"
|
||||||
LABEL org.opencontainers.image.licenses="AGPL"
|
LABEL org.opencontainers.image.licenses="AGPL"
|
||||||
|
|
||||||
ARG WWWUSER=1000
|
ARG WWWUSER=1000
|
||||||
ARG WWWGROUP=1000
|
ARG WWWGROUP=1000
|
||||||
ARG TZ=UTC
|
ARG TZ=UTC
|
||||||
|
ARG APP_DIR=/var/www/html
|
||||||
|
|
||||||
ENV DEBIAN_FRONTEND=noninteractive \
|
ENV DEBIAN_FRONTEND=noninteractive \
|
||||||
TERM=xterm-color \
|
TERM=xterm-color \
|
||||||
WITH_HORIZON=false \
|
WITH_HORIZON=false \
|
||||||
WITH_SCHEDULER=false \
|
WITH_SCHEDULER=false \
|
||||||
OCTANE_SERVER=swoole \
|
OCTANE_SERVER=frankenphp \
|
||||||
USER=octane \
|
USER=octane \
|
||||||
ROOT=/var/www/html \
|
ROOT=${APP_DIR} \
|
||||||
COMPOSER_FUND=0 \
|
COMPOSER_FUND=0 \
|
||||||
COMPOSER_MAX_PARALLEL_HTTP=24
|
COMPOSER_MAX_PARALLEL_HTTP=24 \
|
||||||
|
XDG_CONFIG_HOME=${APP_DIR}/.config \
|
||||||
|
XDG_DATA_HOME=${APP_DIR}/.data
|
||||||
|
|
||||||
WORKDIR ${ROOT}
|
WORKDIR ${ROOT}
|
||||||
|
|
||||||
SHELL ["/bin/bash", "-eou", "pipefail", "-c"]
|
SHELL ["/bin/bash", "-eou", "pipefail", "-c"]
|
||||||
|
|
||||||
RUN ln -snf /usr/share/zoneinfo/${TZ} /etc/localtime \
|
RUN ln -snf /usr/share/zoneinfo/${TZ} /etc/localtime \
|
||||||
&& echo ${TZ} > /etc/timezone
|
&& echo ${TZ} > /etc/timezone
|
||||||
|
|
||||||
ADD --chmod=0755 https://github.com/mlocati/docker-php-extension-installer/releases/latest/download/install-php-extensions /usr/local/bin/
|
|
||||||
|
|
||||||
RUN apt-get update; \
|
RUN apt-get update; \
|
||||||
apt-get upgrade -yqq; \
|
apt-get upgrade -yqq; \
|
||||||
apt-get install -yqq --no-install-recommends --show-progress \
|
apt-get install -yqq --no-install-recommends --show-progress \
|
||||||
apt-utils \
|
apt-utils \
|
||||||
curl \
|
curl \
|
||||||
wget \
|
wget \
|
||||||
nano \
|
nano \
|
||||||
ncdu \
|
ncdu \
|
||||||
ca-certificates \
|
procps \
|
||||||
supervisor \
|
ca-certificates \
|
||||||
libsodium-dev \
|
supervisor \
|
||||||
# Install PHP extensions
|
libsodium-dev \
|
||||||
&& install-php-extensions \
|
# Install PHP extensions (included with dunglas/frankenphp)
|
||||||
bz2 \
|
&& install-php-extensions \
|
||||||
pcntl \
|
bz2 \
|
||||||
mbstring \
|
pcntl \
|
||||||
bcmath \
|
mbstring \
|
||||||
sockets \
|
bcmath \
|
||||||
pgsql \
|
sockets \
|
||||||
pdo_pgsql \
|
pgsql \
|
||||||
opcache \
|
pdo_pgsql \
|
||||||
exif \
|
opcache \
|
||||||
pdo_mysql \
|
exif \
|
||||||
zip \
|
pdo_mysql \
|
||||||
intl \
|
zip \
|
||||||
gd \
|
intl \
|
||||||
redis \
|
gd \
|
||||||
rdkafka \
|
redis \
|
||||||
memcached \
|
rdkafka \
|
||||||
igbinary \
|
memcached \
|
||||||
ldap \
|
igbinary \
|
||||||
swoole \
|
ldap \
|
||||||
&& apt-get -y autoremove \
|
&& apt-get -y autoremove \
|
||||||
&& apt-get clean \
|
&& apt-get clean \
|
||||||
&& docker-php-source delete \
|
&& docker-php-source delete \
|
||||||
&& rm -rf /var/lib/apt/lists/* /tmp/* /var/tmp/* \
|
&& rm -rf /var/lib/apt/lists/* /tmp/* /var/tmp/* \
|
||||||
&& rm /var/log/lastlog /var/log/faillog
|
&& rm /var/log/lastlog /var/log/faillog
|
||||||
|
|
||||||
RUN wget -q "https://github.com/aptible/supercronic/releases/download/v0.2.29/supercronic-linux-amd64" \
|
RUN arch="$(uname -m)" \
|
||||||
-O /usr/bin/supercronic \
|
&& case "$arch" in \
|
||||||
&& chmod +x /usr/bin/supercronic \
|
armhf) _cronic_fname='supercronic-linux-arm' ;; \
|
||||||
&& mkdir -p /etc/supercronic \
|
aarch64) _cronic_fname='supercronic-linux-arm64' ;; \
|
||||||
&& echo "*/1 * * * * php ${ROOT}/artisan schedule:run --verbose --no-interaction" > /etc/supercronic/laravel
|
x86_64) _cronic_fname='supercronic-linux-amd64' ;; \
|
||||||
|
x86) _cronic_fname='supercronic-linux-386' ;; \
|
||||||
|
*) echo >&2 "error: unsupported architecture: $arch"; exit 1 ;; \
|
||||||
|
esac \
|
||||||
|
&& wget -q "https://github.com/aptible/supercronic/releases/download/v0.2.29/${_cronic_fname}" \
|
||||||
|
-O /usr/bin/supercronic \
|
||||||
|
&& chmod +x /usr/bin/supercronic \
|
||||||
|
&& mkdir -p /etc/supercronic \
|
||||||
|
&& echo "*/1 * * * * php ${ROOT}/artisan schedule:run --no-interaction" > /etc/supercronic/laravel
|
||||||
|
|
||||||
RUN userdel --remove --force www-data \
|
RUN userdel --remove --force www-data \
|
||||||
&& groupadd --force -g ${WWWGROUP} ${USER} \
|
&& groupadd --force -g ${WWWGROUP} ${USER} \
|
||||||
&& useradd -ms /bin/bash --no-log-init --no-user-group -g ${WWWGROUP} -u ${WWWUSER} ${USER}
|
&& useradd -ms /bin/bash --no-log-init --no-user-group -g ${WWWGROUP} -u ${WWWUSER} ${USER}
|
||||||
|
|
||||||
RUN chown -R ${USER}:${USER} ${ROOT} /var/{log,run} \
|
RUN chown -R ${USER}:${USER} ${ROOT} /var/{log,run} \
|
||||||
&& chmod -R a+rw /var/{log,run}
|
&& chmod -R a+rw ${ROOT} /var/{log,run}
|
||||||
|
|
||||||
RUN cp ${PHP_INI_DIR}/php.ini-production ${PHP_INI_DIR}/php.ini
|
RUN cp ${PHP_INI_DIR}/php.ini-production ${PHP_INI_DIR}/php.ini
|
||||||
|
|
||||||
USER ${USER}
|
USER ${USER}
|
||||||
|
|
||||||
COPY --chown=${USER}:${USER} --from=vendor /usr/bin/composer /usr/bin/composer
|
COPY --chown=${USER}:${USER} --from=vendor /usr/bin/composer /usr/bin/composer
|
||||||
|
#COPY --chown=${USER}:${USER} composer.json composer.lock ./
|
||||||
|
#
|
||||||
|
#RUN composer install \
|
||||||
|
# --no-dev \
|
||||||
|
# --no-interaction \
|
||||||
|
# --no-autoloader \
|
||||||
|
# --no-ansi \
|
||||||
|
# --no-scripts \
|
||||||
|
# --audit
|
||||||
|
|
||||||
COPY --chown=${USER}:${USER} . .
|
COPY --chown=${USER}:${USER} . .
|
||||||
|
#COPY --chown=${USER}:${USER} --from=build ${ROOT}/public public
|
||||||
|
|
||||||
RUN mkdir -p \
|
RUN mkdir -p \
|
||||||
storage/framework/{sessions,views,cache,testing} \
|
storage/framework/{sessions,views,cache,testing} \
|
||||||
storage/logs \
|
storage/logs \
|
||||||
bootstrap/cache && chmod -R a+rw storage
|
bootstrap/cache && chmod -R a+rw storage
|
||||||
|
|
||||||
COPY --chown=${USER}:${USER} docker/prod/deployment/supervisord.*.conf /etc/supervisor/conf.d/
|
COPY --chown=${USER}:${USER} ${DOCKER_FILES_BASE_PATH}deployment/supervisord.conf /etc/supervisor/
|
||||||
COPY --chown=${USER}:${USER} docker/prod/deployment/php.ini ${PHP_INI_DIR}/conf.d/99-octane.ini
|
COPY --chown=${USER}:${USER} ${DOCKER_FILES_BASE_PATH}deployment/octane/FrankenPHP/supervisord.frankenphp.conf /etc/supervisor/conf.d/
|
||||||
COPY --chown=${USER}:${USER} docker/prod/deployment/start-container /usr/local/bin/start-container
|
COPY --chown=${USER}:${USER} ${DOCKER_FILES_BASE_PATH}deployment/supervisord.*.conf /etc/supervisor/conf.d/
|
||||||
|
COPY --chown=${USER}:${USER} ${DOCKER_FILES_BASE_PATH}deployment/start-container /usr/local/bin/start-container
|
||||||
|
COPY --chown=${USER}:${USER} ${DOCKER_FILES_BASE_PATH}deployment/php.ini ${PHP_INI_DIR}/conf.d/99-octane.ini
|
||||||
|
|
||||||
RUN cat .env
|
# FrankenPHP embedded PHP configuration
|
||||||
RUN php artisan env
|
COPY --chown=${USER}:${USER} ${DOCKER_FILES_BASE_PATH}deployment/php.ini /lib/php.ini
|
||||||
RUN php artisan storage:link
|
|
||||||
|
#RUN composer install \
|
||||||
|
# --classmap-authoritative \
|
||||||
|
# --no-interaction \
|
||||||
|
# --no-ansi \
|
||||||
|
# --no-dev \
|
||||||
|
# && composer clear-cache
|
||||||
|
|
||||||
RUN chmod +x /usr/local/bin/start-container
|
RUN chmod +x /usr/local/bin/start-container
|
||||||
|
|
||||||
RUN cat docker/prod/deployment/utilities.sh >> ~/.bashrc
|
RUN cat ${DOCKER_FILES_BASE_PATH}deployment/utilities.sh >> ~/.bashrc
|
||||||
|
|
||||||
EXPOSE 8000
|
EXPOSE 8000
|
||||||
|
|
||||||
|
|||||||
@@ -1,128 +0,0 @@
|
|||||||
# Laravel Octane Dockerfile
|
|
||||||
<a href="/LICENSE"><img alt="License" src="https://img.shields.io/github/license/exaco/laravel-octane-dockerfile"></a>
|
|
||||||
<a href="https://github.com/exaco/laravel-octane-dockerfile/releases"><img alt="GitHub release (latest by date)" src="https://img.shields.io/github/v/release/exaco/laravel-octane-dockerfile"></a>
|
|
||||||
<a href="https://github.com/exaco/laravel-octane-dockerfile/pulls"><img alt="GitHub closed pull requests" src="https://img.shields.io/github/issues-pr-closed/exaco/laravel-octane-dockerfile"></a>
|
|
||||||
<a href="https://github.com/exaco/laravel-octane-dockerfile/actions/workflows/tests.yml"><img alt="GitHub Workflow Status" src="https://github.com/exaco/laravel-octane-dockerfile/actions/workflows/roadrunner-test.yml/badge.svg"></a>
|
|
||||||
<a href="https://github.com/exaco/laravel-octane-dockerfile/actions/workflows/tests.yml"><img alt="GitHub Workflow Status" src="https://github.com/exaco/laravel-octane-dockerfile/actions/workflows/swoole-test.yml/badge.svg"></a>
|
|
||||||
<a href="https://github.com/exaco/laravel-octane-dockerfile/actions/workflows/tests.yml"><img alt="GitHub Workflow Status" src="https://github.com/exaco/laravel-octane-dockerfile/actions/workflows/frankenphp-test.yml/badge.svg"></a>
|
|
||||||
|
|
||||||
|
|
||||||
Production-ready Dockerfiles for [Laravel Octane](https://github.com/laravel/octane)
|
|
||||||
powered web services and microservices.
|
|
||||||
|
|
||||||
The Docker configuration provides the following setup:
|
|
||||||
|
|
||||||
- PHP 8.2 and 8.3 official Debian-based images
|
|
||||||
- Preconfigured JIT compiler and OPcache
|
|
||||||
|
|
||||||
## Container modes
|
|
||||||
|
|
||||||
You can run the Docker container in different modes:
|
|
||||||
|
|
||||||
| Mode | `CONTAINER_MODE` | HTTP server |
|
|
||||||
| --------------------- | ---------------- | ------------------- |
|
|
||||||
| HTTP Server (default) | `http` | FrankenPHP / Swoole / RoadRunner |
|
|
||||||
| Horizon | `horizon` | - |
|
|
||||||
| Scheduler | `scheduler` | - |
|
|
||||||
| Worker | `worker` | - |
|
|
||||||
|
|
||||||
## Usage
|
|
||||||
|
|
||||||
### Building Docker image
|
|
||||||
1. Clone this repository:
|
|
||||||
```
|
|
||||||
git clone --depth 1 git@github.com:exaco/laravel-octane-dockerfile.git
|
|
||||||
```
|
|
||||||
2. Copy cloned directory content including `deployment` directory, `Dockerfile`, and `.dockerignore` into your Octane powered Laravel project
|
|
||||||
3. Change the directory to your Laravel project
|
|
||||||
4. Build your image:
|
|
||||||
```
|
|
||||||
docker build -t <image-name>:<tag> -f <your-octane-driver>.Dockerfile .
|
|
||||||
```
|
|
||||||
### Running Docker container
|
|
||||||
|
|
||||||
```bash
|
|
||||||
# HTTP mode
|
|
||||||
docker run -p <port>:80 --rm <image-name>:<tag>
|
|
||||||
|
|
||||||
# Horizon mode
|
|
||||||
docker run -e CONTAINER_MODE=horizon --rm <image-name>:<tag>
|
|
||||||
|
|
||||||
# Scheduler mode
|
|
||||||
docker run -e CONTAINER_MODE=scheduler --rm <image-name>:<tag>
|
|
||||||
|
|
||||||
# HTTP mode with Horizon
|
|
||||||
docker run -e WITH_HORIZON=true -p <port>:80 --rm <image-name>:<tag>
|
|
||||||
|
|
||||||
# HTTP mode with Scheduler
|
|
||||||
docker run -e WITH_SCHEDULER=true -p <port>:80 --rm <image-name>:<tag>
|
|
||||||
|
|
||||||
# HTTP mode with Scheduler and Horizon
|
|
||||||
docker run -e WITH_SCHEDULER=true -e WITH_HORIZON=true -p <port>:80 --rm <image-name>:<tag>
|
|
||||||
|
|
||||||
# Worker mode
|
|
||||||
docker run -e CONTAINER_MODE=worker -e WORKER_COMMAND="php /var/www/html/artisan foo:bar" --rm <image-name>:<tag>
|
|
||||||
|
|
||||||
# Running a single command
|
|
||||||
docker run --rm <image-name>:<tag> php artisan about
|
|
||||||
```
|
|
||||||
|
|
||||||
## Configuration
|
|
||||||
|
|
||||||
### Recommended `Swoole` options in `octane.php`
|
|
||||||
|
|
||||||
```php
|
|
||||||
// config/octane.php
|
|
||||||
|
|
||||||
return [
|
|
||||||
'swoole' => [
|
|
||||||
'options' => [
|
|
||||||
'http_compression' => true,
|
|
||||||
'http_compression_level' => 6, // 1 - 9
|
|
||||||
'compression_min_length' => 20,
|
|
||||||
'package_max_length' => 20 * 1024 * 1024, // 20MB
|
|
||||||
'open_http2_protocol' => true,
|
|
||||||
'document_root' => public_path(),
|
|
||||||
'enable_static_handler' => true,
|
|
||||||
]
|
|
||||||
]
|
|
||||||
];
|
|
||||||
```
|
|
||||||
|
|
||||||
## Utilities
|
|
||||||
|
|
||||||
Also, some useful Bash functions and aliases are added in `utilities.sh` that maybe help.
|
|
||||||
|
|
||||||
## Notes
|
|
||||||
|
|
||||||
- Laravel Octane logs request information only in the `local` environment.
|
|
||||||
- Please be aware of `.dockerignore` content
|
|
||||||
|
|
||||||
## ToDo
|
|
||||||
- [x] Add support for PHP 8.3
|
|
||||||
- [x] Add support for worker mode
|
|
||||||
- [ ] Build assets with Bun
|
|
||||||
- [ ] Create standalone and self-executable app
|
|
||||||
- [x] Add support for Horizon
|
|
||||||
- [x] Add support for RoadRunner
|
|
||||||
- [x] Add support for FrankenPHP
|
|
||||||
- [x] Add support for the full-stack apps (Front-end assets)
|
|
||||||
- [ ] Add support `testing` environment and CI
|
|
||||||
- [x] Add support for the Laravel scheduler
|
|
||||||
- [ ] Add support for Laravel Dusk
|
|
||||||
- [x] Support more PHP extensions
|
|
||||||
- [x] Add tests
|
|
||||||
- [ ] Add Alpine-based images
|
|
||||||
|
|
||||||
## Contributing
|
|
||||||
|
|
||||||
Thank you for considering contributing! If you find an issue, or have a better way to do something, feel free to open an
|
|
||||||
issue, or a PR.
|
|
||||||
|
|
||||||
## Credits
|
|
||||||
- [SMortexa](https://github.com/smortexa)
|
|
||||||
- [All contributors](https://github.com/exaco/laravel-octane-dockerfile/graphs/contributors)
|
|
||||||
|
|
||||||
## License
|
|
||||||
|
|
||||||
This repository is open-sourced software licensed under the [MIT license](https://opensource.org/licenses/MIT).
|
|
||||||
@@ -0,0 +1,51 @@
|
|||||||
|
[program:octane]
|
||||||
|
process_name=%(program_name)s_%(process_num)02d
|
||||||
|
command=php %(ENV_ROOT)s/artisan octane:start --server=frankenphp --host=0.0.0.0 --port=8000 --admin-port=2019
|
||||||
|
; command=php %(ENV_ROOT)s/artisan octane:start --server=frankenphp --host=localhost --port=443 --admin-port=2019 --https --http-redirect
|
||||||
|
user=%(ENV_USER)s
|
||||||
|
autostart=true
|
||||||
|
autorestart=true
|
||||||
|
environment=LARAVEL_OCTANE="1"
|
||||||
|
stdout_logfile=/dev/stdout
|
||||||
|
stdout_logfile_maxbytes=0
|
||||||
|
stderr_logfile=/dev/stderr
|
||||||
|
stderr_logfile_maxbytes=0
|
||||||
|
|
||||||
|
[program:horizon]
|
||||||
|
process_name=%(program_name)s_%(process_num)02d
|
||||||
|
command=php %(ENV_ROOT)s/artisan horizon
|
||||||
|
user=%(ENV_USER)s
|
||||||
|
autostart=%(ENV_WITH_HORIZON)s
|
||||||
|
autorestart=true
|
||||||
|
stdout_logfile=%(ENV_ROOT)s/storage/logs/horizon.log
|
||||||
|
stdout_logfile_maxbytes=200MB
|
||||||
|
stderr_logfile=%(ENV_ROOT)s/storage/logs/horizon.log
|
||||||
|
stderr_logfile_maxbytes=200MB
|
||||||
|
stopwaitsecs=3600
|
||||||
|
|
||||||
|
[program:scheduler]
|
||||||
|
process_name=%(program_name)s_%(process_num)02d
|
||||||
|
command=supercronic -overlapping /etc/supercronic/laravel
|
||||||
|
user=%(ENV_USER)s
|
||||||
|
autostart=%(ENV_WITH_SCHEDULER)s
|
||||||
|
autorestart=true
|
||||||
|
stdout_logfile=%(ENV_ROOT)s/storage/logs/scheduler.log
|
||||||
|
stdout_logfile_maxbytes=200MB
|
||||||
|
stderr_logfile=%(ENV_ROOT)s/storage/logs/scheduler.log
|
||||||
|
stderr_logfile_maxbytes=200MB
|
||||||
|
|
||||||
|
[program:clear-scheduler-cache]
|
||||||
|
process_name=%(program_name)s_%(process_num)02d
|
||||||
|
command=php %(ENV_ROOT)s/artisan schedule:clear-cache
|
||||||
|
user=%(ENV_USER)s
|
||||||
|
autostart=%(ENV_WITH_SCHEDULER)s
|
||||||
|
autorestart=false
|
||||||
|
startsecs=0
|
||||||
|
startretries=1
|
||||||
|
stdout_logfile=%(ENV_ROOT)s/storage/logs/scheduler.log
|
||||||
|
stdout_logfile_maxbytes=200MB
|
||||||
|
stderr_logfile=%(ENV_ROOT)s/storage/logs/scheduler.log
|
||||||
|
stderr_logfile_maxbytes=200MB
|
||||||
|
|
||||||
|
[include]
|
||||||
|
files=/etc/supervisor/supervisord.conf
|
||||||
25
docker/prod/deployment/octane/RoadRunner/.rr.prod.yaml
Normal file
25
docker/prod/deployment/octane/RoadRunner/.rr.prod.yaml
Normal file
@@ -0,0 +1,25 @@
|
|||||||
|
version: '2.7'
|
||||||
|
rpc:
|
||||||
|
listen: 'tcp://127.0.0.1:6001'
|
||||||
|
server:
|
||||||
|
relay: pipes
|
||||||
|
http:
|
||||||
|
middleware: [ "static", "gzip", "headers" ]
|
||||||
|
max_request_size: 20
|
||||||
|
static:
|
||||||
|
dir: "public"
|
||||||
|
forbid: [ ".php", ".htaccess" ]
|
||||||
|
uploads:
|
||||||
|
forbid: [".php", ".exe", ".bat", ".sh"]
|
||||||
|
pool:
|
||||||
|
allocate_timeout: 10s
|
||||||
|
destroy_timeout: 10s
|
||||||
|
supervisor:
|
||||||
|
max_worker_memory: 128
|
||||||
|
exec_ttl: 60s
|
||||||
|
logs:
|
||||||
|
mode: production
|
||||||
|
level: debug
|
||||||
|
encoding: json
|
||||||
|
status:
|
||||||
|
address: localhost:2114
|
||||||
@@ -0,0 +1,50 @@
|
|||||||
|
[program:octane]
|
||||||
|
process_name=%(program_name)s_%(process_num)02d
|
||||||
|
command=php %(ENV_ROOT)s/artisan octane:start --server=roadrunner --host=0.0.0.0 --port=8000 --rpc-port=6001 --rr-config=%(ENV_ROOT)s/.rr.yaml
|
||||||
|
user=%(ENV_USER)s
|
||||||
|
autostart=true
|
||||||
|
autorestart=true
|
||||||
|
environment=LARAVEL_OCTANE="1"
|
||||||
|
stdout_logfile=/dev/stdout
|
||||||
|
stdout_logfile_maxbytes=0
|
||||||
|
stderr_logfile=/dev/stderr
|
||||||
|
stderr_logfile_maxbytes=0
|
||||||
|
|
||||||
|
[program:horizon]
|
||||||
|
process_name=%(program_name)s_%(process_num)02d
|
||||||
|
command=php %(ENV_ROOT)s/artisan horizon
|
||||||
|
user=%(ENV_USER)s
|
||||||
|
autostart=%(ENV_WITH_HORIZON)s
|
||||||
|
autorestart=true
|
||||||
|
stdout_logfile=%(ENV_ROOT)s/storage/logs/horizon.log
|
||||||
|
stdout_logfile_maxbytes=200MB
|
||||||
|
stderr_logfile=%(ENV_ROOT)s/storage/logs/horizon.log
|
||||||
|
stderr_logfile_maxbytes=200MB
|
||||||
|
stopwaitsecs=3600
|
||||||
|
|
||||||
|
[program:scheduler]
|
||||||
|
process_name=%(program_name)s_%(process_num)02d
|
||||||
|
command=supercronic -overlapping /etc/supercronic/laravel
|
||||||
|
user=%(ENV_USER)s
|
||||||
|
autostart=%(ENV_WITH_SCHEDULER)s
|
||||||
|
autorestart=true
|
||||||
|
stdout_logfile=%(ENV_ROOT)s/storage/logs/scheduler.log
|
||||||
|
stdout_logfile_maxbytes=200MB
|
||||||
|
stderr_logfile=%(ENV_ROOT)s/storage/logs/scheduler.log
|
||||||
|
stderr_logfile_maxbytes=200MB
|
||||||
|
|
||||||
|
[program:clear-scheduler-cache]
|
||||||
|
process_name=%(program_name)s_%(process_num)02d
|
||||||
|
command=php %(ENV_ROOT)s/artisan schedule:clear-cache
|
||||||
|
user=%(ENV_USER)s
|
||||||
|
autostart=%(ENV_WITH_SCHEDULER)s
|
||||||
|
autorestart=false
|
||||||
|
startsecs=0
|
||||||
|
startretries=1
|
||||||
|
stdout_logfile=%(ENV_ROOT)s/storage/logs/scheduler.log
|
||||||
|
stdout_logfile_maxbytes=200MB
|
||||||
|
stderr_logfile=%(ENV_ROOT)s/storage/logs/scheduler.log
|
||||||
|
stderr_logfile_maxbytes=200MB
|
||||||
|
|
||||||
|
[include]
|
||||||
|
files=/etc/supervisor/supervisord.conf
|
||||||
50
docker/prod/deployment/octane/Swoole/supervisord.swoole.conf
Normal file
50
docker/prod/deployment/octane/Swoole/supervisord.swoole.conf
Normal file
@@ -0,0 +1,50 @@
|
|||||||
|
[program:octane]
|
||||||
|
process_name=%(program_name)s_%(process_num)02d
|
||||||
|
command=php %(ENV_ROOT)s/artisan octane:start --server=swoole --host=0.0.0.0 --port=8000
|
||||||
|
user=%(ENV_USER)s
|
||||||
|
autostart=true
|
||||||
|
autorestart=true
|
||||||
|
environment=LARAVEL_OCTANE="1"
|
||||||
|
stdout_logfile=/dev/stdout
|
||||||
|
stdout_logfile_maxbytes=0
|
||||||
|
stderr_logfile=/dev/stderr
|
||||||
|
stderr_logfile_maxbytes=0
|
||||||
|
|
||||||
|
[program:horizon]
|
||||||
|
process_name=%(program_name)s_%(process_num)02d
|
||||||
|
command=php %(ENV_ROOT)s/artisan horizon
|
||||||
|
user=%(ENV_USER)s
|
||||||
|
autostart=%(ENV_WITH_HORIZON)s
|
||||||
|
autorestart=true
|
||||||
|
stdout_logfile=%(ENV_ROOT)s/storage/logs/horizon.log
|
||||||
|
stdout_logfile_maxbytes=200MB
|
||||||
|
stderr_logfile=%(ENV_ROOT)s/storage/logs/horizon.log
|
||||||
|
stderr_logfile_maxbytes=200MB
|
||||||
|
stopwaitsecs=3600
|
||||||
|
|
||||||
|
[program:scheduler]
|
||||||
|
process_name=%(program_name)s_%(process_num)02d
|
||||||
|
command=supercronic -overlapping /etc/supercronic/laravel
|
||||||
|
user=%(ENV_USER)s
|
||||||
|
autostart=%(ENV_WITH_SCHEDULER)s
|
||||||
|
autorestart=true
|
||||||
|
stdout_logfile=%(ENV_ROOT)s/storage/logs/scheduler.log
|
||||||
|
stdout_logfile_maxbytes=200MB
|
||||||
|
stderr_logfile=%(ENV_ROOT)s/storage/logs/scheduler.log
|
||||||
|
stderr_logfile_maxbytes=200MB
|
||||||
|
|
||||||
|
[program:clear-scheduler-cache]
|
||||||
|
process_name=%(program_name)s_%(process_num)02d
|
||||||
|
command=php %(ENV_ROOT)s/artisan schedule:clear-cache
|
||||||
|
user=%(ENV_USER)s
|
||||||
|
autostart=%(ENV_WITH_SCHEDULER)s
|
||||||
|
autorestart=false
|
||||||
|
startsecs=0
|
||||||
|
startretries=1
|
||||||
|
stdout_logfile=%(ENV_ROOT)s/storage/logs/scheduler.log
|
||||||
|
stdout_logfile_maxbytes=200MB
|
||||||
|
stderr_logfile=%(ENV_ROOT)s/storage/logs/scheduler.log
|
||||||
|
stderr_logfile_maxbytes=200MB
|
||||||
|
|
||||||
|
[include]
|
||||||
|
files=/etc/supervisor/supervisord.conf
|
||||||
@@ -4,6 +4,7 @@ upload_max_filesize = 100M
|
|||||||
expose_php = 0
|
expose_php = 0
|
||||||
realpath_cache_size = 16M
|
realpath_cache_size = 16M
|
||||||
realpath_cache_ttl = 360
|
realpath_cache_ttl = 360
|
||||||
|
max_input_time = 5
|
||||||
|
|
||||||
[Opcache]
|
[Opcache]
|
||||||
opcache.enable = 1
|
opcache.enable = 1
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
#!/usr/bin/env bash
|
#!/usr/bin/env sh
|
||||||
set -e
|
set -e
|
||||||
|
|
||||||
container_mode=${CONTAINER_MODE:-http}
|
container_mode=${CONTAINER_MODE:-"http"}
|
||||||
octane_server=${OCTANE_SERVER}
|
octane_server=${OCTANE_SERVER}
|
||||||
auto_db_migrate=${AUTO_DB_MIGRATE:-false}
|
auto_db_migrate=${AUTO_DB_MIGRATE:-false}
|
||||||
echo "Container mode: $container_mode"
|
echo "Container mode: $container_mode"
|
||||||
@@ -9,7 +9,7 @@ echo "Container mode: $container_mode"
|
|||||||
initialStuff() {
|
initialStuff() {
|
||||||
if [ ${auto_db_migrate} = "true" ]; then
|
if [ ${auto_db_migrate} = "true" ]; then
|
||||||
echo "Auto database migration enabled."
|
echo "Auto database migration enabled."
|
||||||
php artisan migrate --force
|
php artisan migrate --isolated --force
|
||||||
fi
|
fi
|
||||||
php artisan optimize:clear; \
|
php artisan optimize:clear; \
|
||||||
php artisan event:cache; \
|
php artisan event:cache; \
|
||||||
@@ -22,7 +22,16 @@ if [ "$1" != "" ]; then
|
|||||||
elif [ ${container_mode} = "http" ]; then
|
elif [ ${container_mode} = "http" ]; then
|
||||||
echo "Octane Server: $octane_server"
|
echo "Octane Server: $octane_server"
|
||||||
initialStuff
|
initialStuff
|
||||||
exec /usr/bin/supervisord -c /etc/supervisor/conf.d/supervisord.swoole.conf
|
if [ ${octane_server} = "frankenphp" ]; then
|
||||||
|
exec /usr/bin/supervisord -c /etc/supervisor/conf.d/supervisord.frankenphp.conf
|
||||||
|
elif [ ${octane_server} = "swoole" ]; then
|
||||||
|
exec /usr/bin/supervisord -c /etc/supervisor/conf.d/supervisord.swoole.conf
|
||||||
|
elif [ ${octane_server} = "roadrunner" ]; then
|
||||||
|
exec /usr/bin/supervisord -c /etc/supervisor/conf.d/supervisord.roadrunner.conf
|
||||||
|
else
|
||||||
|
echo "Invalid Octane server supplied."
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
elif [ ${container_mode} = "horizon" ]; then
|
elif [ ${container_mode} = "horizon" ]; then
|
||||||
initialStuff
|
initialStuff
|
||||||
exec /usr/bin/supervisord -c /etc/supervisor/conf.d/supervisord.horizon.conf
|
exec /usr/bin/supervisord -c /etc/supervisor/conf.d/supervisord.horizon.conf
|
||||||
|
|||||||
14
docker/prod/deployment/supervisord.conf
Normal file
14
docker/prod/deployment/supervisord.conf
Normal file
@@ -0,0 +1,14 @@
|
|||||||
|
[supervisord]
|
||||||
|
nodaemon=true
|
||||||
|
user=%(ENV_USER)s
|
||||||
|
logfile=/var/log/supervisor/supervisord.log
|
||||||
|
pidfile=/var/run/supervisord.pid
|
||||||
|
|
||||||
|
[unix_http_server]
|
||||||
|
file=/var/run/supervisor.sock
|
||||||
|
|
||||||
|
[supervisorctl]
|
||||||
|
serverurl=unix:///var/run/supervisor.sock
|
||||||
|
|
||||||
|
[rpcinterface:supervisor]
|
||||||
|
supervisor.rpcinterface_factory=supervisor.rpcinterface:make_main_rpcinterface
|
||||||
@@ -1,9 +1,3 @@
|
|||||||
[supervisord]
|
|
||||||
nodaemon=true
|
|
||||||
user=%(ENV_USER)s
|
|
||||||
logfile=/var/log/supervisor/supervisord.log
|
|
||||||
pidfile=/var/run/supervisord.pid
|
|
||||||
|
|
||||||
[program:horizon]
|
[program:horizon]
|
||||||
process_name=%(program_name)s_%(process_num)02d
|
process_name=%(program_name)s_%(process_num)02d
|
||||||
command=php %(ENV_ROOT)s/artisan horizon
|
command=php %(ENV_ROOT)s/artisan horizon
|
||||||
@@ -15,3 +9,6 @@ stdout_logfile_maxbytes=0
|
|||||||
stderr_logfile=/dev/stderr
|
stderr_logfile=/dev/stderr
|
||||||
stderr_logfile_maxbytes=0
|
stderr_logfile_maxbytes=0
|
||||||
stopwaitsecs=3600
|
stopwaitsecs=3600
|
||||||
|
|
||||||
|
[include]
|
||||||
|
files=/etc/supervisor/supervisord.conf
|
||||||
@@ -1,9 +1,3 @@
|
|||||||
[supervisord]
|
|
||||||
nodaemon=true
|
|
||||||
user=%(ENV_USER)s
|
|
||||||
logfile=/var/log/supervisor/supervisord.log
|
|
||||||
pidfile=/var/run/supervisord.pid
|
|
||||||
|
|
||||||
[program:scheduler]
|
[program:scheduler]
|
||||||
process_name=%(program_name)s_%(process_num)02d
|
process_name=%(program_name)s_%(process_num)02d
|
||||||
command=supercronic -overlapping /etc/supercronic/laravel
|
command=supercronic -overlapping /etc/supercronic/laravel
|
||||||
@@ -21,7 +15,12 @@ command=php %(ENV_ROOT)s/artisan schedule:clear-cache
|
|||||||
user=%(ENV_USER)s
|
user=%(ENV_USER)s
|
||||||
autostart=true
|
autostart=true
|
||||||
autorestart=false
|
autorestart=false
|
||||||
|
startsecs=0
|
||||||
|
startretries=1
|
||||||
stdout_logfile=/dev/stdout
|
stdout_logfile=/dev/stdout
|
||||||
stdout_logfile_maxbytes=0
|
stdout_logfile_maxbytes=0
|
||||||
stderr_logfile=/dev/stderr
|
stderr_logfile=/dev/stderr
|
||||||
stderr_logfile_maxbytes=0
|
stderr_logfile_maxbytes=0
|
||||||
|
|
||||||
|
[include]
|
||||||
|
files=/etc/supervisor/supervisord.conf
|
||||||
@@ -1,9 +1,3 @@
|
|||||||
[supervisord]
|
|
||||||
nodaemon=true
|
|
||||||
user=%(ENV_USER)s
|
|
||||||
logfile=/var/log/supervisor/supervisord.log
|
|
||||||
pidfile=/var/run/supervisord.pid
|
|
||||||
|
|
||||||
[program:worker]
|
[program:worker]
|
||||||
process_name=%(program_name)s_%(process_num)02d
|
process_name=%(program_name)s_%(process_num)02d
|
||||||
command=%(ENV_WORKER_COMMAND)s
|
command=%(ENV_WORKER_COMMAND)s
|
||||||
@@ -14,3 +8,6 @@ stdout_logfile=/dev/stdout
|
|||||||
stdout_logfile_maxbytes=0
|
stdout_logfile_maxbytes=0
|
||||||
stderr_logfile=/dev/stderr
|
stderr_logfile=/dev/stderr
|
||||||
stderr_logfile_maxbytes=0
|
stderr_logfile_maxbytes=0
|
||||||
|
|
||||||
|
[include]
|
||||||
|
files=/etc/supervisor/supervisord.conf
|
||||||
Reference in New Issue
Block a user