├── .gitignore ├── CHANGELOG.md ├── README.md ├── metaphactory-graphdb └── docker-compose.yml ├── metaphactory-rdfox └── docker-compose.yml ├── metaphactory-stardog └── docker-compose.yml ├── metaphactory └── docker-compose.yml ├── nginx ├── docker-compose.acme.yml ├── docker-compose.nginx.yml ├── readme.md └── service-template │ ├── .env │ ├── certs │ └── readme.md │ ├── conf.d │ └── proxy.conf │ ├── docker-compose.base.yml │ ├── docker-compose.overwrite.yml │ └── templates │ └── nginx.tmpl └── service-template ├── database-config ├── .env_default ├── .env_graphdb ├── .env_rdfox ├── .env_stardog ├── docker-compose.graphdb.yml ├── docker-compose.rdfox.yml ├── docker-compose.stardog.yml ├── graphdb-config │ ├── graphdb-repository-config.ttl │ ├── graphdb-with-SHACL-config-example.ttl │ ├── graphdb9-repository-config.ttl │ ├── license │ │ └── graphdb.license │ └── metaphactory.ttl ├── rdfox-config │ ├── RDFox.lic │ ├── init │ │ └── initialize.rdfox │ └── metaphactory.ttl ├── stardog-config │ ├── database-template.properties │ ├── stardog-license-key.bin │ └── stardog.properties └── stardog-repository-config │ └── myDB.ttl ├── docker-compose.base.yml └── docker-compose.overwrite.yml /.gitignore: -------------------------------------------------------------------------------- 1 | *.bin 2 | *.env 3 | .project 4 | test-*/ 5 | .DS_Store 6 | -------------------------------------------------------------------------------- /CHANGELOG.md: -------------------------------------------------------------------------------- 1 | # Changelog 2 | 3 | All notable changes to the docker-compose setup are documented in this file. 4 | 5 | Note: when updating to a newer release of metaphactory, also regard the information from the respective [Changelog](https://help.metaphacts.com/resource/Help:Start?tab=Changelog). Updates to the application content may be required as specified in the upgrade notes. 6 | 7 | If not mentioned otherwise, the docker-compose definitions are backwards compatible to the previous released version. 8 | 9 | ## 2025-03-28 (Release 5.7.0) 10 | 11 | The docker tags have been updated to the 5.7.0 release of metaphactory. 12 | 13 | Other changes: 14 | 15 | - Update GraphDB to 10.8.4 16 | - Update RDFox to 7.3c 17 | - Update Nginx-proxy to 1.7.0 (Nginx version: 1.27.3) 18 | - Update ACME Companion to 2.5.2 19 | 20 | 21 | ## 2024-12-20 (Release 5.6.0) 22 | 23 | The docker tags have been updated to the 5.6.0 release of metaphactory. 24 | 25 | Other changes: 26 | 27 | - Update GraphDB to 10.8.2 28 | - Update RDFox to 7.2b, update RDFox repository config type, fix default-graph-name 29 | - Update Nginx-proxy to 1.6.4 (Nginx version: 1.27.2) 30 | - We now recommend Docker >= 20.10.0 and docker-compose >= 1.21.2 31 | - Add "strict-parsing" option to Stardog database properties template 32 | 33 | 34 | 35 | ## 2024-10-11 (Release 5.5.1) 36 | 37 | The docker tags have been updated to the 5.5.1 release of metaphactory. 38 | 39 | 40 | ## 2024-09-25 (Release 5.5.0) 41 | 42 | The docker tags have been updated to the 5.5.0 release of metaphactory. 43 | 44 | Other changes: 45 | 46 | - Update GraphDB to 10.7.3 47 | - Update Nginx-proxy to 1.6.1 (Nginx version: 1.27.1) 48 | 49 | 50 | ## 2024-07-05 (Release 5.4.0) 51 | 52 | The docker tags have been updated to the 5.4.0 release of metaphactory. 53 | 54 | Other changes: 55 | 56 | - Update GraphDB to 10.6.4 57 | - Update RDFox to 7.1a 58 | - Update Nginx-proxy to 1.6.0 (Nginx version: 1.27.0) 59 | - Maintain security headers in nginx.tmpl 60 | 61 | 62 | 63 | ## 2024-03-28 (Release 5.3.0) 64 | 65 | The docker tags have been updated to the 5.3.0 release of metaphactory. 66 | 67 | Other changes: 68 | 69 | - Update GraphDB to 10.6.2 & increase graceful shutdown timeout 70 | - Update Nginx-proxy to 1.5.1 (Nginx version: 1.25.4) 71 | - Maintain nginx.tmpl from nginx-proxy upstream 72 | 73 | 74 | ## 2024-02-01 (Release 5.2.1) 75 | 76 | The docker tags have been updated to the 5.2.1 release of metaphactory. 77 | 78 | Other changes: 79 | 80 | - Refine RDFox datastore settings 81 | 82 | 83 | ## 2024-01-15 (Release 5.2.0) 84 | 85 | The docker tags have been updated to the 5.2.0 release of metaphactory. 86 | 87 | Other changes: 88 | 89 | - Add RDFox 7.0 integration 90 | - Maintain nginx.tmpl from nginx-proxy upstream 91 | - Update GraphDB to 10.4.3 92 | 93 | 94 | ## 2023-10-06 (Release 5.1.0) 95 | 96 | The docker tags have been updated to the 5.1.0 release of metaphactory. 97 | 98 | Other changes: 99 | 100 | - Update GraphDB to 10.3.2 101 | - Adjust GraphDB repository configuration to throw exception on query timeouts 102 | - Update readme instructions to use `docker compose` as command 103 | 104 | 105 | ## 2023-07-27 (Release 5.0.0) 106 | 107 | The docker tags have been updated to the 5.0.0 release of metaphactory. 108 | 109 | Other changes: 110 | 111 | - Update GraphDB to 10.2.3 112 | 113 | 114 | ## 2023-06-07 (Release 4.8.6) 115 | 116 | The docker tags have been updated to the security patch release 4.8.6 of metaphactory. 117 | 118 | Other changes: 119 | 120 | - The nginx-proxy image has been updated to 1.3.1, acme-companion to 2.2.8 121 | - Update GraphDB to 10.2.1 122 | 123 | 124 | ## 2023-03-03 (Release 4.8.4) 125 | 126 | The docker tags have been updated to the security patch release 4.8.4 of metaphactory. 127 | 128 | Other changes: 129 | 130 | - The nginx-proxy image has been updated to 1.2.2, acme-companion to 2.2.6 131 | - Update GraphDB to 10.1.5 132 | 133 | 134 | ## 2022-12-21 (Release 4.8.0) 135 | 136 | The docker tags have been updated to the 4.8.0 release of metaphactory. 137 | 138 | Other changes: 139 | 140 | - Adjust Content Security Policy configuration in Nginx to define `image-src: blob:` (required for exporting PNGs of Charts) 141 | - Update GraphDB to 10.1.2 142 | - Set `enable-context-index=true` in GraphDB repository configurations 143 | - Removed GraphScope container configuration 144 | 145 | ## 2022-11-21 (Release 4.7.2) 146 | 147 | The docker tags have been updated to the security patch release 4.7.2 of metaphactory. 148 | 149 | 150 | ## 2022-10-20 (Release 4.7.0) 151 | 152 | The docker tags have been updated to the 4.7.0 release of metaphactory. 153 | 154 | Other changes 155 | 156 | - Update GraphDB to 10.0.2 (incl. repository configuration snippets) 157 | - Adjust license configuration for GraphDB (no longer use volume mounts, instead upload through the GraphDB workbench 158 | - Deprecate and remove docker-compose integration for Blazegraph 159 | - Adjust Content Security Policy configuration in Nginx to define font-src (required for embedded fonts in diagram printing) 160 | 161 | 162 | ## 2022-08-19 (Release 4.6.2) 163 | 164 | The docker tags have been updated to the security patch release 4.6.2 of metaphactory. 165 | 166 | 167 | ## 2022-07-22 (Release 4.6.1) 168 | 169 | The docker tags have been updated to the bug fix release 4.6.1 of metaphactory. 170 | 171 | 172 | ## 2022-07-11 (Release 4.6.0) 173 | 174 | The docker tags have been updated to the 4.6.0 release of metaphactory. 175 | 176 | The docker-compose setup for Nginx has been revised (particularly w.r.t new official nginx images). 177 | 178 | Users are encouraged to migrate existing environments. Note that this is a **breaking** change as the images and compose structure for Nginx has changed. It is easiest to re-setup nginx following the instructions of the [readme](README.md). 179 | 180 | - use latest official images from https://hub.docker.com/r/nginxproxy/nginx-proxy 181 | - revise compose structure: docker-gen is now integrated in nginx-proxy image 182 | - use official nginxproxy ACME companion 183 | 184 | See also [here](nginx/readme.md) for details on the Nginx security configuration. 185 | 186 | Other changes 187 | 188 | - Add compatibility instructions of metaphactory >= 4.6.0 with GraphDB 9.x 189 | - Update GraphDB to 9.11.2-ee 190 | 191 | 192 | ## 2022-04-01 (Release 4.5.0) 193 | 194 | The docker tags have been updated to the 4.5.0 release of metaphactory. 195 | 196 | As of 4.5.0 metaphactory is shipped as a multi-architecture container image. 197 | 198 | Other changes 199 | 200 | - Add GraphDB 10 repository configuration examples 201 | - Add compatibility instructions of metaphactory <= 4.5.0 with GraphDB 10 202 | - Updated Nginx to 1.21.4, Letsencrypt Companion to 2.2.0 203 | - Refine Nginx security header documentation (enclose with quotes) 204 | 205 | 206 | ## 2021-12-20 (Release 4.4.1) 207 | 208 | The docker tags have been updated to the security patch release 4.4.1 of metaphactory. 209 | 210 | 211 | ## 2021-12-16 (Release 4.4.0) 212 | 213 | The docker tags have been updated to the 4.4.0 release of metaphactory. 214 | 215 | Other changes: 216 | 217 | - Updated Nginx to 1.21.4 218 | - Refined instructions for setting up Nginx with HTTPS 219 | - GraphDB version in docker-compose template updated to 9.10.0 220 | - update Blazegraph image to use a newer base image (Jetty 9.4.44 + Java 8u302) 221 | 222 | 223 | ## 2021-09-30 (Release 4.3.0) 224 | 225 | The docker tags have been updated to the 4.3.0 release of metaphactory. 226 | 227 | The docker-compose setup for Nginx has been updated to latest versions of the software. Users are encouraged to update their respective service instantiations. 228 | 229 | - update Nginx to 1.21.3 230 | 231 | Other changes: 232 | 233 | - GraphDB version in docker-compose template updated to 9.9.0 234 | 235 | 236 | 237 | ## 2021-07-09 (Release 4.2.0) 238 | 239 | The docker tags have been updated to the 4.2.0 release of metaphactory. 240 | 241 | The docker-compose setup for Nginx has been updated to latest versions of the software. Users are encouraged to update their respective service instantiations. 242 | 243 | - update Nginx to 1.21.0 244 | - update Nginx Let's Encrypt companion to 2.1.0 for newer ACME based security standards 245 | 246 | Other changes: 247 | 248 | - improve Nginx [proxy configuration](nginx/service-template/conf.d/proxy.conf) to enable gzipped transfer of RDF files 249 | - update Blazegraph image to use a newer base image (Jetty 9.4.41 + Java 8u292) 250 | - GraphDB version in docker-compose template updated to 9.8.0 251 | - improve GraphDB memory settings using container configuration 252 | 253 | 254 | 255 | ## 2021-04-13 (Release 4.1.0) 256 | 257 | The docker tags have been updated to the 4.1.0 release of metaphactory. 258 | 259 | Other changes: 260 | 261 | - make GraphScope an optional service to start on-demand only 262 | - make `/storage` in metaphactory image a persistent Docker volume 263 | - improve documentation for using a custom keystore 264 | 265 | 266 | ## 2021-03-16 267 | 268 | - Robustness for GraphDB compose setup w.r.t. configuration container 269 | 270 | 271 | ## 2021-03-02 272 | 273 | - Fix Stardog compose setup to execute as "root" user for proper volume permissions 274 | 275 | 276 | ## 2021-02-15 (Release 4.0.0) 277 | 278 | The docker tags have been updated to the 4.0.0 release of metaphactory. 279 | 280 | The docker-compose setup for Nginx has been revised (particularly w.r.t security aspects). 281 | 282 | Users are encouraged to migrate existing environments. Note that this is a **breaking** change as the folder and compose structure for Nginx has changed. It is easiest to re-setup nginx following the instructions of the [readme](README.md). 283 | 284 | - improved nginx docker compose setup with integrated security best practices 285 | - use latest "named" version of nginx and letsencrypt images 286 | 287 | See also [here](nginx/readme.md) for details on the Nginx security configuration. 288 | 289 | Other changes: 290 | 291 | - GraphDB version in docker-compose template updated to 9.5.0 292 | - GraphDB example repository configuration for enabling SHACL validation 293 | - update Blazegraph image to use a newer base image (Jetty 9.4.35 + Java 8u275) 294 | 295 | 296 | 297 | ## 2020-09-29 (Release 3.6.0) 298 | 299 | The docker tags have been updated to the 3.6.0 release of metaphactory. 300 | 301 | - add docker-compose template and instructions for GraphDB 302 | - add docker-compose instructions on how to expose a https connector 303 | - updated Blazegraph image to use a newer base image (Jetty 9.4.31 + Java 8u265) 304 | 305 | 306 | ## 2020-07-10 (Release 3.5.0) 307 | 308 | The docker tags have been updated to the 3.5.0 release of metaphactory. 309 | 310 | - updated GIT links to point to the new repository location at GitHub 311 | - updated Blazegraph image to use a newer base image (Jetty 9.4.27 + Java 8u252) 312 | - improved documentation for the Nginx network setup 313 | - introduced a changelog for the docker-compose setup 314 | 315 | 316 | ## 2020-03-31 (Release 3.4.0) 317 | 318 | The docker tags have been updated to the 3.4.0 release of metaphactory. 319 | 320 | Additional improvements 321 | 322 | - activate Stardog specific optimization strategy in GraphScope configuration 323 | - improved documentation of Nginx setup (e.g. proxy timeout) 324 | 325 | 326 | 327 | ## 2020-01-17 (Release 3.3.0.1) 328 | 329 | The docker tags have been updated to the 3.3.0.1 patch release of metaphactory. 330 | 331 | 332 | ## 2019-12-13 (Release 3.3.0) 333 | 334 | The docker tags have been updated to the 3.3.0 release of metaphactory. 335 | 336 | Additional improvements 337 | 338 | - upgrade Blazegraph docker image to Jetty 9.4.18 / Java 8u212 339 | - improved setup instructions GraphScope 340 | - added instructions on how to connect to Stardog 341 | 342 | 343 | ## 2019-10-09 (Release 3.2.0) 344 | 345 | In metaphactory 3.2.0 the Docker container has been optimized: 346 | 347 | - **Breaking**: Don't create and attach external nginx network by default (c.f. Optional Nginx Setup, Step 8) 348 | - **Breaking**: New folder and service-template structure. New logic for composing docker-compose files in the .env file. 349 | - The Jetty web server does not run as root and no longer changes file ownership in volumes so the (existing) file permissions matter 350 | 351 | The docker-compose definition is not compatible to previous releases. -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # metaphactory deployments with docker-compose 2 | 3 | **Prerequisites:** 4 | 5 | * docker installed (version >= 20.10.0, check with `docker --version`) 6 | * (optional) docker-compose installed (version >= 1.21.2, check with `docker-compose --version`) 7 | Please note that `docker-compose` is deprecated, and replaced by `docker compose` 8 | * a Docker host system with `x86_64` / `amd64` or `aarch64` / `arm64` architecture. 9 | Please note that as of 4.5.0 metaphactory is shipped as a multi-architecture container image. When pulling the image the host will automatically select the right variant for the local architecture. 10 | * outgoing HTTP/HTTPS traffic, allowing to access external Docker registries (e.g. Docker Hub or other private/corporate Docker registries) 11 | 12 | ## metaphactory Deployment and Maintenance 13 | 14 | **Prerequisites:** 15 | 16 | Please request your personal token to access our private docker hub registry via https://metaphacts.com/get-started (select "Docker - any graph database"). 17 | 18 | ### Initial Deployment 19 | 20 | The following instructions are tested and validated on Linux and macOS. If running on Windows, please use the PowerShell UI for maximum compatibility. 21 | 22 | To create a new deployment, start as follows: 23 | 24 | 1. Clone this GIT repository with `git clone https://github.com/metaphacts/metaphactory-docker-compose.git` 25 | 2. Create a copy of the `service-template` folder i.e. `cp -r service-template my-deployment`. The idea is to maintain one subfolder for every deployment. 26 | 27 | Then, depending on which database backend you want to use, enter the newly created deployment directory, and choose an option: 28 | 29 | 30 | #### metaphactory only - for use with existing graph databases 31 | 32 | 3. run `cp ./database-config/.env_default .env` 33 | 4. Open the file `.env` e.g. `vi .env` and perform following changes: 34 | 1. Change the value of the `COMPOSE_PROJECT_NAME` variable to a unique name (default is `my-deployment-1`). The name will be used to prefix container names as well as `vhost` entry in the nginx proxy (if used). 35 | 5. If you want to connect to a SPARQL endpoint accessible only via the docker hostmachine, please see the instructions in the section [Accessing docker hostmachine from docker container](#accessing-docker-hostmachine-from-docker-container). 36 | 6. Run `docker compose up -d`. It is **important to run the command in the 'my-deployment' folder (containing the .env file)**, since docker-compose will pick up the `.env` file for parameterization. 37 | 7. Open `http://localhost:10214` and login with user `admin` and password `admin` 38 | 39 | #### metaphactory with GraphDB 40 | 41 | 3. run `cp ./database-config/.env_graphdb .env`. 42 | 4. Open the file `.env` e.g. `vi .env` and perform following changes: 43 | 1. Change the value of the `COMPOSE_PROJECT_NAME` variable to a unique name (default is `my-deployment-1`). The name will be used to prefix container names as well as `vhost` entry in the nginx proxy (if used). 44 | 45 | 46 | 5. Please perform additional steps below to prepare the GraphDB configuration: 47 | 1. (Optional) modify GraphDB-specific parameters in the `./database-config/docker-compose.graphdb.yml` file, for example changing the default memory settings, or modifying the location where GraphDB stores its data on the host machine (by default, in the directory `graphdb-data` in the deployment directory). 48 | 2. (Optional) modify the configuration of the default GraphDB database, which is automatically created on first boot. You can do so by editing `./database-config/graphdb-config/graphdb-repository-config.ttl`. For GraphDB 9.x please make sure to activate `./database-config/graphdb-config/graphdb9-repository-config.ttl` in `./database-config/docker-compose.graphdb.yml` (line 45f). If you wish to enable SHACL validation, a separate example configuration is provided in `./database-config/graphdb-config/graphdb-with-SHACL-config-example.ttl`. 49 | 3. (Optional) you can also modify the `./database-config/graphdb-config/metaphactory.ttl` file, i.e. to use a different GraphDB database name or changing the default credentials for the repository connection with GraphDB. The credentials can optionally be externalized using the keys `repository.default.username` and `repository.default.password`, see https://help.metaphacts.com/resource/Help:ExternalizedSecrets for further details. 50 | 51 | 6. Run `docker compose up -d`. It is **important to run the command in the 'my-deployment' folder (containing the .env file)**, since docker-compose will pick up the `.env` file for parameterization. 52 | 7. GraphDB is started without a license pre-configured. As of GraphDB 10 the database will operate in _Free Mode_. To activate GraphDB SE/EE, a valid license can be set in the GraphDB workbench UI (http://localhost:7200). Note that a (trial) license can be requested through metaphacts. Alternatively, a license file can be mounted as volume through Docker by replacing `database-config/graphdb-config/license/graphdb.license` with a valid license and uncommenting the overriden _command_ of `database-config/docker-compose.graphdb.yml`. 53 | 8. Open `http://localhost:10214` and login with user `admin` and password `admin` 54 | 9. (Optional) For small and medium-sized databases you can create an out-of-the-box Lucene full-text search connector by running the query which is provided on the corresponding help page. 55 | Please refer to http://localhost:10214/resource/Help:HowToConnectToGraphDB#full-text-search for more details. 56 | 57 | ##### Compatibility mode of GraphDB 9.x and metaphactory >= 4.6.0 58 | 59 | When using metaphactory >= 4.6.0 with GraphDB 9.x, it is required to enable a compatibility mode for the data transfer. The data transfer relies on the RDF4J binary protocol, which evolved in the RDF4J 4.0 release. 60 | 61 | In order to enable the compatibility mode, the following system property needs to be set on the Java Virtual Machine running metaphactory: `-Dorg.eclipse.rdf4j.rio.binary.format_version=1`. When using our metaphactory docker-compose for metaphactory this can be done by adding the property to the `METAPHACTORY_OPTS` environment variable in the `.env` file. 62 | 63 | Note that this compatibility mode is prepared in the provided compose scripts for GraphDB. When upgrading to GraphDB 10 make sure to remove the respective setting from the `.env` file. 64 | 65 | 66 | ##### Compatibility mode of GraphDB 10 and metaphactory <= 4.5.0 67 | 68 | When using GraphDB 10 with metaphactory <= 4.5.0, it is required to enable a compatibility mode for the data transfer (similar to above). Note that metaphactory <= 4.5.0 is running on RDF4J 3.7.x, while GraphDB 10 is using the 4.0 major release of RDF4J. 69 | 70 | With metaphactory >= 4.5.0 it is possible to adjust the preferred RDF transfer format as part of the repository configuration, and thus overcome the incompatibility of the binary protocol. This can be done by setting the preferred RDF format to trig using `mph:preferredRdfFormat "trig"` in the repository configuration. 71 | 72 | In order to enable the compatibility mode on the RDF4J server side, the following system property needs to be set on the Java Virtual Machine running GraphDB: `-Dorg.eclipse.rdf4j.rio.binary.format_version=1`. When using the metaphactory docker-compose for GraphDB this can be done by applying the following snippet to the `docker-compose.overwrite.yml` file: 73 | 74 | ``` 75 | services 76 | metaphactory: 77 | # metaphactory definitions here 78 | 79 | graphdb: 80 | environment: 81 | GDB_JAVA_OPTS: >- 82 | -XX:+UseContainerSupport -XX:InitialRAMPercentage=30.0 -XX:MaxRAMPercentage=75.0 83 | -Dgraphdb.workbench.importDirectory=/opt/graphdb/home/graphdb-import 84 | -Dgraphdb.license.file=/etc/graphdb-license 85 | -Dorg.eclipse.rdf4j.rio.encode_rdf_star=false 86 | -Dorg.eclipse.rdf4j.rio.binary.format_version=1 87 | ``` 88 | 89 | 90 | #### metaphactory with Stardog 91 | 92 | **Please note:** use of Stardog requires that you own a valid Stardog license file. 93 | 94 | 3. run `cp ./database-config/.env_stardog .env`. 95 | 4. Open the file `.env` e.g. `vi .env` and perform following changes: 96 | 1. Change the value of the `COMPOSE_PROJECT_NAME` variable to a unique name (default is `my-deployment-1`). The name will be used to prefix container names as well as `vhost` entry in the nginx proxy (if used). 97 | 5. (Only for **metaphactory with Stardog**) Please perform additional steps below to prepare the Stardog configuration: 98 | 1. Add your Stardog license into the `./database-config/stardog-config` folder by replacing the existing file `stardog-license-key.bin`. 99 | 2. You may want to modify Stardog specific parameters in the `./database-config/docker-compose.stardog.yml` file i.e. changing the default memory settings 100 | 3. You can also modify the `./database-config/stardog-repository-config/myDB.ttl` file, i.e. to use a different Stardog database name or changing the default credentials for the repository connection with Stardog. The credentials can optionally be externalized using the keys `repository.default.username` and `repository.default.password`, see https://help.metaphacts.com/resource/Help:ExternalizedSecrets for further details. Please note that changes to the database name require modification of the database configuration in `./database-config/stardog-config/database-template.properties`. 101 | 102 | 6. Run `docker compose up -d`. It is **important to run the command in the 'my-deployment' folder (containing the .env file)**, since docker-compose will pick up the `.env` file for parameterization. 103 | 7. Run `docker compose exec stardog /opt/stardog/bin/stardog-admin db create -c /var/opt/stardog/database-template.properties -n myDB` to create a Stardog database. Also modify the database name from `myDB` to the name you used (e.g. if you modified the `myDB.ttl` file). 104 | 105 | **Please note:** For the creation of the stardog database the `stardog-config/database-template.properties` will be used. This is important, since this property file sets some database configurations (for example, enabling text search/indexing and querying of all named graphs) which are important to make metaphactory seamlessly work with Stardog. 106 | 107 | 8. Open `http://localhost:10214` and login with user `admin` and password `admin` 108 | 109 | **Note:** we are running the Stardog container as `root` user to avoid restricted volume permissions in Stardog images > 7.4.0, c.f. `database-config/docker-compose.stardog.yml`. 110 | 111 | 112 | #### metaphactory with RDFox 113 | 114 | 3. run `cp ./database-config/.env_rdfox .env`. 115 | 4. Open the file `.env` e.g. `vi .env` and perform following changes: 116 | 1. Change the value of the `COMPOSE_PROJECT_NAME` variable to a unique name (default is `my-deployment-1`). The name will be used to prefix container names as well as `vhost` entry in the nginx proxy (if used). 117 | 118 | 5. Please perform additional steps below to prepare the RDFox configuration: 119 | 1. Replace the content of the file at `./database-config/rdfox-config/RDFox.lic` with a valid RDFox license key. 120 | 2. (Optional) The initial value of the `max-memory` server parameter can be adjusted in `.env` using `RDFOX_MAX_MEMORY`. See https://docs.oxfordsemantic.tech/7.0/servers.html#server-parameters for further details 121 | 122 | 6. Run `docker compose up -d`. It is **important to run the command in the 'my-deployment' folder (containing the .env file)**, since docker-compose will pick up the `.env` file for parameterization. 123 | 7. To access the Metaphactory interface, open `http://localhost:10214` and login with user `admin` and password `admin`. 124 | 8. To access the RDFox console, open `http://localhost:12110/console/` and login with user `admin` and password `admin` 125 | 126 | ## Troubleshooting 127 | 128 | Please run `docker compose down` before running `docker compose up` after failed attempts (for example due to missing license file), especially if you experience errors like `unknown: Are you trying to mount a directory onto a file (or vice-versa)? Check if the specified host path exists and is the expected type`. 129 | 130 | ## Accessing docker hostmachine from docker container 131 | 132 | * **Linux** If you want to connect to a SPARQL endpoint accessible only on the docker hostmachine, e.g. http://localhost:5828/myDB/query, please identify the IP of your docker0 network using the following command `ip -4 addr show scope global dev docker0 | grep inet | awk '{print $2}' | cut -d "/" -f 1`. In the file `my-deployment/docker-compose.overwrite.yml` uncomment the line `extra_hosts` and the line below and put the IP of your docker0 network behind 'hostmachine:', e.g. - hostmachine:172.17.0.1. Now, the SPARQL endpoint is accessible via http://hostmachine:/, for example http://hostmachine:5820/myDB/query. Use this URL in your repository setup. 133 | * **Mac/Windows** (for development purposes only) The host is accessible using the pre-configured hostname `host.docker.internal` from docker version 18.03 onwards. 134 | 135 | ## Connecting a Git Storage for Knowledge Graph Asset Management 136 | 137 | As part of Asset Management metaphactory supports maintaining versions of assets (e.g. ontologies or vocabularies) in a central Git repository. To enable version control it is required to configure and connect to such a Git Storage. The detailed steps for doing so are described in https://help.metaphacts.com/resource/Help:AssetStorageConfig. 138 | 139 | 140 | ## Update of Deployments 141 | The most frequent use-case will be updating the runtime (i.e. software) container, for example, of the metaphactory, but leaving the deployment specific data and configuration assets untouched. 142 | 143 | 1. Modify the .env file in the folder of the deployment you want to update and increase/change the docker version tag of the metaphactory container i.e. `METAPHACTORY_IMAGE`. 144 | 2. Run `docker compose up -d` will re-create only the containers, that have been changed. 145 | 146 | ## Deletion of Deployments 147 | Run `docker compose down` in the folder for deployment you want to purge. Please note, that **all containers and non-external volumes and networks** for the deployment will be removed and deleted. Make sure that you are in the correct folder (where the respective `.env` file for the deployment is located), before executing the down command. 148 | 149 | ## Optional Setup: Activate HTTPS connector in metaphactory 150 | 151 | metaphactory is typically run behind a reverse proxy (e.g. nginx or AWS ALB) which takes care of TLS termination and certificate handling. This is the preferred setup as this moves certificate handling etc. to a centrally managed endpoint and avoids having to configure all aspects of HTTPS/TLS communication within the metaphactory container. 152 | 153 | When encrypted access to metaphactory is required, e.g. because the container is directly exposed to other services without a reverse proxy or for encrypted communication within the service network in some environments, the HTTPS connector can be exposed as well. 154 | 155 | The container by default runs a https connector on port `8443` with a self-signed certificate. When encrypted access is desired this port needs to be exposed to any port in the outside world, e.g. `10213`. This can be done by un-commenting the corresponding line in `docker-compose.overwrite.yml`. 156 | 157 | 158 | In case required by the environment: the container-internal ports can also be adjusted by specifying the following properties using environment variable `PLATFORM_JETTY_OPTS`: `PLATFORM_JETTY_OPTS=jetty.http.port=8081 jetty.ssl.port=8444` 159 | 160 | Jetty will use a self-signed certificate by default and the keystore is located in `/var/lib/jetty/etc/keystore.p12`. 161 | To use a custom certificate this keystore can be replaced, e.g. using a Docker volume (just) for that file, specifying the location and keystore password by adding the following settings to the environment variable `PLATFORM_JETTY_OPTS` (e.g. in the `.env` file). 162 | 163 | The following example provides a snippet for the keystore `mykeystore.p12` with password `changeit`. This can be used in `docker-compose.overwrite.yml`. 164 | 165 | 166 | services: 167 | metaphactory: 168 | # metaphactory overwrites here 169 | #... 170 | volumes: 171 | - ./mykeystore.p12:/var/lib/jetty/etc/mykeystore.p12 172 | environment: 173 | - PLATFORM_JETTY_OPTS=jetty.sslContext.keyStorePath=etc/mykeystore.p12 jetty.sslContext.keyStorePassword=changeit jetty.sslContext.keyManagerPassword=changeit 174 | 175 | **Notes:** 176 | 177 | * The keystore path is **always** relative to `/var/lib/jetty/`, so any externally injected keystore file must be placed there! 178 | * It is recommended to place a single certificate into the keystore, and assign the alias `jetty` 179 | * For managing keystores the JDK provided keytool, or visual tools (such as the [Keystore Explorer](https://keystore-explorer.org/)) can be used 180 | * The environment setting `PLATFORM_JETTY_OPTS` must not use quotes 181 | * The default password for the Jetty provided `keystore.p12` is `changeit` 182 | 183 | 184 | ## Optional Setup: NGINX Proxy Container 185 | 186 | **Please note:** 187 | 188 | * This setup is currently not compatible with Windows hosts 189 | 190 | It is recommended to use a proxy container with virtual host mappings to proxy the incoming HTTP traffic to the individual container instances. Reasons are: 191 | 192 | * Security 193 | * Not every container/deployment should expose a port (neither on localhost nor to the outside network). Firewall needs to open only two ports. 194 | * SSL certificate handling in a single place. Instead of dealing with certificates individually or using self-signed certificates, there will be only one officially signed wildcard certificate. One-time installation, valid for all deployments. 195 | * Ability to automatically issue certificates with [Let's Encrypt](https://letsencrypt.org/). 196 | * Easy to .htaccess protect containers/deployments that have no built-in authentication mechanism 197 | * Dealing with hostnames is much easier than dealing with IPs and Ports 198 | * Changes to the underlying (container) setup/infrastructure can be handled transparently. 199 | * Single place for special HTTP settings i.e. easy to enable CORS, GZIP, HTTP2 or modifying HTTP header for individual or all deployments. 200 | 201 | **Prerequisites:** 202 | 203 | * Wildcard CNAME record for the hostname DNS entry e.g. *.mydocker.example.com 204 | * Inbound rules for Port 80, 443 in firewall 205 | * Wildcard SSL certificate for the DNS entry *.mydocker.example.com placed in `/home/docker/config/nginx/certs`. Obviously, it is not required to use HTTPS. However, while the obvious reason for taking this extra step is security, there is another positive side-effect: Performance i.e. only with HTTPS new HTTP2 features are available, which will greatly speed-up the performance of many client-side applications. 206 | 207 | ### Setup 208 | 1. Create a copy of the provided `config template` folder i.e. `cp -r nginx/service-template nginx/config`. The idea is to maintain a deployment specific configuration. In the metaphactory AMI the prepared location is `/opt/metaphactory/docker-compose/nginx/config`. 209 | 2. Copy the SSL certificate to `config/certs` i.e. the *.key file and *.crt file must be named equivalent to the hostname (e.g. mydocker.example.com.key and mydocker.example.com.crt). Note that the same holds if you have a wildcard certificate for *.mydocker.example.com. Make sure to set proper permissions to protect the key file (i.e. docker must be able to read it, but no one else). The *.crt file should contain only the certificate body (from `-----BEGIN CERTIFICATE----- ` to `-----END CERTIFICATE----- `) and also all intermediate certificates/root certificate required for the certificate chain. You can simple concatenate these, however, order matters: 210 | 211 | -----BEGIN CERTIFICATE----- 212 | (Your Primary SSL certificate: your_domain_name.crt) 213 | -----END CERTIFICATE----- 214 | -----BEGIN CERTIFICATE----- 215 | (Your Intermediate certificate: xCertCA.crt) 216 | -----END CERTIFICATE----- 217 | -----BEGIN CERTIFICATE----- 218 | (Your Root certificate: TrustedRoot.crt) 219 | -----END CERTIFICATE---- 220 | 221 | 3. Go into the `certs` folder i.e. `cd ./nginx/config/certs` and generate [Diffie–Hellman](https://en.wikipedia.org/wiki/Diffie%E2%80%93Hellman_key_exchange) parameters using `openssl dhparam -dsaparam -out mydocker.example.com.dhparam.pem 4096`. `-dsaparam` [option instructs OpenSSL to produce "DSA-like" DH parameters ](https://wiki.openssl.org/index.php/Manual:Dhparam(1)#OPTIONS) , which is magnitude faster then computing the dhparam 4096 (see explanation [on stackexchange](https://security.stackexchange.com/a/95184)) 222 | Go into folder `nginx/config` 223 | 4. Now we are ready to create and start the proxy container. Running `docker compose up -d` should result in: 224 | Creating network "nginx_proxy_network" with the default driver 225 | Creating nginx-proxy ... 226 | Creating nginx-proxy ... done 227 | 228 | 5. Verify with `docker ps` that a container `nginx-proxy` is running with two ports exposed: ```80, 443``` 229 | 6. From now on the `nginx-proxy` will listen to container changes on the docker daemon. As soon as a new docker container instance is started with an environment variable `VIRTUAL_HOST={name}.mydocker.example.com`, nginx will automatically create a vhost entry to proxy incoming HTPP(S) request on `{name}.mydocker.example.com` to the respective container. The environment variable is automatically set when using the metaphactory `docker-compose.yml` as described above. It uses the `HOST_NAME` and the `COMPOSE_PROJECT_NAME` from the `.env` file and exposes it as `VIRTUAL_HOST` to be picked up by the nginx environment. Alternatively, the `VIRTUAL_HOST` variable can be explicitly defined in the `docker-compose.overwrite.yml` in the `environment` section. Note that `VIRTUAL_PORT` can be optionally used if either multiple containers are exposed through nginx or when your container exposes more than one port. 230 | 7. The metaphactory container needs to be configured to use the `nginx_proxy_network` as default external network, e.g. by adding the following snippets to the `docker-compose.overwrite.yml` in the active service instance: 231 | 232 | metaphactory: 233 | networks: 234 | - default 235 | 236 | networks: 237 | default: 238 | external: 239 | name: nginx_proxy_network 240 | 241 | 8. Some final fine-tuning of configuration can be done in `nginx/config/conf.d/proxy.conf`. The body size can be increased as needed e.g. by other front- or backend-containers and depending on the use-cases (nginx's default is usually 2MB for security reasons, whereas the metaphactory platform uses usually 100MB as a default). The `proxy_read_timeout` setting can be adjusted to configure the HTTP read timeouts, e.g. for long running queries it may be required to increase the timeout. In order to activate changes restart the `nginx-proxy` with `docker restart nginx-proxy` to load the configuration. 242 | 9. See also [here](nginx/readme.md) for more details on Nginx Security hardening 243 | 244 | **Please Note:** 245 | 246 | * If you do not want to use HTTPS, make sure to not have any SSL certificates in the `certs` folder. The volumes section of the `docker-compose` files is also the place to be modified, in case you want to use a different location to place your configuration files including specific vhost configs or certificates. For details, please refer to the official [nginxproxy/nginx-proxy documentation](https://hub.docker.com/r/nginxproxy/nginx-proxy).

