【问题标题】:Expose service on local kubernetes在本地 Kubernetes 上公开服务
【发布时间】:2018-08-19 12:36:20
【问题描述】:

我在 Mac OS 上运行与 docker 捆绑的本地 kubernetes。

如何公开服务,以便我可以通过 Mac 上的浏览​​器访问该服务?

我已经创建了:

a) 部署包括 apache httpd。

b) 通过 yaml 服务:

apiVersion: v1
kind: Service
metadata:
  name: apaches
spec:
  selector:
    app: web
  type: NodePort
  ports:
  - protocol: TCP
    port: 80
  externalIPs:
  - 192.168.1.10 # Network IP of my Mac

我的服务看起来像:

$ kubectl get service apaches
NAME      TYPE       CLUSTER-IP       EXTERNAL-IP    PORT(S)        AGE
apaches   NodePort   10.102.106.158   192.168.1.10   80:31137/TCP   14m

我可以通过wget $CLUSTER-IP本地访问我的kubernetes集群中的服务

我尝试在我的 Mac 上调用 http://192.168.1.10/,但它不起作用。

这个question 处理类似的问题。但是解决方案没有帮助,因为我不知道我可以使用哪个 IP。

更新

感谢 Michael Hausenblas,我使用Ingress 制定了一个解决方案。 尽管如此,仍有一些悬而未决的问题:

  • 服务的外部IP是什么意思?当我不直接从外部访问服务时,为什么需要外部 IP?
  • 服务端口31137是什么意思?
    • kubernetes 文档描述了一种[通过 NodePort 在 minikube 中发布服务][4] 的方法。 Docker 上捆绑的 kubernetes 也可以做到这一点吗?

