Sign inSign up

oorabona/php

By oorabona

•Updated 1 day ago

php container

Image
0

10K+

oorabona/php repository overview

⁠PHP-FPM

Production-ready PHP-FPM container with Composer integration, optimized for modern PHP applications. Built on Alpine Linux with essential extensions and security hardening.

Docker Hub GHCR Build

⁠Verify this image

Every build ships a Sigstore-signed SBOM and a full Trivy scan — verify them yourself, no login required:

gh attestation verify oci://ghcr.io/oorabona/php:8.4-fpm-alpine --owner oorabona

Full walkthrough (SBOM payload, Trivy findings, multi-arch manifest inspection, upstream dependency tracking) → https://oorabona.github.io/docker-containers/verify-images/⁠

⁠Quick Start

# Pull from GitHub Container Registry
docker pull ghcr.io/oorabona/php:8.4-fpm-alpine

# Pull from Docker Hub
docker pull oorabona/php:8.4-fpm-alpine

⁠Features

⁠PHP Extensions
  • gd - Image processing with FreeType and JPEG support
  • mysqli - MySQL database connectivity
  • opcache - Opcode caching for performance
  • zip - ZIP archive handling
  • apcu - User-space caching
⁠Included Tools
  • Composer 2.9.5 - Dependency management
  • Git - Version control for Composer
  • Custom helper scripts:
    • entrypoint-fpm - Container initialization
    • healthcheck-fpm - Health monitoring
    • command-loop - Background command runner
    • command-loop-w-cooldown - Command runner with cooldown
⁠Configuration
  • Production-ready php.ini settings
  • Optimized OPcache configuration (512MB, 20,000 files)
  • APCu enabled for user-space caching
  • Security hardening (expose_php=off, session security)
  • Custom PHP-FPM pool configuration
  • Session management ready for Redis (commented out)
⁠Security Features
  • Non-root user (nobody)
  • Minimal Alpine base (reduced attack surface)
  • Multi-stage build (build dependencies removed)
  • Hardened session security (HTTPOnly, Secure, SameSite)
  • Read-only filesystem compatible
  • Capability dropping support

⁠Usage

⁠Docker Compose
services:
  php:
    image: ghcr.io/oorabona/php:8.4-fpm-alpine
    volumes:
      - ./app:/var/www/app
      - composer-cache:/var/www/.composer
    environment:
      APP_ENV: prod
      APP_DEBUG: 0
    networks:
      - backend
    healthcheck:
      test: ["CMD", "healthcheck-fpm"]
      interval: 30s
      timeout: 10s
      retries: 3

  nginx:
    image: nginx:alpine
    ports:
      - "80:80"
    volumes:
      - ./app:/var/www/app:ro
      - ./nginx.conf:/etc/nginx/conf.d/default.conf:ro
    depends_on:
      - php
    networks:
      - backend

networks:
  backend:

volumes:
  composer-cache:
⁠Docker Run
# Run PHP-FPM
docker run -d \
  --name php-fpm \
  -v $(pwd)/app:/var/www/app \
  -v composer-cache:/var/www/.composer \
  ghcr.io/oorabona/php:8.4-fpm-alpine

# Run Composer commands
docker run --rm \
  -v $(pwd):/var/www/app \
  -w /var/www/app \
  ghcr.io/oorabona/php:8.4-fpm-alpine \
  composer install
⁠Nginx Configuration Example

PHP-FPM requires a web server (Nginx, Apache, Caddy, etc.). Example Nginx configuration:

server {
    listen 80;
    root /var/www/app/public;
    index index.php;

    location / {
        try_files $uri $uri/ /index.php?$query_string;
    }

    location ~ \.php$ {
        fastcgi_pass php:9000;  # PHP-FPM service name
        fastcgi_index index.php;
        fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
        include fastcgi_params;
    }
}

⁠Configuration

