每个Pod都有一个IP地址,当使用Deployment控制器时,Pod的IP往往会动态变化。使用Service为一组功能相同的Pod提供单一不变的接入点资源,通过Service可以获得稳定的IP地址,且在Service生命周期内有效,与Pod的IP地址是否变化无关。
1.服务发现:防止Pod失联,新启动的Pod会向Service注册新的Pod_IP。
2.负载均衡:Service为一组功能相同的Pod定义访问规则,外部通过Service来访问到这一组Pod。
它们也是根据label和selector标签来建立关系。
Service里,
spec:
selector: #选择器对象
app: web #标签(可以有多个标签),用于匹配Pod里的标签
Pod里,
template:
labels:
app: web #Pod里的标签
在这里可以看到,只要带有app: web标签的Pod,都属于这个Service。
外部访问时,先访问到的是Service的IP(虚拟IP)。
可以通过kubectl expose -h | grep type来查看支持的类型,一般前三种比较常见。
[root@master-146 ~]# kubectl expose deployment web --port=80 --target-port=80 --name=web-svc --dry-run=client -o yaml
apiVersion: v1
kind: Service
metadata:
creationTimestamp: null
labels:
app: web
name: web-svc
spec:
ports:
- port: 80
protocol: TCP
targetPort: 80
selector:
app: web
status:
loadBalancer: {}
kubectl apply -f web-svc.yaml
kubectl get pod,svc
[root@master-146 ~]# kubectl apply -f web-svc.yaml
service/web-svc created
[root@master-146 ~]# kubectl get pod,svc
NAME READY STATUS RESTARTS AGE
pod/web-66bf4959f5-p9dn5 1/1 Running 0 4h51m
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
service/kubernetes ClusterIP 10.96.0.1 443/TCP 45h
service/web-svc ClusterIP 10.98.2.183 80/TCP 2s
集群内部访问测试:
[root@worker-144 ~]# curl 10.98.2.183
<html>
<head>
<title>Welcome to nginx!title>
<style>
body {
width: 35em;
margin: 0 auto;
font-family: Tahoma, Verdana, Arial, sans-serif;
}
style>
head>
<body>
<h1>Welcome to nginx!h1>
<p>If you see this page, the nginx web server is successfully installed and
working. Further configuration is required.p>
<p>For online documentation and support please refer to
<a href="http://nginx.org/">nginx.orga>.<br/>
Commercial support is available at
<a href="http://nginx.com/">nginx.coma>.p>
<p><em>Thank you for using nginx.em>p>
body>
html>
[root@master-146 ~]# kubectl expose deployment web --port=80 --type=NodePort --target-port=80 --name=web-svc --dry-run=client -o yaml
apiVersion: v1
kind: Service
metadata:
creationTimestamp: null
labels:
app: web
name: web-svc
spec:
ports:
- port: 80
protocol: TCP
targetPort: 80
selector:
app: web
type: NodePort
status:
loadBalancer: {}
yaml中增加type: NodePort
kubectl apply -f web-svc.yaml
[root@master-146 ~]# kubectl get pod,svc
NAME READY STATUS RESTARTS AGE
pod/web-66bf4959f5-p9dn5 1/1 Running 0 5h
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
service/kubernetes ClusterIP 10.96.0.1 <none> 443/TCP 45h
service/web-svc NodePort 10.98.2.183 <none> 80:32192/TCP 9m19s
这个时候就可以对外部提供访问服务了。
一般来说,node都是在内网进行部署应用的,外网不可以访问到。要实现这个过程:
(1).在一台可以访问外网的机器上做nginx反向代理,需要手动把可以给外网访问的内部节点添加到nginx里面。
(2).公有云的LoadBalancer,公有云一般都会有负载均衡控制器,外部直接连接这个负载均衡器,它会自动分配到相应的节点。
内部客户端使用Service的DNS名称作为外部DNS名称的别名。
如果需要对Pod进行分组,且不需要稳定的IP地址,就可以使用Headless服务。