【问题讨论】:

    标签: kubernetes


    【解决方案1】:

    在 Kubernetes 中暴露服务有几种解决方案: http://alesnosek.com/blog/2017/02/14/accessing-kubernetes-pods-from-outside-of-the-cluster/

    这是我根据 alesnosek 针对与 docker 捆绑的本地 kubernetes 的解决方案:

    1.主机网络

    hostNetwork: true
    

    脏(出于安全原因不应共享主机网络)=>我没有检查此解决方案。

    2。主机端口

    hostPort: 8086
    

    不适用于服务 => 我没有检查此解决方案。

    3。节点端口

    通过定义一个 nodePort 来暴露服务:

    apiVersion: v1
    kind: Service
    metadata:
      name: apaches
    spec:
      type: NodePort
      ports:
        - port: 80
          nodePort: 30000
      selector:
        app: apache
    

    4.负载均衡器

    编辑 @MathObsessed 发布了solution in his anwer

    5.入口

    一个。安装Ingress Controller

    git clone https://github.com/jnewland/local-dev-with-docker-for-mac-kubernetes.git
    
    kubectl apply -f nginx-ingress/namespaces/nginx-ingress.yaml -Rf nginx-ingress
    

    b.配置入口

    kubectl apply -f apache-ing.yaml

    apiVersion: extensions/v1beta1
    kind: Ingress
    metadata:
      name: apache-ingress
    spec:
      rules:
      - host: localhost
        http:
          paths:
          - path: /
            backend:
              serviceName: apaches
              servicePort: 80
    

    现在我可以通过调用 http://localhost/ 来访问我使用 kubernetes 部署的 apache

    使用local-dev-with-docker-for-mac-kubernetes的备注

    更多文档

    【讨论】:

    • 对于“Ingress”类型,值得一提的是,有很多不同的选项。 IstioTraefik
    【解决方案2】:

    对于那些仍在寻找答案的人。我已经设法通过添加另一个 Kube 服务来将我的应用程序公开给 localhost 调用(通过浏览器或 Postman)来实现这一点:

    kind: Service
    apiVersion: v1
    metadata:
      name: apaches-published
    spec:
      ports:
        - name: http
          port: 8080
          targetPort: 80
          protocol: TCP
      selector:
        app: web
      type: LoadBalancer
    

    立即试用:http://localhost:8080

    【讨论】:

    • 我没有得到外部 IP 类型:Loadbalancer: apaches LoadBalancer 10.98.28.154 ...
    • 可能是因为你的8080端口已经被占用了?例如,您有另一个本地服务或使用此端口的程序?我首先会尝试两件事:1)docker ps -a(查看正在运行的进程)2)尝试像87438090这样的花哨端口而不是8080,以确保没有其他应用程序正在使用它3)我正在使用 Docker Desktop,也许您在 Linux 上,并且那里的工作方式有所不同 4) 另外我正在使用 kubectl,而您可能正在使用 minikube
    • 你是对的,修复错误的端口后我可以访问服务了。
    【解决方案3】:

    正如马蒂亚斯女士的回答中已经提到的,有几种方法。

    由于官方 Kubernetes 文档专门描述了 using a Service with a type NodePort,我想描述一下工作流程。

    NodePort:在每个节点的 IP 上的静态端口(@98​​7654326@)上公开服务。自动创建ClusterIP 服务,NodePort 服务路由到该服务。您可以通过请求 <NodeIP>:<NodePort> 从集群外部联系 NodePort 服务。

    如果将type 字段设置为NodePort,Kubernetes 控制平面会从--service-node-port-range 标志指定的范围内分配一个端口(默认值:30000-32767)。每个节点都将该端口(每个节点上的相同端口号)代理到您的服务中。您的服务在其.spec.ports[*].nodePort 字段中报告分配的端口。

    使用typeNodePort 设置服务

    apiVersion: v1
    kind: Service
    metadata:
      name: my-service
    spec:
      selector:
        app: MyApp
      ports:
        - protocol: TCP
          port: 80
          targetPort: 9376
      clusterIP: 10.0.171.239
      type: NodePort
    

    然后你可以检查Service暴露在哪个端口上

    kubectl get svc
    
    NAME                           TYPE           CLUSTER-IP       EXTERNAL-IP   PORT(S)                      AGE
    my-service                     NodePort       10.103.218.215   <none>        9376:31040/TCP               52s
    

    并使用暴露的端口通过 localhost 访问它。例如

    curl http://localhost:31040
    

    【讨论】:

    • 你检查过它是否暴露在 127.0.0.1 上吗?
    • Failed to connect to localhost port 32179: Connection refused
    【解决方案4】:

    非常简单的例子

    方法1

    $ kubectl create deployment nginx-dep --image=nginx --replicas=2
    
    • 获取豆荚
    $ kubectl get pods
    NAME                        READY   STATUS    RESTARTS   AGE
    nginx-dep-5c5477cb4-76t9q   1/1     Running   0          7h5m
    nginx-dep-5c5477cb4-9g84j   1/1     Running   0          7h5m
    
    • 使用kubectl port访问pod
    $ kubectl port-forward nginx-dep-5c5477cb4-9g84j 8888:80
    Forwarding from 127.0.0.1:8888 -> 80
    Forwarding from [::1]:8888 -> 80
    
    • 现在向localhost:8888 发送curl
    $ curl -v http://localhost:8888 
    

    方法2

    您可以公开部署的port 80(应用程序在其中运行,即 nginx 端口) 通过 NodePort

    $ kubectl expose deployment nginx-dep --name=nginx-dep-svc --type=NodePort --port=80
    
    • 获取服务
    $ kubectl get svc 
    NAME            TYPE        CLUSTER-IP     EXTERNAL-IP   PORT(S)        AGE
    kubernetes      ClusterIP   10.96.0.1      <none>        443/TCP        31d
    nginx-dep-svc   NodePort    10.110.80.21   <none>        80:31239/TCP   21m
    
    • 使用 hte NodePort 访问部署
    $ curl http://localhost:31239  
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-04-07
      • 2019-01-10
      • 2022-12-12
      • 2021-12-21
      • 2019-01-04
      相关资源
      最近更新 更多