How to control traffic out of OpenShift Service Mesh

Voravit L
5 min readFeb 23, 2021

Control traffic to go out of the Mesh with Service Entry

One of the great features of Istio is traffic control. You can control traffic for service to service within Service Mesh, control traffic coming into Service Mesh (Ingress) and absolutely control traffic out of Service Mesh.

If you are interested in controlling incoming traffic. You can check the following previous blogs.

How to get traffic into OpenShift Service Mesh

You can control traffic out of service mesh by using Service Entry ( and also with Egress Gateway but Egress Gateway is beyond scope of this blog)

With Service Entry, you can control traffic going out of service mesh and also can apply Istio policies to control behavior of outgoing traffic e.g. timeout.

This blog will get you through the process of configuring Istio service entry to control traffic out of Service Mesh

Prerequisites

Check my previous blog that I mentioned previously for setup Service Mesh, Ingress gateway with demo application.

In brief, We have a simple demo consisting of 2 deployments including frontend and backend. We exposed frontend service with Istio ingress gateway. Frontend is configured call backend and backend is call external service to http://httpbin.org/status/200

Overall architecture of demo application

Outbound Traffic Policy

OpenShift Service Mesh default allows outbound traffic policy to go out of its mesh. This is configured in the config map in control plane namespace.

The naming convention of this config map is istio-<Service Mesh Control Plane CRD name>.

Let’s check our istio-basic-install configmap. OutboundTrafficPolicy mode is set to ALLOW_ALL

Control Plane ConfigMap

We can change this behavior to blocking by default by change mode to REGISTRY only.

oc get configmap istio-basic-install -n control-plane -o yaml \| sed 's/mode: ALLOW_ANY$/mode: REGISTRY_ONLY/g' \| oc replace -n control-plane -f -

Try to access the frontend application. You will get HTTP response code 503 with message Remote host terminated the handshake.

curl $(oc get route frontend -n control-plane -o jsonpath='{.spec.host}')#Sample outputFrontend version: 1.0.0 => [Backend: http://backend:8080, Response: 503, Body: Backend version:v1, Response:503, Host:backend-v1-f4dbf777f-728xc, Status:503, Message: Remote host terminated the handshake]

Check Kiali console for Graph

Kiali Graph — PassthroughCluster and BlackholeCluster

PassThroughCluster and BlackHoleCluster are virtual clusters that are created when the control plane is configured with ALLOW_ANY mode and REGISTRY_ONLY mode respectively.

With REGISTRY_ONLY mode, all outbound traffic to the external system are blocked unless Service Entry is created for that service.

Service Entry

We will create a Service Entry to allow outgoing traffic to httpbin.org.

Take a quick review for Service Entry for httpbin.org

Service Entry — httpbin.org

Line 7 is the host name for external service.

Line 8–14 are configured for allow protocol that are HTTP and HTTPS along with ports

Create Service Entry in the data plane.

https://raw.githubusercontent.com/voraviz/openshift-service-mesh-istio-gateway/main/httpbin-service-entry.yaml  | \
oc create -n data-plane -f -

Test with curl again. This times you will get 200 OK then check Kiali Graph.

Kiali Graph — Service Entry

Notice that in the rightmost of the graph. There is a service entry name httpbin.org and traffic goes through this service entry.

Try to connect to another external service rather than httpbin.org

oc set env deployment/backend-v1 APP_BACKEND=https://redhat.com -n data-plane

Test with cURL. You will get HTTP error 503 Service Unavailable

curl -v  http://$(oc get route frontend -n control-plane -o jsonpath='{.spec.host}')
# Sample output
< HTTP/1.1 503 Service Unavailable< x-correlation-id: 0e5fa2f2-819b-4584-92ad-91f13a875af7< x-powered-by: Express< content-type: text/html; charset=utf-8< content-length: 185

Control outgoing traffic

Istio can control traffic through Service Entry using the same method with internal service that is destination rule and virtual service.

Let’s say that we want to define timeout for external service if external service latency is greater than 3 seconds. We will give up and return HTTP error Gateway Timeout to client.

First, we will set a backend service to call to httpbin.org/delay/6 to simulate the slowness of external service.

oc set env deployment/backend-v1 APP_BACKEND=http://httpbin.org/delay/6 -n data-plane

Test with cURL. Notice that total time is slightly longer than 6 sec.

curl -w "\nTotal Time: %{time_total}s\n" http://$(oc get route frontend -n control-plane -o jsonpath='{.spec.host}')#Sample OutputFrontend version: 1.0.0 => [Backend: http://backend:8080, Response: 200, Body: Backend version:v1, Response:200, Host:backend-v1-7d566c7856-97kvr, Status:200, Message: Hello, Quarkus]Total Time: 6.646115s

Then we create virtual service for service entry httpbin.org to set timeout to 3 sec.

Virtual Service with timeout

Line 13 is set timeout to 3 sec

Create virtual service for Service Entry httpbin.org

curl -s https://raw.githubusercontent.com/voraviz/openshift-service-mesh-istio-gateway/main/httpbin-virtual-service.yaml |  \
oc create -n data-plane -f -

Test with cURL again. You will receive HTTP 504 Gateway Timeout

curl -v -w "\nTotal Time: %{time_total}s\n" \
http://$(oc get route frontend -n control-plane -o jsonpath='{.spec.host}')
# Sample output< HTTP/1.1 504 Gateway Timeout< x-correlation-id: ef5fc097-3a51-4b6f-95cf-f37ade06d119< x-powered-by: Express< content-type: text/html; charset=utf-8< content-length: 183Frontend version: 1.0.0 => [Backend: http://backend:8080, Response: 504, Body: Backend version:v1, Response:504, Host:backend-v1-b7d9d4545-pqqwr, Status:504, Message: Hello, Quarkus]
Total Time: 3.132835s

Check Kiali Graph again you will find that Service Entry has a virtual service icon.

Kiali Graph — Service Entry with Virtual Service

Summary

Istio Service Mesh provided you a mechanism to control traffic at the edge of the mesh in both incoming and outgoing traffic. For outgoing traffic, you can easily create a whitelist of allowed URLs with Service Entry and also possible to enable Istio policies with Service Entry.

You can find all YAML files here

Or you can learn Istio from this Online tutorial provided by Red Hat

Have fun with Service Mesh :)

--

--