1.service介绍
Service可以看作是一组提供相同服务的Pod对外的访问接口。借助Service,应 用可以方便地实现服务发现和负载均衡。
service默认只支持4层负载均衡能力,没有7层功能。(可以通过Ingress实现)
service的类型:
ClusterIP:默认值,k8s系统给service自动分配的虚拟IP,只能在集群内部访问。 NodePort:将Service通过指定的Node上的端口暴露给外部,访问任意一个NodeIP:nodePort都将路由到ClusterIP。 LoadBalancer:在 NodePort 的基础上,借助 cloud provider 创建一个外部的负载均衡器,并将请求转发到 :NodePort,此模式只能在云服务器上使用。 ExternalName:将服务通过 DNS CNAME 记录方式转发到指定的域名(通过spec.externlName 设定)
2.IPVS模式
安装服务 yum install -y ipvsadm lsmod |grep ip_vs 
2.1更改ipvs模式
更改配置文件的模式为ipvs kubectl -n kube-system get cm  kubectl -n kube-system edit cm kube-proxy 其中将mode后 引号里面加 ipvs 
2.2更新pod
更新kube-proxy pod
kubectl get pod -n kube-system |grep kube-proxy |awk '{system("kubectl delete pod "$1" -n kube-system")}'
查看 ipvsadm -ln ip addr 后有vip mkdir service cd service/ vi service.yaml
apiVersion: v1
kind: Service
metadata:
name: web-service
spec:
ports:
- name: http
port: 80
targetPort: 80
selector:
app: nginx
type: ClusterIP
kubectl apply -f service.yaml #执行 kubectl get svc 查看信息  cp /root/pod/deployment/deployment.yaml . vi deployment.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
name: deployment
spec:
replicas: 3
selector:
matchLabels:
app: nginx
template:
metadata:
labels:
app: nginx
spec:
containers:
- name: nginx
image: myapp:v1
kubectl apply -f deployment.yaml kubectl get pod 查看pod kubectl describe svc web-service 查找ip  测试: curl 10.107.208.28/hostname.html 并 ipvsadm -ln 发现实现负载均衡 kubectl delete pod --all
3.service实现外部访问
3.1 NodePort方式
vi service.yaml
apiVersion: v1
kind: Service
metadata:
name: web-service
spec:
ports:
- name: http
port: 80
targetPort: 80
selector:
app: nginx
type: NodePort
kubectl apply -f service.yaml kubectl get svc 而且产生的端口在每个虚拟机都已经生成了! netstat -antlp|grep :30123   可以直接在外部访问测试:实现了负载均衡 
3.2metallb结合LoadBalancer
3.2.1.介绍
Kubernetes不提供网络负载均衡器的实现(LoadBalancer类型的服务)用于裸机集群。Kubernetes附带的Network LB的实现都是调用各种IaaS平台(GCP,AWS,Azure等)的粘合代码。如果您未在受支持的IaaS平台(GCP,AWS,Azure等)上运行,则LoadBalancers在创建时将无限期保持“待处理”状态。 裸机集群运营商只剩下两个较小的工具,即“ NodePort”和“ externalIPs”服务,可将用户流量引入其集群。这两个选项在生产用途上都有很大的缺点,这使裸金属集群成为Kubernetes生态系统中的二等公民。 MetalLB旨在通过提供与标准网络设备集成的Network LB实现来解决这种不平衡问题,从而使裸机群集上的外部服务也尽可能“正常运行”。
3.2.2部署
修改kube-proxy的配置
kubectl edit configmap -n kube-system kube-proxy
strictARP: true
 更新kube-proxy pod
kubectl get pod -n kube-system |grep kube-proxy | awk '{system("kubectl delete pod "$1" -n kube-system")}'
创建一个目录metallb专门用来存放metallb的文件:
cd
mkdir metallb
cd metallb
wget https://raw.githubusercontent.com/metallb/metallb/v0.10.2/manifests/namespace.yaml
wget https://raw.githubusercontent.com/metallb/metallb/v0.10.2/manifests/metallb.yaml
修改metallb.yaml文件   在私有仓库中创建一个新的公开项目metallb 将镜像下载好,平且上传至私有仓库  执行metallb.yaml清单:
kubectl apply -f metallb.yaml
kubectl get ns
查看metallb-system节点
kubectl -n metallb-system get pod
自动生成secrets memberlist 查看:
kubectl -n metallb-system get secrets

3.2.3.定义地址池
vi configmap.yaml
apiVersion: v1
kind: ConfigMap
metadata:
namespace: metallb-system
name: config
data:
config: |
address-pools:
- name: default
protocol: layer2
addresses:
- 172.25.76.10-172.25.76.20
执行configmap.yaml 查看到cm中的配置信息已读取
kubectl apply -f configmap.yaml
kubectl get cm -n metallb-system

3.2.4测试
我们创建一个svc进行测试
apiVersion: v1
kind: Service
metadata:
name: lb-svc
spec:
ports:
- name: http
port: 80
targetPort: 80
selector:
app: myapp
type: LoadBalancer
执行lb-svc.yaml并查看svc状态
kubectl apply -f lb-svc.yaml
kubectl get svc
且deployment.yaml的myapp pod也需要开着 可以看到分配到了前面定义的10-20之间的IP并且集群外部访问分配的IP实现负载均衡 
3.3 ExternalIP
需要外部添加IP到网卡中才可生效! 将lb-svc删掉
vi exc-ip.yaml
apiVersion: v1
kind: Service
metadata:
name: ex-service
spec:
selector:
app: myapp
ports:
- name: http
protocol: TCP
port: 80
targetPort: 80
externalIPs:
- 172.25.76.100
执行并查看svc
kubectl apply -f exc-ip.yaml
kubectl get svc
 查看当前配置的虚拟服务和RS的权重 ipvsadm -ln 可以看到172.25.76.100已经出现  但是此时在真机上访问172.25.76.100发现不能访问出现如下图情况:  后面解决发现,是因为没有在server2或者server3上添加172.25.76.100的IP地址,因为他不能自动解析地址,需要手动添加
ip addr add 172.25.76.100/24 dev eth0
然后访问就可以成功了
curl 172.25.76.100 
3.4.Externalname
通过给定域名访问解析
vi ex-svc.yaml
apiVersion: v1
kind: Service
metadata:
name: my-service
spec:
type: ExternalName
externalName: www.baidu.com
执行ex-svc.yaml后查看svc信息
kubectl apply -f ex-svc.yaml
kubectl get svc
 可以看到域名出现 我们dig查看详细解析A记录
dig -t my-service.default.svc.cluster.local. @10.96.0.10
 发现域名
3.5 Headless无头模式
以DNS记录的方式解析出被代理Pod的IP地址,不需要通过Ip地址访问,可直接访问服务名称
查看所有的pod并显示标签 
vi headless.yaml
apiVersion: v1
kind: Service
metadata:
name: websvc
spec:
ports:
- name: http
port: 80
targetPort: 80
selector:
app: myapp
clusterIP: None
应用配置,可以看到新创建了一个websvc的服务
kubectl apply -f headless.yaml
kubectl get svc
 查看websvc服务的域名解析,可以看到对应三个负载均衡服务器,测试访问,三个ip轮询应答
kubectl run demo -it --image=busyboxplus --restart=Never
curl websvc.default.svc.cluster.local./hostname.html
 使用下图命令,查看10.96.0.10服务的A记录 dig -t A websvc.default.svc.cluster.local. @10.96.0.10 
|