Gateway API是由SIG-NETWORK社区管理的开源项目,通过提供可表达的、可扩展的、面向角色的接口来改善服务网络。您可以使用Gateway API对集群内应用访问的路由规则进行条件限制。本文介绍如何使用Gateway API定义集群内应用的路由规则。

前提条件

步骤一:在ACK集群中部署示例应用

  1. 为default命名空间开启自动注入。具体操作,请参见启用自动注入
  2. 通过kubectl连接集群。具体操作,请参见通过kubectl管理Kubernetes集群
  3. 使用以下内容,创建名为httpbin的YAML文件。
    apiVersion: v1
    kind: ServiceAccount
    metadata:
      name: httpbin
    ---
    apiVersion: v1
    kind: Service
    metadata:
      name: httpbin
      labels:
        app: httpbin
        service: httpbin
    spec:
      ports:
      - name: http
        port: 8000
        targetPort: 80
      selector:
        app: httpbin
    ---
    apiVersion: apps/v1
    kind: Deployment
    metadata:
      name: httpbin
    spec:
      replicas: 1
      selector:
        matchLabels:
          app: httpbin
          version: v1
      template:
        metadata:
          labels:
            app: httpbin
            version: v1
        spec:
          serviceAccountName: httpbin
          containers:
          - image: docker.io/kennethreitz/httpbin
            imagePullPolicy: IfNotPresent
            name: httpbin
            ports:
            - containerPort: 80
  4. 执行以下命令,创建httpbin应用。
    kubectl apply -f httpbin.yaml
  5. 执行以下命令,验证Pod是否正常运行。
    kubectl get pod |grep httpbin

    预期输出:

    httpbin-66cdbdb6c5-vhsh6          2/2     Running   0          11s

步骤二:在ASM中配置Gateway API

  1. 通过kubectl连接ASM实例,具体操作,请参见通过kubectl连接ASM实例
  2. 使用以下内容,创建名为gw的YAML文件。
    apiVersion: networking.x-k8s.io/v1alpha1
    kind: GatewayClass
    metadata:
      name: istio
    spec:
      controller: istio.io/gateway-controller
    ---
    apiVersion: networking.x-k8s.io/v1alpha1
    kind: Gateway
    metadata:
      name: gateway
      namespace: istio-system
    spec:
      gatewayClassName: istio
      listeners:
      - hostname: "*"
        port: 80
        protocol: HTTP
        routes:
          namespaces:
            from: All
          selector:
            matchLabels:
              selected: "yes"
          kind: HTTPRoute
    ---
    apiVersion: networking.x-k8s.io/v1alpha1
    kind: HTTPRoute
    metadata:
      name: http
      namespace: default
      labels:
        selected: "yes"
    spec:
      gateways:
        allow: All
      hostnames: ["httpbin.aliyun.com"]
      rules:
      - matches:
        - path:
            type: Prefix
            value: /get
        filters:
        - type: RequestHeaderModifier
          requestHeaderModifier:
            add:
              my-added-header: added-value
        forwardTo:
        - serviceName: httpbin
          port: 8000
    • 配置Gateway

      port:设置端口为80,表示通过80端口访问应用。

    • 配置HTTPRoute
      • hostnames:主机名称,本文设置为httpbin.aliyun.com
      • path:设置typePrefixvalue/get,表示访问应用的URL中必须有get参数。
  3. 执行以下命令,配置Gateway API。
    kubectl --kubeconfig=<ASM实例对应的Kubeconfig文件> apply -f gw.yaml

步骤三:获取入口网关的地址

  1. 登录容器服务管理控制台
  2. 在控制台左侧导航栏中,单击集群
  3. 集群列表页面中,单击目标集群名称或者目标集群右侧操作列下的详情
  4. 在集群管理页左侧导航栏中,选择服务与路由 > 服务
  5. 服务页面顶部设置命名空间为istio-system,查看istio-ingressgateway外部端点列下端口为80的IP地址。

结果验证

  • 执行以下命令,访问httpbin应用。
    curl -s -HHost:httpbin.aliyun.com "http://$INGRESS_HOST:$INGRESS_PORT/get"

    使用-H将HTTP的Host设置为httpbin.aliyun.com。即上文配置HTTPRoute时设置的hostnames值。

    预期输出:

    {
      "args": {},
      "headers": {
        "Accept": "*/*",
        "Content-Length": "0",
        "Host": "httpbin.aliyun.com",
        "My-Added-Header": "added-value",
        "User-Agent": "curl/7.75.0",
        "X-Envoy-Attempt-Count": "1",
        "X-Envoy-External-Address": "xxxxxx"
      },
      "origin": "xxxxxx",
      "url": "http://httpbin.aliyun.com/get"
    }
  • 执行以下命令,访问httpbin应用。
    curl -I -HHost:httpbin.aliyun.com "http://$INGRESS_HOST:$INGRESS_PORT/headers"

    预期输出:

    HTTP/1.1 404 Not Found

可以看到,包含get参数的URL访问应用成功,包含headers参数的URL访问应用失败。说明只有包含get参数的URL,才能访问应用成功。使用Gateway API定义路由规则成功。