⁠Build Arguments
ArgumentDescriptionDefault
VERSIONPHP base image version(required)
COMPOSER_VERSIONComposer version2.9.5
APCU_VERSIONAPCu extension version5.1.28
COMPOSER_AUTHComposer authentication JSON for private repos""
⁠Environment Variables
VariableDescriptionDefault
APP_ENVApplication environmentprod
APP_DEBUGDebug mode (0=off, 1=on)0
APP_BASE_PATHApplication base path/var/www/app/
COMPOSER_AUTHComposer authentication (build-time)""
COMPOSER_CACHE_DIRComposer cache directory/var/www/.composer/
⁠Volumes
PathPurpose
/var/www/Application root and Composer cache
/var/www/app/Application code directory
/var/www/.composer/Composer cache (mount for persistence)
/var/log/shared/Shared log directory
⁠Ports
PortProtocolPurpose
9000TCPPHP-FPM FastCGI (NOT HTTP)

Important: PHP-FPM listens on port 9000 for FastCGI connections. This is NOT an HTTP port. You must use a web server (Nginx, Apache, etc.) to handle HTTP requests and proxy to PHP-FPM.

⁠Security

⁠Base Security
  • Non-root user: Runs as nobody user
  • Alpine-based: Minimal base image (~80MB)
  • Multi-stage build: Build dependencies removed from final image
  • Production php.ini: Secure defaults (expose_php=off)
  • Session hardening: HTTPOnly, Secure, SameSite=Strict
  • Read-only filesystem: Compatible with --read-only flag
⁠Runtime Hardening
services:
  php:
    image: ghcr.io/oorabona/php:8.4-fpm-alpine
    read_only: true
    tmpfs:
      - /tmp
      - /run
    cap_drop:
      - ALL
    security_opt:
      - no-new-privileges:true
    volumes:
      - ./app:/var/www/app:ro
      - composer-cache:/var/www/.composer
    user: "nobody:nobody"
⁠Docker Run Security
docker run -d \
  --name php-fpm \
  --read-only \
  --tmpfs /tmp \
  --tmpfs /run \
  --cap-drop ALL \
  --security-opt no-new-privileges:true \
  -v $(pwd)/app:/var/www/app:ro \
  -v composer-cache:/var/www/.composer \
  ghcr.io/oorabona/php:8.4-fpm-alpine
⁠Security Best Practices
  • Never include COMPOSER_AUTH with credentials in version control
  • Use Docker secrets or environment variables for sensitive data
  • Mount application code as read-only in production (:ro)
  • Keep PHP and dependencies updated via automated builds
  • Review uploaded files if handling file uploads
  • Use HTTPS only (ensure session.cookie_secure=1 works)

⁠PHP Configuration Details

⁠OPcache Settings
opcache.memory_consumption=512        # 512MB cache
opcache.max_accelerated_files=20000   # Cache up to 20,000 files
opcache.validate_timestamps=0         # No revalidation (production)
opcache.revalidate_freq=2             # Check every 2 seconds (if enabled)
opcache.enable_cli=1                  # Enable for CLI scripts
⁠APCu Settings
apc.enable_cli=1                      # Enable for CLI
apc.enable=1                          # Enable for web requests
⁠Resource Limits
memory_limit=256M                     # 256MB per request
max_execution_time=360                # 6 minutes
post_max_size=100M                    # Max POST size
upload_max_filesize=100M              # Max file upload size
⁠Session Security
session.cookie_httponly=1             # JavaScript cannot access
session.cookie_secure=1               # HTTPS only
session.cookie_same_site=Strict       # CSRF protection
session.use_strict_mode=1             # Reject uninitialized session IDs

⁠Dependencies

This container includes pinned versions of third-party dependencies:

DependencyVersionSourceLicense
Composer2.9.5composer/composer⁠MIT
APCu5.1.28krakjoe/apcu⁠PHP-3.01

Versions are automatically monitored and updated via GitHub Actions.

⁠Architecture

Supported Platforms:

  • linux/amd64
  • linux/arm64

Base Images:

  • Build stage: composer:${COMPOSER_VERSION} (Alpine)
  • Runtime stage: php:${VERSION} (Alpine FPM)

