Configuration

Stretchy Orchestrator can be configured using a configuration file called application.properties. See Table 1 for where to find it.

Table 1. Location of Orchestrator configuration by system
System family Home directory

Linux

/usr/local/stretchy-orchestrator/config/application.properties

macOS

/usr/local/stretchy-orchestrator/config/application.properties

Windows

@@

Databases

Stretchy Orchestrator uses a SQL database to store all its state. You can choose between:

Choose the database you are most comfortable with. Stretchy is fully validated with H2 and PostgreSQL.

H2

H2 is included with Stretchy Orchestrator.

To enable H2, add the content of Example 1 to your application.properties after replacing the values in angle brackets.

Example 1. H2 configuration
spring.datasource.password=<password>
spring.datasource.url=jdbc:h2:<data-dir>/stretchy;AUTO_SERVER=TRUE;SCHEMA=public (1)
spring.datasource.username=<username>
1 Replace <data-dir> with the path where H2 should store the database.

When Stretchy Orchestrator starts for the first time, it will automatically initialize the database.

PostgreSQL

To enable PostgreSQL, add the content of Example 2 to your application.properties after replacing the values in angle brackets.

Example 2. PostgreSQL configuration
spring.datasource.password=<password>
spring.datasource.url=jdbc:postgresql://<host>:5432/<database>?currentSchema=public
spring.datasource.username=<username>

When Stretchy Orchestrator starts for the first time, it will automatically initialize the database.

Public Address

Stretchy Orchestrator requires that you configure a “public address”. That is the address that users see in the address bar of their browsers when they visit Stretchy Orchestrator’s web UI. It will use it to generate links pointing back to the Orchestrator.

stretchy.public-address=https://example.com/stretchy/

Network

Stretchy Orchestrator comes with an embedded Tomcat that listens on all IPv4 addresses of a system on port 8080.

For all advanced configuration needs, like SSL or IPv4/IPv6 dual stack, we recommend setting a web server up like Caddy or nginx in front of Stretchy Orchestrator that acts as a reverse proxy.

Address

By default, Stretchy Orchestrator listens on all IPv4 interfaces of a system. To change that, use the property server.address like in Example 3.

Example 3. Listen on an IPv6 interface
server.address=2001:0db8:85a3:08d3::0370:7344

Port

The default port of Stretchy Orchestrator is 8080. To listen on a different port, use the property server.port as in Example 4.

Example 4. Listen on port 8081
server.port=8081

Reverse Proxy

When running behind a reverse proxy, add server.forward-headers-strategy=NATIVE and server.tomcat.redirect-context-root=false to your application.properties.

Stretchy Orchestrator uses HTTP and WebSocket.

External Identity Providers

Optionally, Stretchy Orchestrator integrates with external identity providers that support OpenID Connect (OIDC). That allows users to log into Stretchy Orchestrator with Google, Keycloak, or Okta, amongst others.

Some identity providers such as GitHub do not let you control which of their users may log into a connected service. By enabling GitHub as an IdP, you effectively allow any GitHub user to log into Stretchy Orchestrator.

Setting up an external identity provider is a three-step process:

  1. Create a new client in the identity provider of your choice.

  2. Configure the identity provider in Orchestrator’s application.properties.

  3. Enable OAuth 2.0 login in Orchestrator’s application.properties by setting stretchy.security.enable-o-auth2=true.

Stretchy Orchestrator allows configuring multiple identity providers simultaneously.

In the following examples, we assume that Stretchy Orchestrator is reachable at https://example.com/stretchy. Furthermore, you have to pick a registration identifier (ASCII, lowercase) beforehand that uniquely identifies the identity provider in Stretchy Orchestrator. The following examples use my-idp.

The heavy lifting is done by Spring Security. Please see its documentation on OAuth 2.0 Login for advanced configuration scenarios not covered in this manual.

Creating a New Client

Please consult the documentation of the identity provider of your choice how to create a new client.

Usually, you will be asked for the URL of your application and a callback URL. Once the new client is set up, you should receive a Client ID, a Client Secret, and an Issuer URI.

The URL of your application is the address you see in your browser when visiting Stretchy Orchestrator, for example, https://example.com/stretchy.

