新建项目

go mod init elastic-web

kubebuilder init –domain com.puresai

kubebuilder create api --group sai --version v1 --kind ElasticWeb
/*
Copyright 2021.

Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at

http://www.apache.org/licenses/LICENSE-2.0

Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/

package v1

import (
"fmt"

"github.com/spf13/cast"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
)

type ElasticWebSpec struct {
// 镜像
Image string `json:"image"`
// 端口
Port *int `json:"port"`
// 单个 pod 的 qps
SingleQPS *int `json:"singleQPS"`
// 总 qps
TotalQPS *int `json:"totalQPS"`
}

// ElasticWebStatus defines the observed state of ElasticWeb
type ElasticWebStatus struct {
// 实际 qps
RealQPS *int `json:"realQPS"`
}

type ElasticWeb struct {
metav1.TypeMeta `json:",inline"`
metav1.ObjectMeta `json:"metadata,omitempty"`
Spec ElasticWebSpec `json:"spec,omitempty"`
Status ElasticWebStatus `json:"status,omitempty"`
}

func (web *ElasticWeb) String() string {
realQPS := ""
if web.Status.RealQPS == nil {
realQPS = "nil"
} else {
realQPS = cast.ToString(*web.Status.RealQPS)
}

return fmt.Sprintf("Image [%s], Port [%d], SingleQPS [%d], TotalQPS [%d], RealQPS [%s]", web.Spec.Image, *web.Spec.Port, *web.Spec.SingleQPS, *web.Spec.TotalQPS, realQPS)
}

// ElasticWebList contains a list of ElasticWeb
type ElasticWebList struct {
metav1.TypeMeta `json:",inline"`
metav1.ListMeta `json:"metadata,omitempty"`
Items []ElasticWeb `json:"items"`
}

func init() {
SchemeBuilder.Register(&ElasticWeb{}, &ElasticWebList{})
}

设置RBAC权限:

elasticweb_controller.go:

//+kubebuilder:rbac:groups=k8s.com.puresai,resources=elasticwebs,verbs=get;list;watch;create;update;patch;delete
//+kubebuilder:rbac:groups=k8s.com.puresai,resources=elasticwebs/status,verbs=get;update;patch
//+kubebuilder:rbac:groups=k8s.com.puresai,resources=elasticwebs/finalizers,verbs=update

// RBAC 新增
//+kubebuilder:rbac:groups=apps,resources=deployments,verbs=get;list;watch;create;update;patch;delete
//+kubebuilder:rbac:groups=core,resources=services,verbs=get;list;watch;create;update;patch;delete

代码比较枯燥,
主要方法都在controller,

  • getExpectReplicas
  • createServiceIfNotExists
  • createDeployment
  • Reconcile(默认)

可参考:https://github.com/puresai/kubebuilder-demo/tree/master/elasticWeb

编码完成后:

make install

kubectl api-versions|grep “k8s.com”

Kubebuilder2

最后可以执行

make run

apiVersion: v1
kind: Namespace
metadata:
name: sai-test
labels:
name: test
---

apiVersion: k8s.com.puresai/v1
kind: ElasticWeb
metadata:
namespace: sai-test
name: elasticweb-sample
spec:
# Add fields here
image: nginx:1.20.2-alpine
port: 80
singleQPS: 1000
totalQPS: 8800

kubectl apply -f config/samples/k8s_v1_elasticweb.yaml


参考: