Skip to content

Instantly share code, notes, and snippets.

@luishgp
Created February 24, 2024 00:01
Show Gist options
  • Save luishgp/873a9b4759457169b6c6cd7aaea19707 to your computer and use it in GitHub Desktop.
Save luishgp/873a9b4759457169b6c6cd7aaea19707 to your computer and use it in GitHub Desktop.
Dockerfile Alpine with gRPC
FROM php:8.2-fpm-alpine AS build-base
# Install build packages
RUN apk update && apk add --no-cache --virtual \
build-essentials \
linux-headers \
curl \
git \
grep \
build-base \
imagemagick-dev \
pcre-dev \
libtool \
make \
autoconf \
g++ \
libpq-dev \
icu-dev \
icu-libs \
zlib-dev \
automake \
libzip-dev \
libpng-dev \
libwebp-dev \
libjpeg-turbo-dev \
freetype-dev \
libxml2-dev
FROM build-base AS grpc-ext
# Build gRPC PHP dependency
RUN apk add --no-cache grpc-cpp grpc-dev $PHPIZE_DEPS \
&& git clone --depth 1 -b v1.59.4 https://github.com/grpc/grpc /tmp/grpc \
&& cd /tmp/grpc/src/php/ext/grpc \
&& phpize \
&& ./configure \
&& make \
&& make install \
&& rm -rf /tmp/grpc \
&& apk del --no-cache grpc-dev $PHPIZE_DEPS
FROM build-base AS mongodb-ext
# Build MongoDB PHP dependency
RUN git clone --branch 1.17.2 --depth 1 https://github.com/mongodb/mongo-php-driver.git /tmp/mongodb \
&& cd /tmp/mongodb && git submodule update --init \
&& phpize \
&& ./configure \
&& make all \
&& make install \
&& rm -rf /tmp/mongodb
FROM build-base AS xhprof-ext
# Build XHProf Extension
RUN curl "https://pecl.php.net/get/xhprof-2.3.9.tgz" -fsL -o /tmp/xhprof-2.3.9.tgz \
&& mkdir /tmp/xhprof \
&& mkdir /xhprof \
&& tar xf /tmp/xhprof-2.3.9.tgz -C /tmp/xhprof \
&& mv /tmp/xhprof/xhprof-2.3.9/xhprof_lib /xhprof/ \
&& cd /tmp/xhprof/xhprof-2.3.9/extension \
&& phpize \
&& ./configure \
&& make \
&& make install \
&& rm -rf /tmp/xhprof && rm -rf /tmp/xhprof-2.3.9.tgz
FROM build-base AS xdebug-ext
# Build xDebug Extension
RUN git clone --branch master --depth 1 https://github.com/xdebug/xdebug.git /tmp/xdebug \
&& cd /tmp/xdebug \
&& phpize \
&& ./configure \
&& make \
&& make install \
&& rm -rf /tmp/xdebug
FROM build-base AS imagick-ext
# Build and install imagick
RUN docker-php-source extract \
&& git clone --branch 3.7.0 --depth 1 https://github.com/imagick/imagick /tmp/imagick \
&& cd /tmp/imagick \
&& phpize \
&& ./configure \
&& make \
&& make install \
&& rm -rf /tmp/imagick
FROM build-base AS gd-ext
# Install others php dependencies
RUN docker-php-source extract \
# GD
&& docker-php-ext-configure gd --enable-gd --with-freetype --with-jpeg --with-webp \
&& docker-php-ext-install gd \
## cleanup
&& docker-php-source delete
FROM alpine:latest AS final-stage
LABEL Maintainer="Luis Henrique Guimarães <contato@luishgp.com.br>" \
Description="Lightweight container with Nginx & PHP-FPM based on Alpine Linux."
RUN apk update && apk add --no-cache \
curl \
git \
supervisor \
nginx \
runit \
php82 \
php82-fpm \
php82-phar \
php82-openssl \
php82-curl \
php82-opcache \
php82-redis \
php82-pgsql \
php82-pdo_pgsql \
php82-dom \
php82-xml \
php82-simplexml \
php82-xmlwriter \
php82-soap \
php82-exif \
php82-sodium \
php82-tokenizer \
php82-fileinfo \
php82-iconv \
php82-bcmath \
openssh \
grpc-cpp \
zstd-libs \
libpng \
libjpeg \
libwebp \
freetype \
libgomp \
imagemagick-libs \
# Bring in gettext so we can get `envsubst`, then throw
# the rest away. To do this, we need to install `gettext`
# then move `envsubst` out of the way so `gettext` can
# be deleted completely, then move `envsubst` back.
&& apk add --no-cache --virtual .gettext gettext \
&& mv /usr/bin/envsubst /tmp/ \
&& runDeps="$( \
scanelf --needed --nobanner /tmp/envsubst \
| awk '{ gsub(/,/, "\nso:", $2); print "so:" $2 }' \
| sort -u \
| xargs -r apk info --installed \
| sort -u \
)" \
&& apk add --no-cache $runDeps \
&& apk del .gettext \
&& mv /tmp/envsubst /usr/local/bin/ \
# Remove alpine cache
&& rm -rf /var/cache/apk/* \
# Remove default server definition
&& rm /etc/nginx/http.d/default.conf
ARG USERNAME=pilot
ARG USER_UID=1000
ARG USER_GID=$USER_UID
# Create system user to run Composer and Artisan Commands
RUN addgroup -g $USER_GID $USERNAME \
&& adduser -u $USER_UID -G $USERNAME -s /bin/bash -h /home/$USERNAME -D $USERNAME \
&& mkdir -p /home/$USERNAME/.composer \
&& chown -R $USERNAME:$USERNAME /home/$USERNAME
# Add configuration files
COPY --chown=$USERNAME rootfs/ /
# Get latest Composer
COPY --from=composer:latest /usr/bin/composer /usr/bin/composer
# Copy extensions from the php-ext stage
COPY --from=grpc-ext /usr/local/lib/php/extensions/no-debug-non-zts-20220829/grpc.so /usr/lib/php82/modules/grpc.so
COPY --from=mongodb-ext /usr/local/lib/php/extensions/no-debug-non-zts-20220829/mongodb.so /usr/lib/php82/modules/mongodb.so
COPY --from=imagick-ext /usr/local/lib/php/extensions/no-debug-non-zts-20220829/imagick.so /usr/lib/php82/modules/imagick.so
COPY --from=gd-ext /usr/local/lib/php/extensions/no-debug-non-zts-20220829/gd.so /usr/lib/php82/modules/gd.so
RUN echo 'extension=grpc' >> /etc/php82/conf.d/30_grpc.ini \
&& echo 'extension=mongodb' >> /etc/php82/conf.d/30_mongodb.ini \
&& echo 'extension=imagick' >> /etc/php82/conf.d/30_imagick.ini \
&& echo 'extension=gd' >> /etc/php82/conf.d/30_gd.ini
# Make sure files/folders needed by the processes are accessable when they run under the nobody user
RUN chown -R $USERNAME:$USERNAME /run \
&& chown -R $USERNAME:$USERNAME /var/lib/nginx \
&& chown -R $USERNAME:$USERNAME /var/log/nginx
# Add application
WORKDIR /var/www/html
# Expose the port nginx is reachable on
EXPOSE 8080
# Let runit start nginx & php-fpm
CMD [ "/bin/docker-entrypoint.sh" ]
# Configure a healthcheck to validate that everything is up&running
HEALTHCHECK --timeout=10s CMD curl --silent --fail http://127.0.0.1:8080/fpm-ping
FROM final-stage AS php82-prod
# Production only dependencies, settings and paramteres
# Switch to use a non-root user from here on
USER $USERNAME
ENV clear_env=no \
display_errors=Off \
max_execution_time=0 \
max_input_time=-1 \
max_input_vars=1000 \
memory_limit=512M \
post_max_size=8M \
upload_max_filesize=2M \
zlib_output_compression=On \
opcache_enabled=1 \
opcache_memory_consumption=512M \
opcache_validate_timestamps=0 \
max_children=100
FROM final-stage AS php82-dev
# Development only dependencies, settings and paramteres
# Switch to use a non-root user from here on
USER $USERNAME
ENV clear_env=no \
display_errors=On \
max_execution_time=0 \
max_input_time=-1 \
max_input_vars=1000 \
memory_limit=512M \
post_max_size=8M \
upload_max_filesize=2M \
zlib_output_compression=On \
opcache_enabled=1 \
opcache_memory_consumption=512M \
opcache_validate_timestamps=0 \
max_children=100
FROM final-stage AS php82-local
## Local only dependencies, settings and paramteres
RUN \
mkdir -p /profiles/xdebug \
&& mkdir -p /profiles/xhprof \
&& mkdir -p /xhprof \
&& chmod -R 777 /profiles
COPY --from=xhprof-ext /usr/local/lib/php/extensions/no-debug-non-zts-20220829/xhprof.so /usr/lib/php82/modules/xhprof.so
COPY --from=xhprof-ext /xhprof /xhprof
COPY --from=xdebug-ext /usr/local/lib/php/extensions/no-debug-non-zts-20220829/xdebug.so /usr/lib/php82/modules/xdebug.so
COPY scripts/02-php-debug.sh /docker-entrypoint-init.d/02-php-debug.sh
RUN \
chown -R $USERNAME:$USERNAME /profiles \
&& chown $USERNAME:$USERNAME /docker-entrypoint-init.d/02-php-debug.sh \
&& chmod +X /docker-entrypoint-init.d/02-php-debug.sh
# Switch to use a non-root user from here on
USER $USERNAME
ENV clear_env=no \
display_errors=On \
max_execution_time=0 \
max_input_time=-1 \
max_input_vars=1000 \
memory_limit=512M \
post_max_size=8M \
upload_max_filesize=2M \
zlib_output_compression=On \
opcache_enabled=0 \
max_children=100
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment