Tyk Gateway on Ubuntu 24.04 on Azure User Guide
Overview
This guide covers the deployment and configuration of Tyk Gateway on Ubuntu 24.04 on Azure using cloudimg Azure Marketplace images. Tyk Gateway is a fast, cloud native, open source API gateway written in Go. It sits in front of your upstream services and handles authentication, authorization, rate limiting, quotas, request and response transformation, versioning and analytics, all driven by declarative API definitions that you manage over its control API.
The cloudimg image ships the free and open source, MPL-2.0 licensed Tyk Gateway (the OSS Gateway only, with no Dashboard or commercial components), installed as the stock package from the official Tyk apt repository and run as a native systemd service. It is paired with a local Redis datastore (the gateway's required store for keys, rate limit counters and analytics), bound to the loopback interface, and fronted by nginx on port 80. Because a gateway control plane must never ship with a known secret, the gateway's control API secret is generated uniquely for each VM on first boot, written to a 0600 root:root credentials file. Backed by 24/7 cloudimg support.
Tyk is a trademark of its respective owner. This image is produced by cloudimg and is not affiliated with, endorsed by, or sponsored by Tyk Technologies. It ships the free and open source MPL-2.0 licensed Tyk Gateway (open source edition), unmodified.

What is included:
- Tyk Gateway v5.14.0 (the open source, MPL-2.0 licensed Gateway edition), installed from the official Tyk apt repository
- A local Redis 7 datastore (the gateway's required store for keys, counters and analytics), bound to
127.0.0.1only, never published to a host port - nginx on port
80reverse proxying the gateway data plane and its public/hellohealth endpoint, and returning403for the control API path so the control plane is never internet reachable redis-server.service,tyk-gateway-firstboot.service,tyk-gateway.serviceandnginx.serviceas systemd units, enabled and active on boot- A unique control API secret generated per VM on first boot, never baked into the image, written to
/root/tyk-gateway-credentials.txt - A clean gateway on first boot: no shipped API definitions, no shipped secret, no prior data
- Ubuntu 24.04 LTS base with latest security patches applied at build time
- Azure Linux Agent for seamless cloud integration and SSH key injection
- 24/7 cloudimg support with guaranteed 24 hour response SLA
Prerequisites
- Active Azure subscription, SSH public key, VNet + subnet in target region
- Subscription to the Tyk Gateway listing on Azure Marketplace
Recommended virtual machine size: Standard_B2s (2 vCPU, 4 GB RAM) is a sensible starting point. For higher request volumes use Standard_D2s_v5 or larger. NSG inbound: allow 22/tcp from your management network and 80/tcp for the API from the networks that call it.
Step 1: Deploy from the Azure Portal
Sign in to the Azure Portal, choose Create a resource, search the Marketplace for Tyk Gateway by cloudimg, and select Create. On Basics pick your subscription, resource group, region and size; under Administrator account choose SSH public key and paste your key; under Inbound port rules allow SSH (22) and HTTP (80). Then Review + create and Create.
Step 2: Deploy from the Azure CLI
RG="tyk-prod"; LOCATION="eastus"; VM_NAME="tyk-01"
GALLERY_IMAGE_ID="/subscriptions/<sub-id>/resourceGroups/azure-cloudimg/providers/Microsoft.Compute/galleries/cloudimgGallery/images/tyk-gateway-ubuntu-24-04/versions/<version>"
SSH_KEY="$(cat ~/.ssh/id_rsa.pub)"
az group create --name "$RG" --location "$LOCATION"
az network vnet create -g "$RG" --name tyk-vnet --address-prefix 10.100.0.0/16 --subnet-name tyk-subnet --subnet-prefix 10.100.1.0/24
az network nsg create -g "$RG" --name tyk-nsg
az network nsg rule create -g "$RG" --nsg-name tyk-nsg --name allow-ssh --priority 100 \
--source-address-prefixes "<your-mgmt-cidr>" --destination-port-ranges 22 --access Allow --protocol Tcp
az network nsg rule create -g "$RG" --nsg-name tyk-nsg --name allow-http --priority 110 \
--destination-port-ranges 80 --access Allow --protocol Tcp
az vm create -g "$RG" --name "$VM_NAME" --image "$GALLERY_IMAGE_ID" \
--size Standard_B2s --storage-sku StandardSSD_LRS \
--admin-username azureuser --ssh-key-values "$SSH_KEY" \
--vnet-name tyk-vnet --subnet tyk-subnet --nsg tyk-nsg --public-ip-sku Standard
Step 3: Verify the services
SSH to the VM as azureuser and confirm the gateway, its Redis datastore and nginx are running, and check the listeners:
sudo /opt/tyk-gateway/tyk --version
systemctl is-active redis-server tyk-gateway nginx
sudo ss -tlnp | grep -E ':80 |:8080|:6379' | awk '{print $1" "$4}' | sort -u
The version prints 5.14.0, all three services report active, and the listeners show nginx on 0.0.0.0:80 with the Tyk gateway on 127.0.0.1:8080 and Redis on 127.0.0.1:6379 — the gateway and Redis are bound to the loopback interface, so the only public entry point is nginx on port 80.

Step 4: Check the health endpoint
The gateway exposes a public, unauthenticated /hello liveness endpoint that reports the gateway version and the health of its Redis datastore. It is served through nginx on port 80, ideal for a load balancer health probe:
curl -s http://localhost/hello
This returns a JSON document with "status":"pass", the gateway version, and a redis component also reporting "status":"pass". No authentication is required for this endpoint.
Step 5: Review the per instance secret
The gateway control API is protected by a secret that is generated uniquely on the first boot of each VM. It is written, along with the resolved public URL, to a 0600 root:root credentials file. View it (the secret is masked in the guide, but the real value is on your VM):
sudo stat -c '%A %U:%G %n' /root/tyk-gateway-credentials.txt
sudo grep -E '^TYK_SECRET=|^TYK_URL=' /root/tyk-gateway-credentials.txt \
| sed -r 's/(TYK_SECRET)=.*/\1=<PER-VM-64-HEX-SECRET>/'
The file is -rw------- root:root. The TYK_SECRET is a 64 hex character value unique to this VM, generated by openssl rand -hex 32 on first boot before the gateway started. There is no default or known secret in the image, and the same secret gates every control API call.

Step 6: Verify the control API security model
The control API lives at /tyk/* on the loopback interface (127.0.0.1:8080) and is gated by the secret. nginx returns 403 for /tyk/ on the public port 80, so the control plane is never reachable from the internet. Confirm that a missing or wrong secret is rejected with 403, while the per instance secret authenticates:
SECRET=$(sudo grep '^TYK_SECRET=' /root/tyk-gateway-credentials.txt | cut -d= -f2-)
curl -s -o /dev/null -w 'control API (no secret): %{http_code}\n' http://127.0.0.1:8080/tyk/apis
curl -s -o /dev/null -w 'control API (wrong secret): %{http_code}\n' -H 'x-tyk-authorization: wrong' http://127.0.0.1:8080/tyk/apis
curl -s -o /dev/null -w 'control API (real secret): %{http_code}\n' -H "x-tyk-authorization: $SECRET" http://127.0.0.1:8080/tyk/apis
curl -s -o /dev/null -w 'control API via public :80: %{http_code}\n' http://localhost/tyk/apis
The no secret and wrong secret calls are rejected with 403, the call with the real per instance secret returns 200, and the control API path on the public port 80 returns 403. This is the whole security model: the health probe is open, the data plane proxies your APIs, and the control plane is on loopback, gated by the per instance secret, and never exposed publicly.

Step 7: Create your first proxied API
The gateway is managed by posting API definitions to the control API and hot reloading. Create a simple keyless API that proxies /httpbin/ to the public httpbin.org service, reload the gateway, then send a request through the data plane and watch it proxy to the upstream:
SECRET=$(sudo grep '^TYK_SECRET=' /root/tyk-gateway-credentials.txt | cut -d= -f2-)
curl -s -H "x-tyk-authorization: $SECRET" -H 'Content-Type: application/json' -X POST \
-d '{"name":"httpbin","api_id":"httpbin","org_id":"cloudimg","use_keyless":true,
"version_data":{"not_versioned":true,"versions":{"Default":{"name":"Default"}}},
"proxy":{"listen_path":"/httpbin/","target_url":"http://httpbin.org","strip_listen_path":true},
"active":true}' \
http://127.0.0.1:8080/tyk/apis
curl -s -H "x-tyk-authorization: $SECRET" http://127.0.0.1:8080/tyk/reload/group >/dev/null
sleep 2
curl -s http://localhost/httpbin/get | head -c 200
echo
The POST /tyk/apis returns {"key":"httpbin","status":"ok","action":"added"}, the reload returns 200, and the request to http://localhost/httpbin/get is proxied through the gateway to httpbin.org and returns the upstream JSON response. You have just published an API through Tyk. Replace target_url with your own upstream service and listen_path with the route you want to expose.

Step 8: Protect an API with a key
Most real APIs are not keyless. Set use_keyless to false with an auth token configuration, then mint a key over the control API. The following creates a protected API on /secure/, then creates a key scoped to it:
SECRET=$(sudo grep '^TYK_SECRET=' /root/tyk-gateway-credentials.txt | cut -d= -f2-)
curl -s -H "x-tyk-authorization: $SECRET" -H 'Content-Type: application/json' -X POST \
-d '{"name":"secure-api","api_id":"secure","org_id":"cloudimg","use_keyless":false,
"auth":{"auth_header_name":"Authorization"},
"version_data":{"not_versioned":true,"versions":{"Default":{"name":"Default"}}},
"proxy":{"listen_path":"/secure/","target_url":"http://httpbin.org","strip_listen_path":true},
"active":true}' \
http://127.0.0.1:8080/tyk/apis >/dev/null
curl -s -H "x-tyk-authorization: $SECRET" http://127.0.0.1:8080/tyk/reload/group >/dev/null
sleep 2
curl -s -o /dev/null -w 'secure API (no key): %{http_code}\n' http://localhost/secure/get
KEY=$(curl -s -H "x-tyk-authorization: $SECRET" -H 'Content-Type: application/json' -X POST \
-d '{"allowance":1000,"rate":100,"per":60,"quota_max":-1,
"access_rights":{"secure":{"api_id":"secure","api_name":"secure-api","versions":["Default"]}}}' \
http://127.0.0.1:8080/tyk/keys | python3 -c 'import sys,json;print(json.load(sys.stdin)["key_id"])')
curl -s -o /dev/null -w 'secure API (with key): %{http_code}\n' -H "Authorization: $KEY" http://localhost/secure/get
The unauthenticated call to /secure/get is rejected with 401, and the same call with the minted key returns 200. Keys carry their own rate limit (rate/per) and quota, which the gateway enforces using its Redis datastore.
Step 9: Call the API from your own machine
From anywhere that can reach the VM on port 80, call your published APIs at the VM public IP. The /hello health check and any keyless API need no credentials:
curl http://<vm-ip>/hello
curl http://<vm-ip>/httpbin/get
To manage the gateway (add or change API definitions) from off box, SSH in and use the control API on 127.0.0.1:8080 with the per instance secret, or front the gateway with your own management tooling. The control API is intentionally not exposed on the public port.
Step 10: Use your own domain and HTTPS (production)
The image serves the API over plain HTTP on port 80, which is convenient behind a load balancer or private network. For production you should terminate TLS in front of Tyk so credentials and payloads travel encrypted:
- Front the VM with Azure Application Gateway, a load balancer with a managed certificate, or a CDN, and forward to nginx on port
80. - Or install your own certificate: add a TLS
serverblock to/etc/nginx/sites-available/tyk-gatewayreferencing your certificate and key, open443/tcpon the NSG, thensudo systemctl reload nginx. - Point a DNS name you control at the VM public IP and use that name (and
https://) for your API consumers.
Step 11: Server components
| Component | Version / Detail |
|---|---|
| API gateway | Tyk Gateway v5.14.0 (open source, MPL-2.0, Gateway edition) |
| API front | nginx on :80 reverse proxying to 127.0.0.1:8080 |
| Datastore | local Redis 7 (loopback 127.0.0.1:6379, no host port) |
| Control API | /tyk/* on loopback 127.0.0.1:8080, gated by the per instance secret; 403 on public :80 |
| Health endpoint | /hello (public, no auth) reporting gateway + Redis health |
| Control API secret | per instance, generated first boot into /root/tyk-gateway-credentials.txt |
| Mode | OSS file based (use_db_app_configs false), no Dashboard |
Support
Every cloudimg image is backed by 24/7 support with a guaranteed 24 hour response SLA. For help with this image, contact support@cloudimg.co.uk.
Tyk is a trademark of its respective owner. This image ships the free and open source MPL-2.0 licensed Tyk Gateway (open source edition), unmodified, and is not affiliated with or endorsed by Tyk Technologies.