README-ZH.md
1 # Controller 示例 2 3 这个示例演示了如何使用生成的 clientset、informer 和 lister 来操作 BatchSandbox 和 Pool 自定义资源。 4 5 ## 功能介绍 6 7 ### 1. Clientset (客户端集) 8 用于直接与 Kubernetes API Server 交互,执行 CRUD 操作: 9 - **Create**: 创建新的资源 10 - **Get**: 获取特定资源 11 - **List**: 列出所有资源 12 - **Update**: 更新现有资源 13 - **Delete**: 删除资源 14 15 ### 2. Informer (通知器) 16 用于监听资源变化并维护本地缓存: 17 - 自动监听 API Server 的资源变化 18 - 触发事件处理器 (Add/Update/Delete) 19 - 维护资源的本地缓存,减少 API Server 压力 20 21 ### 3. Lister (列表器) 22 用于从 Informer 的本地缓存中读取资源: 23 - 高性能的本地缓存读取 24 - 避免频繁访问 API Server 25 - 支持按命名空间和标签过滤 26 27 ## 运行示例 28 29 ### 前提条件 30 1. 已安装 CRD 定义到 Kubernetes 集群 31 2. 有访问集群的 kubeconfig 文件 32 33 ### 安装 CRD 34 ```bash 35 # 从项目根目录运行 36 kubectl apply -f config/crd/bases/ 37 ``` 38 39 ### 运行示例程序 40 ```bash 41 # 使用默认 kubeconfig (~/.kube/config) 42 go run examples/controller/main.go 43 44 # 或指定 kubeconfig 路径 45 go run examples/controller/main.go -kubeconfig=/path/to/kubeconfig 46 ``` 47 48 ## 示例输出 49 50 程序将执行以下操作: 51 52 1. **创建 Pool 资源** 53 ``` 54 Successfully created Pool: example-pool 55 ``` 56 57 2. **获取 Pool 资源** 58 ``` 59 Successfully retrieved Pool: example-pool, PoolMin: 2, PoolMax: 10 60 ``` 61 62 3. **列出所有 Pool 资源** 63 ``` 64 Found 1 Pool(s): 65 - example-pool (PoolMin: 2, PoolMax: 10) 66 ``` 67 68 4. **更新 Pool 资源** 69 ``` 70 Successfully updated Pool: example-pool, new PoolMax: 20 71 ``` 72 73 5. **创建 BatchSandbox 资源** 74 ``` 75 Successfully created BatchSandbox: example-batchsandbox, Replicas: 3 76 ``` 77 78 6. **获取和更新 BatchSandbox** 79 ``` 80 Successfully updated BatchSandbox: example-batchsandbox, new Replicas: 5 81 ``` 82 83 7. **使用 Lister 从缓存读取** 84 ``` 85 Retrieved Pool from cache: example-pool, PoolMax: 20 86 Found 1 BatchSandbox(es) from cache 87 ``` 88 89 8. **清理资源** 90 ``` 91 Successfully deleted BatchSandbox: example-batchsandbox 92 Successfully deleted Pool: example-pool 93 ``` 94 95 ## 代码结构 96 97 ``` 98 main.go 99 ├── Controller struct # 控制器结构 100 ├── NewController() # 创建控制器并注册事件处理器 101 ├── DemonstrateClientsetUsage() # 演示 Clientset CRUD 操作 102 └── DemonstrateListerUsage() # 演示 Lister 缓存读取 103 ``` 104 105 ## 关键概念 106 107 ### Clientset vs Lister 108 109 **何时使用 Clientset:** 110 - 需要创建、更新或删除资源 111 - 需要获取资源的最新状态 112 - 执行写操作 113 114 **何时使用 Lister:** 115 - 只需要读取资源 116 - 可以接受轻微的数据延迟 117 - 需要高性能的批量读取 118 - 减少 API Server 负载 119 120 ### Informer 事件处理 121 122 Informer 会在资源变化时触发相应的事件处理器: 123 ```go 124 AddFunc: func(obj interface{}) { 125 // 资源被创建时调用 126 } 127 UpdateFunc: func(old, new interface{}) { 128 // 资源被更新时调用 129 } 130 DeleteFunc: func(obj interface{}) { 131 // 资源被删除时调用 132 } 133 ``` 134 135 ## 生产环境建议 136 137 1. **使用 Lister 而不是频繁调用 Clientset.Get()** 138 - Lister 从本地缓存读取,性能更好 139 - 减少对 API Server 的压力 140 141 2. **正确处理 Informer 重新同步** 142 - 设置合理的 resync 周期 (如 30 秒) 143 - 在事件处理器中使用幂等操作 144 145 3. **使用 Workqueue 处理事件** 146 - 避免在事件处理器中执行耗时操作 147 - 使用 workqueue 实现重试机制 148 149 4. **处理资源版本冲突** 150 - Update 操作时使用 optimistic locking 151 - 捕获 Conflict 错误并重试 152 153 ## 扩展阅读 154 155 - [Kubernetes Client-go 文档](https://github.com/kubernetes/client-go) 156 - [编写 Kubernetes 控制器](https://kubernetes.io/docs/concepts/extend-kubernetes/api-extension/custom-resources/) 157 - [Sample Controller](https://github.com/kubernetes/sample-controller)