Size: ~80MB compressed

⁠Advanced Usage

⁠Using Composer Authentication

For private repositories, pass authentication at build time:

# Create composer auth JSON
cat > auth.json <<EOF
{
  "github-oauth": {
    "github.com": "ghp_yourTokenHere"
  }
}
EOF

# Build with authentication
docker build \
  --build-arg VERSION=8.4-fpm-alpine \
  --build-arg COMPOSER_AUTH="$(cat auth.json)" \
  -t php:custom .

Warning: Never commit COMPOSER_AUTH to version control. Use build secrets or CI variables.

⁠Custom PHP Extensions

To add additional extensions, create a custom Dockerfile:

FROM ghcr.io/oorabona/php:8.4-fpm-alpine

USER root
RUN apk add --no-cache --virtual .build-deps $PHPIZE_DEPS \
    && pecl install redis \
    && docker-php-ext-enable redis \
    && apk del .build-deps

USER nobody
⁠Development Mode

For development, you may want timestamps validation and display_errors:

FROM ghcr.io/oorabona/php:8.4-fpm-alpine

USER root
RUN echo "opcache.validate_timestamps=1" >> $PHP_INI_DIR/conf.d/php.ini \
    && echo "display_errors=on" >> $PHP_INI_DIR/conf.d/php.ini \
    && echo "error_reporting=E_ALL" >> $PHP_INI_DIR/conf.d/php.ini

USER nobody
ENV APP_ENV=dev
ENV APP_DEBUG=1
⁠Command Loop Scripts

The container includes helper scripts for running background commands:

# Run command repeatedly
docker exec php-fpm command-loop "php artisan queue:work"

# Run with cooldown period between executions
docker exec php-fpm command-loop-w-cooldown "php artisan schedule:run"

⁠Version Management

# Check current version
./version.sh

# Check latest upstream version
./version.sh latest

# Output format (JSON for CI integration)
./version.sh --json

⁠Building Locally

# From repository root
cd php

# Build with specific PHP version
docker build \
  --build-arg VERSION=8.4-fpm-alpine \
  --build-arg COMPOSER_VERSION=2.9.5 \
  --build-arg APCU_VERSION=5.1.28 \
  -t php:8.4-fpm-alpine .

# Build with docker-compose
docker-compose build

⁠Common Frameworks

⁠Laravel
services:
  php:
    image: ghcr.io/oorabona/php:8.4-fpm-alpine
    volumes:
      - ./laravel:/var/www/app
    environment:
      APP_ENV: production
      APP_DEBUG: 0
    working_dir: /var/www/app
⁠Symfony
services:
  php:
    image: ghcr.io/oorabona/php:8.4-fpm-alpine
    volumes:
      - ./symfony:/var/www/app
    environment:
      APP_ENV: prod
      APP_DEBUG: 0
    working_dir: /var/www/app/public
⁠WordPress

For WordPress, consider using the wordpress container⁠ which includes additional optimizations.

⁠Troubleshooting

⁠Health Check Failing
# Check PHP-FPM status
docker exec php-fpm healthcheck-fpm

# Check PHP-FPM logs
docker logs php-fpm

# Validate FPM configuration
docker exec php-fpm php-fpm -t
⁠Connection Issues
# Verify PHP-FPM is listening on port 9000
docker exec php-fpm netstat -tlnp | grep 9000

# Test from web server container
docker exec nginx nc -zv php 9000
⁠Composer Issues
# Clear Composer cache
docker exec php-fpm composer clear-cache

# Diagnose Composer
docker exec php-fpm composer diagnose

# Check Composer version
docker exec php-fpm composer --version
⁠Permission Issues
# Check ownership
docker exec php-fpm ls -la /var/www/

# Fix ownership (if needed)
docker exec -u root php-fpm chown -R nobody:nobody /var/www/

Tag summary

Content type

Image

Digest

sha256:57c3bf373…

Size

43.8 MB

Last updated

1 day ago

docker pull oorabona/php