如何使集群中监听localhost的应用被其它Pod访问

本文介绍如何在应用监听localhost的情况下,通过配置Sidecar资源,使监听localhost的应用可以被集群中其它Pod通过Service访问。

问题现象

当部署在集群中的应用监听localhost时,即使通过Service暴露应用的服务端口,该服务也无法被集群中的其他Pod访问。

不同语言的应用监听localhost示例如下:

  • Golang:net.Listen("tcp", "localhost:8080")

  • Node.js:http.createServer().listen(8080, "localhost")

  • Python:socket.socket().bind(("localhost", 8083))

问题原因

当集群中应用监听localhost网络地址时,由于localhost是本地地址,集群中的其它Pod对其访问不通是正常现象。

解决方案

您可以任选以下方式,对外暴露应用服务。

  • 方式一:修改应用监听的网络地址

    如果您希望应用提供的服务对外暴露,建议修改应用代码,将应用监听的网络地址从localhost改为0.0.0.0。

  • 方式二:使用服务网格暴露监听localhost的服务

    如果您不希望修改应用代码,同时需要将监听localhost的应用暴露给集群中的其它Pod,可以通过ASM控制台创建Sidecar资源。操作步骤如下:

    1. 登录ASM控制台,在左侧导航栏,选择服务网格 > 网格管理

    2. 网格管理页面,单击目标实例名称,然后在左侧导航栏,选择流量管理中心 > Sidecar流量配置,然后单击使用YAML创建

    3. 创建页面,选择命名空间和任意场景模版,配置以下YAML,然后单击创建

      请您按照实际情况对以下字段进行替换。

      字段

      说明

      {namespace}

      替换为应用部署所在的命名空间。

      {container_port}

      替换为应用监听localhost的容器端口。

      {port}

      替换为应用的Service端口。

      {key} : {value}

      替换为选中应用Pod的标签。

      apiVersion: networking.istio.io/v1beta1
      kind: Sidecar
      metadata:
        name: localhost-access
        namespace: {namespace}
      spec:
        ingress:
          - defaultEndpoint: '127.0.0.1:{container_port}'
            port:
              name: tcp
              number: {port}
              protocol: TCP
        workloadSelector:
          labels:
            {key}: {value}