Switch to Istio Service Mesh and Gateway

Feature Flag

To use this feature, you need to first enable the enableModernQuiverRouting feature flag

When Istio is enabled in the Helm chart, GoodData.CN no longer creates Kubernetes Ingress resources for organization routing. Instead, a shared Istio Gateway and organization-specific VirtualService resources are used to expose per-organization hostnames and route requests into the platform.

Routing rules for all GoodData.CN backend services live in a shared VirtualService delivered by the Helm chart. Each organization’s VirtualService delegates to this shared routing definition.

This architecture enables centralized TLS handling (including wildcard certificates) while keeping per-organization hostnames isolated.

Prerequisites

  • A functional Istio installation (istiod, ingressgateway).
  • The Istio ingress gateway is exposed via LoadBalancer or an equivalent upstream.
  • If your cluster enforces sidecar injection, ensure GoodData.CN namespaces comply with your injection policy.
  • TLS secrets for the Gateway must be created in the namespace of the Istio ingress gateway (commonly istio-system).

Enable Istio in Helm

In your Helm chart values file add:

istio:
  enabled: true
  gateway:
    enabled: true
    selector:
      istio: ingressgateway

Effects:

  • The organization controller:
    • Creates a shared Gateway for the installation.
    • Creates one VirtualService per organization, each delegating routing to the shared VirtualService.
  • A shared VirtualService defining all GoodData API routes is installed by the Helm chart.
  • No Kubernetes Ingress resources are created.

Shared Gateway model

A single Istio Gateway handles TLS termination and accepts traffic for all organization hostnames.

Each organization receives a VirtualService that:

  • Matches its hostname.
  • References the shared Gateway.
  • Delegates routing to the shared platform VirtualService (gooddata-cn) containing the API paths and backend services.

This model is required for wildcard certificate support and consistent routing behavior.

TLS and wildcard certificate limitations

These limitations are inherited from Envoy (Istio’s underlying proxy):

  • No overlapping wildcard and specific certificates for the same domain hierarchy:
    • For example, you cannot use both *.something.com and a separate certificate for xyz.something.com on the same Gateway at the same time.
  • Dex endpoint and wildcard certificates:
    • If you use Istio Gateway mode, Dex IdP, and a wildcard certificate, do not host Dex on a domain covered by that wildcard certificate.
    • Dex must use its own certificate on a different hostname that does not conflict with the wildcard certificate used on the shared Gateway.
  • Wildcard certificate reuse across multiple Gateways:
    • The same wildcard certificate cannot be reused across multiple different Gateway servers.
    • In practice, do not attempt to share the same wildcard certificate between “managed” and “unmanaged” endpoints or across multiple separate GoodData.CN deployments. Use a single shared Gateway per deployment or distinct certificates.

Dex on a separate hostname

When running with Istio Gateway and wildcard TLS, deploy Dex on a separate hostname with its own certificate, outside the wildcard’s scope, to avoid certificate conflicts and failed handshakes.

Examples of Created Resources

Example shapes of the resources created/managed by the platform:

# Shared Gateway (one per installation/namespace)
apiVersion: networking.istio.io/v1beta1
kind: Gateway
metadata:
  name: gooddata-shared-gateway
  namespace: gooddata-cn
spec:
  selector:
    istio: ingressgateway
  servers:
    - port:
        number: 443
        name: https
        protocol: HTTPS
      tls:
        mode: SIMPLE
        credentialName: gooddata-wildcard-tls # points to a secret with certificate and key
      hosts:
        - "*.example.company"
# One VirtualService per Organization
apiVersion: networking.istio.io/v1beta1
kind: VirtualService
metadata:
  name: org-foo-routing
  namespace: gooddata-cn
spec:
  hosts:
    - foo.example.company
  gateways:
    - gooddata-shared-gateway
  http:
    - match:
        - uri:
            prefix: /
      route:
        - destination:
            host: api-gw.gooddata-cn.svc.cluster.local
            port:
              number: 80

Notes:

  • Names and exact shapes are illustrative; the organization controller manages these and may differ across versions.
  • credentialName must reference a Kubernetes secret in the same namespace as the Gateway that contains a certificate valid for the served hostnames (wildcard or SANs as appropriate).

Known limitations

  • Certificate overlap conflicts cannot be worked around at the Envoy level. Plan your hostname strategy to avoid overlaps between wildcard and single‑host certificates.
  • Do not reuse the same wildcard certificate across multiple Gateways. Prefer a single shared Gateway per deployment or use distinct certificates per Gateway.
  • If moving an existing deployment from NGINX Ingress to Istio, verify:
    • External DNS records point to the Istio ingress gateway.
    • TLS secrets exist and are referenced by the shared Gateway.
    • Dex is reachable on its separate hostname and certificate.

Troubleshooting

  • TLS handshake errors on specific hostnames:
    • Check for certificate overlap (wildcard vs specific cert) and remove the conflict.
    • Confirm credentialName secret has the correct certificate chain and private key.
  • Dex login fails or loops:
    • Ensure Dex is not served via the shared wildcard certificate when Istio Gateway mode is used.
    • Verify Dex’s hostname and certificate are independent of the shared Gateway’s wildcard domain.
  • 404/503 on Organization hostname:
    • Confirm VirtualService exists for the hostname and references the shared Gateway.
    • Ensure routes point to the correct in‑cluster service (api-gw/edge).