2 [kustz] 先从模仿创建 Deployment、service、ingress开始

本文涉及的产品
容器服务 Serverless 版 ACK Serverless,317元额度 多规格
容器服务 Serverless 版 ACK Serverless,952元额度 多规格
简介: 2 [kustz] 先从模仿创建 Deployment、service、ingress开始

大家好, 我是老麦, 一个小运维。今天我们继续手写这个 kustz

文章内容并不是所有代码块都有详细描述。部分内容, 我觉得不太重要的就一笔带过了。每个代码片段都提供了文件路径, 可以自己到 Github 上查看。

https://github.com/tangx/kustz/tree/chapter/01-sample-deployment

我觉得今天的内容特基础, 但有相对比较重要, 因为我们之后所有的工作都是为了简化(或者说抽象) 这些 API 的配置。

image.png

2.1. [kustz] 定义字符串创建 Deployment

先做个假设

为了简单, 我们假定所管理的 Deployment 都是 单容器 的。

首先参考 kubectl create 命令

$ kubectl create deployment my-dep --image=busybox --replicas 1 --dry-run=client -o yaml

安装 client-go API

访问 client-go https://github.com/kubernetes/client-go

$ go get k8s.io/client-go@v0.25.4

这里直接选用最新版本 v0.25.4。对于其他版本的兼容, 留在以后再做。

定义 Kustz Config

参考 kubectl create 命令, 创建配置文件 kustz.yml 结构如下

# kustz.yml
namespace: demo-demo
name: srv-webapp-demo
service:
  name: nginx
  image: docker.io/library/nginx:alpine
  replicas: 2

在 service 中添加了 name 字段, 这是在 kubectl create 命令中没有的。后者直接使用了镜像名称作为 name 的值。

由于我们的设计只有一个容器, 这里也可以 省略或使用默认值。这里增加字段 完全是为了展示凑 API

/pkg/kustz/kustz.go 中创建 Config, 对应所有字段。

type Config struct {
 Name      string  `json:"name"`
 Namespace string  `json:"namespace"`
 Service   Service `json:"service"`
}
type Service struct {
 Name     string `json:"name"`
 Image    string `json:"image"`
 Replicas int32  `json:"replicas"`
}

拼凑 Deployment API

从这个标题就可以看出来, 这里就就没什么难度了, 就是把 kustz.Config 中的所有字段全部放在 Deployment API 中。

kustz.Config 添加 KubeDeployment 方法, 在 /pkg/kustz/k_deployment.go 中。

func (kz *Config) KubeDeployment() *appv1.Deployment {
 return &appv1.Deployment{
  TypeMeta: metav1.TypeMeta{
   Kind:       "Deployment",
   APIVersion: "apps/v1",
  },
  ObjectMeta: metav1.ObjectMeta{
   Name:      kz.Name,
   Namespace: kz.Namespace,
   Labels:    CommonLabels(*kz),
  },
  Spec: appv1.DeploymentSpec{
   Replicas: &kz.Service.Replicas,
   Template: kz.KubePod(),
   Selector: &metav1.LabelSelector{
    MatchLabels: CommonLabels(*kz),
   },
  },
 }
}

可以看到, 拼凑主要由 3 部分, 都是很熟悉的字段。

  1. TypeMeta: Deployment 的信息申明
  2. ObjectMeta: 应用服务 的信息申明
  3. Spec: 就是具体信息了。

如果你看的够仔细,可以在 Spec 中发现 Template 字段就开始 套娃 了。

KubeDeployment 中调用了 /pkg/kustz/k_pod.go 中的 KubePod 方法。

func (kz *Config) KubeDeployment() *appv1.Deployment {
 return &appv1.Deployment{
  Spec: appv1.DeploymentSpec{
   // ... 省略
   Template: kz.KubePod(),
  },
 }
}

KubePod 中调用了 /pkg/kustz/k_container.go 中的 KubeContainer 方法。

func (kz *Config) KubePod() corev1.PodTemplateSpec {
 return corev1.PodTemplateSpec{
  // ... 省略
  Spec: corev1.PodSpec{
   Containers: kz.KubeContainer(),
  },
 }
}

最后, 在 KubeContainer 方法中, 创建了最里面的 container 信息。

func (kz *Config) KubeContainer() []corev1.Container {
 if kz.Service.Name == "" {
  kz.Service.Name = kz.Name
 }
 // ...省略
 return []corev1.Container{c}
}

前面我们说到过 kz.Service.Name 为了展示 API 的拼凑。为了以后使用方便, 这里我们设置其默认值为应用服务名 kz.Name

公共标签

在 Kubernetes 中, 不同 API 之间的关系都是通过 标签选择 关联的。为了方便, 在 /pkg/kustz/common.go 中使用函数 CommonLabels() 创建公共标签, 方便关联。

文件解析

细心的你可以已经发现了, 明明配置文件用的是 yaml 格式, 但是在 Config 中的标签却是 json:"name"

这里只是为了 单纯 为了保障 yaml 库一致, 在 /pkg/kubeutils/yaml.go 中使用了 sigs.k8s.io/yaml 库而已, 这个库可以兼容 json, yaml 标签。

测试

进入 kustz, 执行命令

$ go test -v .
$ kubectl create deployment srv-webapp-demo --image=nginx -n demo-demo --dry-run=client -o  yaml

对比二者内容, 基本上完全一样了。

