The Docker-Compose Template
When starting an app, Portal simply brings up a docker-compose file just like you would with docker-compose up
.
This file is generated during installation of the app from a docker-compose.yml.template
that you have to provide.
The template is a normal docker-compose file with some special variables that Portal will replace with the correct values.
Minimal Example
Let's first look at a minimal example. This is the most basic template for an app made up of a single container and no dependencies and no special configuration. Click on the plus buttons for a description of each field.
YAML | |
---|---|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 |
|
- This is the network that Portal uses to connect all apps together and to the reverse proxy and Portal core. You need to include this in your template.
- This is the image that will be used for your app. Please specify a fixed version, not just
my-app:latest
. When you update your app, you will also need to release a new version of the metadata including a new template. - You must explicitly set the container name, and it must match with the service name.
- In order to persist data, you need to mount a host directory.
For data that only concerns your app, you should use the
fs.app_data
variable and a subdirectory that matches the directory inside the container. Read more in the section on persisting data. - You need to connect your app to the
portal
network specified above.
Complex Example
Now let's look at a more complex example. Here we have an app that depends on a redis database and has some environment variables that need to be set. We also want to access the shared part of the filesystem where apps can store data that is shared between them.
YAML | |
---|---|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 |
|
- The app container depends on the redis container, so that the redis container will be started first.
- We mount the shared data directory into the app container in order for the app to be able to exchange data with other apps.
- The app need to know the hostname of the redis container, so we set it as an environment variable.
- Some apps need to know their base URL, so we set it as an environment variable.
Since the Portal's domain name is only known at install time, we need to use the
portal.domain
variable. An app's domain name is always<app-name>.<portal domain>
. - We can also use the
portal.short_id
variable to get the Portal's six-digit unique identifier. This is useful for example to set the title of the app. - This app need a redis database, so we add a redis container to the docker-compose file.
The naming convention for additional containers is
my-app-<name>
, where<name>
is the name of the container. - We mount a directory for redis to store its data. Note that we use
fs.app_data
just as for the app itself so the redis data will be stored in the same directory as the app data.
Variables
Here is a complete list of all variables that you can use in your template.
Portal Variables
variable | description | example |
---|---|---|
portal.domain |
The fully qualified domain name of the Portal | 8271dd.p.getportal.org |
portal.id |
The full-length hash-ID of the Portal | 8271ddlqxa [...] 8s598f2 |
portal.short_id |
The first six digits of the Portal's hash-ID | 8271dd |
portal.public_key_pem |
The Portal's public key in PEM format | -----BEGIN PUBLIC KEY-----\nMIICI [...] wEAAQ==\n-----END PUBLIC KEY-----\n |
Filesystem Variables
variable | description | example |
---|---|---|
fs.app_data |
The absolute path to your app's directory | /home/portal/user_data/app_data/my-app |
fs.all_app_data |
The absolute path to the app data parent directory | /home/portal/user_data/app_data |
fs.shared |
The absolute path to the directory for shared data | /home/portal/user_data/shared |
Limitations
Technically, you can use any docker-compose feature in your template. However, since this would allow you to write apps that break things or are malicious, we enforce some limitations on what you can do. When you submit your app for the app store, we will check that it does not violate these limitations.
Filesystem access
You may not mount any host directories other than the ones provided in the filesystem variables.
And when mounting fs.all_app_data
, you should have a good reason.
Docker Socket
You may mount the docker socket into your container, as long as you mount it with the read-only flag. This is useful for apps that monitor the docker daemon, for example to show the status of other apps. The mount entry should look like this:
YAML | |
---|---|
1 2 |
|
Performance
Memory and CPU capacity on a Portal vary depending on a Portal's size and are never infinite.
So starting a large number of containers or containers that use a lot of resources can slow down the Portal.
Also remember that your app might not be the only one running at any time.
If your app is very resource intensive, you should set the min_portal_size
option in the app_meta.json
to a high value.