All Products
Search
Document Center

Alibaba Cloud Service Mesh:Configure an egress gateway to route all outbound traffic in ASM

Last Updated:Nov 12, 2024

When applications in an ASM instance need to communicate with external services, you can use an egress gateway to centrally manage all outbound traffic. After you configure an egress gateway, you can implement security control and routing of traffic to improve the security and observability of applications in the ASM instance.

Important

Before reading this topic, make sure you understand the content in Use ASMEgressTrafficPolicy to manage egress traffic. This topic uses ASM resources to transparently redirect requests to access external services to the egress gateway, where security policies are enforced before sending them to external services. The configuration is relatively complex. If the content in Use ASMEgressTrafficPolicy to manage egress traffic does not meet your requirements, see this topic.

Prerequisites

Configuration process

配置流程

Step 1: Deploy a sample application

  1. Deploy the sleep application.

    1. Use the following content to create sleep.yaml:

      Expand to view sleep.yaml

      apiVersion: v1
      kind: ServiceAccount
      metadata:
        name: sleep
      ---
      apiVersion: v1
      kind: Service
      metadata:
        name: sleep
        labels:
          app: sleep
          service: sleep
      spec:
        ports:
        - port: 80
          name: http
        selector:
          app: sleep
      ---
      apiVersion: apps/v1
      kind: Deployment
      metadata:
        name: sleep
      spec:
        replicas: 1
        selector:
          matchLabels:
            app: sleep
        template:
          metadata:
            labels:
              app: sleep
          spec:
            terminationGracePeriodSeconds: 0
            serviceAccountName: sleep
            containers:
            - name: sleep
              image: curlimages/curl
              command: ["/bin/sleep", "infinity"]
              imagePullPolicy: IfNotPresent
              volumeMounts:
              - mountPath: /etc/sleep/tls
                name: secret-volume
            volumes:
            - name: secret-volume
              secret:
                secretName: sleep-secret
                optional: true
      ---
    2. In the KubeConfig environment of the ACK cluster, run the following command to deploy the sleep application:

      For more information about how to use kubectl to manage clusters, see Obtain the kubeconfig file of a cluster and use kubectl to connect to the cluster.

      kubectl apply -f sleep.yaml
  2. Run the following command to access an external service from the pod where the sleep application resides:

    You can run the kubectl get pod -n default command to view the name of the sleep application pod.

    kubectl exec -it ${sleep pod name} -- /bin/sh
    curl aliyun.com -I

    The following is a sample output:

    HTTP/1.1 301 Moved Permanently
    server: envoy
    date: Thu, 14 Dec 2023 03:05:41 GMT
    content-type: text/html
    content-length: 239
    location: https://aliyun.com/
    eagleeye-traceid: 0b57ff8717025231418255220e****
    timing-allow-origin: *
    x-envoy-upstream-service-time: 69

    If 301 is returned, it indicates that the application in the ASM instance can access the external service. In this case, an HTTP access request is initiated by default. The web server returns a 301 response to redirect the request.

    Note

    By default, ASM uses the ALLOW_ANY policy to allow applications in an ASM instance to access all external services. In this case, you cannot implement permission control or use the observability capabilities provided by ASM. We recommend that you change the policy to REGISTRY_ONLY to allow applications in the ASM instance to access only specific external services, and that you use an egress gateway to route all the outbound traffic.

(Optional) Step 2: Set the policy for accessing external services to REGISTRY_ONLY

By default, ASM uses the ALLOW_ANY policy for accessing external services. We recommend that you change the policy to REGISTRY_ONLY. After you change the policy to REGISTRY_ONLY, sidecar proxies deny access to external hosts for which service entries are not defined in the ASM instance. This guarantees the security of applications in the ASM instance.

Note
  • If you have enabled REGISTRY_ONLY but have not created a service entry, access to external services is denied.

  • If you have not enabled REGISTRY_ONLY and have not created a service entry, you can access services, but the configured egress gateway does not take effect.

  1. Log on to the ASM console. In the left-side navigation pane, choose Service Mesh > Mesh Management.

  2. On the Mesh Management page, click the name of the ASM instance. In the left-side navigation pane, choose Data Plane Component Management > Sidecar Proxy Setting.

  3. On the Sidecar Proxy Setting page, click the global tab, click Outbound Traffic Policy, set External Access Policy to REGISTRY_ONLY, and then click Update Settings.

  4. Run the following command to access an external service from the pod where the sleep application resides:

    kubectl exec -it ${sleep pod name} -- /bin/sh
    curl aliyun.com -I

    The following is a sample output:

    HTTP/1.1 502 Bad Gateway
    date: Thu, 14 Dec 2023 03:08:46 GMT
    server: envoy
    transfer-encoding: chunked

    A 502 error code is returned, indicating that the application in the ASM instance cannot access an external service that is not defined in the service registry of the ASM instance.