The callback URL is the address where users will be redirected after a successful login. That pattern is https://example.com/stretchy/login/oauth2/code/<registration-identifier>. So if your registration identifier is my-idp, the URL would be https://example.com/stretchy/login/oauth2/code/my-idp.

If your identity provider requires to explicitly enable Client Scopes, enable openid, email and profile.

Configuring the Identity Provider

Add the configuration listed in Example 5 to the application.properties of Stretchy Orchestrator after replacing the values in angle brackets.

Example 5. Identity provider configuration
spring.security.oauth2.client.registration.<registration-identifier>.client-id=<client-id> (1)
spring.security.oauth2.client.registration.<registration-identifier>.client-secret=<client-secret> (2)
spring.security.oauth2.client.registration.<registration-identifier>.client-name=My IDP (3)
spring.security.oauth2.client.registration.<registration-identifier>.scope=openid
spring.security.oauth2.client.provider.<registration-identifier>.issuer-uri=<issuer-uri> (4)
1 Enter the Client ID generated by your identity provider.
2 This is the Client Secret generated by your identity provider.
3 This name is displayed to the users of Stretchy Orchestrator on the login screen.
4 The Issuer URI is the address where users of Stretchy Orchestrator are redirected to log into your identity provider, for example, https://accounts.google.com or https://keycloak.example.com/realms/my-realm.

Simplified Identity Provider Configuration

With Facebook (registration identifier: facebook), GitHub (github), Google (google), and Okta (okta), it is possible to take advantage of a simplified configuration that requires only specifying a Client ID and a Client Secret.

If you use one of those services, add the configuration listed in Example 6 to the application.properties of Stretchy Orchestrator after replacing the values in angle brackets.

Example 6. Simplified identity provider configuration
spring.security.oauth2.client.registration.<registration-identifier>.client-id=<client-id> (1)
spring.security.oauth2.client.registration.<registration-identifier>.client-secret=<client-secret> (2)
1 Enter the Client ID generated by your identity provider.
2 This is the Client Secret generated by your identity provider.

systemd

Credentials

If your Orchestrator configuration contains credentials, we recommend using systemd credentials to securely pass them to Stretchy Orchestrator.

For Stretchy Orchestrator to automatically recognize systemd credentials, alter the systemd service configuration according to Example 7.

Example 7. Load systemd credentials into configuration properties
[Service]
...
ExecStart=/usr/local/stretchy-orchestrator/lib/runtime/bin/java \
    --enable-preview \
    -cp '/usr/local/stretchy-orchestrator/lib/app/*' \
    -Dspring.config.import=configtree:${CREDENTIALS_DIRECTORY}/ \ (1)
    dev.stretchy.orchestrator.StretchyOrchestrator
LoadCredential=spring.datasource.password:/path/to/database-password (2)
1 Instruct Stretchy Orchestrator to ingest systemd credentials automatically.
2 The file name spring.datasource.password is converted to a configuration property of the same name that will be assigned the contents of /path/to/database-password.

Service Hardening

systemd allows locking services down, thereby providing process isolation on a level approaching containers without incurring their downsides.

Not all capabilities mentioned here might be supported by the version of systemd your system is using.

We have found the configuration in Example 8 to work well in practice. By enabling DynamicUser=, it makes most of the system inaccessible to Stretchy Orchestrator, only allowing access to specific directories and resources.

Example 8. Locked down service configuration for Stretchy Orchestrator
[Service]
...
CapabilityBoundingSet=CAP_NET_BIND_SERVICE
DynamicUser=true (1)
PrivateUsers=true
ProcSubset=pid
ProtectClock=true
ProtectControlGroups=true
ProtectHome=true
ProtectHostname=true
ProtectKernelLogs=true
ProtectKernelModules=true
ProtectKernelTunables=true
ProtectProc=invisible
RestrictNamespaces=true
StateDirectory=stretchy-orchestrator (2)
SystemCallFilter=@system-service
1 If DynamicUser= is enabled, systemd creates the user and group specified with User= and Group= respectively on the fly and removes them once the service is stopped.
2 Only required when using H2. Makes a writeable directory available in /var/lib with the name stretchy-orchestrator. If you are using H2, you must store your database in /var/lib/stretchy-orchestrator.
To evaluate the service configuration yourself, run systemd-analyze security stretchy-orchestrator.service.