AlmaForge Standalone Deployment
AlmaForge is a self-hosted infrastructure access platform. It issues short-lived certificates for servers, Kubernetes clusters, databases, applications, and APIs, with protocol audit events and terminal replay under your recording policy. The control plane runs inside your environment, with no SaaS dependency or telemetry.
Try AlmaForge with the Quick Start demo.
Allow about 30 minutes once the host, DNS, and identity-provider prerequisites are ready. You will install AlmaForge on one Linux host, connect your identity provider, sign in, and open a server session. This setup is for evaluation and lab work. For production, start with Cluster on Linux or Cluster on Kubernetes.
For the control-plane and data-plane architecture, read How it Works.
What you need
- A Linux host. RHEL, AlmaLinux, Rocky Linux, or Oracle Linux 8+,
Ubuntu 22.04 LTS+, or Debian 12+, on amd64 or arm64, with 2 vCPU,
2 GB RAM, 10 GB of free disk, and
sudoaccess. - A DNS name that resolves to the host. An
AorAAAArecord is enough for this guide. Add a wildcard*record under the same name if you plan to publish internal web applications later. - Inbound TCP/443, reachable from your workstation and Let's Encrypt's public validation servers. This port carries the web UI, the CLI, and every protocol AlmaForge proxies.
- Outbound HTTPS from the host to your identity provider and Let's Encrypt. See egress requirements.
- An SSO identity provider that speaks OIDC: Okta, Microsoft Entra, Google Workspace, Keycloak, or another OIDC provider. Routine user sign-in uses SSO. Break-glass provides emergency administrator access for setup and recovery.
Create an OIDC application in that provider before you reach Step 5. It gives you the three values the connector needs: an issuer URL, a client ID, and a client secret. The SSO Integration guides walk through it per provider. You do not need it to start, because a new cluster has no sign-in method at all and break-glass is how you add one.
Creating that application takes administrator rights in the identity provider, and on Okta it also needs a custom authorization server. If someone else runs your identity provider, send them the relevant SSO Integration guide early. Waiting on that is usually the longest part of this page.
Every command below uses almaforge.example.com as the cluster hostname.
Substitute your own DNS name throughout.
See System Requirements and Networking.
Step 1. Install the package
Pick your distribution:
- Ubuntu / Debian
- RHEL / Fedora / AlmaLinux
- Binary tarball
These instructions apply to APT-based (Ubuntu and Debian) distributions and their derivatives.
Supported APT-based Linux distributions
The APT package supports these distribution families. Check their upstream maintenance windows when choosing a production host:
| Distribution | Codename | Version | Release Date | Upstream EOL |
|---|---|---|---|---|
| Ubuntu | Jammy | 22.04 LTS | April 2022 | April 2027 |
| Ubuntu | Noble | 24.04 LTS | April 2024 | April 2029 |
| Debian | Bookworm | 12 | June 2023 | July 2026 (regular), June 2028 (LTS) |
| Debian | Trixie | 13 | August 2025 | August 2028 (regular), June 2030 (LTS) |
See Debian release support for the distinction between regular support and LTS.
Other distributions with glibc 2.28+ may also work. Please contact us if you run into any issues.
The snippet below configures the https://get.almaforge.com repository and installs the almaforge package from the repository:
sudo install -m 0755 -d /etc/apt/keyringscurl -sfLS https://get.almaforge.com/almaforge.gpg | \ gpg --dearmor | sudo tee "/etc/apt/keyrings/almaforge.gpg" >/dev/nullecho "deb [signed-by=/etc/apt/keyrings/almaforge.gpg] https://get.almaforge.com generic main" | \ sudo tee "/etc/apt/sources.list.d/almaforge.list"sudo apt-get updatesudo apt-get install -y almaforgecurl, gpg, and sudo are often missing in stripped-down images.
Verify that almad is installed:
almad versionAlmaForge v2026.1.0+gaef6f26d4cThese instructions apply to RHEL 8+, AlmaLinux, Rocky Linux, Oracle Linux 8+, and other compatible distributions or derivatives.
Supported RPM-based Linux distributions
The RPM package supports these distribution families. Check their upstream maintenance windows when choosing a production host:
| Distribution | Version | Release Date | Upstream EOL |
|---|---|---|---|
| RHEL | 10 | May 2025 | May 2035 |
| AlmaLinux | 10 | May 2025 | May 2035 |
| Rocky Linux | 10 | June 2025 | May 2035 |
| Oracle Linux | 10 | June 2025 | June 2035 |
| RHEL | 9 | May 2022 | May 2032 |
| AlmaLinux | 9 | May 2022 | May 2032 |
| Rocky Linux | 9 | July 2022 | May 2032 |
| Oracle Linux | 9 | June 2022 | June 2032 |
| RHEL | 8 | May 2019 | May 2029 |
| AlmaLinux | 8 | Mar 2021 | May 2029 |
| Rocky Linux | 8 | May 2021 | May 2029 |
| Oracle Linux | 8 | July 2019 | July 2029 |
Other distributions with glibc 2.28+ may also work. Please contact us if you run into any issues.
The snippet below configures the https://get.almaforge.com repository and installs the almaforge package from the repository:
sudo tee /etc/yum.repos.d/almaforge.repo <<EOF[almaforge]name=AlmaForgebaseurl=https://get.almaforge.comgpgkey=https://get.almaforge.com/almaforge.gpgenabled=1repo_gpgcheck=1gpgcheck=1EOFsudo dnf install -y --best almaforgesudo is often missing in stripped-down images.
Verify that almad is installed:
almad versionAlmaForge v2026.1.0+gaef6f26d4cAlmaForge can be installed from a binary tarball. This approach is intended for Linux systems without a supported package manager, including minimal distributions and CI/CD environments.
A quick shell snippet, which picks the tarball for the machine it runs on:
ARCH="$(uname -m)"case "$ARCH" in \ x86_64|amd64) TARBALL="almaforge-2026.1.0-linux-amd64.tar.xz" ;; \ aarch64|arm64) TARBALL="almaforge-2026.1.0-linux-arm64.tar.xz" ;; \ *) echo "Unsupported architecture: $ARCH" >&2; exit 1 ;; \ esaccd ~/Downloads || cd /var/tmpVERSION="2026.1.0"curl -fSL --retry 3 --retry-delay 2 -O "https://get.almaforge.com/almaforge/v$VERSION/$TARBALL"Before extracting, download the matching checksum and detached signature and verify both using artifact verification. The signing key and fingerprint identify the release publisher. Then install the verified archive:
sudo mkdir -p /usr/local/binsudo tar -xavf "$TARBALL" -C /usr/local/bin --strip-components=1 --exclude='VERSION'The snippet above uses curl, tar, xz, and sudo, which may be absent in stripped-down minimal images.
Verify that almad is installed:
almad versionAlmaForge v2026.1.0+gaef6f26d4c(Recommended) Install the systemd unit:
sudo almad install systemdDownloadable artifacts
The package installs the almad daemon, the alma
CLI, the almad systemd unit, and /var/lib/almaforge for runtime state. The
daemon runs as root and does not start during installation.
Step 2. Configure the daemon
Configure almad with environment variables and CLI flags.
The systemd unit reads environment variables from /etc/almaforge/almad.env
at startup.
A package installation creates /etc/almaforge, /etc/almaforge/almad.d and
/var/lib/almaforge with mode 0700. A direct tarball installation creates
none of them, though the daemon creates /var/lib/almaforge itself on first
start. These paths can contain credentials, and the root daemon reads
them at mode 0700. After a tarball installation, create the two config
directories:
sudo install -d -o root -g root -m 0700 /etc/almaforge /etc/almaforge/almad.dSave almad.env as
/etc/almaforge/almad.env. Replace almaforge.example.com with your DNS name
and use an email address you control:
# Environment file for a single-host AlmaForge cluster.
#
# One almad process runs the Auth, Proxy, and SSH Services. The host is
# both the control plane and your first server. Split those roles across
# separate hosts before production.
#
# Path: /etc/almaforge/almad.env
# Permissions: chown root:root, chmod 0600
ALMA_AUTH_SERVICE=true
ALMA_PROXY_SERVICE=true
# Serve this host as an SSH target without provisioning a second
# machine. Remove this setting when the control plane should not accept
# user sessions.
ALMA_SSH_SERVICE=true
# Multiplex the web UI, CLI, Kubernetes, databases, and agent reverse
# tunnels on one TLS port through SNI and ALPN. The packaged systemd
# unit runs as root and can bind port 443.
ALMA_LISTEN=0.0.0.0:443
# Public hostname for clients and agents. It must match the DNS record
# and TLS certificate. It also forms the base of SSO redirect URLs and
# the ACME challenge below.
ALMA_ADVERTISE=almaforge.example.com:443
# Let's Encrypt issues and renews the certificate over the TLS-ALPN-01
# challenge on port 443. Port 443 must be reachable from Let's
# Encrypt's public validation servers. Swap for ALMA_TLS_CERT and
# ALMA_TLS_KEY to use a certificate from your own CA.
ALMA_ACME_ENABLED=true
[email protected]
# ALMA_LABELS sets operator-defined labels. Use stable keys such as env,
# region, and team. Keep fast-changing values out of this setting.
#
# The agent also advertises generated labels. It refreshes AWS and Azure
# tags from instance metadata once an hour and prefixes their keys
# with aws/ or azure/. Hetzner supplies hetzner/instance-id,
# hetzner/region, hetzner/availability-zone, hetzner/hostname, and
# hetzner/local-ipv4. Every host that sends heartbeats also advertises
# internal/expires. Role serverLabels matchers evaluate the full set.
ALMA_LABELS=env=demo
# Without a storage URI, cluster state, audit events, and session
# recordings stay on local disk under this directory. Use this default
# for evaluation only.
ALMA_DATA_DIR=/var/lib/almaforge
# Resource manifests placed here are applied at every start.
ALMA_CONFIG_DIR=/etc/almaforge/almad.d
Cluster state, audit events, and session recordings default to local
disk under /var/lib/almaforge, so this file names no storage backend. Move
them to PostgreSQL, etcd, S3, or another backend before production.
See the Storage Guide.
The file is read by root only:
sudo chown root:root /etc/almaforge/almad.envsudo chmod 0600 /etc/almaforge/almad.envThis setup uses built-in Let's Encrypt certificate management. For a private endpoint or an organization-managed certificate, see operator-supplied TLS certificates.
Every supported variable is listed in Environment Variables.
Step 3. Start the daemon
sudo systemctl enable --now almadsudo systemctl is-active almadactiveThe first start initializes cluster state, creates the cluster certificate authority, and requests a TLS certificate over ACME. Watch startup and certificate issuance in the logs:
sudo journalctl -u almad -fIf the daemon does not reach active or the page below does not load,
check DNS and port 443 first. ALMA_ADVERTISE must match a name that
resolves publicly to this host. Let's Encrypt must also reach port 443
to issue the certificate. See Troubleshooting.
Open https://almaforge.example.com/ in a browser. Because no identity provider
is connected, the sign-in page shows Set up this cluster. The card
prints the next command with this host's addresses already filled in.
Step 4. Sign in with break-glass
The cluster cannot accept an SSO sign-in until you add a connector. Break-glass turns shell access on the cluster host into one short browser session so you can add it.
Run the command on the almad host. /var/lib/almaforge is owned by
root, so use sudo:
sudo alma login --breakglass
Break-glass recovery requested. Open this link within five minutes:
https://almaforge.example.com/login#breakglass=<claim>
It can be used once and opens a short administrator session as "breakglass".If you changed the data directory or the port almad listens
on, add --data-dir=<path> and --auth-server=<host:port>. The
sign-in page prints the command with this host's values already filled
in. Copy it from there.
Open the link yourself in a browser within five minutes. Do not forward it. The one-time claim sits in the URL fragment and stays out of server and proxy logs. Whoever opens the link first gets the session. Confirm on the Emergency administrator access card to enter the web UI.
The built-in breakglass user carries the wildcard admin role. Its
sessions last at most one hour and cannot be renewed. Run the command
again if you need a fresh session.
Filesystem access to /var/lib/almaforge on an Auth host authorizes
break-glass. Anyone who can read that directory can use it. Treat every
use as a security event and restrict access to the host. The full
procedure, including day-2 recovery, is in
Break-Glass Access.
Step 5. Connect your identity provider
Your emergency session lasts one hour. Use it to connect your identity provider.
In the OIDC application you created for
What you need, register this callback URL. It is your
cluster hostname plus a fixed path: https://almaforge.example.com/api/v1/oidc/callback.
Then create the connector. Both paths produce the same resource.
- Web UI
- CLI
In the sidebar, open Access control, then SSO, and add a connector. Choose your provider to load a starter template. Enter the issuer URL, client ID, client secret, and claim mapping.
oidc-connector.yaml,
applied with alma apply:
# First OIDC connector for a new cluster. Apply it with
# `alma apply -f oidc-connector.yaml`, or enter the same values in the
# web UI connector editor.
#
# Register https://almaforge.example.com/api/v1/oidc/callback as a
# redirect URI on the identity provider side before applying this.
apiVersion: almaforge.com/v1
kind: OIDCConnector
metadata:
name: corp
spec:
# Shown on the sign-in button in the web UI.
display: Corporate SSO
# Your provider's OIDC discovery base, without /.well-known.
issuerURL: <paste-from-your-IdP>
clientID: <paste-from-your-IdP>
clientSecret: <paste-from-your-IdP>
# Scopes requested at sign-in.
scope:
- openid
- email
- profile
# Uncomment for Microsoft Entra, Okta, and other providers.
# Google rejects this scope. Use googleAdminEmail and
# googleServiceAccount instead.
# https://almaforge.com/sso/google/
# - groups
# Every sign-in evaluates every entry and grants the union of all
# matching roles.
#
# `claim` is the claim name as your provider emits it.
#
# `value` has to match what the provider actually sends, which is
# often not the name you see in its admin console:
#
# Okta group-name
# Microsoft Entra GUID of the group
# Google [email protected]
#
# The roles most clusters map first: `admin` (everything, one-hour
# sessions), `access` (use resources), `auditor` (read-only plus the
# audit log). `member` and `reviewer` cover the access-request
# workflow.
claimsToRoles:
- claim: groups
value: platform-admins
roles:
- admin
- access
- claim: groups
value: engineers
roles:
- access
Save it as oidc-connector.yaml and apply it on the cluster host. At
this point, only that host has an administrative identity:
sudo alma apply -f oidc-connector.yamlclaimsToRoles decides who gets in and what they can do. Each sign-in
evaluates every entry and grants the union of all matching roles. For
this evaluation, ensure a claim you hold maps to admin, which lets
you configure the cluster and connect to its resources. The example
grants admin and access to the platform-admins group. Replace
that group with a value from your provider.
A new cluster includes these roles for different responsibilities:
| Role | Grants |
|---|---|
member | See every resource and request access to it. Nothing else. |
access | Connect to resources the role's label matchers select, including as root, ec2-user, or ubuntu on every server. |
auditor | Read-only, including the audit log and recordings. |
admin | Everything, with a one-hour session cap. |
reviewer decides the requests a member files. See Just-in-time access. When
the defaults no longer fit, use the RBAC Guide to write
your own roles.
Map a claim your provider returns for you, such as your email address
or a group you belong to. For a group mapping, value has to match
the group exactly as your provider emits it, which is not always the
name you see in its admin console. The
SSO Integration guides show where to read that value
for each provider, along with the issuer URL.
If no mapping matches, sign-in is refused rather than granting an empty
session. Run sudo alma login --breakglass on the cluster host
again, correct the connector, and retry.
Success signal: after you sign out and reload
https://almaforge.example.com/, the sign-in page shows your provider instead
of the setup card.
Step 6. Install the CLI and sign in as yourself
Install alma on your macOS or Linux workstation:
curl -fL https://get.almaforge.com/install.sh | shThe installer places both alma and almad on your
workstation and creates /etc/almaforge/almad.d and /var/lib/almaforge. It sets
/var/lib/almaforge to mode 0700. A Linux package installation also adds a
disabled systemd unit. The workstation uses alma for sign-in.
almad remains stopped.
Windows runs through WSL. See CLI installation for package manager and signed installer options.
Sign in against the cluster:
alma login --proxy=almaforge.example.com:443A browser opens for the SSO flow. The cluster then issues a short-lived certificate bound to the roles mapped from your claims. Check the identity:
alma statusOpen your first server session
The configuration in Step 2 also enabled the SSH Service, so the cluster host is already your first server. List it, then connect using an OS account that exists on that host and is allowed by your role:
alma get nodesalma ssh <login>@<host>The built-in admin and access roles allow root, ec2-user, and ubuntu.
Use the hostname returned by get nodes. See
server access roles if your host uses a
different login.
Success signal: the shell opens through AlmaForge. After you exit, open Recordings in the Web UI and replay the session. Your evaluation cluster is ready. The remaining sections explore it and add resources.
Look around
Web UI
The sidebar at https://almaforge.example.com/ covers daily operations:
| Section | What is there |
|---|---|
| Resources | Every server, Kubernetes cluster, database, and application you can reach, with a connect dialog for each. |
| Requests | Ask for elevated roles you do not hold, and review other people's requests. See Just-in-time access. |
| Sessions | Sessions happening right now. |
| Audit Log | Every sign-in, connection, and configuration change. |
| Recordings | Replay of finished sessions. |
| SSO | The connector editor from Step 5. |
| Roles | What each role can reach and what it can do. See the RBAC Guide. |
| Users | Who has signed in, and the roles they carry. |
| Locks | Block a user, role, or host once the lock reaches the enforcing services, typically within seconds over a healthy Auth connection. See Revoking access. |
| Instances | The almad processes in the cluster and their versions. |
| Storage | Which backends hold state, audit events, and recordings. |
CLI
If you use kubectl, the model is familiar. Resources are
apiVersion / kind / metadata / spec documents. The same verbs
work across all of them. These are command examples for separate tasks,
not a sequence to run. apply, edit, and delete change cluster resources:
alma status # current identity, roles, expiryalma get nodes # reachable SSH hostsalma get role # all rolesalma get role/access -o yaml # one resource in fullalma apply -f <role-file>.yaml # create or updatealma edit role/<role-name> # open in $EDITOR, apply on savealma delete role/<role-name> # remove the named rolealma ssh <login>@<host> # open a sessionalma kube login <name> # write a kubeconfig entryalma db login <name> # issue a database client certificatealma recording ls # list session recordingsalma logout # discard the local identityCertificates expire automatically. Run alma login again
when a new sign-in is required. The kubeconfig integration obtains
credentials for kubectl through alma. See the
CLI Reference for the full command
tree.
Step 7. Add your resources
The control plane, SSO, and first server session are working. The resource sections below are optional and independent. Use only the ones you need, or continue to production planning.
The agent examples below follow three steps: issue a join token, start an agent with that token, and grant access through RBAC. The agent maintains an outbound connection to the Proxy. Agent hosts need no inbound connection from the Proxy or public address. The access guides also cover other join methods and deployment options.
Servers
The Step 2 env file set ALMA_SSH_SERVICE=true, so the cluster host is
already an SSH target. Other machines join with a token. Issue one from
your workstation, using the identity from Step 6:
alma create token --services=sshToken created. client_id: bbf4a1c2d3e4f5a6b7c8d9e0f1a2b3c4 client_secret: 9f8e7d6c5b4a39281706f5e4d3c2b1a0Save the client_secret now, it cannot be retrieved later. The clusterstores only its SHA-256 digest.
This token will expire in 30 minutes.The token can enroll multiple hosts before it expires. Each host trades it for a separate identity.
On the new machine, install the package as shown in
Step 1, then write /etc/almaforge/almad.env:
ALMA_PROXY=almaforge.example.com:443
ALMA_CLIENT_ID=bbf4a1c2d3e4f5a6b7c8d9e0f1a2b3c4
ALMA_CLIENT_SECRET=9f8e7d6c5b4a39281706f5e4d3c2b1a0
ALMA_SSH_SERVICE=true
ALMA_LABELS=env=demo
ALMA_PROXY routes the join through the Proxy. The agent validates the
Proxy's TLS certificate against the host's system trust store. Step 3
configured a Let's Encrypt certificate, which the public trust store
already recognizes.
ALMA_CA_PIN pins the Auth Service CA for a direct join selected by
ALMA_AUTH_SERVER. Configure one join address, not both
ALMA_AUTH_SERVER and ALMA_PROXY. Proxy joins ignore ALMA_CA_PIN.
For a private Proxy
certificate, install the signing CA in the host's trust store. See
cluster authentication for both trust paths.
sudo chmod 0600 /etc/almaforge/almad.envsudo systemctl enable --now almadThe host appears within seconds:
alma get nodesHost UUID Public Address Labels Version------- ------------------------------------- --------------- --------- -------web-01 3f0a6e2c-1d4b-4f3e-9c2a-5d7e8b9c0f1a env=demo 2026.1.0Open a session with an OS login your role allows:
alma ssh <login>@web-01If the error says your role does not allow the requested OS login, add an account that exists on the host:
alma edit role/accessYour editor opens on the role. Add the login under
spec.allow.serverLogins, save, then run alma login again
to obtain a certificate that permits the added login. Retry the SSH
connection. See
Server Access for secretless cloud join,
agentless OpenSSH hosts, and host user creation.
Success signal: the shell opens. After you exit, the session appears under Recordings.
Kubernetes clusters
The agent runs inside the target cluster. The Kubernetes API needs no public endpoint.
Point kubectl at the target cluster through your existing admin path:
gcloud container clusters get-credentials,
aws eks update-kubeconfig, or your own kubeconfig. The manifests
below create a Namespace and a ClusterRole, so this step requires
cluster-admin. Keep that path working for recovery if the agent enters
a bad state.
Issue the join token, then apply the agent manifest served by the Proxy. The manifest is the same for every cluster:
alma create token --services=kuberneteskubectl apply -f https://almaforge.example.com/install.yamlThe pods wait for two cluster-specific objects: the join credentials
and a KubernetesTarget. Both belong in the almaforge namespace
created by the manifest.
kubectl -n almaforge create secret generic almaforge-env \ --from-literal=ALMA_PROXY=almaforge.example.com:443 \ --from-literal=ALMA_CLIENT_ID=<client-id-from-the-token> \ --from-literal=ALMA_CLIENT_SECRET=<client-secret-from-the-token> \ --from-literal=ALMA_KUBERNETES_SERVICE=true \ --from-literal=ALMA_MATCH_LABELS='*=*' \ --from-literal=ALMA_DIAG_LISTEN=0.0.0.0:3000ALMA_MATCH_LABELS selects the targets this agent serves. Without it,
the agent starts but watches nothing. ALMA_DIAG_LISTEN is also
required because the StatefulSet probes /healthz and /readyz on
port 3000.
kubernetes-target.yaml
is the cluster's own registration:
# Registers the Kubernetes cluster where the agent runs. Add it to the
# almaforge-resources ConfigMap under the kubernetes.yaml key. The
# ConfigMap mounts at /etc/almaforge/almad.d, where almad reads resource
# files and hot-reloads changes.
apiVersion: almaforge.com/v1
kind: KubernetesTarget
metadata:
name: prod-eu-central # The name users type into `alma kube login`.
labels: # Matched by Role.kubernetesLabels and by ALMA_MATCH_LABELS.
env: prod
region: eu-central
# An empty spec makes the agent broker its local cluster with its
# mounted ServiceAccount token. To broker a remote cluster instead,
# supply a kubeconfig on the agent host.
spec: {}
Save it under that name in the current directory, then load it:
kubectl -n almaforge create configmap almaforge-resources \ --from-file=kubernetes.yaml=kubernetes-target.yamlThe agent mounts the ConfigMap at /etc/almaforge/almad.d/, the same drop-in
directory used on a VM. It reads the file once at startup. Kubernetes
updates the mounted copy when you change the ConfigMap, but a running
agent keeps the configuration it started with, so roll the StatefulSet
after any edit.
The pods start after both objects exist. Wait for the rollout, then confirm that AlmaForge sees the cluster:
kubectl -n almaforge rollout status statefulset/almaforge --timeout=120salma get kubeCluster Labels Version---------------- --------------------------- -------prod-eu-central env=prod,region=eu-central 2026.1.0Point kubectl at it:
alma kube login prod-eu-centralkubectl get pods -Akube login writes a kubeconfig context backed by your short-lived
certificate. Each call is checked against your roles and recorded in
the audit log. Your role needs kubernetesGroups and
kubernetesLabels to allow the request.
After the agent starts, revoke the join token with
alma delete token/<client-id>. See
Kubernetes Access to inspect or adapt
the agent manifests, join through the cluster's ServiceAccount without
a secret, or run the agent outside the cluster with a kubeconfig. To
generate the commands in the web UI, open Resources, then Enroll
resource.
Success signal: kubectl get pods -A returns, and the call appears
in Audit Log.
Web applications
Publish internal dashboards and APIs at <name>.almaforge.example.com.
Users authenticate through the same SSO connector, with no VPN or
inbound exposure of the upstream.
This requires the wildcard * DNS record from
What you need. ACME issues a certificate when each
app hostname is first requested. No per-app certificate setup is
required.
Issue a token from your workstation:
alma create token --services=appOn a host that can reach the app, install the package as shown in
Step 1, then write /etc/almaforge/almad.env:
ALMA_PROXY=almaforge.example.com:443
ALMA_CLIENT_ID=<client-id-from-the-token>
ALMA_CLIENT_SECRET=<client-secret-from-the-token>
ALMA_APP_SERVICE=true
ALMA_SSH_SERVICE=false
ALMA_MATCH_LABELS=*=*
sudo chmod 0600 /etc/almaforge/almad.envsudo systemctl enable --now almadALMA_MATCH_LABELS is what makes this agent pick up the app you
register below. Without it the agent starts and serves nothing. Narrow
it from *=* to something like env=prod to split apps across several
agents.
Then register the app itself. Save
http-apptarget.yaml
to a file, replace spec.uri and spec.fqdn with your own values, and
apply it with alma apply -f:
# HTTP/HTTPS web app behind the App agent. Users open it at
# https://<name>.<cluster> in a browser.
apiVersion: almaforge.com/v1
kind: AppTarget
metadata:
name: grafana # DNS-label name; users type this and it becomes <name>.<cluster>.
labels: # Static labels matched by Role.appLabels for RBAC.
env: prod
team: sre
spec:
uri: http://grafana.monitoring.svc:3000 # Upstream URL; scheme picks http / https / tcp.
fqdn: grafana.almaforge.example.com # Externally visible hostname; must be covered by the Proxy's wildcard cert.
spec.uri is the upstream address, which only the agent host must
reach. spec.fqdn is the public name users enter, and it has to sit
under the wildcard DNS record for this cluster. Confirm the app is
registered, then open it:
alma get appsYour role needs an appLabels matcher that selects the app. Otherwise,
the Proxy returns 403. See
Application Access for header
injection, JWT identity propagation, TCP apps, and mTLS
service-to-service access.
Success signal: after the SSO redirect,
https://grafana.almaforge.example.com loads in the browser.
Databases
PostgreSQL, MySQL, MongoDB, and other databases use
--services=database and a DatabaseTarget. After running
alma db login, users connect with their normal client and a
credential issued by AlmaForge. See
Database Access.
What's next
This single-host cluster stores everything on local disk and runs one of each service. Before serving production traffic:
- Cluster on Linux for the high-availability topology with external storage.
- Cluster on Kubernetes for the same shape on Kubernetes.
- Hardening Guide for the production security baseline.
- Storage Guide to move state, audit, and recordings off local disk.
- Infrastructure as Code to keep roles, connectors, tokens, and targets in Git.
- Operations for upgrades, backups, CA rotation, and incident response.