2.2. [kustz] 定义字符串创建 Service

image.png

大家好, 我是老麦, 一个小运维。 今天我们为 kustz 增加 Service 功能。

代码还是在 Github, 文章中有不清楚的可以上去看看

https://github.com/tangx/kustz/tree/chapter/02-define-strings-to-service

image.png

Kube Service

通过 kubectl create service 命令可以看到, service 的模式还是挺多的。

$ kubectl create service -h
Create a service using a specified subcommand.
Aliases:
service, svc
Available Commands:
  clusterip      Create a ClusterIP service
  externalname   Create an ExternalName service
  loadbalancer   Create a LoadBalancer service
  nodeport       Create a NodePort service

除了以上列出来的四种之外, 还用一种 Headless Service(https://kubernetes.io/docs/concepts/services-networking/service/#headless-services)。

Headless Service 是当 类型 为 ClusterIP,且 IP 值为 None。 所以是 Cluster IP 的一种特殊情况。

# 创建一个新的 ClusterIP service
$ kubectl create service clusterip my-cs --tcp=5678:8080
# 创建一个新的 ClusterIP service (headless 模式)
$ kubectl create service clusterip my-cs --clusterip="None"

Service API 中的 Port

如果你之前留意过 Service API, 你就应该会发现 API 中带有 port 的字段就有 3 个。 弄清楚他们分别对应什么这点很重要

先来看看一个 NodePort 的 API。

# $ kubectl create service nodeport my-cs --tcp=80:8080 --dry-run=client -o yaml
apiVersion: v1
kind: Service
  # ... 省略
spec:
  ports:
  - name: 80-8080
    nodePort: 18080
    port: 80
    protocol: TCP
    targetPort: 8080
  selector:
    app: my-cs
  type: NodePort

对于 nodePort, port, targetPort 这三个名词如果还不能直接回答的话, 认真记住下面这张图。

image.png

  1. 集群外部用户通过 nodePort -> port -> targetPort
  2. 集群内部用户通过 port -> targetPort
相关实践学习
通过Ingress进行灰度发布
本场景您将运行一个简单的应用,部署一个新的应用用于新的发布,并通过Ingress能力实现灰度发布。
容器应用与集群管理
欢迎来到《容器应用与集群管理》课程,本课程是“云原生容器Clouder认证“系列中的第二阶段。课程将向您介绍与容器集群相关的概念和技术,这些概念和技术可以帮助您了解阿里云容器服务ACK/ACK Serverless的使用。同时,本课程也会向您介绍可以采取的工具、方法和可操作步骤,以帮助您了解如何基于容器服务ACK Serverless构建和管理企业级应用。 学习完本课程后,您将能够: 掌握容器集群、容器编排的基本概念 掌握Kubernetes的基础概念及核心思想 掌握阿里云容器服务ACK/ACK Serverless概念及使用方法 基于容器服务ACK Serverless搭建和管理企业级网站应用
相关文章
|
Kubernetes 网络协议 数据安全/隐私保护
Kubernetes 的核心概念:Pod、Service 和 Namespace 解析
Kubernetes 的核心概念:Pod、Service 和 Namespace 解析
333 1
|
6月前
|
运维 Kubernetes Linux
Kubernetes详解(七)——Service对象部署和应用
Kubernetes详解(七)——Service对象部署和应用
74 3
|
负载均衡 Kubernetes 应用服务中间件
Deployment、Service资源
Deployment、Service资源
118 0
|
Kubernetes 负载均衡 应用服务中间件
k8s部署nginx(Pod、Deployment、Service)
k8s部署nginx(Pod、Deployment、Service)
2861 0
k8s部署nginx(Pod、Deployment、Service)
|
存储 Kubernetes 调度
【云原生】k8s核心概念—Pod & Controller & Service & Serect & ConfigMap介绍——20230213
【云原生】k8s核心概念—Pod & Controller & Service & Serect & ConfigMap介绍——20230213
271 0
|
存储 Kubernetes 关系型数据库
【Kubernetes的Configmap、SecretMetric service及HPA、Wordpress应用Mysql主从PVPVCSCHPA】
【Kubernetes的Configmap、SecretMetric service及HPA、Wordpress应用Mysql主从PVPVCSCHPA】
118 0
|
JSON Kubernetes 安全
Kubernetes Admission Controller 简介 - 注入 sidacar 示例
Kubernetes Admission Controller 简介 - 注入 sidacar 示例
113 0
|
负载均衡 Perl
09-Kubernetes-Service入门
09-Kubernetes-Service入门
|
Kubernetes 负载均衡 网络协议
Kubernetes Service解析
我们都知道,在K8S集群中,每个Pod都有自己的私有IP地址,并且这些IP地址不是固定的。这意味着其不依赖IP地址而存在。例如,当我们因某种业务需求,需要对容器进行更新操作,则容器很有可能在随后的启动运行过程中被分配到其他IP地址。此外,在K8S集群外部看不到该Pod。因此,Pod若单独运行于K8S体系中,在实际的业务场景中是不现实的,故我们需要通过其他的策略去解决,那么解决方案是什么? 由此,我们引入了Serivce这个概念以解决上述问题。
111 0
|
JSON Kubernetes 监控
K8S之yaml 文件详解(pod、deployment、service)
K8S之yaml 文件详解(pod、deployment、service)
9091 3
K8S之yaml 文件详解(pod、deployment、service)