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
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
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
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
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.
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.
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.
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 :)