247 | * If you do not want to or are not able to use the nginx proxy at all (for example, you do not have a DNS entry for your host), you can still use the compose scripts to maintain your deployments. However, you will need to map/expose the metaphactory docker container port `8080` to a free host port (you basically need one port / deployment). Simply uncomment and modify the ports section in the `docker-compose.overwrite.yml` file of the service template. 248 | 249 | ### Optional: Setup with Let's Encrypt 250 | For Let's Encrypt the system should be accessible from the outside world. Otherwise the setup is exactly the same as for default nginx. In order to activate Let's Encrypt uncomment the respective line in the `nginx/config/.env` file (see file comments for details). 251 | 252 | Note that in addition to the `VIRTUAL_HOST` the nginx generator tool inspects the `LETSENCRYPT_HOST` and `LETSENCRYPT_EMAIL` (which are by default defined through the respective settings in `.env` or alternatively explicitly defined as environment variable). 253 | -------------------------------------------------------------------------------- /metaphactory-graphdb/docker-compose.yml: -------------------------------------------------------------------------------- 1 | version: "2.2" 2 | services: 3 | graphdb: 4 | container_name: "${COMPOSE_PROJECT_NAME}-graphdb" 5 | image: "${GRAPHDB_IMAGE}" 6 | restart: unless-stopped 7 | mem_limit: 2g 8 | mem_reservation: 1g 9 | stop_grace_period: 1m 10 | environment: 11 | GDB_JAVA_OPTS: >- 12 | -XX:+UseContainerSupport -XX:InitialRAMPercentage=30.0 -XX:MaxRAMPercentage=75.0 13 | -Dgraphdb.workbench.importDirectory=/opt/graphdb/home/graphdb-import 14 | -Dorg.eclipse.rdf4j.rio.encode_rdf_star=false 15 | networks: 16 | - metaphactory_network 17 | volumes: 18 | - graphdb_data:/opt/graphdb/home 19 | logging: 20 | driver: json-file 21 | options: 22 | max-size: "200k" 23 | max-file: "10" 24 | 25 | metaphactory: 26 | depends_on: 27 | - graphdb 28 | 29 | volumes: 30 | graphdb_data: 31 | -------------------------------------------------------------------------------- /metaphactory-rdfox/docker-compose.yml: -------------------------------------------------------------------------------- 1 | version: "2.2" 2 | services: 3 | rdfox: 4 | cap_drop: 5 | - ALL 6 | container_name: "${COMPOSE_PROJECT_NAME}-rdfox" 7 | depends_on: 8 | initialize-rdfox: 9 | condition: service_completed_successfully 10 | image: "${RDFOX_IMAGE}" 11 | logging: 12 | driver: json-file 13 | options: 14 | max-size: "200k" 15 | max-file: "10" 16 | networks: 17 | - metaphactory_network 18 | platform: linux/amd64 19 | volumes: 20 | - rdfox_server_directory:/home/rdfox/.RDFox 21 | restart: unless-stopped 22 | 23 | initialize-rdfox: 24 | command: 25 | [ 26 | "-persistence", "file", 27 | "-allowed-schemes-on-load", "file https", 28 | "-channel-timeout", "unlimited", 29 | "-connection-keep-alive-time", "0", 30 | "-elf-logger-fields", "date time cs-method cs-uri-stem cs-uri-query sc-status sc-bytes time-taken", 31 | "-query-time-limit", "unlimited", 32 | "-request-logger", "elf", 33 | "-max-memory", "${RDFOX_MAX_MEMORY}", 34 | ] 35 | container_name: "${COMPOSE_PROJECT_NAME}-initialize-rdfox" 36 | environment: 37 | - RDFOX_ROLE 38 | - RDFOX_PASSWORD 39 | - RDFOX_MAX_MEMORY 40 | image: "${RDFOX_INIT_IMAGE}" 41 | platform: linux/amd64 42 | volumes: 43 | - rdfox_server_directory:/home/rdfox/.RDFox 44 | - ./init:/data 45 | logging: 46 | driver: json-file 47 | options: 48 | max-size: "200k" 49 | max-file: "10" 50 | 51 | metaphactory: 52 | depends_on: 53 | - rdfox 54 | 55 | volumes: 56 | rdfox_server_directory: 57 | -------------------------------------------------------------------------------- /metaphactory-stardog/docker-compose.yml: -------------------------------------------------------------------------------- 1 | version: "2.2" 2 | services: 3 | stardog: 4 | container_name: "${COMPOSE_PROJECT_NAME}-stardog" 5 | image: "${STARDOG_IMAGE}" 6 | restart: unless-stopped 7 | environment: 8 | - STARDOG_SERVER_JAVA_ARGS=-Djava.io.tmpdir=/var/opt/tmp -Xms4g -Xmx4g -XX:MaxDirectMemorySize=8g 9 | - STARDOG_EXT=/var/opt/stardog-ext 10 | networks: 11 | - metaphactory_network 12 | volumes: 13 | - stardog_data:/var/opt/stardog # main Stardog directory where database files will be stored, ideally on SSD 14 | - stardog_tmp:/var/opt/tmp # directory for temporary files (potentially big) 15 | - stardog_ext:/var/opt/stardog-ext # directory for additional jar files, e.g. jdbc drivers etc 16 | - stardog_opennlp:/var/opt/stardog-opennlp #directory for opennlp models 17 | logging: 18 | driver: json-file 19 | options: 20 | max-size: "200k" 21 | max-file: "10" 22 | 23 | metaphactory: 24 | depends_on: 25 | - stardog 26 | 27 | volumes: 28 | stardog_data: 29 | stardog_tmp: 30 | stardog_ext: 31 | stardog_opennlp: -------------------------------------------------------------------------------- /metaphactory/docker-compose.yml: -------------------------------------------------------------------------------- 1 | version: "2.2" 2 | services: 3 | 4 | metaphactory: 5 | container_name: "${COMPOSE_PROJECT_NAME}-metaphactory" 6 | image: "${METAPHACTORY_IMAGE}" 7 | restart: unless-stopped 8 | mem_limit: 1g 9 | mem_reservation: 1g 10 | environment: 11 | - PLATFORM_OPTS=${METAPHACTORY_OPTS} 12 | - VIRTUAL_HOST=${COMPOSE_PROJECT_NAME}.${HOST_NAME} 13 | - JAVA_OPTS= 14 | - GENERATE_METAPHACTORY_PASSWORD=${GENERATE_METAPHACTORY_PASSWORD} 15 | # LETSENCRYPT variables will take effect only when nginx-proxy is setup with Let's Encrypt support 16 | - LETSENCRYPT_HOST=${COMPOSE_PROJECT_NAME}.${HOST_NAME} 17 | - LETSENCRYPT_EMAIL=${LETSENCRYPT_EMAIL} 18 | networks: 19 | # - default 20 | - metaphactory_network 21 | volumes: 22 | - metaphactory-runtime-data:/runtime-data 23 | - metaphactory-apps:/apps 24 | - metaphactory-storage:/storage 25 | logging: 26 | driver: json-file 27 | options: 28 | max-size: "200k" 29 | max-file: "10" 30 | 31 | volumes: 32 | metaphactory-runtime-data: 33 | metaphactory-apps: 34 | metaphactory-storage: 35 | 36 | networks: 37 | # default: 38 | # external: 39 | # name: nginx_proxy_network 40 | metaphactory_network: 41 | -------------------------------------------------------------------------------- /nginx/docker-compose.acme.yml: -------------------------------------------------------------------------------- 1 | version: "2.2" 2 | services: 3 | nginx-proxy-acme: 4 | container_name: nginx-proxy-acme 5 | image: "${ACME_COMPANION_IMAGE}" 6 | restart: unless-stopped 7 | volumes: 8 | - /var/run/docker.sock:/var/run/docker.sock:ro 9 | - ./conf.d:/etc/nginx/conf.d:rw 10 | - ./vhost.d:/etc/nginx/vhost.d:rw 11 | - ./html:/usr/share/nginx/html:rw 12 | - ./certs:/etc/nginx/certs:rw 13 | - ./acme:/etc/acme.sh:rw 14 | networks: 15 | - proxy_network 16 | environment: 17 | NGINX_PROXY_CONTAINER: "nginx-proxy" 18 | 19 | 20 | -------------------------------------------------------------------------------- /nginx/docker-compose.nginx.yml: -------------------------------------------------------------------------------- 1 | version: "2.2" 2 | services: 3 | 4 | nginx-proxy: 5 | container_name: nginx-proxy 6 | image: "${NGINX_IMAGE}" 7 | restart: unless-stopped 8 | volumes: 9 | - /var/run/docker.sock:/tmp/docker.sock:ro 10 | - ./certs:/etc/nginx/certs:ro 11 | - ./vhost.d:/etc/nginx/vhost.d:ro 12 | - ./conf.d:/etc/nginx/conf.d:rw 13 | - ./htpasswd:/etc/nginx/htpasswd:ro 14 | - ./html:/usr/share/nginx/html:ro 15 | - ./templates/nginx.tmpl:/app/nginx.tmpl:ro 16 | networks: 17 | - proxy_network 18 | environment: 19 | - DEFAULT_HOST=${DEFAULT_HOST} 20 | - HSTS=max-age=31536000; includeSubDomains; preload 21 | ports: 22 | - "443:443" 23 | - "80:80" 24 | logging: 25 | driver: json-file 26 | options: 27 | max-size: "200k" 28 | max-file: "10" 29 | 30 | networks: 31 | proxy_network: 32 | -------------------------------------------------------------------------------- /nginx/readme.md: -------------------------------------------------------------------------------- 1 | # Readme Nginx 2 | 3 | (for installation see [main readme](../README.md)) 4 | 5 | Run the Nginx compose setup from the instantiated `service-template`, e.g. 6 | 7 | ``` 8 | cp -r nginx/service-template nginx/config 9 | cd nginx/config 10 | docker-compose up -d 11 | ``` 12 | 13 | 14 | ## Security hardening options 15 | 16 | The templating definition allows to define security headers through environment variables in the container definition for `nginx-proxy` (see `docker-compose.overwrite.yml`). Alternatively, the environment variables can be specified on the virtual host, i.e. the metaphactory instance. 17 | 18 | ``` 19 | services: 20 | metaphactory: 21 | environment: 22 | - "SSL_POLICY=Mozilla-Modern" 23 | ``` 24 | 25 | The following environment variables are available: 26 | 27 | Note: the value can be set to `off` to disable (i.e. not define the header). 28 | 29 | | Name | Description | Default | 30 | |-------------------------------------|--------------------------------------------|---------------------------------------------------------------------------------------------------------------------------------------------------------------------| 31 | | HSTS | Strict Transport Security | max-age=31536000; includeSubDomains; preload | 32 | | X_FRAME_OPTIONS | X-Frame-Options header | DENY | 33 | | CONTENT_SECURITY_POLICY | Content-Security-Policy header | default-src 'self'; script-src 'self' 'unsafe-eval'; style-src 'self' 'unsafe-inline'; object-src 'none'; img-src 'self' https: data: blob:; font-src 'self' data:; | 34 | | CONTENT_SECURITY_POLICY_REPORT_ONLY | Content-Security-Policy-Report-Only header | off | 35 | | X_CONTENT_TYPE_OPTIONS | X-Content-Type-Option header | nosniff | 36 | | X_XSS_Protection | X-XSS-Protection header | off | 37 | | REFERRER_POLICY | Referrer-Policy header | same-origin | 38 | | PERMISSIONS_POLICY | Permissions-Policy header | off | 39 | 40 | 41 | ## Activating changed settings 42 | 43 | * if environment variables in the container (see above) have been changed run `docker-compose up -d` to re-create the respective containers 44 | * to re-generate and activate changed configuration, run `docker restart nginx-proxy` -------------------------------------------------------------------------------- /nginx/service-template/.env: -------------------------------------------------------------------------------- 1 | ##### VERSION DEFINITION ##### 2 | 3 | NGINX_IMAGE=nginxproxy/nginx-proxy:1.7.0 4 | ACME_COMPANION_IMAGE=nginxproxy/acme-companion:2.5.2 5 | 6 | 7 | ##### COMPOSE DEFINITION ##### 8 | 9 | # Note: the project name must not be changed as this impacts the name 10 | # of the shared network (i.e. nginx-proxy-network) 11 | COMPOSE_PROJECT_NAME=nginx 12 | 13 | # CHOOSE BETWEEN NGINX or NGINX + ACME 14 | 15 | # compose definition for Nginx proxy 16 | COMPOSE_FILE=./docker-compose.base.yml:../docker-compose.nginx.yml:./docker-compose.overwrite.yml 17 | 18 | # compose definition for Nginx proxy with ACME (i.e. Let's Encrypt) 19 | # UNCOMMENT to activate 20 | #COMPOSE_FILE=./docker-compose.base.yml:../docker-compose.nginx.yml:../docker-compose.acme.yml:./docker-compose.overwrite.yml 21 | -------------------------------------------------------------------------------- /nginx/service-template/certs/readme.md: -------------------------------------------------------------------------------- 1 | # Place your certificates here -------------------------------------------------------------------------------- /nginx/service-template/conf.d/proxy.conf: -------------------------------------------------------------------------------- 1 | client_max_body_size 100m; 2 | gzip on; 3 | gzip_proxied any; 4 | gzip_vary on; 5 | gzip_disable "MSIE [1-6]\.(?!.*SV1)"; 6 | gzip_types application/sparql-results+json application/x-sparqlstar-results+json text/turtle application/x-trig application/rdf+xml text/plain text/n3; 7 | proxy_read_timeout 60s; 8 | server_tokens off; -------------------------------------------------------------------------------- /nginx/service-template/docker-compose.base.yml: -------------------------------------------------------------------------------- 1 | version: "2.2" 2 | # used to set the location relevant to this folder, should not be used for any configurations -------------------------------------------------------------------------------- /nginx/service-template/docker-compose.overwrite.yml: -------------------------------------------------------------------------------- 1 | version: "2.2" 2 | services: 3 | nginx-proxy: 4 | # uncomment to adjust nginx template configuration 5 | #environment: 6 | # - "SSL_POLICY=Mozilla-Modern" 7 | # - "REFERRER_POLICY=off" 8 | 9 | networks: 10 | proxy_network: 11 | # uncomment the two lines below if you run docker-compose for nginx after other containers have already connected to the network 12 | # name: nginx_proxy_network 13 | # external: true 14 | -------------------------------------------------------------------------------- /nginx/service-template/templates/nginx.tmpl: -------------------------------------------------------------------------------- 1 | # nginx-proxy{{ if $.Env.NGINX_PROXY_VERSION }} version : {{ $.Env.NGINX_PROXY_VERSION }}{{ end }} 2 | 3 | {{- /* 4 | * Global values. Values are stored in this map rather than in individual 5 | * global variables so that the values can be easily passed to embedded 6 | * templates. (Go templates cannot access variables outside of their own 7 | * scope.) 8 | */}} 9 | {{- $globals := dict }} 10 | {{- $_ := set $globals "containers" $ }} 11 | {{- $_ := set $globals "Env" $.Env }} 12 | {{- $_ := set $globals "Docker" $.Docker }} 13 | {{- $_ := set $globals "CurrentContainer" (where $globals.containers "ID" $globals.Docker.CurrentContainerID | first) }} 14 | {{- $_ := set $globals "default_cert_ok" (and (exists "/etc/nginx/certs/default.crt") (exists "/etc/nginx/certs/default.key")) }} 15 | {{- $_ := set $globals "external_http_port" (coalesce $globals.Env.HTTP_PORT "80") }} 16 | {{- $_ := set $globals "external_https_port" (coalesce $globals.Env.HTTPS_PORT "443") }} 17 | {{- $_ := set $globals "sha1_upstream_name" (parseBool (coalesce $globals.Env.SHA1_UPSTREAM_NAME "false")) }} 18 | {{- $_ := set $globals "default_root_response" (coalesce $globals.Env.DEFAULT_ROOT "404") }} 19 | {{- $_ := set $globals "trust_downstream_proxy" (parseBool (coalesce $globals.Env.TRUST_DOWNSTREAM_PROXY "true")) }} 20 | {{- $_ := set $globals "access_log" (or (and (not $globals.Env.DISABLE_ACCESS_LOGS) "access_log /var/log/nginx/access.log vhost;") "") }} 21 | {{- $_ := set $globals "enable_ipv6" (parseBool (coalesce $globals.Env.ENABLE_IPV6 "false")) }} 22 | {{- $_ := set $globals "ssl_policy" (or ($globals.Env.SSL_POLICY) "Mozilla-Intermediate") }} 23 | {{- $_ := set $globals "vhosts" (dict) }} 24 | {{- $_ := set $globals "networks" (dict) }} 25 | # Networks available to the container running docker-gen (which are assumed to 26 | # match the networks available to the container running nginx): 27 | {{- /* 28 | * Note: $globals.CurrentContainer may be nil in some circumstances due to 29 | * . For more context 30 | * see . 31 | */}} 32 | {{- if $globals.CurrentContainer }} 33 | {{- range sortObjectsByKeysAsc $globals.CurrentContainer.Networks "Name" }} 34 | {{- $_ := set $globals.networks .Name . }} 35 | # {{ .Name }} 36 | {{- else }} 37 | # (none) 38 | {{- end }} 39 | {{- else }} 40 | # /!\ WARNING: Failed to find the Docker container running docker-gen. All 41 | # upstream (backend) application containers will appear to be 42 | # unreachable. Try removing the -only-exposed and -only-published 43 | # arguments to docker-gen if you pass either of those. See 44 | # . 45 | {{- end }} 46 | 47 | {{- /* 48 | * Template used as a function to get a container's IP address. This 49 | * template only outputs debug comments; the IP address is "returned" by 50 | * storing the value in the provided dot dict. 51 | * 52 | * The provided dot dict is expected to have the following entries: 53 | * - "globals": Global values. 54 | * - "container": The container's RuntimeContainer struct. 55 | * 56 | * The return value will be added to the dot dict with key "ip". 57 | */}} 58 | {{- define "container_ip" }} 59 | {{- $ip := "" }} 60 | # networks: 61 | {{- range sortObjectsByKeysAsc $.container.Networks "Name" }} 62 | {{- /* 63 | * TODO: Only ignore the "ingress" network for Swarm tasks (in case 64 | * the user is not using Swarm mode and names a network "ingress"). 65 | */}} 66 | {{- if eq .Name "ingress" }} 67 | # {{ .Name }} (ignored) 68 | {{- continue }} 69 | {{- end }} 70 | {{- if eq .Name "host" }} 71 | {{- /* Handle containers in host nework mode */}} 72 | {{- if (index $.globals.networks "host") }} 73 | # both container and proxy are in host network mode, using localhost IP 74 | {{- $ip = "127.0.0.1" }} 75 | {{- continue }} 76 | {{- end }} 77 | {{- range sortObjectsByKeysAsc $.globals.CurrentContainer.Networks "Name" }} 78 | {{- if and . .Gateway (not .Internal) }} 79 | # container is in host network mode, using {{ .Name }} gateway IP 80 | {{- $ip = .Gateway }} 81 | {{- break }} 82 | {{- end }} 83 | {{- end }} 84 | {{- if $ip }} 85 | {{- continue }} 86 | {{- end }} 87 | {{- end }} 88 | {{- if and (not (index $.globals.networks .Name)) (not $.globals.networks.host) }} 89 | # {{ .Name }} (unreachable) 90 | {{- continue }} 91 | {{- end }} 92 | {{- /* 93 | * Do not emit multiple `server` directives for this container if it 94 | * is reachable over multiple networks. This avoids accidentally 95 | * inflating the effective round-robin weight of a server due to the 96 | * redundant upstream addresses that nginx sees as belonging to 97 | * distinct servers. 98 | */}} 99 | {{- if $ip }} 100 | # {{ .Name }} (ignored; reachable but redundant) 101 | {{- continue }} 102 | {{- end }} 103 | # {{ .Name }} (reachable) 104 | {{- if and . .IP }} 105 | {{- $ip = .IP }} 106 | {{- else }} 107 | # /!\ No IP for this network! 108 | {{- end }} 109 | {{- else }} 110 | # (none) 111 | {{- end }} 112 | # IP address: {{ if $ip }}{{ $ip }}{{ else }}(none usable){{ end }} 113 | {{- $_ := set $ "ip" $ip }} 114 | {{- end }} 115 | 116 | {{- /* 117 | * Template used as a function to get the port of the server in the given 118 | * container. This template only outputs debug comments; the port is 119 | * "returned" by storing the value in the provided dot dict. 120 | * 121 | * The provided dot dict is expected to have the following entries: 122 | * - "container": The container's RuntimeContainer struct. 123 | * 124 | * The return value will be added to the dot dict with key "port". 125 | */}} 126 | {{- define "container_port" }} 127 | {{- /* If only 1 port exposed, use that as a default, else 80. */}} 128 | # exposed ports:{{ range sortObjectsByKeysAsc $.container.Addresses "Port" }} {{ .Port }}/{{ .Proto }}{{ else }} (none){{ end }} 129 | {{- $default_port := when (eq (len $.container.Addresses) 1) (first $.container.Addresses).Port "80" }} 130 | # default port: {{ $default_port }} 131 | {{- $port := or $.container.Env.VIRTUAL_PORT $default_port }} 132 | # using port: {{ $port }} 133 | {{- $addr_obj := where $.container.Addresses "Port" $port | first }} 134 | {{- if and $addr_obj $addr_obj.HostPort }} 135 | # /!\ WARNING: Virtual port published on host. Clients 136 | # might be able to bypass nginx-proxy and 137 | # access the container's server directly. 138 | {{- end }} 139 | {{- $_ := set $ "port" $port }} 140 | {{- end }} 141 | 142 | {{- define "ssl_policy" }} 143 | {{- if eq .ssl_policy "Mozilla-Modern" }} 144 | ssl_protocols TLSv1.3; 145 | {{- /* 146 | * This ssl_ciphers directive is not used but necessary to get TLSv1.3 only. 147 | * see https://serverfault.com/questions/1023766/nginx-with-only-tls1-3-cipher-suites 148 | */}} 149 | ssl_ciphers ECDHE-ECDSA-AES256-GCM-SHA384; 150 | ssl_conf_command Ciphersuites TLS_AES_128_GCM_SHA256:TLS_AES_256_GCM_SHA384:TLS_CHACHA20_POLY1305_SHA256; 151 | ssl_prefer_server_ciphers off; 152 | {{- else if eq .ssl_policy "Mozilla-Intermediate" }} 153 | ssl_protocols TLSv1.2 TLSv1.3; 154 | ssl_ciphers 'ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-CHACHA20-POLY1305:ECDHE-RSA-CHACHA20-POLY1305:DHE-RSA-AES128-GCM-SHA256:DHE-RSA-AES256-GCM-SHA384:DHE-RSA-CHACHA20-POLY1305'; 155 | ssl_prefer_server_ciphers off; 156 | {{- else if eq .ssl_policy "Mozilla-Old" }} 157 | ssl_protocols TLSv1 TLSv1.1 TLSv1.2 TLSv1.3; 158 | ssl_ciphers 'ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-CHACHA20-POLY1305:ECDHE-RSA-CHACHA20-POLY1305:DHE-RSA-AES128-GCM-SHA256:DHE-RSA-AES256-GCM-SHA384:DHE-RSA-CHACHA20-POLY1305:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA256:ECDHE-ECDSA-AES128-SHA:ECDHE-RSA-AES128-SHA:ECDHE-ECDSA-AES256-SHA384:ECDHE-RSA-AES256-SHA384:ECDHE-ECDSA-AES256-SHA:ECDHE-RSA-AES256-SHA:DHE-RSA-AES128-SHA256:DHE-RSA-AES256-SHA256:AES128-GCM-SHA256:AES256-GCM-SHA384:AES128-SHA256:AES256-SHA256:AES128-SHA:AES256-SHA:DES-CBC3-SHA'; 159 | ssl_prefer_server_ciphers on; 160 | {{- else if eq .ssl_policy "AWS-TLS13-1-3-2021-06" }} 161 | ssl_protocols TLSv1.3; 162 | {{- /* 163 | * This ssl_ciphers directive is not used but necessary to get TLSv1.3 only. 164 | * see https://serverfault.com/questions/1023766/nginx-with-only-tls1-3-cipher-suites 165 | */}} 166 | ssl_ciphers ECDHE-ECDSA-AES256-GCM-SHA384; 167 | ssl_conf_command Ciphersuites TLS_AES_128_GCM_SHA256:TLS_AES_256_GCM_SHA384:TLS_CHACHA20_POLY1305_SHA256; 168 | ssl_prefer_server_ciphers on; 169 | {{- else if eq .ssl_policy "AWS-TLS13-1-2-2021-06" }} 170 | ssl_protocols TLSv1.2 TLSv1.3; 171 | ssl_ciphers 'ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-AES256-SHA384:ECDHE-RSA-AES256-SHA384'; 172 | ssl_prefer_server_ciphers on; 173 | {{- else if eq .ssl_policy "AWS-TLS13-1-2-Res-2021-06" }} 174 | ssl_protocols TLSv1.2 TLSv1.3; 175 | ssl_ciphers 'ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384'; 176 | ssl_prefer_server_ciphers on; 177 | {{- else if eq .ssl_policy "AWS-TLS13-1-2-Ext1-2021-06" }} 178 | ssl_protocols TLSv1.2 TLSv1.3; 179 | ssl_ciphers 'ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-AES256-SHA384:ECDHE-RSA-AES256-SHA384:AES128-GCM-SHA256:AES128-SHA256:AES256-GCM-SHA384:AES256-SHA256'; 180 | ssl_prefer_server_ciphers on; 181 | {{- else if eq .ssl_policy "AWS-TLS13-1-2-Ext2-2021-06" }} 182 | ssl_protocols TLSv1.2 TLSv1.3; 183 | ssl_ciphers 'ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA256:ECDHE-ECDSA-AES128-SHA:ECDHE-RSA-AES128-SHA:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-AES256-SHA384:ECDHE-RSA-AES256-SHA384:ECDHE-RSA-AES256-SHA:ECDHE-ECDSA-AES256-SHA:AES128-GCM-SHA256:AES128-SHA256:AES128-SHA:AES256-GCM-SHA384:AES256-SHA256:AES256-SHA'; 184 | ssl_prefer_server_ciphers on; 185 | {{- else if eq .ssl_policy "AWS-TLS13-1-1-2021-06" }} 186 | ssl_protocols TLSv1.1 TLSv1.2 TLSv1.3; 187 | ssl_ciphers 'ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA256:ECDHE-ECDSA-AES128-SHA:ECDHE-RSA-AES128-SHA:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-AES256-SHA384:ECDHE-RSA-AES256-SHA384:ECDHE-RSA-AES256-SHA:ECDHE-ECDSA-AES256-SHA:AES128-GCM-SHA256:AES128-SHA256:AES128-SHA:AES256-GCM-SHA384:AES256-SHA256:AES256-SHA'; 188 | ssl_prefer_server_ciphers on; 189 | {{- else if eq .ssl_policy "AWS-TLS13-1-0-2021-06" }} 190 | ssl_protocols TLSv1 TLSv1.1 TLSv1.2 TLSv1.3; 191 | ssl_ciphers 'ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA256:ECDHE-ECDSA-AES128-SHA:ECDHE-RSA-AES128-SHA:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-AES256-SHA384:ECDHE-RSA-AES256-SHA384:ECDHE-RSA-AES256-SHA:ECDHE-ECDSA-AES256-SHA:AES128-GCM-SHA256:AES128-SHA256:AES128-SHA:AES256-GCM-SHA384:AES256-SHA256:AES256-SHA'; 192 | ssl_prefer_server_ciphers on; 193 | {{- else if eq .ssl_policy "AWS-FS-1-2-Res-2020-10" }} 194 | ssl_protocols TLSv1.2; 195 | ssl_ciphers 'ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384'; 196 | ssl_prefer_server_ciphers on; 197 | {{- else if eq .ssl_policy "AWS-FS-1-2-Res-2019-08" }} 198 | ssl_protocols TLSv1.2; 199 | ssl_ciphers 'ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-AES256-SHA384:ECDHE-RSA-AES256-SHA384'; 200 | ssl_prefer_server_ciphers on; 201 | {{- else if eq .ssl_policy "AWS-FS-1-2-2019-08" }} 202 | ssl_protocols TLSv1.2; 203 | ssl_ciphers 'ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA256:ECDHE-ECDSA-AES128-SHA:ECDHE-RSA-AES128-SHA:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-AES256-SHA384:ECDHE-RSA-AES256-SHA384:ECDHE-RSA-AES256-SHA:ECDHE-ECDSA-AES256-SHA'; 204 | ssl_prefer_server_ciphers on; 205 | {{- else if eq .ssl_policy "AWS-FS-1-1-2019-08" }} 206 | ssl_protocols TLSv1.1 TLSv1.2; 207 | ssl_ciphers 'ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA256:ECDHE-ECDSA-AES128-SHA:ECDHE-RSA-AES128-SHA:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-AES256-SHA384:ECDHE-RSA-AES256-SHA384:ECDHE-RSA-AES256-SHA:ECDHE-ECDSA-AES256-SHA'; 208 | ssl_prefer_server_ciphers on; 209 | {{- else if eq .ssl_policy "AWS-FS-2018-06" }} 210 | ssl_protocols TLSv1 TLSv1.1 TLSv1.2; 211 | ssl_ciphers 'ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA256:ECDHE-ECDSA-AES128-SHA:ECDHE-RSA-AES128-SHA:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-AES256-SHA384:ECDHE-RSA-AES256-SHA384:ECDHE-RSA-AES256-SHA:ECDHE-ECDSA-AES256-SHA'; 212 | ssl_prefer_server_ciphers on; 213 | {{- else if eq .ssl_policy "AWS-TLS-1-2-Ext-2018-06" }} 214 | ssl_protocols TLSv1.2; 215 | ssl_ciphers 'ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA256:ECDHE-ECDSA-AES128-SHA:ECDHE-RSA-AES128-SHA:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-AES256-SHA384:ECDHE-RSA-AES256-SHA384:ECDHE-RSA-AES256-SHA:ECDHE-ECDSA-AES256-SHA:AES128-GCM-SHA256:AES128-SHA256:AES128-SHA:AES256-GCM-SHA384:AES256-SHA256:AES256-SHA'; 216 | ssl_prefer_server_ciphers on; 217 | {{- else if eq .ssl_policy "AWS-TLS-1-2-2017-01" }} 218 | ssl_protocols TLSv1.2; 219 | ssl_ciphers 'ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-AES256-SHA384:ECDHE-RSA-AES256-SHA384:AES128-GCM-SHA256:AES128-SHA256:AES256-GCM-SHA384:AES256-SHA256'; 220 | ssl_prefer_server_ciphers on; 221 | {{- else if eq .ssl_policy "AWS-TLS-1-1-2017-01" }} 222 | ssl_protocols TLSv1.1 TLSv1.2; 223 | ssl_ciphers 'ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA256:ECDHE-ECDSA-AES128-SHA:ECDHE-RSA-AES128-SHA:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-AES256-SHA384:ECDHE-RSA-AES256-SHA384:ECDHE-RSA-AES256-SHA:ECDHE-ECDSA-AES256-SHA:AES128-GCM-SHA256:AES128-SHA256:AES128-SHA:AES256-GCM-SHA384:AES256-SHA256:AES256-SHA'; 224 | ssl_prefer_server_ciphers on; 225 | {{- else if eq .ssl_policy "AWS-2016-08" }} 226 | ssl_protocols TLSv1 TLSv1.1 TLSv1.2; 227 | ssl_ciphers 'ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA256:ECDHE-ECDSA-AES128-SHA:ECDHE-RSA-AES128-SHA:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-AES256-SHA384:ECDHE-RSA-AES256-SHA384:ECDHE-RSA-AES256-SHA:ECDHE-ECDSA-AES256-SHA:AES128-GCM-SHA256:AES128-SHA256:AES128-SHA:AES256-GCM-SHA384:AES256-SHA256:AES256-SHA'; 228 | ssl_prefer_server_ciphers on; 229 | {{- else if eq .ssl_policy "AWS-2015-05" }} 230 | ssl_protocols TLSv1 TLSv1.1 TLSv1.2; 231 | ssl_ciphers 'ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA256:ECDHE-ECDSA-AES128-SHA:ECDHE-RSA-AES128-SHA:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-AES256-SHA384:ECDHE-RSA-AES256-SHA384:ECDHE-RSA-AES256-SHA:ECDHE-ECDSA-AES256-SHA:AES128-GCM-SHA256:AES128-SHA256:AES128-SHA:AES256-GCM-SHA384:AES256-SHA256:AES256-SHA:DES-CBC3-SHA'; 232 | ssl_prefer_server_ciphers on; 233 | {{- else if eq .ssl_policy "AWS-2015-03" }} 234 | ssl_protocols TLSv1 TLSv1.1 TLSv1.2; 235 | ssl_ciphers 'ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA256:ECDHE-ECDSA-AES128-SHA:ECDHE-RSA-AES128-SHA:DHE-RSA-AES128-SHA:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-AES256-SHA384:ECDHE-RSA-AES256-SHA384:ECDHE-RSA-AES256-SHA:ECDHE-ECDSA-AES256-SHA:AES128-GCM-SHA256:AES128-SHA256:AES128-SHA:AES256-GCM-SHA384:AES256-SHA256:AES256-SHA:DHE-DSS-AES128-SHA:DES-CBC3-SHA'; 236 | ssl_prefer_server_ciphers on; 237 | {{- else if eq .ssl_policy "AWS-2015-02" }} 238 | ssl_protocols TLSv1 TLSv1.1 TLSv1.2; 239 | ssl_ciphers 'ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA256:ECDHE-ECDSA-AES128-SHA:ECDHE-RSA-AES128-SHA:DHE-RSA-AES128-SHA:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-AES256-SHA384:ECDHE-RSA-AES256-SHA384:ECDHE-RSA-AES256-SHA:ECDHE-ECDSA-AES256-SHA:AES128-GCM-SHA256:AES128-SHA256:AES128-SHA:AES256-GCM-SHA384:AES256-SHA256:AES256-SHA:DHE-DSS-AES128-SHA'; 240 | ssl_prefer_server_ciphers on; 241 | {{- end }} 242 | {{- end }} 243 | 244 | {{- define "location" }} 245 | {{- $override := printf "/etc/nginx/vhost.d/%s_%s_location_override" .Host (sha1 .Path) }} 246 | {{- if and (eq .Path "/") (not (exists $override)) }} 247 | {{- $override = printf "/etc/nginx/vhost.d/%s_location_override" .Host }} 248 | {{- end }} 249 | {{- if exists $override }} 250 | include {{ $override }}; 251 | {{- else }} 252 | {{- $keepalive := coalesce (first (keys (groupByLabel .Containers "com.github.nginx-proxy.nginx-proxy.keepalive"))) "disabled" }} 253 | location {{ .Path }} { 254 | {{- if eq .NetworkTag "internal" }} 255 | # Only allow traffic from internal clients 256 | include /etc/nginx/network_internal.conf; 257 | {{- end }} 258 | 259 | {{- if eq .Proto "uwsgi" }} 260 | include uwsgi_params; 261 | uwsgi_pass {{ trim .Proto }}://{{ trim .Upstream }}; 262 | {{- else if eq .Proto "fastcgi" }} 263 | root {{ trim .VhostRoot }}; 264 | include fastcgi_params; 265 | fastcgi_pass {{ trim .Upstream }}; 266 | {{- if ne $keepalive "disabled" }} 267 | fastcgi_keep_conn on; 268 | {{- end }} 269 | {{- else if eq .Proto "grpc" }} 270 | grpc_pass {{ trim .Proto }}://{{ trim .Upstream }}; 271 | {{- else if eq .Proto "grpcs" }} 272 | grpc_pass {{ trim .Proto }}://{{ trim .Upstream }}; 273 | {{- else }} 274 | proxy_pass {{ trim .Proto }}://{{ trim .Upstream }}{{ trim .Dest }}; 275 | set $upstream_keepalive {{ if ne $keepalive "disabled" }}true{{ else }}false{{ end }}; 276 | {{- end }} 277 | 278 | {{- if (exists (printf "/etc/nginx/htpasswd/%s_%s" .Host (sha1 .Path) )) }} 279 | auth_basic "Restricted {{ .Host }}{{ .Path }}"; 280 | auth_basic_user_file {{ (printf "/etc/nginx/htpasswd/%s_%s" .Host (sha1 .Path)) }}; 281 | {{- else if (exists (printf "/etc/nginx/htpasswd/%s" .Host)) }} 282 | auth_basic "Restricted {{ .Host }}"; 283 | auth_basic_user_file {{ (printf "/etc/nginx/htpasswd/%s" .Host) }}; 284 | {{- end }} 285 | 286 | {{- if (exists (printf "/etc/nginx/vhost.d/%s_%s_location" .Host (sha1 .Path) )) }} 287 | include {{ printf "/etc/nginx/vhost.d/%s_%s_location" .Host (sha1 .Path) }}; 288 | {{- else if (exists (printf "/etc/nginx/vhost.d/%s_location" .Host)) }} 289 | include {{ printf "/etc/nginx/vhost.d/%s_location" .Host}}; 290 | {{- else if (exists "/etc/nginx/vhost.d/default_location") }} 291 | include /etc/nginx/vhost.d/default_location; 292 | {{- end }} 293 | } 294 | {{- end }} 295 | {{- end }} 296 | 297 | {{- define "upstream" }} 298 | upstream {{ .Upstream }} { 299 | {{- $servers := 0 }} 300 | {{- $loadbalance := first (keys (groupByLabel .Containers "com.github.nginx-proxy.nginx-proxy.loadbalance")) }} 301 | {{- if $loadbalance }} 302 | # From the container's loadbalance label: 303 | {{ $loadbalance }} 304 | {{- end }} 305 | {{- range $container := .Containers }} 306 | # Container: {{ $container.Name }} 307 | {{- $args := dict "globals" $.globals "container" $container }} 308 | {{- template "container_ip" $args }} 309 | {{- $ip := $args.ip }} 310 | {{- $args := dict "container" $container }} 311 | {{- template "container_port" $args }} 312 | {{- $port := $args.port }} 313 | {{- if $ip }} 314 | {{- $servers = add1 $servers }} 315 | server {{ $ip }}:{{ $port }}; 316 | {{- end }} 317 | {{- end }} 318 | {{- /* nginx-proxy/nginx-proxy#1105 */}} 319 | {{- if lt $servers 1 }} 320 | # Fallback entry 321 | server 127.0.0.1 down; 322 | {{- end }} 323 | {{- $keepalive := coalesce (first (keys (groupByLabel .Containers "com.github.nginx-proxy.nginx-proxy.keepalive"))) "disabled" }} 324 | {{- if and (ne $keepalive "disabled") (gt $servers 0) }} 325 | {{- if eq $keepalive "auto" }} 326 | keepalive {{ mul $servers 2 }}; 327 | {{- else }} 328 | keepalive {{ $keepalive }}; 329 | {{- end }} 330 | {{- end }} 331 | } 332 | {{- end }} 333 | 334 | # If we receive X-Forwarded-Proto, pass it through; otherwise, pass along the 335 | # scheme used to connect to this server 336 | map $http_x_forwarded_proto $proxy_x_forwarded_proto { 337 | default {{ if $globals.trust_downstream_proxy }}$http_x_forwarded_proto{{ else }}$scheme{{ end }}; 338 | '' $scheme; 339 | } 340 | 341 | map $http_x_forwarded_host $proxy_x_forwarded_host { 342 | default {{ if $globals.trust_downstream_proxy }}$http_x_forwarded_host{{ else }}$host{{ end }}; 343 | '' $host; 344 | } 345 | 346 | # If we receive X-Forwarded-Port, pass it through; otherwise, pass along the 347 | # server port the client connected to 348 | map $http_x_forwarded_port $proxy_x_forwarded_port { 349 | default {{ if $globals.trust_downstream_proxy }}$http_x_forwarded_port{{ else }}$server_port{{ end }}; 350 | '' $server_port; 351 | } 352 | 353 | # Include the port in the Host header sent to the container if it is non-standard 354 | map $server_port $host_port { 355 | default :$server_port; 356 | 80 ''; 357 | 443 ''; 358 | } 359 | 360 | # If the request from the downstream client has an "Upgrade:" header (set to any 361 | # non-empty value), pass "Connection: upgrade" to the upstream (backend) server. 362 | # Otherwise, the value for the "Connection" header depends on whether the user 363 | # has enabled keepalive to the upstream server. 364 | map $http_upgrade $proxy_connection { 365 | default upgrade; 366 | '' $proxy_connection_noupgrade; 367 | } 368 | map $upstream_keepalive $proxy_connection_noupgrade { 369 | # Preserve nginx's default behavior (send "Connection: close"). 370 | default close; 371 | # Use an empty string to cancel nginx's default behavior. 372 | true ''; 373 | } 374 | # Abuse the map directive (see ) to ensure 375 | # that $upstream_keepalive is always defined. This is necessary because: 376 | # - The $proxy_connection variable is indirectly derived from 377 | # $upstream_keepalive, so $upstream_keepalive must be defined whenever 378 | # $proxy_connection is resolved. 379 | # - The $proxy_connection variable is used in a proxy_set_header directive in 380 | # the http block, so it is always fully resolved for every request -- even 381 | # those where proxy_pass is not used (e.g., unknown virtual host). 382 | map "" $upstream_keepalive { 383 | # The value here should not matter because it should always be overridden in 384 | # a location block (see the "location" template) for all requests where the 385 | # value actually matters. 386 | default false; 387 | } 388 | 389 | # Apply fix for very long server names 390 | server_names_hash_bucket_size 128; 391 | 392 | # Default dhparam 393 | {{- if (exists "/etc/nginx/dhparam/dhparam.pem") }} 394 | ssl_dhparam /etc/nginx/dhparam/dhparam.pem; 395 | {{- end }} 396 | 397 | # Set appropriate X-Forwarded-Ssl header based on $proxy_x_forwarded_proto 398 | map $proxy_x_forwarded_proto $proxy_x_forwarded_ssl { 399 | default off; 400 | https on; 401 | } 402 | 403 | gzip_types text/plain text/css application/javascript application/json application/x-javascript text/xml application/xml application/xml+rss text/javascript; 404 | 405 | 406 | {{- /* See https://nginx.org/en/docs/http/ngx_http_log_module.html#log_format for details and variables 407 | * LOG_FORMAT_ESCAPE sets the escape part of the log format 408 | * LOG_FORMAT sets the log format 409 | */}} 410 | {{- $logEscape := printf "escape=%s" (or $globals.Env.LOG_FORMAT_ESCAPE "default") }} 411 | {{- $logFormat := or $globals.Env.LOG_FORMAT `$host $remote_addr - $remote_user [$time_local] "$request" $status $body_bytes_sent "$http_referer" "$http_user_agent" "$upstream_addr"` }} 412 | 413 | {{- if parseBool (or $globals.Env.LOG_JSON "false") }} 414 | {{- /* LOG_JSON is a shorthand 415 | * that sets logging defaults to JSON format 416 | */}} 417 | # JSON Logging enabled (via LOG_JSON env variable) 418 | {{- $logEscape = printf "escape=%s" (or $globals.Env.LOG_FORMAT_ESCAPE "json") }} 419 | {{- $logFormat = or $globals.Env.LOG_FORMAT `{"time_local":"$time_iso8601","client_ip":"$http_x_forwarded_for","remote_addr":"$remote_addr","request":"$request","status":"$status","body_bytes_sent":"$body_bytes_sent","request_time":"$request_time","upstream_response_time":"$upstream_response_time","upstream_addr":"$upstream_addr","http_referrer":"$http_referer","http_user_agent":"$http_user_agent","request_id":"$request_id"}` }} 420 | {{- end }} 421 | 422 | log_format vhost {{ $logEscape }} '{{ or $globals.Env.LOG_FORMAT $logFormat }}'; 423 | 424 | access_log off; 425 | 426 | {{- template "ssl_policy" (dict "ssl_policy" $globals.ssl_policy) }} 427 | error_log /dev/stderr; 428 | 429 | {{- if $globals.Env.RESOLVERS }} 430 | resolver {{ $globals.Env.RESOLVERS }}; 431 | {{- end }} 432 | 433 | {{- if (exists "/etc/nginx/proxy.conf") }} 434 | include /etc/nginx/proxy.conf; 435 | {{- else }} 436 | # HTTP 1.1 support 437 | proxy_http_version 1.1; 438 | proxy_set_header Host $host$host_port; 439 | proxy_set_header Upgrade $http_upgrade; 440 | proxy_set_header Connection $proxy_connection; 441 | proxy_set_header X-Real-IP $remote_addr; 442 | proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; 443 | proxy_set_header X-Forwarded-Host $proxy_x_forwarded_host; 444 | proxy_set_header X-Forwarded-Proto $proxy_x_forwarded_proto; 445 | proxy_set_header X-Forwarded-Ssl $proxy_x_forwarded_ssl; 446 | proxy_set_header X-Forwarded-Port $proxy_x_forwarded_port; 447 | proxy_set_header X-Original-URI $request_uri; 448 | 449 | # Mitigate httpoxy attack (see README for details) 450 | proxy_set_header Proxy ""; 451 | {{- end }} 452 | 453 | {{- /* Precompute some information about each vhost. */}} 454 | {{- range $hostname, $containers := groupByMulti $globals.containers "Env.VIRTUAL_HOST" "," }} 455 | {{- $hostname = trim $hostname }} 456 | {{- if not $hostname }} 457 | {{- /* Ignore containers with VIRTUAL_HOST set to the empty string. */}} 458 | {{- continue }} 459 | {{- end }} 460 | 461 | {{- $certName := first (groupByKeys $containers "Env.CERT_NAME") }} 462 | {{- $vhostCert := closest (dir "/etc/nginx/certs") (printf "%s.crt" $hostname) }} 463 | {{- $vhostCert = trimSuffix ".crt" $vhostCert }} 464 | {{- $vhostCert = trimSuffix ".key" $vhostCert }} 465 | {{- $cert := or $certName $vhostCert }} 466 | {{- $cert_ok := and (ne $cert "") (exists (printf "/etc/nginx/certs/%s.crt" $cert)) (exists (printf "/etc/nginx/certs/%s.key" $cert)) }} 467 | 468 | {{- $default := eq $globals.Env.DEFAULT_HOST $hostname }} 469 | {{- $https_method := or (first (groupByKeys $containers "Env.HTTPS_METHOD")) $globals.Env.HTTPS_METHOD "redirect" }} 470 | {{- $http2_enabled := parseBool (or (first (keys (groupByLabel $containers "com.github.nginx-proxy.nginx-proxy.http2.enable"))) $globals.Env.ENABLE_HTTP2 "true")}} 471 | {{- $http3_enabled := parseBool (or (first (keys (groupByLabel $containers "com.github.nginx-proxy.nginx-proxy.http3.enable"))) $globals.Env.ENABLE_HTTP3 "false")}} 472 | 473 | {{- $is_regexp := hasPrefix "~" $hostname }} 474 | {{- $upstream_name := when (or $is_regexp $globals.sha1_upstream_name) (sha1 $hostname) $hostname }} 475 | 476 | {{- /* Get the SERVER_TOKENS defined by containers w/ the same vhost, falling back to "". */}} 477 | {{- $server_tokens := trim (or (first (groupByKeys $containers "Env.SERVER_TOKENS")) "") }} 478 | 479 | {{- /* Get the SSL_POLICY defined by containers w/ the same vhost, falling back to empty string (use default). */}} 480 | {{- $ssl_policy := or (first (groupByKeys $containers "Env.SSL_POLICY")) "" }} 481 | 482 | {{- /* Get the HSTS defined by containers w/ the same vhost, falling back to "max-age=31536000". */}} 483 | {{- $hsts := or (first (groupByKeys $containers "Env.HSTS")) (or $globals.Env.HSTS "max-age=31536000") }} 484 | 485 | 486 | {{- /* Get the X-Content-Type-Options defined by containers w/ the same vhost, falling back to "nosniff" */}} 487 | {{- $x_content_type := or (first (groupByKeys $containers "Env.X_CONTENT_TYPE_OPTIONS")) (or $globals.Env.X_CONTENT_TYPE_OPTIONS "nosniff") }} 488 | 489 | {{- /* Get the X-XSS-Protection defined by containers w/ the same vhost, falling back to "off" */}} 490 | {{- $x_xss_protection := or (first (groupByKeys $containers "Env.X_XSS_Protection")) (or $globals.Env.X_XSS_Protection "off") }} 491 | 492 | {{- /* Get the Referrer-Policy defined by containers w/ the same vhost, falling back to "same-origin" */}} 493 | {{- $referrer_policy := or (first (groupByKeys $containers "Env.REFERRER_POLICY")) (or $globals.Env.REFERRER_POLICY "same-origin") }} 494 | 495 | {{- /* Get the Permissions-Policy defined by containers w/ the same vhost, falling back to "off" */}} 496 | {{- $permissions_policy := or (first (groupByKeys $containers "Env.PERMISSIONS_POLICY")) (or $globals.Env.PERMISSIONS_POLICY "off") }} 497 | 498 | {{- /* Get the Content-Security-Policy defined by containers w/ the same vhost, falling back to "default-src 'self'; script-src 'self' 'unsafe-eval'; style-src 'self' 'unsafe-inline'; object-src 'none'; img-src 'self' https: data: blob:; font-src 'self' data:;" */}} 499 | {{- $content_security_policy := or (first (groupByKeys $containers "Env.CONTENT_SECURITY_POLICY")) (or $globals.Env.CONTENT_SECURITY_POLICY "default-src 'self'; script-src 'self' 'unsafe-eval'; style-src 'self' 'unsafe-inline'; object-src 'none'; img-src 'self' https: data: blob:; font-src 'self' data:;") }} 500 | 501 | {{- /* Get the Content-Security-Policy-Report-Only defined by containers w/ the same vhost, falling back to "off" */}} 502 | {{- $content_security_policy_report_only := or (first (groupByKeys $containers "Env.CONTENT_SECURITY_POLICY_REPORT_ONLY")) (or $globals.Env.CONTENT_SECURITY_POLICY_REPORT_ONLY "off") }} 503 | 504 | {{- /* Get the X-Frame-Options defined by containers w/ the same vhost, falling back to "DENY" */}} 505 | {{- $x_frame_options := or (first (groupByKeys $containers "Env.X_FRAME_OPTIONS")) (or $globals.Env.X_FRAME_OPTIONS "DENY") }} 506 | 507 | 508 | 509 | 510 | {{- /* Get the VIRTUAL_ROOT By containers w/ use fastcgi root */}} 511 | {{- $vhost_root := or (first (groupByKeys $containers "Env.VIRTUAL_ROOT")) "/var/www/public" }} 512 | 513 | 514 | {{- $tmp_paths := groupBy $containers "Env.VIRTUAL_PATH" }} 515 | {{- $has_virtual_paths := gt (len $tmp_paths) 0}} 516 | {{- if not $has_virtual_paths }} 517 | {{- $tmp_paths = dict "/" $containers }} 518 | {{- end }} 519 | 520 | {{ $paths := dict }} 521 | 522 | {{- range $path, $containers := $tmp_paths }} 523 | {{- /* Get the VIRTUAL_PROTO defined by containers w/ the same vhost-vpath, falling back to "http". */}} 524 | {{- $proto := trim (or (first (groupByKeys $containers "Env.VIRTUAL_PROTO")) "http") }} 525 | {{- /* Get the NETWORK_ACCESS defined by containers w/ the same vhost, falling back to "external". */}} 526 | {{- $network_tag := or (first (groupByKeys $containers "Env.NETWORK_ACCESS")) "external" }} 527 | 528 | {{- $upstream := $upstream_name }} 529 | {{- $dest := "" }} 530 | {{- if $has_virtual_paths }} 531 | {{- $sum := sha1 $path }} 532 | {{- $upstream = printf "%s-%s" $upstream $sum }} 533 | {{- $dest = (or (first (groupByKeys $containers "Env.VIRTUAL_DEST")) "") }} 534 | {{- end }} 535 | {{- $_ := set $paths $path (dict 536 | "containers" $containers 537 | "dest" $dest 538 | "proto" $proto 539 | "network_tag" $network_tag 540 | "upstream" $upstream 541 | ) }} 542 | {{- end }} 543 | 544 | {{- $_ := set $globals.vhosts $hostname (dict 545 | "cert" $cert 546 | "cert_ok" $cert_ok 547 | "default" $default 548 | "hsts" $hsts 549 | "x_content_type" $x_content_type 550 | "x_xss_protection" $x_xss_protection 551 | "referrer_policy" $referrer_policy 552 | "permissions_policy" $permissions_policy 553 | "content_security_policy" $content_security_policy 554 | "content_security_policy_report_only" $content_security_policy_report_only 555 | "x_frame_options" $x_frame_options 556 | "https_method" $https_method 557 | "http2_enabled" $http2_enabled 558 | "http3_enabled" $http3_enabled 559 | "paths" $paths 560 | "server_tokens" $server_tokens 561 | "ssl_policy" $ssl_policy 562 | "vhost_root" $vhost_root 563 | ) }} 564 | {{- end }} 565 | 566 | {{- /* 567 | * If needed, create a catch-all fallback server to send an error code to 568 | * clients that request something from an unknown vhost. 569 | * 570 | * This server must appear first in the generated config because nginx uses 571 | * the first `server` directive to handle requests that don't match any of 572 | * the other `server` directives. An alternative approach would be to add 573 | * the `default_server` option to the `listen` directives inside this 574 | * `server`, but some users inject a custom `server` directive that uses 575 | * `default_server`. Using `default_server` here would cause nginx to fail 576 | * to start for those users. See 577 | * . 578 | */}} 579 | {{- block "fallback_server" $globals }} 580 | {{- $globals := . }} 581 | {{- $http_exists := false }} 582 | {{- $https_exists := false }} 583 | {{- $default_http_exists := false }} 584 | {{- $default_https_exists := false }} 585 | {{- $http3_enabled := false }} 586 | {{- range $vhost := $globals.vhosts }} 587 | {{- $http := or (ne $vhost.https_method "nohttp") (not $vhost.cert_ok) }} 588 | {{- $https := ne $vhost.https_method "nohttps" }} 589 | {{- $http_exists = or $http_exists $http }} 590 | {{- $https_exists = or $https_exists $https }} 591 | {{- $default_http_exists = or $default_http_exists (and $http $vhost.default) }} 592 | {{- $default_https_exists = or $default_https_exists (and $https $vhost.default) }} 593 | {{- $http3_enabled = or $http3_enabled $vhost.http3_enabled }} 594 | {{- end }} 595 | {{- $fallback_http := and $http_exists (not $default_http_exists) }} 596 | {{- $fallback_https := and $https_exists (not $default_https_exists) }} 597 | {{- /* 598 | * If there are no vhosts at all, create fallbacks for both plain http 599 | * and https so that clients get something more useful than a connection 600 | * refused error. 601 | */}} 602 | {{- if and (not $http_exists) (not $https_exists) }} 603 | {{- $fallback_http = true }} 604 | {{- $fallback_https = true }} 605 | {{- end }} 606 | {{- if or $fallback_http $fallback_https }} 607 | server { 608 | server_name _; # This is just an invalid value which will never trigger on a real hostname. 609 | server_tokens off; 610 | {{ $globals.access_log }} 611 | http2 on; 612 | {{- if $fallback_http }} 613 | listen {{ $globals.external_http_port }}; {{- /* Do not add `default_server` (see comment above). */}} 614 | {{- if $globals.enable_ipv6 }} 615 | listen [::]:{{ $globals.external_http_port }}; {{- /* Do not add `default_server` (see comment above). */}} 616 | {{- end }} 617 | {{- end }} 618 | {{- if $fallback_https }} 619 | listen {{ $globals.external_https_port }} ssl; {{- /* Do not add `default_server` (see comment above). */}} 620 | {{- if $globals.enable_ipv6 }} 621 | listen [::]:{{ $globals.external_https_port }} ssl; {{- /* Do not add `default_server` (see comment above). */}} 622 | {{- end }} 623 | {{- if $http3_enabled }} 624 | http3 on; 625 | listen {{ $globals.external_https_port }} quic reuseport; {{- /* Do not add `default_server` (see comment above). */}} 626 | {{- if $globals.enable_ipv6 }} 627 | listen [::]:{{ $globals.external_https_port }} quic reuseport; {{- /* Do not add `default_server` (see comment above). */}} 628 | {{- end }} 629 | {{- end }} 630 | ssl_session_cache shared:SSL:50m; 631 | ssl_session_tickets off; 632 | {{- end }} 633 | {{- if $globals.default_cert_ok }} 634 | ssl_certificate /etc/nginx/certs/default.crt; 635 | ssl_certificate_key /etc/nginx/certs/default.key; 636 | {{- else }} 637 | # No default.crt certificate found for this vhost, so force nginx to emit a 638 | # TLS error if the client connects via https. 639 | {{- /* See the comment in the main `server` directive for rationale. */}} 640 | ssl_ciphers aNULL; 641 | set $empty ""; 642 | ssl_certificate data:$empty; 643 | ssl_certificate_key data:$empty; 644 | if ($https) { 645 | return 444; 646 | } 647 | {{- end }} 648 | return 503; 649 | } 650 | {{- end }} 651 | {{- end }} 652 | 653 | {{- range $hostname, $vhost := $globals.vhosts }} 654 | {{- $default_server := when $vhost.default "default_server" "" }} 655 | 656 | {{- range $path, $vpath := $vhost.paths }} 657 | # {{ $hostname }}{{ $path }} 658 | {{ template "upstream" (dict "globals" $globals "Upstream" $vpath.upstream "Containers" $vpath.containers) }} 659 | {{- end }} 660 | 661 | {{- if and $vhost.cert_ok (eq $vhost.https_method "redirect") }} 662 | server { 663 | server_name {{ $hostname }}; 664 | {{- if $vhost.server_tokens }} 665 | server_tokens {{ $vhost.server_tokens }}; 666 | {{- end }} 667 | {{ $globals.access_log }} 668 | listen {{ $globals.external_http_port }} {{ $default_server }}; 669 | {{- if $globals.enable_ipv6 }} 670 | listen [::]:{{ $globals.external_http_port }} {{ $default_server }}; 671 | {{- end }} 672 | 673 | # Do not HTTPS redirect Let's Encrypt ACME challenge 674 | location ^~ /.well-known/acme-challenge/ { 675 | auth_basic off; 676 | auth_request off; 677 | allow all; 678 | root /usr/share/nginx/html; 679 | try_files $uri =404; 680 | break; 681 | } 682 | 683 | location / { 684 | {{- if eq $globals.external_https_port "443" }} 685 | return 301 https://$host$request_uri; 686 | {{- else }} 687 | return 301 https://$host:{{ $globals.external_https_port }}$request_uri; 688 | {{- end }} 689 | } 690 | } 691 | {{- end }} 692 | 693 | server { 694 | server_name {{ $hostname }}; 695 | {{- if $vhost.server_tokens }} 696 | server_tokens {{ $vhost.server_tokens }}; 697 | {{- end }} 698 | {{ $globals.access_log }} 699 | {{- if $vhost.http2_enabled }} 700 | http2 on; 701 | {{- end }} 702 | {{- if or (eq $vhost.https_method "nohttps") (not $vhost.cert_ok) (eq $vhost.https_method "noredirect") }} 703 | listen {{ $globals.external_http_port }} {{ $default_server }}; 704 | {{- if $globals.enable_ipv6 }} 705 | listen [::]:{{ $globals.external_http_port }} {{ $default_server }}; 706 | {{- end }} 707 | {{- end }} 708 | {{- if ne $vhost.https_method "nohttps" }} 709 | listen {{ $globals.external_https_port }} ssl {{ $default_server }}; 710 | {{- if $globals.enable_ipv6 }} 711 | listen [::]:{{ $globals.external_https_port }} ssl {{ $default_server }}; 712 | {{- end }} 713 | 714 | {{- if $vhost.http3_enabled }} 715 | http3 on; 716 | add_header alt-svc 'h3=":{{ $globals.external_https_port }}"; ma=86400;'; 717 | listen {{ $globals.external_https_port }} quic {{ $default_server }}; 718 | {{- if $globals.enable_ipv6 }} 719 | listen [::]:{{ $globals.external_https_port }} quic {{ $default_server }}; 720 | {{- end }} 721 | {{- end }} 722 | 723 | {{- if $vhost.cert_ok }} 724 | {{- template "ssl_policy" (dict "ssl_policy" $vhost.ssl_policy) }} 725 | 726 | ssl_session_timeout 5m; 727 | ssl_session_cache shared:SSL:50m; 728 | ssl_session_tickets off; 729 | 730 | ssl_certificate /etc/nginx/certs/{{ (printf "%s.crt" $vhost.cert) }}; 731 | ssl_certificate_key /etc/nginx/certs/{{ (printf "%s.key" $vhost.cert) }}; 732 | 733 | {{- if (exists (printf "/etc/nginx/certs/%s.dhparam.pem" $vhost.cert)) }} 734 | ssl_dhparam {{ printf "/etc/nginx/certs/%s.dhparam.pem" $vhost.cert }}; 735 | {{- end }} 736 | 737 | {{- if (exists (printf "/etc/nginx/certs/%s.chain.pem" $vhost.cert)) }} 738 | ssl_stapling on; 739 | ssl_stapling_verify on; 740 | ssl_trusted_certificate {{ printf "/etc/nginx/certs/%s.chain.pem" $vhost.cert }}; 741 | {{- end }} 742 | 743 | {{- if (not (or (eq $vhost.https_method "noredirect") (eq $vhost.hsts "off"))) }} 744 | set $sts_header ""; 745 | if ($https) { 746 | set $sts_header "{{ trim $vhost.hsts }}"; 747 | } 748 | add_header Strict-Transport-Security $sts_header always; 749 | {{- end }} 750 | {{- else if $globals.default_cert_ok }} 751 | # No certificate found for this vhost, so use the default certificate and 752 | # return an error code if the user connects via https. 753 | ssl_certificate /etc/nginx/certs/default.crt; 754 | ssl_certificate_key /etc/nginx/certs/default.key; 755 | if ($https) { 756 | return 500; 757 | } 758 | {{- else }} 759 | # No certificate found for this vhost, so force nginx to emit a TLS error if 760 | # the client connects via https. 761 | {{- /* 762 | * The alternative is to not provide an https server for this 763 | * vhost, which would either cause the user to see the wrong 764 | * vhost (if there is another vhost with a certificate) or a 765 | * connection refused error (if there is no other vhost with a 766 | * certificate). A TLS error is easier to troubleshoot, and is 767 | * safer than serving the wrong vhost. Also see 768 | * . 769 | */}} 770 | ssl_ciphers aNULL; 771 | set $empty ""; 772 | ssl_certificate data:$empty; 773 | ssl_certificate_key data:$empty; 774 | if ($https) { 775 | return 444; 776 | } 777 | {{- end }} 778 | {{- end }} 779 | 780 | {{- if (exists (printf "/etc/nginx/vhost.d/%s" $hostname)) }} 781 | include {{ printf "/etc/nginx/vhost.d/%s" $hostname }}; 782 | {{- else if (exists "/etc/nginx/vhost.d/default") }} 783 | include /etc/nginx/vhost.d/default; 784 | {{- end }} 785 | 786 | 787 | {{- if (not (eq $vhost.x_content_type "off")) }} 788 | add_header X-Content-Type-Options "{{ trim $vhost.x_content_type }}" always; 789 | {{- end }} 790 | 791 | {{- if (not (eq $vhost.x_xss_protection "off")) }} 792 | add_header X-XSS-Protection "{{ trim $vhost.x_xss_protection }}" always; 793 | {{- end }} 794 | 795 | {{- if (not (eq $vhost.referrer_policy "off")) }} 796 | add_header Referrer-Policy "{{ trim $vhost.referrer_policy }}" always; 797 | {{- end }} 798 | 799 | {{- if (not (eq $vhost.permissions_policy "off")) }} 800 | add_header Permissions-Policy "{{ trim $vhost.permissions_policy }}" always; 801 | {{- end }} 802 | 803 | {{- if (not (eq $vhost.content_security_policy "off")) }} 804 | add_header Content-Security-Policy "{{ trim $vhost.content_security_policy }}" always; 805 | {{- end }} 806 | 807 | {{- if (not (eq $vhost.content_security_policy_report_only "off")) }} 808 | add_header Content-Security-Policy-Report-Only "{{ trim $vhost.content_security_policy_report_only }}" always; 809 | {{- end }} 810 | 811 | {{- if (not (eq $vhost.x_frame_options "off")) }} 812 | add_header X-Frame-Options "{{ trim $vhost.x_frame_options }}" always; 813 | {{- end }} 814 | 815 | 816 | 817 | {{- range $path, $vpath := $vhost.paths }} 818 | {{- template "location" (dict 819 | "Path" $path 820 | "Proto" $vpath.proto 821 | "Upstream" $vpath.upstream 822 | "Host" $hostname 823 | "VhostRoot" $vhost.vhost_root 824 | "Dest" $vpath.dest 825 | "NetworkTag" $vpath.network_tag 826 | "Containers" $vpath.containers 827 | ) }} 828 | {{- end }} 829 | 830 | {{- if and (not (contains $vhost.paths "/")) (ne $globals.default_root_response "none")}} 831 | location / { 832 | return {{ $globals.default_root_response }}; 833 | } 834 | {{- end }} 835 | } 836 | {{- end }} 837 | -------------------------------------------------------------------------------- /service-template/database-config/.env_default: -------------------------------------------------------------------------------- 1 | #### DOCKER IMAGE VERSIONS #### 2 | 3 | # project/deployment name 4 | # needs to be unique i.e. will be used as container and network name as well as for the vhost entry 5 | COMPOSE_PROJECT_NAME=my-deployment-1 6 | 7 | # base host name that is used for the nginx virtual host directive 8 | # should not be required to change until you change the hostname 9 | HOST_NAME=mydocker.example.com 10 | 11 | # need to be customized only when Let's Encrypt is used. See https://letsencrypt.org/docs/expiration-emails/ 12 | LETSENCRYPT_EMAIL=email@example.com 13 | 14 | #### RUNTIME PLATFORM ENVIORNMENT PARAMS #### 15 | 16 | # can be used to pass specific platform parameter that will override any parameter set in the config files 17 | # to use a different log configuration 18 | #METAPHACTORY_OPTS=-Dlog4j.configurationFile=file:///var/lib/jetty/webapps/etc/log4j2-debug.xml 19 | # to set a pre-defined repository URL, use this setting: 20 | #METAPHACTORY_OPTS=-Dconfig.environment.sparqlEndpoint=http://database.example.com:8080/blazegraph/sparql 21 | METAPHACTORY_OPTS= 22 | 23 | #### DOCKER IMAGE VERSIONS #### 24 | 25 | METAPHACTORY_IMAGE=metaphacts/metaphactory:5.7.0 26 | 27 | ##### DO NOT CHANGE BELOW ### 28 | 29 | # path to main docker-compose file, should not be required to change 30 | COMPOSE_FILE=./docker-compose.base.yml:../metaphactory/docker-compose.yml:./docker-compose.overwrite.yml 31 | COMPOSE_PATH_SEPARATOR=: 32 | COMPOSE_CONVERT_WINDOWS_PATHS=1 33 | -------------------------------------------------------------------------------- /service-template/database-config/.env_graphdb: -------------------------------------------------------------------------------- 1 | #### Project/deployment name #### 2 | # needs to be unique i.e. will be used as container and network name as well as for the vhost entry 3 | COMPOSE_PROJECT_NAME=my-deployment-1 4 | 5 | # base host name that is used for the nginx virtual host directive 6 | # should not be required to change until you change the hostname 7 | HOST_NAME=mydocker.example.com 8 | 9 | # need to be customized only when Let's Encrypt is used. See https://letsencrypt.org/docs/expiration-emails/ 10 | LETSENCRYPT_EMAIL=email@example.com 11 | 12 | #### RUNTIME PLATFORM ENVIORNMENT PARAMS #### 13 | 14 | # can be used to pass specific platform parameter that will override any parameter set in the config files 15 | # to use a different log configuration 16 | #METAPHACTORY_OPTS=-Dlog4j.configurationFile=file:///var/lib/jetty/webapps/etc/log4j2-debug.xml 17 | # Note that when using metaphactory >= 4.6 with GraphDB 9.x we require to use a compatibility mode 18 | # can be activated through -Dorg.eclipse.rdf4j.rio.binary.format_version=1 19 | # see the main Readme (section GraphDB) for details 20 | METAPHACTORY_OPTS= 21 | 22 | #### DOCKER IMAGE VERSIONS #### 23 | 24 | GRAPHDB_IMAGE=ontotext/graphdb:10.8.4 25 | METAPHACTORY_IMAGE=metaphacts/metaphactory:5.7.0 26 | 27 | 28 | ##### DO NOT CHANGE BELOW ### 29 | 30 | # path to main docker-compose file, should not be required to change 31 | COMPOSE_FILE=./docker-compose.base.yml:../metaphactory/docker-compose.yml:../metaphactory-graphdb/docker-compose.yml:./database-config/docker-compose.graphdb.yml:./docker-compose.overwrite.yml 32 | COMPOSE_PATH_SEPARATOR=: 33 | COMPOSE_CONVERT_WINDOWS_PATHS=1 34 | -------------------------------------------------------------------------------- /service-template/database-config/.env_rdfox: -------------------------------------------------------------------------------- 1 | #### Project/deployment name #### 2 | # needs to be unique i.e. will be used as container and network name as well as for the vhost entry 3 | COMPOSE_PROJECT_NAME=my-deployment-1 4 | 5 | 6 | #### RUNTIME PLATFORM ENVIORNMENT PARAMS #### 7 | 8 | # can be used to pass specific platform parameter that will override any parameter set in the config files 9 | # to use a different log configuration 10 | #METAPHACTORY_OPTS=-Dlog4j.configurationFile=file:///var/lib/jetty/webapps/etc/log4j2-debug.xml 11 | METAPHACTORY_OPTS= 12 | 13 | #### RDFOX ADMIN USER CREDENTIALS #### 14 | 15 | RDFOX_ROLE=admin 16 | RDFOX_PASSWORD=admin 17 | 18 | #### RDFOX Memory Init Parameter #### 19 | 20 | # init value for max-memory server parameter of RDFox (in MB), only applied once at first start 21 | RDFOX_MAX_MEMORY=2000 22 | 23 | 24 | #### DOCKER IMAGE VERSIONS #### 25 | 26 | RDFOX_IMAGE=oxfordsemantic/rdfox:7.3c 27 | RDFOX_INIT_IMAGE=oxfordsemantic/rdfox-init:7.3c 28 | METAPHACTORY_IMAGE=metaphacts/metaphactory:5.7.0 29 | 30 | ##### DO NOT CHANGE BELOW ### 31 | 32 | # path to main docker-compose file, should not be required to change 33 | COMPOSE_FILE=./docker-compose.base.yml:../metaphactory/docker-compose.yml:../metaphactory-rdfox/docker-compose.yml:./database-config/docker-compose.rdfox.yml:./docker-compose.overwrite.yml 34 | COMPOSE_PATH_SEPARATOR=: 35 | COMPOSE_CONVERT_WINDOWS_PATHS=1 -------------------------------------------------------------------------------- /service-template/database-config/.env_stardog: -------------------------------------------------------------------------------- 1 | #### DOCKER IMAGE VERSIONS #### 2 | 3 | # project/deployment name 4 | # needs to be unique i.e. will be used as container and network name as well as for the vhost entry 5 | COMPOSE_PROJECT_NAME=my-deployment-1 6 | 7 | # base host name that is used for the nginx virtual host directive 8 | # should not be required to change until you change the hostname 9 | HOST_NAME=mydocker.example.com 10 | 11 | # need to be customized only when Let's Encrypt is used. See https://letsencrypt.org/docs/expiration-emails/ 12 | LETSENCRYPT_EMAIL=email@example.com 13 | 14 | #### RUNTIME PLATFORM ENVIORNMENT PARAMS #### 15 | 16 | # can be used to pass specific platform parameter that will override any parameter set in the config files 17 | # to use a different log configuration 18 | #METAPHACTORY_OPTS=-Dlog4j.configurationFile=file:///var/lib/jetty/webapps/etc/log4j2-debug.xml 19 | METAPHACTORY_OPTS= 20 | 21 | #### DOCKER IMAGE VERSIONS #### 22 | 23 | # stardog does not offer specific versions, but only latest 24 | STARDOG_IMAGE=stardog/stardog:latest 25 | 26 | METAPHACTORY_IMAGE=metaphacts/metaphactory:5.7.0 27 | 28 | 29 | ##### DO NOT CHANGE BELOW ### 30 | 31 | # path to main docker-compose file, should not be required to change 32 | COMPOSE_FILE=./docker-compose.base.yml:../metaphactory/docker-compose.yml:../metaphactory-stardog/docker-compose.yml:./database-config/docker-compose.stardog.yml:./docker-compose.overwrite.yml 33 | COMPOSE_PATH_SEPARATOR=: 34 | COMPOSE_CONVERT_WINDOWS_PATHS=1 35 | -------------------------------------------------------------------------------- /service-template/database-config/docker-compose.graphdb.yml: -------------------------------------------------------------------------------- 1 | version: "2.2" 2 | services: 3 | graphdb: 4 | 5 | # Make direct access to the GraphDB Workbench 6 | # (at http://localhost:7200) available. 7 | ports: 8 | - "7200:7200" 9 | 10 | # Uncomment to limit the amount of memory available to the GraphDB container 11 | # mem_limit: 2g 12 | # mem_reservation: 1g 13 | 14 | volumes: 15 | # By default GraphDB will store all its data in the directory 'graphdb-data' 16 | # in the deployment folder. Modify this mapping if you wish to change this behavior. 17 | - ./graphdb-data:/opt/graphdb/home 18 | 19 | # Mount point of the GraphDB license (replace the file with a valid license) 20 | - ./database-config/graphdb-config/license/graphdb.license:/etc/graphdb-license 21 | 22 | # Uncomment to use mount point for GraphDB license (instead of manual upload) 23 | #command: -Dgraphdb.home=/opt/graphdb/home -Dgraphdb.license.file=/etc/graphdb-license 24 | 25 | # Automated creation and configuration of a database named 'metaphactory' in GraphDB. 26 | # Remove or comment out if you do not want this automatic setup to happen. 27 | graphdb-config: 28 | container_name: "${COMPOSE_PROJECT_NAME}-graphdb-config" 29 | image: "${METAPHACTORY_IMAGE}" 30 | volumes: 31 | - ./database-config/graphdb-config/:/config 32 | depends_on: 33 | - graphdb 34 | networks: 35 | - metaphactory_network 36 | entrypoint: /bin/bash 37 | command: > 38 | -c " 39 | while ! curl -sSf http://graphdb:7200/rest/repositories > /dev/null; 40 | do 41 | echo \"Waiting for GraphDB...\"; 42 | sleep 1; 43 | done; 44 | echo \"GraphDB started\"; 45 | # adjust repository config to your needs 46 | # - graphdb-repository-config.ttl 47 | # - graphdb9-repository-config.ttl 48 | # - graphdb-with-SHACL-config-example.ttl 49 | curl -X POST\\ 50 | http://graphdb:7200/rest/repositories\\ 51 | -H 'Content-Type: multipart/form-data'\\ 52 | -F "config=@/config/graphdb-repository-config.ttl"; 53 | echo \"Repository configuration applied in GraphDB\"; 54 | " 55 | 56 | metaphactory: 57 | depends_on: 58 | - graphdb-config 59 | - graphdb 60 | volumes: 61 | - ./database-config/graphdb-config/metaphactory.ttl:/runtime-data/config/repositories/default.ttl:rw 62 | -------------------------------------------------------------------------------- /service-template/database-config/docker-compose.rdfox.yml: -------------------------------------------------------------------------------- 1 | version: "2.2" 2 | services: 3 | rdfox: 4 | volumes: 5 | # by default data is stored in a volume. Modify this mapping if you wish 6 | # to change this. Note: the same needs applied to the initialize-rdfox service 7 | #- ./rdfox-home:/home/rdfox/.RDFox 8 | 9 | - ./database-config/rdfox-config/RDFox.lic:/opt/RDFox/RDFox.lic 10 | 11 | ports: 12 | - 12110:12110 13 | 14 | initialize-rdfox: 15 | volumes: 16 | # by default data is stored in a volume. Modify this mapping if you wish 17 | # to change this. Note: the same needs applied to the initialize-rdfox service 18 | #- ./rdfox-home:/home/rdfox/.RDFox 19 | 20 | - ./database-config/rdfox-config/RDFox.lic:/opt/RDFox/RDFox.lic 21 | - ./database-config/rdfox-config/init:/data 22 | 23 | metaphactory: 24 | volumes: 25 | - ./database-config/rdfox-config/metaphactory.ttl:/runtime-data/config/repositories/default.ttl:rw -------------------------------------------------------------------------------- /service-template/database-config/docker-compose.stardog.yml: -------------------------------------------------------------------------------- 1 | version: "2.2" 2 | services: 3 | stardog: 4 | # run as root user to avoid restricted volume permissions in certain Stardog images (incl. 7.4.5 and 7.5.) 5 | user: "root" 6 | #stardog-overwrites here 7 | volumes: 8 | - ./database-config/stardog-config/stardog-license-key.bin:/var/opt/stardog/stardog-license-key.bin 9 | - ./database-config/stardog-config/stardog.properties:/var/opt/stardog/stardog.properties 10 | - ./database-config/stardog-config/database-template.properties:/var/opt/stardog/database-template.properties 11 | # Consider to persist database file on the host machine via mounted volumes 12 | # - ./stardog:/var/opt/stardog # main Stardog directory where database files will be stored, ideally on SSD 13 | # - ./stardog-tmp:/var/opt/tmp # directory for temporary files (potentially big) 14 | # - ./stardog-ext:/var/opt/stardog-ext # directory for additional jar files, e.g. jdbc drivers etc 15 | # - ./stardog-opennlp:/var/opt/stardog-opennlp # directory for opennlp models 16 | 17 | # Optionally, for RDF files to be imported and virtual graph configs 18 | #- "/local/host/rdf-datasets:/datasets" 19 | #- "/local/host/virtual-graphs-config:/var/opt/virtual-graphs-config" 20 | #ports: 21 | # - "5820:5820" # expose on local host port 5820 i.e. for local development 22 | #environment: 23 | # - STARDOG_SERVER_JAVA_ARGS=-Djava.io.tmpdir=/var/opt/tmp -Xms4g -Xmx4g -XX:MaxDirectMemorySize=8g 24 | metaphactory: 25 | volumes: 26 | - ./database-config/stardog-repository-config/myDB.ttl:/runtime-data/config/repositories/default.ttl:rw -------------------------------------------------------------------------------- /service-template/database-config/graphdb-config/graphdb-repository-config.ttl: -------------------------------------------------------------------------------- 1 | # 2 | # Configuration template for a GraphDB 10 repository. This is used to 3 | # initialize a default database on docker-compose up. You can change the settings 4 | # in accordance with the GraphDB documentation before first starting up the docker 5 | # containers. 6 | # 7 | # See https://graphdb.ontotext.com/documentation/enterprise/configuring-a-repository.html 8 | @prefix rdfs: . 9 | @prefix rep: . 10 | @prefix sr: . 11 | @prefix sail: . 12 | @prefix graphdb: . 13 | 14 | [] a rep:Repository ; 15 | rep:repositoryID "metaphactory" ; 16 | rdfs:label "" ; 17 | rep:repositoryImpl [ 18 | rep:repositoryType "graphdb:SailRepository" ; 19 | sr:sailImpl [ 20 | sail:sailType "graphdb:Sail" ; 21 | 22 | graphdb:base-URL "http://example.org/owlim#" ; 23 | graphdb:defaultNS "" ; 24 | graphdb:entity-index-size "10000000" ; 25 | graphdb:entity-id-size "32" ; 26 | graphdb:imports "" ; 27 | graphdb:repository-type "file-repository" ; 28 | graphdb:ruleset "empty" ; 29 | graphdb:storage-folder "storage" ; 30 | 31 | graphdb:enable-context-index "true" ; 32 | 33 | graphdb:enablePredicateList "true" ; 34 | 35 | graphdb:in-memory-literal-properties "true" ; 36 | graphdb:enable-literal-index "true" ; 37 | 38 | graphdb:check-for-inconsistencies "false" ; 39 | graphdb:disable-sameAs "true" ; 40 | graphdb:query-timeout "0" ; 41 | graphdb:query-limit-results "0" ; 42 | graphdb:throw-QueryEvaluationException-on-timeout "true" ; 43 | graphdb:read-only "false" ; 44 | ] 45 | ]. 46 | -------------------------------------------------------------------------------- /service-template/database-config/graphdb-config/graphdb-with-SHACL-config-example.ttl: -------------------------------------------------------------------------------- 1 | # 2 | # Configuration template for a GraphDB 10 repository with SHACL. This is used to 3 | # initialize a default database on docker-compose up. You can change the settings 4 | # in accordance with the GraphDB documentation before first starting up the docker 5 | # containers. 6 | # 7 | @prefix rdfs: . 8 | @prefix rep: . 9 | @prefix sr: . 10 | @prefix sail: . 11 | @prefix graphdb: . 12 | @prefix shacl: . 13 | 14 | 15 | [] a rep:Repository ; 16 | rep:repositoryID "metaphactory" ; 17 | rdfs:label "" ; 18 | rep:repositoryImpl [ 19 | rep:repositoryType "graphdb:SailRepository" ; 20 | sr:sailImpl [ 21 | sail:sailType "rdf4j:ShaclSail"; 22 | shacl:validationEnabled "true" ; 23 | shacl:logValidationPlans "false" ; 24 | shacl:logValidationViolations "false" ; 25 | shacl:parallelValidation "true" ; 26 | shacl:globalLogValidationExecution "false" ; 27 | shacl:cacheSelectNodes "true" ; 28 | shacl:performanceLogging "false" ; 29 | shacl:rdfsSubClassReasoning "true" ; 30 | shacl:eclipseRdf4jShaclExtensions "true" ; 31 | shacl:dashDataShapes "true" ; 32 | shacl:validationResultsLimitTotal "1000000" ; 33 | shacl:validationResultsLimitPerConstraint "1000" ; 34 | shacl:transactionalValidationLimit "500000" ; 35 | sail:delegate [ 36 | sail:sailType "graphdb:Sail" ; 37 | 38 | graphdb:base-URL "http://example.org/owlim#" ; 39 | graphdb:defaultNS "" ; 40 | graphdb:entity-index-size "10000000" ; 41 | graphdb:entity-id-size "32" ; 42 | graphdb:imports "" ; 43 | graphdb:repository-type "file-repository" ; 44 | graphdb:ruleset "empty" ; 45 | graphdb:storage-folder "storage" ; 46 | 47 | graphdb:enable-context-index "true" ; 48 | 49 | graphdb:enablePredicateList "true" ; 50 | 51 | graphdb:in-memory-literal-properties "true" ; 52 | graphdb:enable-literal-index "true" ; 53 | 54 | graphdb:check-for-inconsistencies "false" ; 55 | graphdb:disable-sameAs "true" ; 56 | graphdb:query-timeout "0" ; 57 | graphdb:query-limit-results "0" ; 58 | graphdb:throw-QueryEvaluationException-on-timeout "true" ; 59 | graphdb:read-only "false" ; 60 | ] 61 | ] 62 | ]. 63 | -------------------------------------------------------------------------------- /service-template/database-config/graphdb-config/graphdb9-repository-config.ttl: -------------------------------------------------------------------------------- 1 | # 2 | # Configuration template for a GraphDB EE worker repository (GraphDB < 10). This is used to 3 | # initialize a default database on docker-compose up. You can change the settings 4 | # in accordance with the GraphDB documentation before first starting up the docker 5 | # containers. 6 | # 7 | # See https://graphdb.ontotext.com/documentation/enterprise/configuring-a-repository.html 8 | @prefix rdfs: . 9 | @prefix rep: . 10 | @prefix sr: . 11 | @prefix sail: . 12 | @prefix owlim: . 13 | 14 | [] a rep:Repository ; 15 | rep:repositoryID "metaphactory" ; 16 | rdfs:label "metaphacts default database" ; 17 | rep:repositoryImpl [ 18 | rep:repositoryType "owlim:ReplicationClusterWorker" ; 19 | rep:delegate [ 20 | rep:repositoryType "owlim:MonitorRepository" ; 21 | sr:sailImpl [ 22 | sail:sailType "owlimClusterWorker:Sail" ; 23 | 24 | owlim:owlim-license "" ; 25 | 26 | owlim:base-URL "http://example.org/owlim#" ; 27 | owlim:defaultNS "" ; 28 | owlim:entity-index-size "10000000" ; 29 | owlim:entity-id-size "32" ; 30 | owlim:imports "" ; 31 | owlim:repository-type "file-repository" ; 32 | owlim:ruleset "rdfsplus-optimized" ; 33 | owlim:storage-folder "storage" ; 34 | 35 | owlim:enable-context-index "true" ; 36 | 37 | owlim:enablePredicateList "true" ; 38 | 39 | owlim:in-memory-literal-properties "true" ; 40 | owlim:enable-literal-index "true" ; 41 | owlim:check-for-inconsistencies "false" ; 42 | owlim:disable-sameAs "true" ; 43 | owlim:query-timeout "0" ; 44 | owlim:query-limit-results "0" ; 45 | owlim:throw-QueryEvaluationException-on-timeout "false" ; 46 | owlim:read-only "false" ; 47 | owlim:nonInterpretablePredicates "http://www.w3.org/2000/01/rdf-schema#label;http://www.w3.org/1999/02/22-rdf-syntax-ns#type;http://www.ontotext.com/owlim/ces#gazetteerConfig;http://www.ontotext.com/owlim/ces#metadataConfig" ; 48 | ] 49 | ] 50 | ]. 51 | -------------------------------------------------------------------------------- /service-template/database-config/graphdb-config/license/graphdb.license: -------------------------------------------------------------------------------- 1 | ** valid license here ** 2 | -------------------------------------------------------------------------------- /service-template/database-config/graphdb-config/metaphactory.ttl: -------------------------------------------------------------------------------- 1 | @prefix rdfs: . 2 | @prefix rep: . 3 | @prefix hr: . 4 | @prefix mph: . 5 | 6 | [] a rep:Repository ; 7 | rep:repositoryImpl [ 8 | rep:repositoryType "metaphactory:GraphDBRepository" ; 9 | hr:repositoryURL ; 10 | mph:username "${repository.default.username:admin}" ; 11 | mph:password "${repository.default.password:root}" 12 | ]; 13 | rep:repositoryID "default" ; 14 | rdfs:label "GraphDB repository" . 15 | -------------------------------------------------------------------------------- /service-template/database-config/rdfox-config/RDFox.lic: -------------------------------------------------------------------------------- 1 | ** valid license here ** -------------------------------------------------------------------------------- /service-template/database-config/rdfox-config/init/initialize.rdfox: -------------------------------------------------------------------------------- 1 | dstore create metaphactory default-graph-name urn:rdfox:default-graph 2 | active metaphactory 3 | dsprop set query-validation standard-compliant 4 | dsprop set invalid-literal-policy as-string -------------------------------------------------------------------------------- /service-template/database-config/rdfox-config/metaphactory.ttl: -------------------------------------------------------------------------------- 1 | @prefix rep: . 2 | @prefix sail: . 3 | @prefix sr: . 4 | @prefix rdfs: . 5 | @prefix mph: . 6 | @prefix ephedra: . 7 | @prefix fedsail: . 8 | @prefix sparqlr: . 9 | 10 | [] a rep:Repository; 11 | rep:repositoryID "default"; 12 | rdfs:label "RDFox repository"; 13 | rep:repositoryImpl [ 14 | rep:repositoryType "metaphactory:RDFoxRepository"; 15 | sparqlr:query-endpoint ; 16 | mph:quadMode true; 17 | mph:username "admin"; 18 | mph:password "admin" 19 | ] . -------------------------------------------------------------------------------- /service-template/database-config/stardog-config/database-template.properties: -------------------------------------------------------------------------------- 1 | # c.f. https://www.stardog.com/docs/#_configuration_options 2 | database.name = myDB 3 | 4 | search.enabled = true 5 | search.wildcard.search.enabled = true 6 | query.all.graphs = true 7 | reasoning.type=NONE 8 | docs.opennlp.models.path=/var/opt/stardog-opennlp 9 | #query.timeout = 60 10 | #edge.properties=true 11 | #strict.parsing=true -------------------------------------------------------------------------------- /service-template/database-config/stardog-config/stardog-license-key.bin: -------------------------------------------------------------------------------- 1 | replace with a valid license file -------------------------------------------------------------------------------- /service-template/database-config/stardog-config/stardog.properties: -------------------------------------------------------------------------------- 1 | query.timeout=0 2 | database.connection.timeout=24h 3 | query.all.graphs=true -------------------------------------------------------------------------------- /service-template/database-config/stardog-repository-config/myDB.ttl: -------------------------------------------------------------------------------- 1 | @prefix mph: . 2 | @prefix rdfs: . 3 | @prefix rep: . 4 | @prefix sparqlr: . 5 | @prefix stardog: . 6 | 7 | [] a rep:Repository; 8 | rep:repositoryID "default"; 9 | rep:repositoryImpl [ 10 | rep:repositoryType "metaphacts:StardogRepository"; 11 | mph:username "${repository.default.username:admin}"; 12 | mph:password "${repository.default.password:admin}"; 13 | mph:quadMode true; 14 | sparqlr:query-endpoint ; 15 | sparqlr:update-endpoint 16 | ]; 17 | rdfs:label "Stardog SPARQL repository with basic authentication" . -------------------------------------------------------------------------------- /service-template/docker-compose.base.yml: -------------------------------------------------------------------------------- 1 | version: "2.2" 2 | # used to set the location relevant to this folder, should not be used for any configurations -------------------------------------------------------------------------------- /service-template/docker-compose.overwrite.yml: -------------------------------------------------------------------------------- 1 | version: "2.2" 2 | services: 3 | metaphactory: 4 | # metaphactory overwrites here 5 | ports: 6 | - "10214:8080" 7 | # - "10213:8443" 8 | #mem_limit: 1g 9 | #mem_reservation: 1g 10 | #environment: 11 | #extra_hosts: 12 | # - "hostmachine:172.17.0.1" 13 | 14 | --------------------------------------------------------------------------------