Skip to content
This page View Markdown Open in ChatGPT Open in Claude

Deployment

A website answers at /ssr/<apiPath>/<name>/ of the API Maker server, as soon as it is made. apiPath is the path of its account, as in the addresses of its APIs. So the website shop of the account acme answers at https://api.example.com/ssr/acme/shop/products. A name is unique in its account : two accounts may each have a shop. To show a website at the root of its own domain (https://shop.example.com/products), put a reverse proxy in front.

With Launchpad

Launchpad does all of this from a form, on Caddy, Ferron, Pingap and the built-in web server of API Maker, and nothing in the code of the website changes. On the built-in web server the website needs no address at all : the API Maker it is part of shows it, and no request goes anywhere.

  1. Open Sites of the server, then Add a site, then SSR website.
  2. Paste the address of the website : http://172.236.185.242:8080/ssr/admin/starter/.
  3. Choose how it is reached : a port (http://172.236.185.242:8090), or domains with HTTPS. Launchpad gets their certificates and renews them.
  4. Save and apply.

A website of the environment of the server needs no other address, and follows API Maker when it moves. Any other address works too : another server, another installation.

The address on the server keeps working. A link people kept to it goes to the same page at the new address.

A domain of its own

  1. List the domain in site.config.ts :

    site.config.ts
    export default defineSite({ domains: ['shop.example.com', 'www.shop.example.com'] });
    

    For a request of such a host, the server writes the addresses of the website without /ssr/acme/shop : href="/products", asset('/app.css'), the redirects, the cookies (Path=/), the canonical addresses.

  2. Point the proxy at the website, keeping the host of the request.

server {
    listen 443 ssl;
    server_name shop.example.com;
    ssl_certificate     /etc/letsencrypt/live/shop.example.com/fullchain.pem;
    ssl_certificate_key /etc/letsencrypt/live/shop.example.com/privkey.pem;

    location / {
        proxy_pass http://127.0.0.1:48246/ssr/acme/shop/;
        proxy_set_header Host $host;
        proxy_set_header X-Forwarded-Proto $scheme;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        client_max_body_size 20m;
    }
}
shop.example.com {
    rewrite * /ssr/acme/shop{uri}
    reverse_proxy 127.0.0.1:48246 {
        header_up Host {host}
    }
}
http:
  routers:
    shop:
      rule: Host(`shop.example.com`)
      service: api-maker
      middlewares: [shop-prefix]
      tls: { certResolver: letsencrypt }
  middlewares:
    shop-prefix:
      addPrefix: { prefix: /ssr/acme/shop }
  services:
    api-maker:
      loadBalancer:
        passHostHeader: true
        servers: [{ url: http://127.0.0.1:48246 }]

The settings view of a website in the panel writes these for its address.

Any address, with no setting

A reverse proxy can also say where it shows the website, for each request. Nothing is listed in site.config.ts, so an IP address and a port work too, and so does a proxy behind another proxy. This is what Launchpad does.

Header What it says
X-AM-SSR-Host The host the visitor asked for : shop.example.com, or 172.236.185.242:8090. With it, the addresses of the website have no /ssr/acme/shop
X-AM-SSR-Proto http or https
X-AM-SSR-Port The port, for a proxy whose host has none. A port in X-AM-SSR-Host wins

The proxy must write these headers itself and not pass on what a visitor sends. A host that is not valid is ignored, and a page never sees these headers.

http://:8090 {
    rewrite * /ssr/acme/shop{uri}
    reverse_proxy 127.0.0.1:48246 {
        header_up X-AM-SSR-Host {hostport}
        header_up X-AM-SSR-Proto {scheme}
        header_up -X-AM-SSR-Port
    }
}

HTTPS

The built-in web server of API Maker shows a website at the root of a domain with HTTPS by itself : a site of the type ssr ({ "type": "ssr", "domains": ["shop.example.com"], "account": "admin", "website": "starter" }), certificates included.

Behind another proxy, terminate TLS at the proxy and send X-Forwarded-Proto: https : the session cookie is Secure then (and __Host- at the root of a domain), and the answers carry Strict-Transport-Security. The origin a page knows (ctx.site.origin, the whole addresses of Open Graph and of feeds) is built from the host and that header.

The panel and the websites

Keep the admin panel on another host than the websites : admin.example.com for the panel, shop.example.com for the shop. A website then shares nothing with the panel in the browser. The panel runs on a port of its own by default (adminPanel.port).

Several servers

Every server of the installation answers every website : they read the websites from the database, and a save in the panel (or a pull of git) tells each to build the website again. Pages kept by the cache are kept by each server ; a save drops them everywhere.

The settings of the server

The websites share the server with the APIs. Their engines, threads and cache are set in the configuration of API Maker (ssr.*), and a website may ask for less or more for itself (limits of site.config.ts).

Setting Default What it is
ssr.threads the cores of the machine Threads which render pages, each with its engines
ssr.enginesPerThread 64 Websites a thread keeps loaded ; the one used longest ago goes
ssr.memoryMb 64 Memory of an engine : a render past it fails, the engine is made anew
ssr.cpuMs 2000 Time the code of one render may run : a loop which does not end is stopped
ssr.timeoutMs 30000 Time of one render in all, the waits for data included
ssr.cacheMb 64 Size of the pages kept by the cache, 0 for none

See API Maker configuration.