> ## Documentation Index
> Fetch the complete documentation index at: https://unkey.com/docs/llms.txt
> Use this file to discover all available pages before exploring further.

> ## Agent Instructions
> Unkey is two separate products. Compute builds, deploys, and runs apps behind a gateway. API Management issues API keys, enforces rate limits, manages identities and permissions, and reports usage. Say which product a page belongs to; a reader can use either without the other.
> Every Unkey API endpoint is an HTTP POST to https://api.unkey.com/v2/{service}.{procedure} with a root key in the Authorization: Bearer header. Root keys are workspace scoped.
> Error codes have the form err:{system}:{category}:{specific} and each has a page at /errors/{system}/{category}/{specific}.
> The word environment means production or preview in Compute. Rate limiting has four meanings on this site; the glossary lists them.

# Private networking

> What your instances can and cannot reach, and how to call one app from another today.

We don't offer private networking yet. To call one app from another, call its public hostname. The request goes out over the internet and back in through the [gateway](/docs/compute/gateway/overview), like a call from anywhere else. Your instances can't open connections to each other.

## Call one app from another

Use the other app's hostname, and treat the call as an external one:

```ts theme={"system"}
const res = await fetch("https://billing-acme.unkey.app/invoices", {
  headers: { Authorization: `Bearer ${process.env.BILLING_API_KEY}` },
});
```

1. **Put the hostname and credential in [environment variables](/docs/compute/configure/environment-variables)** of the calling app, not in code. Then a preview <Tooltip tip="One built and running version of an app in one environment.">deployment</Tooltip> can point at a preview of the other app. See [Automatic domains](/docs/compute/networking/automatic-domains) for hostname patterns.
2. **Protect the other app with an [API key policy](/docs/compute/gateway/api-key-auth)**, because the call is public. Give the caller a key. Bad requests are rejected at the gateway, and the caller's identity shows up in the [request log](/docs/compute/observe/requests).
3. **Set a timeout.** Each call is a full HTTP round trip, so avoid chains of internal calls on a latency-sensitive path.

## Share state between instances

Instances can't talk to each other, so anything two of them need belongs in a store they can both reach, such as a managed Redis or Postgres. Don't rely on peer-to-peer cache invalidation, leader election, or gossip between replicas. For long-lived connections, see [WebSockets](/docs/compute/networking/websockets).

## What your instances can and can't reach

* **Outbound: anything.** Your app can call any host it can resolve: a database, a third-party API, an object store, or another Unkey app.
* **Inbound: only the gateway**, on your app's port. Nothing else can reach an instance: not other instances of the same deployment, not other apps in the project, not older deployments of the same app.

A blocked connection isn't refused or reset. It's silently dropped, so the caller just times out. If you see that, this is the likely cause.

Instances also run in a sandbox and get no credentials to our infrastructure.
