Concept

Key Concepts

Domain concepts and API design patterns


Overview
tlsproxy — Architecture Overview Client Browser / App / API Consumer TLS Encrypted TLS Listener Accepts inbound TLS connections on port Certificate Store TLS cert & private key management Proxy Router Decrypts & forwards to backend targets Backend A HTTP / plain-text Backend B HTTP / plain-text Backend C HTTP / plain-text Plain-text TCP Plain-text TCP Plain-text TCP TLS :443 decrypt cert / key route TLS flow Plain TCP Config ref tlsproxy terminates TLS at the edge and forwards decrypted traffic to backend services over plain-text TCP.

This page explains the core concepts behind tlsproxy — how it models TLS termination, what happens to your traffic between client and backend, and how the proxy's API is structured. Understanding these ideas will help you configure tlsproxy correctly and debug issues when connections behave unexpectedly.


Content

What TLS Termination Means for Your Traffic

When a client connects to tlsproxy, it establishes an encrypted TLS session with the proxy itself — not with your backend service. tlsproxy decrypts the incoming traffic, then forwards the plain-text request to your backend over a standard unencrypted connection. This pattern is called TLS termination.

This design lets your backend services remain simple: they speak plain HTTP and never need to manage certificates. The proxy handles the cryptographic handshake, certificate presentation, and cipher negotiation on their behalf.

Client  ──[TLS]──▶  tlsproxy  ──[plain HTTP]──▶  Backend

Because the leg between tlsproxy and your backend is unencrypted, both components should run in a trusted network environment — for example, on the same host, within a private subnet, or over a loopback interface.


The Proxy as an HTTP API

tlsproxy exposes its own configuration and control surface as an HTTP API. You interact with the proxy — to register backends, inspect state, or shut it down — by sending HTTP requests to its management interface. This means two distinct HTTP surfaces exist side by side:

  • The forwarding surface: the TLS listener that your end users connect to. Traffic here is proxied transparently to a backend.
  • The management API: the plain HTTP interface you use as an operator or developer to configure and control the proxy.

Keeping these surfaces separate lets you lock down the management API to localhost or an internal network while still exposing the forwarding listener to the public internet.


Backends

A backend is a plain-text HTTP service that tlsproxy forwards decrypted traffic to. Each backend is defined by a host and port address. When you register a backend via the management API, tlsproxy begins accepting TLS connections on its listener and forwarding matching requests to that address.

You can register multiple backends. Routing between them is determined by configuration — typically by the incoming hostname (via SNI, the TLS Server Name Indication extension) or by request path patterns, depending on how tlsproxy is configured.


TLS Certificates and SNI

tlsproxy uses SNI to determine which TLS certificate to present to a connecting client. SNI is a standard TLS extension where the client announces the hostname it wants to reach before the cryptographic handshake completes. The proxy reads this hostname and selects the appropriate certificate from its configured store.

This allows a single tlsproxy instance to terminate TLS for multiple domains simultaneously — each domain gets its own certificate, and the correct one is served based on what the client requested.


Request Lifecycle

Understanding the full lifecycle of a request helps you reason about where failures occur:

  1. TLS handshake — The client connects and negotiates a TLS session with tlsproxy. The proxy presents a certificate matched via SNI.
  2. Decryption — tlsproxy decrypts the incoming byte stream into a plain HTTP request.
  3. Backend lookup — The proxy identifies the correct backend using its routing configuration.
  4. Forwarding — The plain-text request is sent to the backend over TCP.
  5. Response path — The backend's plain-text response travels back through tlsproxy, is optionally processed, and is re-encrypted before being returned to the client.

Each stage can be a source of errors. A failed TLS handshake points to a certificate or cipher mismatch. A connection refused error points to a misconfigured or unavailable backend.


Idempotency and State

tlsproxy's management API is designed around idempotent operations where possible. Registering a backend that already exists should not produce an error — the proxy either confirms the existing registration or updates it. This makes it safe to re-run provisioning scripts without first checking current state.

Configuration state in tlsproxy is held in memory by default. If the proxy process restarts, you should re-apply your configuration via the management API, or use a startup configuration file if the proxy supports one.


Examples

Visualizing the two-surface model

The following diagram shows how a single tlsproxy process exposes both surfaces. In this example, port 8443 is the TLS forwarding listener and port 9000 is the management API.

# Forwarding surface — end users connect here over TLS
Client ──[HTTPS :8443]──▶ tlsproxy ──[HTTP :3000]──▶ Your app

# Management surface — you configure the proxy here
curl http://localhost:9000/backends

Checking which backends are registered

Send a GET request to the management API to list all currently registered backends. This is useful for verifying that your configuration was applied correctly.

curl -s http://localhost:9000/backends

Expected response (example shape — fields depend on your tlsproxy version):

{
  "backends": [
    {
      "id": "my-app",
      "address": "127.0.0.1:3000",
      "hostname": "app.example.com"
    }
  ]
}

Tracing a failed TLS handshake

If a client cannot complete the TLS handshake, the connection is dropped before any HTTP request is forwarded. You can reproduce this condition with openssl to inspect what the proxy returns:

openssl s_client -connect localhost:8443 -servername app.example.com

If the handshake succeeds, you will see certificate details printed before the connection prompt. A failure here — such as SSL alert handshake failure — indicates that tlsproxy could not find a matching certificate for the requested SNI hostname, not that your backend is unavailable.


Related concepts
  • Configuration reference — Detailed descriptions of every field you can set when registering backends and configuring the TLS listener.
  • Authentication — How to secure the management API so that only authorised clients can register or modify backends.
  • Error handling — A catalogue of error responses returned by the management API and the forwarding surface, with guidance on what each one means.
  • Getting started — A step-by-step walkthrough of the install → configure → start → verify workflow that puts these concepts into practice.
  • TLS certificate management — How to supply, rotate, and troubleshoot the certificates that tlsproxy presents to connecting clients.