diff --git a/CHANGELOG.md b/CHANGELOG.md
index 0527722b9..4ced42936 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -6,7 +6,8 @@
- Fix ui.env not read when using Linux integration
- Fix check if BunkerNet is activated on default server
- Add \*_CUSTOM_CONF_\* setting to automatically add custom config files from setting value
-- Add DENY_HTTP_STATUS setting to choose standard 403 error (default) or to close connection (444) when access is denied
+- Add DENY_HTTP_STATUS setting to choose standard 403 error page (default) or 444 to close connection when access is denied
+- Add CORS (Cross-Origin Resource Sharing) core plugin
- Add documentation about Docker in rootless mode and podman
- Migrate CI/CD infrastructure to another provider
diff --git a/core/cors/confs/server-http/cors.conf b/core/cors/confs/server-http/cors.conf
index 96eb94916..30cc0d46a 100644
--- a/core/cors/confs/server-http/cors.conf
+++ b/core/cors/confs/server-http/cors.conf
@@ -2,12 +2,4 @@
{% if CORS_ALLOW_ORIGIN != "" %}add_header Access-Control-Allow-Origin '{{ CORS_ALLOW_ORIGIN }}' always;{% endif %}
{% if CORS_EXPOSE_HEADERS != "" %}add_header Access-Control-Expose-Headers '{{ CORS_EXPOSE_HEADERS }}' always;{% endif %}
{% if CORS_ALLOW_CREDENTIALS != "no" %}add_header Access-Control-Allow-Credentials true always;{% endif %}
-if ($request_method == 'OPTIONS') {
- {% if CORS_MAX_AGE != "no" %}add_header Access-Control-Max-Age '{{ CORS_MAX_AGE }}' always;{% endif %}
- {% if CORS_ALLOW_METHODS != "no" %}add_header Access-Control-Allow-Methods '{{ CORS_ALLOW_METHODS }}' always;{% endif %}
- {% if CORS_ALLOW_HEADERS != "no" %}add_header Access-Control-Allow-Headers '{{ CORS_ALLOW_Headers }}' always;{% endif %}
- add_header Content-Type 'text/plain; charset=utf-8';
- add_header Content-Length 0;
- return 204;
-}
{% endif %}
\ No newline at end of file
diff --git a/core/cors/cors.lua b/core/cors/cors.lua
new file mode 100644
index 000000000..ec5cb239c
--- /dev/null
+++ b/core/cors/cors.lua
@@ -0,0 +1,50 @@
+local _M = {}
+_M.__index = _M
+
+local utils = require "utils"
+local datastore = require "datastore"
+local logger = require "logger"
+
+function _M.new()
+ local self = setmetatable({}, _M)
+ return self, nil
+end
+
+function _M:access()
+ -- Check if access is needed
+ local cors, err = utils.get_variable("USE_CORS")
+ if cors == nil then
+ return false, err, nil, nil
+ end
+ if cors == "no" then
+ return true, "CORS not activated", nil, nil
+ end
+
+ -- Check if method is OPTIONS
+ if ngx.var.request_method ~= "OPTIONS" then
+ return true, "method is not OPTIONS", nil, nil
+ end
+
+ -- Add headers
+ local cors_headers = {
+ ["CORS_MAX_AGE"] = "Access-Control-Max-Age",
+ ["CORS_ALLOW_METHODS"] = "Access-Control-Allow-Methods",
+ ["CORS_ALLOW_HEADERS"] = "Access-Control-Allow-Headers"
+ }
+ for variable, header in pairs(cors_headers) do
+ local value, err = utils.get_variable(variable)
+ if value == nil then
+ logger.log(ngx.ERR, "CORS", "can't get " .. variable .. " from datastore : " .. err)
+ elseif value ~= "" then
+ ngx.header[header] = value
+ end
+ end
+ ngx.header["Content-Type"] = "text/html"
+ ngx.header["Content-Length"] = "0"
+
+ -- Send CORS policy with a 204 (no content) status
+ return true, "sent CORS policy", true, ngx.HTTP_NO_CONTENT
+
+end
+
+return _M
\ No newline at end of file
diff --git a/docs/integrations.md b/docs/integrations.md
index d6adc27c4..f10ee27c2 100644
--- a/docs/integrations.md
+++ b/docs/integrations.md
@@ -223,8 +223,8 @@ docker run \
docker network connect bw-services mybunker
```
-!!! info "Using Docker in rootless mode"
- If you are using [Docker in rootless mode](https://docs.docker.com/engine/security/rootless), you will need to replace the mount with the following value : `$XDG_RUNTIME_DIR/docker.sock:/var/run/docker.sock:ro`.
+!!! warning "Using Docker in rootless mode"
+ If you are using [Docker in rootless mode](https://docs.docker.com/engine/security/rootless), you will need to replace the mount of the docker socket with the following value : `$XDG_RUNTIME_DIR/docker.sock:/var/run/docker.sock:ro`.
And the autoconf one :
diff --git a/examples/cors/bw-data/www/app1.example.com/index.php b/examples/cors/bw-data/www/app1.example.com/index.php
new file mode 100644
index 000000000..cffe7a91c
--- /dev/null
+++ b/examples/cors/bw-data/www/app1.example.com/index.php
@@ -0,0 +1,5 @@
+
diff --git a/examples/cors/bw-data/www/app2.example.com/index.php b/examples/cors/bw-data/www/app2.example.com/index.php
new file mode 100644
index 000000000..f8c60fead
--- /dev/null
+++ b/examples/cors/bw-data/www/app2.example.com/index.php
@@ -0,0 +1,16 @@
+
+
+
diff --git a/examples/cors/bw-data/www/app3.example.com/index.php b/examples/cors/bw-data/www/app3.example.com/index.php
new file mode 100644
index 000000000..4afbc430e
--- /dev/null
+++ b/examples/cors/bw-data/www/app3.example.com/index.php
@@ -0,0 +1,16 @@
+
+
+
diff --git a/examples/cors/docker-compose.yml b/examples/cors/docker-compose.yml
new file mode 100644
index 000000000..fa236e90d
--- /dev/null
+++ b/examples/cors/docker-compose.yml
@@ -0,0 +1,75 @@
+version: '3'
+
+services:
+
+ mybunker:
+ image: bunkerity/bunkerweb:1.4.2
+ ports:
+ - 80:8080
+ - 443:8443
+ # ⚠️ read this if you use local folders for volumes ⚠️
+ # bunkerweb runs as an unprivileged user with UID/GID 101
+ # don't forget to edit the permissions of the files and folders accordingly
+ # example if you need to create a directory : mkdir folder && chown root:101 folder && chmod 770 folder
+ # another example for existing folder : chown -R root:101 folder && chmod -R 770 folder
+ # more info at https://docs.bunkerweb.io
+ volumes:
+ - ./bw-data:/data # contains web files (PHP, assets, ...), don't forget to rename the subfolders
+ environment:
+ - SERVER_NAME=app1.example.com app2.example.com app3.example.com # replace with your domains
+ - MULTISITE=yes
+ - AUTO_LETS_ENCRYPT=yes
+ - DISABLE_DEFAULT_SERVER=yes
+ - USE_CLIENT_CACHE=yes
+ - USE_GZIP=yes
+ - app1.example.com_USE_CORS=yes
+ - app1.example.com_CORS_ALLOW_ORIGIN=https://app2.example.com
+ - app1.example.com_ALLOWED_METHODS=GET|POST|HEAD|OPTIONS
+ - app1.example.com_REMOTE_PHP=myapp1
+ - app1.example.com_REMOTE_PHP_PATH=/app
+ - app2.example.com_REMOTE_PHP=myapp2
+ - app2.example.com_REMOTE_PHP_PATH=/app
+ - app3.example.com_REMOTE_PHP=myapp3
+ - app3.example.com_REMOTE_PHP_PATH=/app
+ networks:
+ - net_app1
+ - net_app2
+ - net_app3
+
+ myapp1:
+ image: php:fpm
+ # ⚠️ UID and GID of mywww (101:101) and php:fpm (33:33) are not the same ⚠️
+ # but both needs access to the files and folders of web-files
+ # don't forget to edit the permissions of the files and folders accordingly
+ # example : chown -R 33:101 ./bw-data/www && find ./bw-data/www -type f -exec chmod 0640 {} \; && find ./bw-data/www -type d -exec chmod 0750 {} \;
+ volumes:
+ - ./bw-data/www/app1.example.com:/app # folder containing PHP app1 (don't forget to rename it)
+ networks:
+ - net_app1
+
+ myapp2:
+ image: php:fpm
+ # ⚠️ UID and GID of bunkerweb (101:101) and php:fpm (33:33) are not the same ⚠️
+ # but both needs access to the files and folders of web-files
+ # don't forget to edit the permissions of the files and folders accordingly
+ # example : chown -R 33:101 ./bw-data/www && find ./bw-data/www -type f -exec chmod 0640 {} \; && find ./bw-data/www -type d -exec chmod 0750 {} \;
+ volumes:
+ - ./bw-data/www/app2.example.com:/app # folder containing PHP app2 (don't forget to rename it)
+ networks:
+ - net_app2
+
+ myapp3:
+ image: php:fpm
+ # ⚠️ UID and GID of bunkerweb (101:101) and php:fpm (33:33) are not the same ⚠️
+ # but both needs access to the files and folders of web-files
+ # don't forget to edit the permissions of the files and folders accordingly
+ # example : chown -R 33:101 ./bw-data/www && find ./bw-data/www -type f -exec chmod 0640 {} \; && find ./bw-data/www -type d -exec chmod 0750 {} \;
+ volumes:
+ - ./bw-data/www/app3.example.com:/app # folder containing PHP app3 (don't forget to rename it)
+ networks:
+ - net_app3
+
+networks:
+ net_app1:
+ net_app2:
+ net_app3:
diff --git a/examples/cors/setup.sh b/examples/cors/setup.sh
new file mode 100755
index 000000000..feea1a687
--- /dev/null
+++ b/examples/cors/setup.sh
@@ -0,0 +1,12 @@
+#!/bin/bash
+
+if [ $(id -u) -ne 0 ] ; then
+ echo "❌ Run me as root"
+ exit 1
+fi
+
+chown -R root:101 bw-data
+chmod -R 770 bw-data
+chown -R 33:101 ./bw-data/www
+find ./bw-data/www -type f -exec chmod 0640 {} \;
+find ./bw-data/www -type d -exec chmod 0750 {} \;
\ No newline at end of file