Reference

Value formats

This page lists the exact forms ScalWS accepts for sizes, durations, CPU quotas, socket addresses, names, domains and paths in scalws.yaml, site files and on the command line.

Units are case-sensitive. Spaces before and after a size, a duration or a CPU quota are ignored; names, domains and paths are taken as written.

Sizes

Used by byte sizes such as server.limits.max_request_body_bytes, server.cache.memory and tenants[].resources.memory, and by scalwsctl limit ram|io.

A size is either a YAML integer (bytes) or a string of digits followed by an optional unit. Spaces between the number and the unit are allowed, and a number without a unit is bytes.

UnitBytes
none, B1
KiB1024
MiB1024² (1 048 576)
GiB1024³
TiB1024⁴
KB, kB1000
MB1000²
GB1000³
TB1000⁴

Binary and decimal units both mean what they say: 10MB is 10 000 000 bytes, 10MiB is 10 485 760 bytes.

AcceptedRejected
1048576, "512", 16KiB, 16 KiB, 4GiB, 10MB, 2kB1.5GiB (no fractions), -1 (no negative sizes), GiB (no number), 16kib, 16K, 16 kilobytes (unknown unit), a value that overflows 64 bits

ScalWS writes sizes back (for example scalwsctl limit --persist) in the largest binary unit that divides them exactly, such as 2GiB or 1536KiB, else in bytes (1000B).

scalwsctl limit io takes a rate as a size followed by /s, for example 20MiB/s.

The configuration schema used by ScalWS Console forms describes sizes with the units B, KB, MB, GB, KiB, MiB and GiB only, so the console’s forms may not accept TiB, TB or kB; use a smaller unit there.

Durations

Used by timeouts and intervals such as server.limits.idle_timeout, server.acme.renew_before and tenants[].applications[].cache.default_ttl.

A duration is a string: a whole number directly followed by one unit.

UnitMeaning
msmilliseconds
sseconds
mminutes
hhours
ddays
AcceptedRejected
500ms, 10s, 5m, 1h, 30d10 (a bare number has no unit), 10 s (space before the unit), 1h30m (one unit only), 1.5s (no fractions), 1w (unknown unit), 10S

Some fields also limit the range, for example server.ai.timeout must be between 1s and 10m.

Durations in controller.yaml

controller.yaml uses plain integers instead: instances.start_timeout, drain_timeout, kill_grace, restart_window and the autoscaling windows and autoscaling.cooldown are whole seconds (drain_timeout: 30); autoscaling.lag_saturated is whole milliseconds (lag_saturated: 5).

CPU quotas

Used by tenants[].resources.cpu.

A CPU quota is a string: a whole number directly followed by %, in percent of one CPU. 100% is one full CPU, 400% is four.

AcceptedRejected
50%, 200%, 400%4 (no %), 0% (must be greater than 0%), 1.5%, 200 %

scalwsctl limit cpu takes the same form; there the % may be left out (50).

CPU lists in controller.yaml

instances.cpus is a string of CPU numbers and ranges separated by commas, for example "0-5", "0,2,4" or "0-3,6". A range a-b needs a <= b and b < 4096.

Socket addresses

Used by server.listeners[].address, server.metrics.address and server.admin.remote.address, and by scalwsctl --address, scalwsd --metrics-address and scalws-console --listen.

A socket address is an IP address and a port, with no host names:

FormExample
IPv4 address and port127.0.0.1:8080, 192.0.2.10:443; 0.0.0.0:443 listens on every IPv4 address
IPv6 address in brackets and port[::]:443 listens on every IPv6 address

Quote them in YAML (address: "127.0.0.1:8080"). Port 0 lets the operating system pick a free port. Two listeners may not use the same address, and a listener may not use the metrics address.

FastCGI addresses

php.fastcgi and scalwsctl site add --php-fastcgi take unix: followed by an absolute path (unix:/run/php/php8.3-fpm.sock) or tcp:host:port with a port from 1 to 65535 (tcp:127.0.0.1:9000). tcp:9000 is rejected.

Upstream URLs

proxy.upstream takes http://host[:port], https://host[:port] or unix:/absolute/path. The host is a name, an IPv4 address or an IPv6 address in brackets; the port defaults to 80 or 443 and may not be 0. A path other than / and user information (user@) are rejected: requests keep their original path.

Networks

server.trusted_proxies entries are an IP address (192.0.2.10, one host) or a network in CIDR form (192.0.2.0/24). The prefix is at most 32 for IPv4 and 128 for IPv6. Host names are rejected.

Names

Tenant names (tenants[].name), application names (tenants[].applications[].name) and listener names (server.listeners[].name) appear in metrics, logs and cgroup paths, so they are restricted:

  • 1 to 63 characters;
  • only a-z, 0-9, - and _;
  • the first character is a letter a-z.
AcceptedRejected
shop, blog-example-com, api_v2Shop (upper case), 1password (starts with a digit), -shop, shop.example (dot), a name of 64 characters

Listener names must be unique, and application names must be unique within their tenant.

When a site file sets no tenant or name, ScalWS derives them from the domain: lower case, every run of other characters becomes one -, leading and trailing - are dropped, s- is put in front when the result does not start with a letter, and the result is cut to 59 characters. shop.example.com becomes shop-example-com, 1password.com becomes s-1password-com.

The instance id of scalwsd --instance-id is 1 to 32 characters of a-z, 0-9 and -.

Domains

Used by tenants[].applications[].domains, server.listeners[].tls.certificates[].server_names, and the domain and aliases of a site file.

A domain is normalized before it is checked and compared:

  • letters are lower-cased (Example.COM is example.com);
  • trailing dots are removed (example.com. is example.com).

The result must be at most 253 characters (without a leading *.) and consist of labels separated by dots. Each label is 1 to 63 characters of a-z, 0-9 and -, and does not start or end with -.

A leading *. makes a wildcard that covers exactly one label: *.example.com matches shop.example.com but not example.com or a.shop.example.com. The part after *. must have at least two labels.

AcceptedRejected
example.com, Shop.Example.COM., localhost, 127.0.0.1, *.example.com, xn--bcher-kva.examplea..b (empty label), -a.example (label starts with -), a_b.example (underscore), foo.*.example (* not first), *.com (wildcard over one label), bücher.example (use punycode), an empty string

Internationalized domain names must be written in punycode (xn--...). A domain may be served by only one application across the main file and all site files; the check reports domain "<name>" is already used by <tenant>/<app>. A server name may be assigned to only one certificate per listener.

Paths

Fields that name a directory or a file to serve must be absolute paths: tenants[].applications[].root, the root of the static and PHP runtimes, the Python runtime’s virtualenv, and PHP’s fpm.binary. A path starting with / is accepted on every platform, so a configuration can be checked on another machine; the server checks that the path exists when it prepares the configuration. Otherwise the check reports <path> must be an absolute path.

include entries are relative to the directory of the main configuration file. An entry may contain one *, and only in the file name (sites.d/*.yaml); a * in a directory part and an entry that names a directory are rejected.