Networking

Private networking between services

5 min readUpdated April 2026

Services in the same StackBlaze project talk to each other over a private cluster network: never the public internet. Each service gets a stable internal DNS name in the form <service-name>.internal that resolves within the project namespace using Kubernetes CoreDNS.

Calling your backend via its public URL adds unnecessary latency, potential egress costs, and routes traffic through the load balancer and TLS handshake for no reason. Internal hostnames skip all of that.

Project network topology

HTTPS publicbackend.internal:3000postgres.internal:5432
Public Internet

User traffic

HTTPS only

Frontend Service

frontend.internal

public + internal

Backend API

backend.internal

internal only

PostgreSQL

postgres.internal

internal only

Service-to-service call

frontend/src/api.ts

// ✗ Never do this, routes through public internet

const res = await fetch("https://backend.myapp.com/api/users")

// ✓ Use the internal hostname, stays in the cluster

const API_URL = process.env.API_URL // "http://backend.internal:3000"

const res = await fetch(`${API_URL}/api/users`)

Auto-injected env vars when you link services

frontend service, environment

# Auto-set when you link the backend service to frontend

API_URL=http://backend.internal:3000

# Auto-set when you attach a PostgreSQL database

DATABASE_URL=postgresql://sb_user:***@postgres.internal:5432/mydb

Under the hood

  • Kubernetes Namespace: each StackBlaze project maps to a dedicated Kubernetes Namespace. Services within the same namespace can resolve each other by short DNS name. Namespaces provide a hard isolation boundary between projects.
  • ClusterIP Service: each StackBlaze service gets a Kubernetes ClusterIP Service resource with the same name. CoreDNS resolves backend.internal to this stable virtual IP without any configuration.
  • Traffic never leaves the cluster: internal calls go directly from pod to pod through the cluster network fabric (Cilium/Calico/Flannel). No NAT, no internet gateway, no egress charges. Latency is typically sub-millisecond.
  • Encrypted at the fabric layer: the CNI encrypts pod-to-pod traffic using WireGuard. Even plain HTTP calls are protected in transit, the encryption happens transparently below the application layer.

Step by step

01

Services in the same project are auto-connected

When you create multiple services within a StackBlaze project, they are automatically placed in the same Kubernetes Namespace. Kubernetes DNS resolves <service-name>.internal within that namespace. No manual configuration required.

02

Use the .internal hostname for all service-to-service calls

Never use the public HTTPS URL when calling a service from within your project. The .internal hostname resolves in microseconds via Kubernetes CoreDNS, bypasses the load balancer entirely, and never incurs egress charges. Use it in environment variables, config files, and SDK clients.

03

No firewall rules needed

By default, all services within the same project namespace can reach each other freely. You don't need to open ports, configure security groups, or manage IP allowlists. If you need to restrict traffic between services, StackBlaze supports Kubernetes NetworkPolicies via the dashboard.

04

Traffic is encrypted at the fabric layer

Even though the internal hostname uses plain HTTP, the underlying cluster network fabric encrypts all pod-to-pod traffic using WireGuard or IPsec depending on the CNI plugin. Your data is protected in transit even inside the cluster.