所以我正在使用Kubernetes进行侧面项目,这很棒。运行一个像我正在进行的小项目更便宜(一个3-5个实例的小集群基本上给了我所需的一切,每月约30美元的GCP)。
我正在努力的唯一领域是尝试使用kubernetes Ingress资源映射到群集并扇出到我的微服务(它们是小Go或Node后端)。我有入口的配置设置映射到不同的服务,那里没有问题。
据我所知,在创建入口资源时,您可以轻松地让GCP启动LoadBalancer。这很好,但它也代表另外20美元/月,这增加了项目的成本。一旦/如果这个东西得到一些牵引力,那可以被忽略,但是现在并且为了更好地理解Kubernetes,我想做以下事情:
有没有办法甚至可以使用Kubernetes和入口资源来完成?
谢谢!
答案 0 :(得分:3)
是的,这是可能的。部署入口控制器,并使用NodePort服务进行部署。例如:
---
apiVersion: v1
kind: Service
metadata:
name: nginx-ingress-controller
namespace: kube-system
labels:
k8s-app: nginx-ingress-controller
spec:
type: NodePort
ports:
- port: 80
targetPort: 80
nodePort: 32080
protocol: TCP
name: http
- port: 443
targetPort: 443
nodePort: 32443
protocol: TCP
name: https
selector:
k8s-app: nginx-ingress-controller
现在,创建一个带有DNS条目的入口:
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
name: my-ingress
spec:
rules:
- host: myapp.example.com
http:
paths:
- path: /
backend:
serviceName: my-app-service #obviously point this to a valid service + port
servicePort: 80
现在,假设您的静态IP附加到运行kube-proxy的任何kubernetes节点,更新DNS以指向静态IP,您应该能够访问myapp.example.com:32080
并且入口会将您映射回你的应用。
其他一些事情:
如果您想使用低于32080的端口,请记住,如果您正在使用CNI网络,you'll have trouble with hostport。它建议让负载均衡器监听端口80,我想你可能只是设置了nginx进行代理传递,但它变得很困难。这就是推荐使用云提供商的负载均衡器的原因:)
答案 1 :(得分:0)
你也可以创建一个nginx-ingress图表,让它拉出一个短暂的IP,然后将其升级为静态。这将为您留下L7单区负载均衡器。
本指南介绍了它。如果你使用kube-lego,你可以忽略TLS的东西,它与nginx-ingress一样好用
https://github.com/kubernetes/ingress-nginx/tree/master/docs/examples/static-ip
答案 2 :(得分:0)
TLDR:如果您想在3000以下的端口上提供网站/网络服务,那么不可能,这是不可能的。如果有人找到了解决方法,我很想知道
我尝试在3000以下的端口上使用时使用的两种主要方法包括:
nginx-ingress
类型为NodePort
的控制器服务,侦听端口80和443。但是,这导致以下错误:
Error: UPGRADE FAILED: Service "nginx-ingress-controller" is invalid:
spec.ports[0].nodePort: Invalid value: 80: provided port is not in the
valid range. The range of valid ports is 30000-32767
解决此错误的方法是更改启动--service-node-port-range
时使用的kube-apiserver
标志。但是,无法在GCP上访问此配置。如果您想尝试一下,可以在这里查看说明:Kubernetes service node port range externalIP
的{{1}}的{{1}}属性。乍一看,这似乎是一个理想的解决方案。但是,service
属性的工作方式存在一个错误。它不接受外部静态IP,而接受内部临时IP。如果您在type: ClusterIP
字段中对内部临时IP进行硬编码,然后通过GCP控制台将外部静态IP附加到群集中的一个节点,则请求将被成功路由。但是,这不是一个可行的解决方案,因为您现在已经在externalIP
定义中对临时IP进行了硬编码,因此,随着节点内部IP的更改,您的网站将不可避免地离线。如果可以在3000以上的端口上使用,请参见下面的说明。
我尝试删除LoadBalancer,这是我能想到的最佳解决方案。它具有以下缺陷:
还有以下好处:
externalIP
舵图。service
,可以根据请求的路径完全控制如何将请求路由到您的nginx-ingress
。假设您已经安装了Helm(如果您不遵循此处的步骤:Installing Helm on GKE),请创建一个ingress
为services
的{{1}}。
nginx-ingress
为您的路由创建入口定义。
type
然后使用
安装NodePort
找到集群的标签。
helm install \
--name nginx-ingress \
stable/nginx-ingress \
--set rbac.create=true \
--set controller.publishService.enabled=true \
--set controller.service.type=NodePort \
--set controller.service.nodePorts.http=30080 \
--set controller.service.nodePorts.https=30443
如果您的集群实例的名称类似于
# my-ingress-resource.yaml
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
name: reverse-proxy
namespace: production # Namespace must be the same as that of target services below.
annotations:
kubernetes.io/ingress.class: nginx
nginx.ingress.kubernetes.io/ssl-redirect: "false" # Set to true once SSL is set up.
spec:
rules:
- http:
paths:
- path: /api
backend:
serviceName: backend
servicePort: 3000
- path: /
backend:
serviceName: frontend
servicePort: 80
然后您的群集标记为kubectl apply -f my-ingress-resource.yaml
。
转到the GCP firewall page。 验证您是否在导航栏中选择了正确的项目。
单击“创建防火墙规则”。给规则起一个体面的名字。您可以将大多数设置保留为默认设置,但是将群集标记保留在“目标标记”下。将源IP范围设置为gcloud compute instances list
。在“协议和端口”下,将“允许所有”更改为“指定的协议和端口”。选中“ TCP”框,然后在输入字段中输入gke-cluster-1-pool-1-fee097a3-n6c8
gke-cluster-1-pool-1-fee097a3-zssz
。点击“创建”。
转到https://console.cloud.google.com/networking/addresses/并单击“保留静态地址”。给它起一个描述性的名称,然后选择正确的区域。选择正确的区域后,您应该能够单击“附加到”下拉列表,然后选择一个Kubernetes节点。点击“保留”。
保留静态IP后,通过查看External IP Address list找出授予了哪个静态IP。
将其复制到浏览器中,然后添加端口(对于HTTP,gke-cluster-1-pool-1-fee097a3
,对于HTTPS,0.0.0.0/0
)。您应该会看到您的网页。
答案 3 :(得分:0)
original source,但它包含我从未使用过的 Digital Ocean 详细信息。老实说,它救了我一命,并且可以使用 3000 以下的端口,但老实说,我不确定它是如何工作的。
我的设置是使用这个 Nginx ingress controller. 使用 helm 安装它,并为其提供一个配置文件:
$ helm install my-nginx ingress-nginx/ingress-nginx -f config.yaml
配置文件应包含:
controller:
kind: DaemonSet
hostNetwork: true
dnsPolicy: ClusterFirstWithHostNet
daemonset:
useHostPort: true
service:
type: ClusterIP
rbac:
create: true
您可以找到默认值 here,但我不知道如何理解该配置。
之后你可以创建你的入口 yaml:
apiVersion: networking.k8s.io/v1beta1
kind: Ingress
metadata:
name: web-app
annotations:
kubernetes.io/ingress.class: "nginx"
nginx.ingress.kubernetes.io/proxy-body-size: "100m"
cert-manager.io/cluster-issuer: "letsencrypt"
nginx.ingress.kubernetes.io/server-alias: "example.com"
labels:
app: web-app
spec:
tls:
- hosts:
- example.com
secretName: prod-certs
rules:
- host: example.com
http:
paths:
- backend:
serviceName: myservice
servicePort: 443
这是我的,可能对你不起作用,但试试吧!
它指向的服务入口规则是NodePort
类型:
apiVersion: v1
kind: Service
metadata:
name: myservice
labels:
app: myservice
spec:
type: NodePort
ports:
- port: 443
targetPort: 80
但我相信 ClusterIP
也可以。
除此之外,其中一个 VM 具有公共静态 IP,我们将该 IP 用于我们的域名。
所以我相信这个过程是。域名转换为该静态 IP。然后流量到达入口控制器,我不知道这是如何工作的,但是在那里您的流量与某个规则匹配,并被重定向到服务。端口是在 Ingress 中定义的,因此您也可以使用 3000 个以下的端口,但我不知道这个“解决方案”在性能方面是如何工作的,而且我也不知道 Ingress 控制器如何接受未公开的流量。
设置 Ingress 可能是我经历过的最糟糕的经历之一,我实际上采用了这种混乱的方法,因为使用 LoadBalancer
服务类型更糟糕。祝你好运!