Renduva

Renduva documentation

Install and run

Renduva is one server program plus LibreOffice, which it uses to make PDFs. Run it as a container (everything included) or install the RPM on Red Hat-family Linux.

Requirements

  • Linux on x86-64.
  • Container: Docker, or Podman 4 or later. The image includes LibreOffice and fonts that match the sizes of Arial, Times New Roman, Courier New, Calibri and Cambria, so Word layouts keep their line breaks.
  • RPM: RHEL, Oracle Linux, Rocky or AlmaLinux 8 or 9, and LibreOffice (see below).
  • About 1 GB of disk and 1 GB of memory; each PDF conversion runs one LibreOffice process.

With Docker

docker load -i renduva-0.1.0.tar.gz
docker run -d --name renduva --restart unless-stopped \
           -p 8080:8080 -v renduva-data:/data localhost/renduva
docker exec renduva renduva key create apex-prod      # prints the key once
docker cp invoice.docx renduva:/data/templates/       # a stored template

API keys and stored templates live in the /data volume, so they survive restarts and upgrades. Server options go after the image name, for example docker run ... localhost/renduva serve -workers 4.

To upgrade, load the new image, then docker rm -f renduva and run the same docker run again.

With Podman, started at boot

Podman runs the same image without root. On Podman 4.4 or later, use the Quadlet file renduva.container that comes with the image:

podman load -i renduva-0.1.0.tar.gz
mkdir -p ~/.config/containers/systemd
cp renduva.container ~/.config/containers/systemd/
systemctl --user daemon-reload               # creates renduva.service from the file
systemctl --user start renduva
sudo loginctl enable-linger $USER            # start it at boot without a login
podman exec renduva renduva key create apex-prod

Quadlet services are not enabled; the file starts it at boot. For a service that runs as root, put the file in /etc/containers/systemd/ and leave out --user. Manage it with systemctl --user status|restart|stop renduva and read its log with journalctl --user -u renduva. After loading a new image, restart picks it up.

Podman before 4.4 has no Quadlet. Start the container once with podman run as in the Docker section, then turn it into a service:

mkdir -p ~/.config/systemd/user && cd ~/.config/systemd/user
podman generate systemd --new --name renduva --files
podman rm -f renduva                         # the service recreates it on every start
systemctl --user daemon-reload
systemctl --user enable --now container-renduva.service
sudo loginctl enable-linger $USER

With the RPM

The RPM installs the server as a systemd service. LibreOffice is not a dependency, because version 9 systems do not ship it, so install it first:

  • Version 8: sudo dnf install libreoffice-writer
  • Any version: the RPMs from libreoffice.org (download the "RPM" archive, unpack it, then sudo dnf install ./RPMS/*.rpm)

Then:

sudo dnf install ./renduva-0.1.0-1.x86_64.rpm
cd /var/lib/renduva && sudo -u renduva renduva key create apex-prod
sudo systemctl start renduva

The installer finds LibreOffice and writes its path into /etc/renduva/renduva.env, which also holds the other server options. Keys and stored templates live in /var/lib/renduva.

Always run key commands as the renduva user, as above. A keys file created by root cannot be read by the service, and every request then fails with 401.

API keys

Every request needs an API key. Keys are created on the server, and only a hash of each key is stored, so a key is shown once, when it is created:

renduva key create apex-prod    # prints the key
renduva key list                # names only
renduva key revoke apex-prod

Changes apply to the next request, without a restart. (In a container, run them through docker exec renduva … or podman exec renduva ….)

Stored templates

Put templates in the server's templates folder (/data/templates in the container, /var/lib/renduva/templates with the RPM) and call them by name: invoice.docx is "template": "invoice". Names may use letters, digits, _ and -. Files are read on every request, so replacing a template takes effect at once.

You can also send the template with each request instead; see the HTTP API.

Server options

Option Default Meaning
-addr :8080 Address and port to listen on
-workers number of CPUs Documents rendered at the same time; the rest wait
-timeout 2m Time limit for LibreOffice per request
-max-body 52428800 (50 MB) Largest request accepted
-keys renduva-keys.txt API key file
-templates templates Stored templates folder
-soffice soffice LibreOffice program

HTTPS

The server speaks plain HTTP. Put it behind a reverse proxy with TLS (nginx, Apache, a load balancer) whenever the traffic crosses a network others can read. Oracle then needs the proxy's certificate in its wallet; see the PL/SQL package.

Logs

The server writes one line per request: time, status, key name, template and output type, number of records and duration. It never logs API keys, template contents or your data.