kubebuilderで作ったcrdを操作するのはcontroller-runtimeを使うのが楽
概要
k8sのリソースをCRUDする代表的な手順と言えば公式のライブラリであるclient-goですね。
これは deployment
なんかのk8sのデフォルトであるリソースや、client-go
で生成されたコードを使うCRDの場合には簡単に使えて便利なんですが、カスタムコントローラーを作るのに一般的に使われるkubebuilderは内部的にcontroller-runtimeってツールを使ってます。これが生成するpkgは client-go
と互換性が無い1ので自作したカスタムリソースの操作を client-go
からじゃできないです。
解決策は kubebuilder
で作られたCRDのリソースの操作には client-go
じゃなくて直接 controller-runtime
を使うことらしいです。
なので controller-runtime
をkubebuilderで生成したカスタムコントローラー外から使う方法を記します。
なお、良い例を見つけることができなかったので以下では基本的に私のコードを使って解説します。
具体的に
では実際にコードを書きましょう。
ライブラリ
まず必要になるライブラリをimportします。
4import (
5 "context"
6 "fmt"
7 "log"
8 "net/http"
9 "net/http/httputil"
10 "os"
11
12 metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
13 "k8s.io/apimachinery/pkg/runtime"
14
15 "sigs.k8s.io/controller-runtime/pkg/client"
16 "sigs.k8s.io/controller-runtime/pkg/client/config"
17
18 escv1alpha1 "github.com/koba1t/ESC/api/v1alpha1"
19)
controller-runtime
のクライアントライブラリだけでなく、k8s公式のクライアントライブラリもschemeやObject
の定義を利用するために必要です。
Schemeの設定
次にScheme
の設定をしましょう。
このScheme
はk8sのAPIオブジェクトをgolangの構造体にマッピングしたりするために使われます。
22var (
23 scheme = runtime.NewScheme()
24)
25
26func init() {
27 // init scheme
28 _ = escv1alpha1.AddToScheme(scheme)
29}
k8sのライブラリを使ってscheme
を新しく生成します。
ここで生成したscheme
にはCRDのリソースを扱う機能がまだ入っていないので、CRD側のライブラリで追加します。
clientの作成
次に k8sのリソースを操作するためのクライアントをcontroller-runtime
のライブラリ から作成しましょう。
54cl, err := client.New(config.GetConfigOrDie(), client.Options{Scheme: scheme})
k8s内で動かす場合は GetConfigOrDie() を使うことで kube-apiserver
にアクセスするための kubeconfig
を自動で設定してくれます。
ここで、client.New
の際に client.Options{Scheme: scheme}
を指定して、今回使用するCRDを追加したschemeを設定するのを忘れないようにしてください。これを指定しないとCRDのリソースが操作できません。2
k8sリソースの作成
後は作りたいリソースのObject
の形式の構造体を組み立てて、先程作成したクライアントでCreate
するだけです。
86 escuser := &escv1alpha1.Userland{
87 ObjectMeta: metav1.ObjectMeta{
88 Namespace: namespaceName,
89 Name: username,
90 },
91 Spec: escv1alpha1.UserlandSpec{
92 TemplateName: escTemplateName,
93 },
94 }
95
96 e := cl.Create(context.Background(), escuser)
97 if e != nil {
98 fmt.Printf("Userland create error: %v\n", e)
99 }
これで実際にkubernetesのリソースが作成されます。
k8sで動かすには
ちなみにCRDに限らずk8sのオブジェクトを操作するためには権限が必要になるので、Roleを作ってRoleBindingしたServiceAccountをコードを動かすコンテナから使えるようにする必要があります。
まとめ
kubebuilderで生成したCRDをcrudしようとした時、参考になる文献が無くてこまったので書きました。3
誰かの助けになれば幸いです。