Step 3: Create a service entry to define an external service

You need to create a service entry to define an external service so that applications in the ASM instance can access the external service by using the egress gateway.

  1. Log on to the ASM console. In the left-side navigation pane, choose Service Mesh > Mesh Management.

  2. On the Mesh Management page, click the name of the ASM instance. In the left-side navigation pane, choose Cluster & Workload Management > External Service(ServiceEntry). On the page that appears, click Create from YAML.

  3. On the Create page, select the namespace where the sleep application resides, select Access mesh external services for Template, configure a YAML example, and then click Create. The following YAML file provides an example.

    apiVersion: networking.istio.io/v1beta1
    kind: ServiceEntry
    metadata:
      name: external-svc-http
    spec:
      hosts:
      - aliyun.com
      location: MESH_EXTERNAL
      ports:
      - number: 80
        name: http
        protocol: HTTP
      resolution: DNS
  4. Run the following command to access the external service from the pod where the sleep application resides:

    kubectl exec -it ${sleep pod name} -- /bin/sh
    curl aliyun.com -I

    If 301 is returned, it indicates that the application in the ASM instance can access the external service. The aliyun.com domain name is defined in the service registry of the ASM instance, and therefore applications in the ASM instance can access this external service. In this case, the pod where the sleep application resides directly sends access requests to the external service and the requests do not pass through the egress gateway.

Step 4: Use an egress gateway to route all the requests to access external services

You have defined the aliyun.com domain name in the service entry of the ASM instance. Therefore, you can configure a virtual service and Istio gateway to manage the traffic to aliyun.com.

  1. Create an egress gateway and configure it to allow HTTP traffic on port 80. For more information, see Create an egress gateway.

  2. Create an Istio gateway and configure the related parameters as instructed in the following figure. For more information, see Manage Istio gateways.

    创建网关规则

  3. Use the following YAML code to create a virtual service. For more information, see Manage virtual services.

    Expand to view the YAML file of the virtual service

    apiVersion: networking.istio.io/v1alpha3
    kind: VirtualService
    metadata:
      name: egressgateway-vs
    spec:
      hosts:
      - aliyun.com
      gateways:
      - egress-gw  # Name of the Istio gateway that you created.
      - mesh
      http:
      - match:
        - gateways:
          - mesh
          port: 80
        route:
        - destination:
            host: istio-egressgateway.istio-system.svc.cluster.local
            port:
              number: 80
          weight: 100
      - match:
        - gateways:
          - egress-gw
          port: 80
        route:
        - destination:
            host: aliyun.com
            port:
              number: 80
          weight: 100
  4. Access the external service to verify the configuration.

    1. Run the following command to access the external service from the pod where the sleep application resides:

      kubectl exec -it ${sleep pod name} -- /bin/sh
      curl aliyun.com -I

      If 301 is returned, it indicates that the application in the ASM instance can access the external service. In this case, the application in the ASM instance does not directly access the external service from the pod where the application resides. Instead, the application accesses the external service through the egress gateway.

    2. Run the following command to view the access logs in the gateway pod:

      Note
      • If your egress gateway pod has multiple replicas, the access logs are generated in one of them. You must run this command on these pod replicas one by one to find the access logs.

      • If you have enabled the access log feature for the egress gateway, you can log on to the Simple Log Service console to view the access records.

      kubectl -n istio-system logs ${egress gateway pod name}  -c istio-proxy | grep aliyun.com | tail -n 1

      The following is a sample output:

      {"trace_id":null,"upstream_host":"106.11.XXX.XX:80","downstream_remote_address":"10.34.0.140:47942","requested_server_name":null,"response_code":301,"upstream_service_time":"24","user_agent":"curl/7.86.0-DEV","path":"/","route_name":null,"bytes_sent":0,"response_flags":"-","upstream_local_address":"10.34.0.141:60388","duration":24,"upstream_cluster":"outbound|80||aliyun.com","upstream_transport_failure_reason":null,"authority":"aliyun.com","request_id":"55789d59-9b81-4e39-b64a-66baf44e****","protocol":"HTTP/1.1","bytes_received":0,"method":"HEAD","downstream_local_address":"10.34.0.141:80","start_time":"2022-11-30T08:03:01.315Z","istio_policy_status":null,"x_forwarded_for":"10.34.0.140"}

      downstream_remote_address indicates the IP address of the pod where the sleep application resides.

      After you complete the configurations, access requests to the specified external service pass through the egress gateway. You can use the observability and security capabilities provided by ASM to manage outbound traffic on the egress gateway in an efficient manner.

References