From 34d536d5a194c9df9073d20c8046c8f09aca6719 Mon Sep 17 00:00:00 2001 From: Robert Lemke Date: Tue, 19 Nov 2024 14:39:01 +0100 Subject: [PATCH] Introduce NGINX_CUSTOM_LOCATION_BLOCK_BASE64 This variable is a very low-level feature. It allows to insert a location block into the Nginx configuration. The variable's value must be Base64-encoded. Example of such a block (not yet encoded): ``` location = /.well-known/com.apple.remotemanagement { default_type application/json; return 200 '{"Servers":[{"Version":"mdm-adde","BaseURL":"https://mdm.example.com/api/v2enrollment/enroll/adde"}]}'; add_header Content-Type 'application/json' always; } ``` --- README.md | 120 +++++++++--------- root-files/opt/flownative/lib/nginx-legacy.sh | 9 ++ 2 files changed, 71 insertions(+), 58 deletions(-) diff --git a/README.md b/README.md index 8c306b9..faabe04 100644 --- a/README.md +++ b/README.md @@ -4,9 +4,12 @@ ![Build Docker Image on tag](https://github.com/flownative/docker-nginx/actions/workflows/docker.build.onpush.yaml/badge.svg) # Flownative Nginx Image -A Docker image providing [Nginx](https://nginx.org) for [Beach](https://www.flownative.com/beach), -[Local Beach](https://www.flownative.com/localbeach) and other purposes. Compared to other -Nginx images, this one provides specific features which come in handy for running a +A Docker image providing [Nginx](https://nginx.org) +for [Beach](https://www.flownative.com/beach), +[Local Beach](https://www.flownative.com/localbeach) and other purposes. +Compared to other +Nginx images, this one provides specific features which come in handy for +running a [Neos CMS](https://www.neos.io) instance or Neos Flow application. ## tl;dr @@ -42,16 +45,16 @@ and /opt/flownative/log/nginx-access.log. If the log format is "json", the access log file is /opt/flownative/log/nginx-access.json.log Note that the error log only contains errors related to the webserver itself. -Requests resulting in status codes like 404 (not found) or 503 (internal -server error) are logged to the access log, if it is enabled. +Requests resulting in status codes like 404 (not found) or 503 (internal +server error) are logged to the access log, if it is enabled. The log level for the error log can be defined via the `NGINX_LOG_LEVEL` environment variable. See the [Nginx documentation](https://docs.nginx.com/nginx/admin-guide/monitoring/logging/) for possible values. The default value is `warn`. -The access log is disabled by default, it can be enabled by setting -`NGINX_ACCESS_LOG_ENABLE` to "true". +The access log is disabled by default, it can be enabled by setting +`NGINX_ACCESS_LOG_ENABLE` to "true". The access log's default format is similar to the standard Nginx "combined" format with a few additions, so that the IP address of @@ -61,67 +64,68 @@ behind a reverse proxy. Instead of the default format, a JSON format can be used by setting `NGINX_ACCESS_LOG_FORMAT` to "json". -The access log may contain a lot of entries, if enabled. If you are only -interested in requests resulting in certain status codes (for example +The access log may contain a lot of entries, if enabled. If you are only +interested in requests resulting in certain status codes (for example internal server errors), you can define a regular expression which filters out -other log entries. Setting `NGINX_ACCESS_LOG_IGNORED_STATUS_CODES_REGEX` to -"^[234]" will ignore all responses whose status code starts with "2", "3" or -"4" respectively. Therefore, only 5xx errors will then end up in the access +other log entries. Setting `NGINX_ACCESS_LOG_IGNORED_STATUS_CODES_REGEX` to +"^[234]" will ignore all responses whose status code starts with "2", "3" or +"4" respectively. Therefore, only 5xx errors will then end up in the access log. By default, connection-related status (1xx) and redirects (3xx) will be ignored. -NOTE: Be careful when specifying the regular expression, because syntax +NOTE: Be careful when specifying the regular expression, because syntax errors might keep Nginx from starting. ### Environment variables -| Variable Name | Type | Default | Description | -|:---------------------------------------------|:--------|:--------------------------------------|:------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| -| NGINX_BASE_PATH | string | /opt/flownative/nginx | Base path for Nginx | -| NGINX_ERROR_LOG_LEVEL | string | warn | Nginx log level (see [documentation](https://docs.nginx.com/nginx/admin-guide/monitoring/logging/)) | -| NGINX_ACCESS_LOG_ENABLE | boolean | no | Nginx log level (see [documentation](https://docs.nginx.com/nginx/admin-guide/monitoring/logging/)) | -| NGINX_ACCESS_LOG_FORMAT | string | default | Format of the access log; possible values are "default" and "json" | -| NGINX_ACCESS_LOG_MODE | string | dynamic | Defines which requests should be logged: "dynamic" only logs dynamic requests to PHP, "all" also includes requests to static files | -| NGINX_ACCESS_LOG_IGNORED_STATUS_CODES_REGEX | string | ^[13] | Regular expression which defines which status codes should NOT be logged into the access log | -| NGINX_CACHE_ENABLE | boolean | no | If the FastCGI cache should be enabled; see section about caching | -| NGINX_CACHE_NAME | string | application | Name of the memory zone Nginx should use for caching | -| NGINX_CACHE_DEFAULT_LIFETIME | string | 5s | Default cache lifetime to use when caching is enabled | -| NGINX_CACHE_MAX_SIZE | string | 1024m | Maximum memory size for the FastCGI cache | -| NGINX_CACHE_INACTIVE | string | 1h | Time after which cache entries are removed automatically | -| NGINX_CACHE_USE_STALE_OPTIONS | string | updating error timeout invalid_header | Options to pass to the `fastcgi_cache_use_stale` directive | -| NGINX_CACHE_BACKGROUND_UPDATE | boolean | off | If background updates should be enabled | -| NGINX_CUSTOM_ERROR_PAGE_CODES | string | 500 501 502 503 | FastCGI error codes which should redirect to the custom error page; codes are separated by spaces | -| NGINX_CUSTOM_ERROR_PAGE_TARGET | string | | Upstream URL to use for custom FastCGI error pages, for example https://example.com/maintenance.html | -| NGINX_STATIC_ROOT | string | /var/www/html | Document root path for when BEACH_NGINX_MODE is "Static" | -| NGINX_STRICT_TRANSPORT_SECURITY_ENABLE | boolean | no | If Strict-Transport-Security headers should be sent (HSTS) | -| NGINX_STRICT_TRANSPORT_SECURITY_PRELOAD | boolean | no | If site should be added to list of HTTPS-only sites by Google and others | -| NGINX_STRICT_TRANSPORT_SECURITY_MAX_AGE | boolean | 31536000 | Maxmimum age for Strict-Transport-Security header, if enabled | -| NGINX_AUTH_BASIC_REALM | string | off | Realm for HTTP Basic Authentication; if "off", authentication is disabled | -| NGINX_AUTH_BASIC_USERNAME | string | | Username for HTTP Basic Authentication | -| NGINX_AUTH_BASIC_ENCODED_HASHED_PASSWORD | string | | Base64-encoded hashed password (using httpasswd) for HTTP Basic Authentication | -| NGINX_ENABLE_UNDERSCORES_IN_HEADERS | boolean | no | Enables or disables the use of underscores in client request header fields. | -| BEACH_NGINX_CUSTOM_METRICS_ENABLE | boolean | no | If support for a custom metrics endpoint should be enabled | -| BEACH_NGINX_CUSTOM_METRICS_SOURCE_PATH | string | /metrics | Path where metrics are located | -| BEACH_NGINX_CUSTOM_METRICS_TARGET_PORT | integer | 8082 | Port at which Nginx should listen to provide the metrics for scraping | -| BEACH_NGINX_MODE | string | Flow | Either "Flow" or "Static"; this variable is going to be renamed in the future | -| BEACH_ASSET_PROXY_ENDPOINT | string | | Endpoint of a cloud storage frontend to use for proxying requests to Flow persistent resources. Requires BEACH_PERSISTENT_RESOURCES_BASE_PATH to be set. Example: "https://assets.flownative.com/example-bucket/" | -| BEACH_ASSET_PROXY_RESOLVER | string | 8.8.8.8 | IP address of a DNS server to use for resolving domains when proxying assets. Set this to 127.0.0.11 when using Local Beach. | -| BEACH_PERSISTENT_RESOURCES_BASE_PATH | string | | Base path of URLs pointing to Flow persistent resources; example: "https://www.flownative.com/assets/" | -| BEACH_STATIC_RESOURCES_LIFETIME | string | 30d | Expiration time for static resources; examples: "3600s" or "7d" or "max" | -| FLOW_HTTP_TRUSTED_PROXIES | string | 10.0.0.0/8 | Nginx passes FLOW_HTTP_TRUSTED_PROXIES to the virtual host using the value of this variable | +| Variable Name | Type | Default | Description | +|:--------------------------------------------|:--------|:--------------------------------------|:------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| +| NGINX_BASE_PATH | string | /opt/flownative/nginx | Base path for Nginx | +| NGINX_ERROR_LOG_LEVEL | string | warn | Nginx log level (see [documentation](https://docs.nginx.com/nginx/admin-guide/monitoring/logging/)) | +| NGINX_ACCESS_LOG_ENABLE | boolean | no | Nginx log level (see [documentation](https://docs.nginx.com/nginx/admin-guide/monitoring/logging/)) | +| NGINX_ACCESS_LOG_FORMAT | string | default | Format of the access log; possible values are "default" and "json" | +| NGINX_ACCESS_LOG_MODE | string | dynamic | Defines which requests should be logged: "dynamic" only logs dynamic requests to PHP, "all" also includes requests to static files | +| NGINX_ACCESS_LOG_IGNORED_STATUS_CODES_REGEX | string | ^[13] | Regular expression which defines which status codes should NOT be logged into the access log | +| NGINX_CACHE_ENABLE | boolean | no | If the FastCGI cache should be enabled; see section about caching | +| NGINX_CACHE_NAME | string | application | Name of the memory zone Nginx should use for caching | +| NGINX_CACHE_DEFAULT_LIFETIME | string | 5s | Default cache lifetime to use when caching is enabled | +| NGINX_CACHE_MAX_SIZE | string | 1024m | Maximum memory size for the FastCGI cache | +| NGINX_CACHE_INACTIVE | string | 1h | Time after which cache entries are removed automatically | +| NGINX_CACHE_USE_STALE_OPTIONS | string | updating error timeout invalid_header | Options to pass to the `fastcgi_cache_use_stale` directive | +| NGINX_CACHE_BACKGROUND_UPDATE | boolean | off | If background updates should be enabled | +| NGINX_CUSTOM_ERROR_PAGE_CODES | string | 500 501 502 503 | FastCGI error codes which should redirect to the custom error page; codes are separated by spaces | +| NGINX_CUSTOM_ERROR_PAGE_TARGET | string | | Upstream URL to use for custom FastCGI error pages, for example https://example.com/maintenance.html | +| NGINX_CUSTOM_LOCATION_BLOCK_BASE64 | string | | Base64-encoded Nginx location block to include in the server configuration. The block will be included in the server configuration before the default location block. Be careful! | +| NGINX_STATIC_ROOT | string | /var/www/html | Document root path for when BEACH_NGINX_MODE is "Static" | +| NGINX_STRICT_TRANSPORT_SECURITY_ENABLE | boolean | no | If Strict-Transport-Security headers should be sent (HSTS) | +| NGINX_STRICT_TRANSPORT_SECURITY_PRELOAD | boolean | no | If site should be added to list of HTTPS-only sites by Google and others | +| NGINX_STRICT_TRANSPORT_SECURITY_MAX_AGE | boolean | 31536000 | Maxmimum age for Strict-Transport-Security header, if enabled | +| NGINX_AUTH_BASIC_REALM | string | off | Realm for HTTP Basic Authentication; if "off", authentication is disabled | +| NGINX_AUTH_BASIC_USERNAME | string | | Username for HTTP Basic Authentication | +| NGINX_AUTH_BASIC_ENCODED_HASHED_PASSWORD | string | | Base64-encoded hashed password (using httpasswd) for HTTP Basic Authentication | +| NGINX_ENABLE_UNDERSCORES_IN_HEADERS | boolean | no | Enables or disables the use of underscores in client request header fields. | +| BEACH_NGINX_CUSTOM_METRICS_ENABLE | boolean | no | If support for a custom metrics endpoint should be enabled | +| BEACH_NGINX_CUSTOM_METRICS_SOURCE_PATH | string | /metrics | Path where metrics are located | +| BEACH_NGINX_CUSTOM_METRICS_TARGET_PORT | integer | 8082 | Port at which Nginx should listen to provide the metrics for scraping | +| BEACH_NGINX_MODE | string | Flow | Either "Flow" or "Static"; this variable is going to be renamed in the future | +| BEACH_ASSET_PROXY_ENDPOINT | string | | Endpoint of a cloud storage frontend to use for proxying requests to Flow persistent resources. Requires BEACH_PERSISTENT_RESOURCES_BASE_PATH to be set. Example: "https://assets.flownative.com/example-bucket/" | +| BEACH_ASSET_PROXY_RESOLVER | string | 8.8.8.8 | IP address of a DNS server to use for resolving domains when proxying assets. Set this to 127.0.0.11 when using Local Beach. | +| BEACH_PERSISTENT_RESOURCES_BASE_PATH | string | | Base path of URLs pointing to Flow persistent resources; example: "https://www.flownative.com/assets/" | +| BEACH_STATIC_RESOURCES_LIFETIME | string | 30d | Expiration time for static resources; examples: "3600s" or "7d" or "max" | +| FLOW_HTTP_TRUSTED_PROXIES | string | 10.0.0.0/8 | Nginx passes FLOW_HTTP_TRUSTED_PROXIES to the virtual host using the value of this variable | ## Asset Proxy -By default, the direct URL of an asset stored in the cloud storage is used as -part of the Flow or Neos frontend output. In order to make URLs more -user-friendly or hide the fact that assets are stored in a cloud storage, -Nginx can act as a reverse proxy and make assets available through a +By default, the direct URL of an asset stored in the cloud storage is used as +part of the Flow or Neos frontend output. In order to make URLs more +user-friendly or hide the fact that assets are stored in a cloud storage, +Nginx can act as a reverse proxy and make assets available through a sub-path of the website's main domain. -For example, if the website is reachable via "https://www.example.com", the -proxy can be configured to map the path "https://www.example.com/assets/" to -assets stored in a cloud storage bucket which is accessible at +For example, if the website is reachable via "https://www.example.com", the +proxy can be configured to map the path "https://www.example.com/assets/" to +assets stored in a cloud storage bucket which is accessible at "https://some.cloud.storage/some-bucket/". The environment variables to set for the above example are as follows: @@ -131,10 +135,10 @@ BEACH_PERSISTENT_RESOURCES_BASE_PATH=/assets/ BEACH_ASSET_PROXY_ENDPOINT=https://some.cloud.storage/some-bucket ``` -> Note: Make sure that both values are formatted exactly like in the given -> examples, for example don't forget the trailing "/" in -> `BEACH_PERSISTENT_RESOURCES_BASE_PATH` and don't add a trailing "/" in -> "BEACH_ASSET_PROXY_ENDPOINT". +> Note: Make sure that both values are formatted exactly like in the given +> examples, for example don't forget the trailing "/" in +> `BEACH_PERSISTENT_RESOURCES_BASE_PATH` and don't add a trailing "/" in +> "BEACH_ASSET_PROXY_ENDPOINT". ## Security aspects diff --git a/root-files/opt/flownative/lib/nginx-legacy.sh b/root-files/opt/flownative/lib/nginx-legacy.sh index e6de6a4..0499be8 100644 --- a/root-files/opt/flownative/lib/nginx-legacy.sh +++ b/root-files/opt/flownative/lib/nginx-legacy.sh @@ -59,6 +59,8 @@ export BEACH_NGINX_CUSTOM_METRICS_ENABLE=${BEACH_NGINX_CUSTOM_METRICS_ENABLE:-fa export BEACH_NGINX_CUSTOM_METRICS_SOURCE_PATH=${BEACH_NGINX_CUSTOM_METRICS_SOURCE_PATH:-/metrics} export BEACH_NGINX_CUSTOM_METRICS_TARGET_PORT=${BEACH_NGINX_CUSTOM_METRICS_TARGET_PORT:-8082} +export NGINX_CUSTOM_LOCATION_BLOCK_BASE64="${NGINX_CUSTOM_LOCATION_BLOCK_BASE64:-}" + export BEACH_NGINX_CUSTOM_ERROR_PAGE_TARGET="${BEACH_NGINX_CUSTOM_ERROR_PAGE_TARGET:-}" export NGINX_CUSTOM_ERROR_PAGE_TARGET=${NGINX_CUSTOM_ERROR_PAGE_TARGET:-${BEACH_NGINX_CUSTOM_ERROR_PAGE_TARGET:-}} @@ -115,7 +117,14 @@ server { if (\$http_user_agent ~* (citrixreceiver)) { return 403; } +EOM + if [ -n "${NGINX_CUSTOM_LOCATION_BLOCK_BASE64}" ]; then + info "Nginx: Enabling custom location block ..." + base64 -d <<<"${NGINX_CUSTOM_LOCATION_BLOCK_BASE64}" >>"${NGINX_CONF_PATH}/sites-enabled/site.conf" + fi + + cat >>"${NGINX_CONF_PATH}/sites-enabled/site.conf" <<-EOM # allow .well-known/... in root location ~ ^/\\.well-known/.+ { allow all;