- Update Nginx logging with structured JSON and standard combined format for Elastic integration.

- Add new upstream PHP-FPM servers to Nginx configuration for enhanced load balancing.
- Introduce Elastic APM PHP agent in `php.ini` and update Dockerfile for better dependency management.
- Secure Kibana and Elasticsearch connections in Metricbeat/Filebeat configurations with credentials.
- Remove unused PHP dependencies from `composer.json` and `composer.lock`.
This commit is contained in:
Jeppe Bundgaard
2026-02-16 10:58:50 +01:00
parent 8d8137852f
commit 8c8de541be
9 changed files with 216 additions and 1566 deletions
+6
View File
@@ -1,3 +1,5 @@
strict.perms: false
filebeat.inputs:
- type: filestream
id: nginx-access
@@ -28,6 +30,10 @@ filebeat.inputs:
fields_under_root: true
setup.kibana.host: "http://kibana:5601"
setup.kibana.username: elastic
setup.kibana.password: ${ELASTIC_PASSWORD}
output.elasticsearch:
hosts: ["http://elasticsearch:9200"]
username: elastic
password: ${ELASTIC_PASSWORD}
+4
View File
@@ -3,10 +3,14 @@ metricbeat.config.modules:
reload.enabled: false
setup.kibana.host: "http://kibana:5601"
setup.kibana.username: elastic
setup.kibana.password: ${ELASTIC_PASSWORD}
setup.dashboards.enabled: true
output.elasticsearch:
hosts: ["http://elasticsearch:9200"]
username: elastic
password: ${ELASTIC_PASSWORD}
metricbeat.modules:
# System metrics (container-level when running in Docker Desktop)
+1 -2
View File
@@ -14,8 +14,7 @@
"php-http/guzzle7-adapter": "^1.1",
"nyholm/psr7": "^1.8",
"mailersend/mailersend": "^0.28.0",
"spipu/html2pdf": "^5.3",
"microsoft/microsoft-graph": "2.7.0"
"spipu/html2pdf": "^5.3"
},
"config": {
"allow-plugins": {
+4 -1539
View File
File diff suppressed because it is too large Load Diff
+52
View File
@@ -34,6 +34,9 @@ http {
least_conn;
server php1:9000 max_fails=3 fail_timeout=10s;
server php2:9000 max_fails=3 fail_timeout=10s;
server php3:9000 max_fails=3 fail_timeout=10s;
server php4:9000 max_fails=3 fail_timeout=10s;
server php5:9000 max_fails=3 fail_timeout=10s;
keepalive 32;
}
@@ -46,6 +49,55 @@ http {
return 301 https://$host$request_uri;
}
# Localhost api server block (api.truckwash.dk)
server {
listen 80;
server_name localhost;
# Logging
add_header X-Request-Id $req_id always;
error_log /var/log/nginx/error.log;
access_log /var/log/nginx/access.ndjson json;
# Index file
index index.php index.html index.htm;
# Root directory (public- uses index.php)
root /var/www/html;
# Location block for PHP files
location ^~ / {
add_header Access-Control-Allow-Methods "GET, POST, OPTIONS, PUT, DELETE";
add_header Access-Control-Allow-Headers "Authorization, Content-Type, X-Requested-With, X-Customer-Number";
add_header Access-Control-Allow-Credentials true;
if ($request_method = 'OPTIONS') {
add_header Access-Control-Allow-Origin *;
add_header Access-Control-Allow-Methods "GET, POST, OPTIONS, PUT, DELETE";
add_header Access-Control-Allow-Headers "Authorization, Content-Type, X-Requested-With, X-Customer-Number";
return 204;
}
include fastcgi_params;
fastcgi_pass php_fpm;
fastcgi_index index.php;
fastcgi_read_timeout 60s;
fastcgi_param SCRIPT_FILENAME $document_root/index.php;
fastcgi_param X_REQUEST_ID $req_id;
fastcgi_keep_conn on;
}
# Deny access to .htaccess files
location ~ /\.ht {
deny all;
}
# Deny access to hidden files
location ~ /\. {
deny all;
}
}
server {
listen 443 ssl;
server_name api.truckwash.dk;
+2 -1
View File
@@ -13,7 +13,8 @@ http {
log_format json escape=json '{"time":"$time_iso8601","req_id":"$req_id","remote":"$remote_addr","host":"$host","method":"$request_method","uri":"$request_uri","status":$status,"bytes":$bytes_sent,"referer":"$http_referer","ua":"$http_user_agent","up_addr":"$upstream_addr","up_st":"$upstream_status","up_rt":$upstream_response_time,"rt":$request_time}';
# Log settings
access_log /var/log/nginx/access.ndjson json;
access_log /var/log/nginx/access.ndjson json; # structured JSON for ELK
access_log /var/log/nginx/access.log; # standard combined for Elastic Agent nginx integration
error_log /var/log/nginx/error.log warn;
# Gzip settings (optional)
+42 -24
View File
@@ -1,6 +1,5 @@
# Use the official PHP 8.2 image with Apache disabled
FROM php:8.2-fpm
FROM php:8.2.15-fpm
# Set the working directory inside the container
WORKDIR /var/www/html
@@ -9,25 +8,44 @@ COPY --from=composer:latest /usr/bin/composer /usr/bin/composer
# Install required extensions and dependencies
# - Include libssl-dev and ca-certificates to guarantee PHP openssl extension and TLS trust store
RUN apt-get update && apt-get install -y \
libpng-dev \
libonig-dev \
libxml2-dev \
libmagickwand-dev \
imagemagick \
pkg-config \
zip \
git \
curl \
libzip-dev \
libssl-dev \
ca-certificates \
default-mysql-client \
&& update-ca-certificates \
&& docker-php-ext-install mbstring exif pcntl bcmath gd pdo_mysql mysqli zip openssl \
&& pecl install imagick \
&& docker-php-ext-enable imagick
# Install required extensions and dependencies
# Install required extensions and dependencies
RUN set -eux; \
apt-get update; \
apt-get install -y --no-install-recommends \
$PHPIZE_DEPS \
libpng-dev \
libjpeg62-turbo-dev \
libfreetype6-dev \
libxml2-dev \
libonig-dev \
libmagickwand-dev \
libmagickcore-dev \
imagemagick \
pkg-config \
zip \
unzip \
git \
curl \
libzip-dev \
libssl-dev \
ca-certificates \
mariadb-client; \
update-ca-certificates; \
docker-php-ext-configure gd --with-freetype --with-jpeg; \
docker-php-ext-install -j"$(nproc)" \
mbstring \
exif \
pcntl \
bcmath \
gd \
pdo_mysql \
mysqli \
zip; \
pecl install imagick-3.7.0; \
docker-php-ext-enable imagick; \
apt-get purge -y --auto-remove -o APT::AutoRemove::RecommendsImportant=false $PHPIZE_DEPS; \
rm -rf /var/lib/apt/lists/*
## Do not copy application code at build time; it will be bind-mounted by docker-compose
## If you wish to build a self-contained image, uncomment the next line and adjust the path:
@@ -44,11 +62,11 @@ ENV COMPOSER_ALLOW_SUPERUSER=1
WORKDIR /var/www/html
# Copy and enable entrypoint that installs Composer deps on first run
COPY services/php/docker-entrypoint.sh /usr/local/bin/docker-entrypoint.sh
RUN chmod +x /usr/local/bin/docker-entrypoint.sh
#COPY services/php/docker-entrypoint.sh /usr/local/bin/docker-entrypoint.sh
#RUN chmod +x /usr/local/bin/docker-entrypoint.sh
# Expose port 9000
EXPOSE 9000
ENTRYPOINT ["/usr/local/bin/docker-entrypoint.sh"]
#ENTRYPOINT ["/usr/local/bin/docker-entrypoint.sh"]
CMD ["php-fpm"]
+6
View File
@@ -8,3 +8,9 @@ session.save_path = "tcp://redis:6379?database=0"
; Logging
log_errors = On
error_log = /var/log/php/error.log
; Elastic APM PHP agent
; The extension is installed via apt (elastic-apm-php)
extension=elastic_apm.so
; Optional bootstrap (enables automatic instrumentation where supported)
;elastic_apm.bootstrap_php_part_file=/opt/elastic/apm-agent-php/src/bootstrap_php_part.php
+99
View File
@@ -8,6 +8,105 @@ Content-Type: application/json
"country_code": 45
}
### POST request to /subusers
POST https://api.truckwash.dk:4433/subusers
Accept: application/json
Content-Type: application/json
Authorization: Bearer e9d4359673de64f6a9bc4231bf50ac9f5726ad5b3ee6fcad5f8ebbb20647c3b8
{
"cvr": 41004355,
"phone_country_code": 45,
"phone": 42331128
}
### GET request to /subusers/setup
GET https://api.truckwash.dk:4433/subusers/setup?token=1c1be8280bac3937487e5c77b76bb839
Accept: application/json
Content-Type: application/json
Authorization: Bearer e9d4359673de64f6a9bc4231bf50ac9f5726ad5b3ee6fcad5f8ebbb20647c3b8
### POST request to /subusers/setup
POST https://api.truckwash.dk:4433/subusers/setup
Accept: application/json
Content-Type: application/json
Authorization: Bearer e9d4359673de64f6a9bc4231bf50ac9f5726ad5b3ee6fcad5f8ebbb20647c3b8
{
"token": "1c1be8280bac3937487e5c77b76bb839",
"name": "Test Subuser",
"username": "testsubuser",
"email": "jb@truckwash.dk",
"password": "Test1234"
}
### POST request to /subusers/auth/password
POST https://api.truckwash.dk:4433/subusers/auth/password
Accept: application/json
Content-Type: application/json
{
"username": "testsubuser",
"password": "Test1234"
}
### GET request to /order-bookings (As subuser)
GET https://api.truckwash.dk:4433/order-bookings
Accept: application/json
Content-Type: application/json
Authorization: Bearer 9ed711260d58165ee7601060bf7463f6e201481edd16c8ee4fc4a5f04b79a232
X-Customer-Number: 42331128
### GET request to /order-bookings (As subuser, specific ID)
GET https://api.truckwash.dk:4433/order-bookings?id=76
Accept: application/json
Content-Type: application/json
Authorization: Bearer 9ed711260d58165ee7601060bf7463f6e201481edd16c8ee4fc4a5f04b79a232
X-Customer-Number: 42331128
### GET request to /vehicles (As subuser)
GET https://api.truckwash.dk:4433/vehicles
Accept: application/json
Content-Type: application/json
Authorization: Bearer 9ed711260d58165ee7601060bf7463f6e201481edd16c8ee4fc4a5f04b79a232
X-Customer-Number: 42331128
### GET request to /vehicles (As subuser, specific ID)
GET https://api.truckwash.dk:4433/vehicles?id=384
Accept: application/json
Content-Type: application/json
Authorization: Bearer 9ed711260d58165ee7601060bf7463f6e201481edd16c8ee4fc4a5f04b79a232
X-Customer-Number: 42331128
### GET request to /orders (As subuser)
GET https://api.truckwash.dk:4433/orders
Accept: application/json
Content-Type: application/json
Authorization: Bearer 9ed711260d58165ee7601060bf7463f6e201481edd16c8ee4fc4a5f04b79a232
X-Customer-Number: 42331128
### GET request to /subusers/me (As subuser)
GET https://api.truckwash.dk:4433/subusers/me
Accept: application/json
Content-Type: application/json
Authorization: Bearer 9ed711260d58165ee7601060bf7463f6e201481edd16c8ee4fc4a5f04b79a232
X-Customer-Number: 42331128
### GET request to /subusers/permission-nodes
GET https://api.truckwash.dk:4433/subusers/permission-nodes
Accept: application/json
Content-Type: application/json
Authorization: Bearer e9d4359673de64f6a9bc4231bf50ac9f5726ad5b3ee6fcad5f8ebbb20647c3b8
### GET request to /subusers/grants (As subuser)
GET https://api.truckwash.dk:4433/subusers/grants
Accept: application/json
Content-Type: application/json
Authorization: Bearer 9ed711260d58165ee7601060bf7463f6e201481edd16c8ee4fc4a5f04b79a232
X-Customer-Number: 42331128
### GET request to order bookings (list all)
GET https://api.truckwash.dk:4433/order-bookings
Accept: application/json