MetalLB 是一个用于裸机 Kubernetes 集群的负载均衡器实现,使用标准路由协议。k8s 并没有为裸机集群实现负载均衡器,因此我们只有在以下 IaaS 平台(GCP, AWS, Azure)上才能使用 LoadBalancer 类型的 service。
因此裸机集群只能使用 NodePort 或者 externalIPs service 来对面暴露服务,然而这两种方式和 LoadBalancer service 相比都有很大的缺点,而 MetalLB 的出现就是为了解决这个问题。
我们就来看看metallb的部署
1.部署要求
1.1.需要 Kubernetes v1.13.0 或者更新的版本
1.2.集群中的 CNI 要能兼容 MetalLB,像常见的 Flannel、Cilium 等都是兼容的,Calico 的话大部分情况都兼容,BGP 模式下需要额外处理
1.3.提供一下 IPv4 地址给 MetalLB 用于分配,一般在内网使用,提供同一网段的地址即可。
1.4.BGP 模式下需要路由器支持 BGP
1.5.L2 模式下需要各个节点间 7946 端口联通
2.metallb的部署
我的k8s集群是hyper-v开的虚拟机进行k8s部署,使用的k8s是1.32.9,calico使用的是v3.29.1,宿主机IP:192.168.0.105,虚拟机IP:192.168.0.180。
我们直接下载metallb部署的yaml进行部署即可,比较简单
METALLB_VERSION="v0.15.2" # metallb 版本
curl -o metallb-native.yaml https://raw.githubusercontent.com/metallb/metallb/${METALLB_VERSION}/config/manifests/metallb-native.yaml然后就可以直接部署
kubectl apply -f metallb-native.yaml部署后我们可以检查以下两个POD是否正常启动

3.配置metallb ip池
根据第一条的要求,我们本地使用的L2模式进行部署,首先创建metallb-config.yaml文件,内容如下
apiVersion: metallb.io/v1beta1
kind: IPAddressPool
metadata:
  name: metallb-ip-pool
  namespace: metallb-system
spec:
  addresses:
  - 192.168.0.190-192.168.0.199
  autoAssign: true
  avoidBuggyIPs: false
---
apiVersion: metallb.io/v1beta1
kind: L2Advertisement
metadata:
  name: l2-advertisement
  namespace: metallb-system
spec:
  ipAddressPools:
  - metallb-ip-poolIP地址池可以根据自己的实际情况进行配置,一些字段说明
CIDR表示法:192.168.10.0/24
显式范围:192.168.9.1-192.168.9.5
IPv6支持:fc00:f853:0ccd:e799::/124
autoAssign字段:布尔值,控制是否自动分配地址,默认为true。设置为false时可保留特定地址池供手动分配。
avoidBuggyIPs字段:避免使用以.0和.255结尾的问题IP地址,默认为false。然后提交yaml文件
kubectl apply -f metallb-config.yaml然后查询下ipaddresspools资源
kubectl get ipaddresspools -n metallb-system
NAME              AUTO ASSIGN   AVOID BUGGY IPS   ADDRESSES
metallb-ip-pool   true          false             ["192.168.0.190-192.168.0.199"]4.创建测试POD进行测试
然后我们创建一个nginx测试页面进行测试下,test-nginx.yaml内容如下
apiVersion: apps/v1
kind: Deployment
metadata:
  name: test-nginx
  namespace: default
spec:
  replicas: 1
  selector:
    matchLabels:
      name: test-nginx
  template:
    metadata:
      labels:
        name: test-nginx
    spec:
      # hostNetwork: true
      containers:
      - name: test-nginx
        image: docker.io/library/nginx:latest
        imagePullPolicy: IfNotPresent
---
apiVersion: v1
kind: Service
metadata:
  name: nginx-service
spec:
  selector:
    name: test-nginx
  ports:
    - protocol: TCP
      port: 80
      targetPort: 80
  type: LoadBalancer
  #loadBalancerIP: "192.168.0.199"然后接着我们查看svc
kubectl get svc -A -o wide
这个时候我们看到已经把192.168.0.190分配给这个svc,使用curl 192.168.0.190命令可以直接获取到nginx的默认页面
5.遇到的问题
但是接着我们发现问题了,宿主机上直接访问192.168.0.190却访问不了。
我们使用arp -a查询arp表中没有到192.168.0.190的条目,于是手工添加了一条,就可以正常访问,这个可能是我hyper-v虚拟机的问题,直接在我的宿主机使用powershell执行以下两条命来添加arp条目。
Get-NetIPAddress | Where-Object {$_.IPAddress -eq "192.168.0.105"} | Format-Table IPAddress, InterfaceAlias, InterfaceIndex#查询到的vEthernet (WLAN)就是我的hyper-v虚拟交换机,00-15-5d-00-69-00是虚拟机网卡的mac地址 netsh interface ipv4 set neighbors "vEthernet (WLAN)" "192.168.0.190" "00-15-5d-00-69-00"
然后再次查询arp表,看到192.168.0.190已经绑定了。

再次使用宿主机访问192.168.0.190就可以看到nginx默认页面了。
6.其他配置
上面提到了我们网络使用的是L2,如果是要使用bgp模式那么metallb-config.yaml文件的配置到如下
apiVersion: metallb.io/v1beta1
kind: IPAddressPool
metadata:
  name: default
  namespace: metallb-system
spec:
  addresses:
  - 192.168.0.190-192.168.0.199
  autoAssign: true
---
apiVersion: metallb.io/v1beta1
kind: BGPAdvertisement
metadata:
  name: default
  namespace: metallb-system
spec:
  ipAddressPools:
  - default
  communities:
  - no-advertise注意需要路由器支持 BGP,没有的话我们可以使用frr替代,还有一些其他配置,实际需要的时候再进行研究。
内容版权声明:除非注明,否则皆为本站原创文章。
转载注明出处:https://sulao.cn/post/1144
相关阅读
- k8s集群部署gpu-operator支持gpu节点自动发现和gpu上报
 - k8s节点多网卡下指定某一个ip为节点INTERNAL-IP
 - k8s使用SA和Secret配置私有仓库镜像拉取凭证
 - k8s使用flannel作为CNI网络插件
 - k8s中harbor-database-0日志报Permissions should be u=rwx (0700)的处理方法
 - k8s使用helm部署harbor镜像仓库并使用nodeport方式暴露
 - k8s集群部署prometheus/node-exporter/dcgm-exporter
 - k8s中calico匹配多种网络接口名字的方法
 - ubuntu22.04使用containerd部署k8s单master集群
 - ubuntu22.04下k8s集群kube-proxy从iptables切换到ipvs模式
 
                                
评论列表