- 介绍了Kubernetes API的基础知识并深入讲解API服务器的内部结构。
- 学习Go语言的Kubernetes编程接口,包括Kubernetes API对象。
- 学习自定义资源,它是Kubernetes生态系统中核心的扩展工具。
- 使用代码标签控制Kubernetes代码生成器为自定义资源生成代码时的行为。
- 编写自定义的控制器和Operator,并为部署到生产环境中做好准备。
- 通过自定义API服务器,扩展Kubernetes的API层。
如果你打算开发原生Kubernetes应用,本书将成为你好的向导。本书面向开发者和应用运维管理员介绍如何构建原生Kubernetes应用程序,这类应用可直接通过API服务器查询或更新资源的状态。AWS开发倡导者Michael Hausenblas和Red Hat首席软件工程师Stefan Schimanski将介绍这类应用的特性并向你展示如何编写Kubernetes程序来构建它们。
你将学到Kubernetes的基础构件,包括client-go API库以及自定义资源。你只需要具备一些初级的开发知识和系统管理工具和实践经验(包括包管理、Go语言和Git)即可上手。
前言
欢迎来到Kubernetes 编程的世界, 感谢你选择本书与我们一同探索Kubernetes 编程的奥秘。在开始深入讨论之前,我们先要解决一些管理和组织方面的问题,还将与你分享一些编写本书时的心得和体会。
目标读者
如果你是一位即将进行云原生(Cloud-Native)应用开发的开发人员,或是想从Kubernetes 中获得收益的应用管理员或运维人员。由于Kubernetes 原生配置和功能无法满足你的需求,所以你想要学习如何对其进行扩展。那很好,你就是本书的目标读者。
为何编写本书
本书的两位作者都是从2015 年初开始使用Kubernetes 的, 同时还教授Kubernetes 课程,进行相关的写作并向社区作贡献。我们为Kubernetes 开发了一些工具和应用,并多次开设Kubernetes 相关的研讨班。有一天,我们问自己,为什么不写一本书呢?通过写书可以让更多的人在不同的地方按自己的进度来学习Kubernetes 编程。因此,我们就创作了本书。希望你能在读书的过程中收获快乐,就像我们在写作时所收获的快乐一样。
生态系统
总体来说,我们现在所处的时代仍是Kubernetes 生态的早期。2018 年初,Kubernetes 逐渐成为容器(及其生命周期)管理领域的工业标准,但是仍然缺少一些基于实践经验的指导去指引开发者编写原生Kubernetes 应用。虽然一些基本的组件,比如client-go、自定义资源(Custom Resource)和云原生编程语言都已经出现了,但是相关的知识仍然十分零碎,它们存在于人们的经验中,分散在各种Slack 频道和StackOverflow 的回答中。
本书写作之时,Kubernetes 的版本是1.15。书中例子的代码是基于1.14的库来编写的,编译后应该可以在低版本(但不低于1.12)的Kubernetes 上运行。部分CRD 相关的高级功能需要1.13 或1.14 版本的Kubernetes 才能正常运行,第9 章介绍的CRD 转换在1.15 版本的Kubernetes 上才能运行。如果你没有足够新的集群用于测试,我们强烈推荐你在本地运行Minikube或kind 来进行测试。
你需要了解的技术
本书是一本中等难度的技术书籍,阅读本书需要理解很多开发和系统管理的概念。在深入具体内容之前,你需要先复习以下知识。
包管理
本书中用到工具常常需要你安装一些软件包才能满足其依赖。了解你所使用的操作系统中的包管理模式是的技能。比如Ubuntu/Debian 系统中的apt、CentOS/RHEL 系统中的yum、macOS 上的port 或brew。不管是哪一种,你都需要了解如何使用它们对软件包进行安装、升级或卸载操作。
Git
Git 已经成为分布式版本控制的标准。如果你熟悉CVS 和SVN,但还没用过Git,那么你还需要重新学习Git。Jon Loeliger 和Matthew McCullough所著的Version Control with Git(OReilly)是一本很好的入门书。与Git 配套的还有GitHub 网站,在上面你可以托管自己的Git 仓库。有关GitHub 你还可以参考其培训课程和交互式教程。
Go 语言
Kubernetes 是用Go 语言(http://golang.org)来编写的。在过去的几年中,Go 成为了很多创业公司和系统相关的开源项目的新型开发语言。本书不会教授Go 语言本身的知识,但会介绍如何用Go 语言来开发Kubernetes 应用。有很多渠道可以学习Go,比如Go 语言网站上的在线文档、博客文章、演讲和各种图书。
排版约定
在本书中,使用以下排版约定:
斜体(Italic)
表示新名词、URL、电子邮件地址、文件名以及文件扩展名。
等宽字体(Constant width)
表示程序代码,以及在正文中引用变量、函数名称、数据类型、环境变量、语句、关键字等代码中的元素。还用于展示命令和命令行的输出。
粗体等宽字体(Constant width bold)
表示需要用户输入的命令或其他文本。
斜体等宽字体(Constant width italic)
表示需要替换成用户自定义的值或根据上下文决定的值。
使用示例代码
本书的目的是帮助你完成工作。本书中使用的示例代码可以从GitHub(https://github.com/programming-kubernetes)中找到。
总的来说,你可以在自己的程序或文档中使用本书所提供的示例代码。如果不是对这些代码进行大规模的分发,就不需要联系我们获取授权。比如,编写一个程序,使用了本书中几段示例代码是不需要授权的。出售或分发包含OReilly 图书完整示例代码的CD-ROM 则需要授权。引用书中的部分内容或示例代码来回答问题不需要授权。在你的产品文档中包含本书中大量的示例代码则需要授权。
我们不强制要求署名,但如果你这么做,我们深表感激。署名一般包括书名、作者、出版社和书号(ISBN)。例如:Programming Kubernetes by Michael Hausenblas and Stefan Schimanski (OReilly). Copyright 2019 Michael Hausenblas and Stefan Schimanski. 。
如果你觉得对示例代码的使用超出了合理的方式或上述许可范围,可以与我们联系:permissions@oreilly.com。
Kubernetes 清单文件、代码示例和其他在本书中使用的脚本都可以从GitHub获取。你可以复制这些代码仓库,按照不同的章节和内容,直接使用这些代码。
OReilly 在线学习平台(OReilly Online Learning)
近40 年来,OReilly Media 致力于提供技术和商业培训、知识和卓越见解,来帮助众多公司取得成功。
我们拥有独一无二的专家和革新者组成的庞大网络,他们通过图书、文章、会议和我们的在线学习平台分享他们的知识和经验。OReilly 的在线学习平台允许你按需访问现场培训课程、深入的学习路径、交互式编程环境,以及OReilly 和200 多家其他出版商提供的大量文本和视频资源。有关的更多信息,请访问http://oreilly.com。
联系我们
请将有关本书的建议和问题发送给出版社:
美国:
OReilly Media, Inc.
1005 Gravenstein Highway North
Sebastopol, CA 95472
中国:
北京市西城区西直门南大街2号成铭大厦C座807室(100035)
奥莱利技术咨询(北京)有限公司
我们为本书提供了一个网页,上面有勘误表、示例和其他相关的信息,请访问:https://oreil.ly/pr-kubernetes。
有关本书的建议或者技术问题,请发邮件到 bookquestions@oreilly.com。
相关其他图书、讲座、会议、新闻的信息,请访问我们的网站:http://www.oreilly.com。
我们的Facebook:http://facebook.com/oreilly。
我们的Twitter:http://twitter.com/oreillymedia。
我们的YouTube:http://www.youtube.com/oreillymedia。
致谢
先要感谢的是Kubernetes 社区,是他们创造了如此出色的软件。Kubernetes社区中的人都非常出色,他们对任何事都有着开放的心态、对人亲切,并乐于助人。还要感谢本书的技术审阅者:Ahmed Belgana、Michael Gasch、Dimitris Gkanatsios、Mingding Han、Jess Males、Max Neunhffer、Ewout Prangsma 和Adrien Trouillaud。你们提供了非常有价值且易于实施的建议,从而使本书更易读、对读者也更有用。感谢你们所花费的时间和付出的努力。Michael 想深深地感谢一直支持着他的棒的家庭: 聪明有趣的妻子Anneliese,孩子们Saphira、Ranya 和Iannis,还有小狗Snoopy。
Stefan 想感谢他的妻子Clelia 在写作本书时对他的支持和鼓励。没有她的支持,这本书就不可能完成。如果在书中发现错别字,那很有可能是我的两只可爱的小猫Nino 和Kira 所贡献的。
后,还要特别感谢OReilly 的团队,尤其是Virginia Wilson 在本书出版过程中对我们的激励,保证了本书能够保质保量按时出版。
Michael Hausenblas是Amazon Web Service容器开发领域的倡导者。他拥有大规模数据处理和容器编排方面的经验,在倡导和实施W3C和IETF标准化方面有着丰富的经验。
Stefan Schimanski是Red Hat的Go、Kubernetes和Open-Shift首席软件工程师,他专注于Kubernetes API服务器及其在自定义资源定义、API Machinery方面的实现,以及Kubernetes预发布仓库的管理。
目录
前言 .1
第1 章 概论 .7
1.1 什么是Kubernetes 编程? .7
1.2 一个实际的例子 10
1.3 扩展模式 11
1.4 控制器和Operator 12
1.4.1 控制循环. 13
1.4.2 事件 14
1.4.3 边沿触发与水平触发 17
1.4.4 改变集群对象或外部系统状态 20
1.4.5 乐观并发. 23
1.4.6 Operator 26
1.5 小结 28
第2 章 Kubernetes API 基础 .30
2.1 API 服务器 30
2.1.1 API 服务器的HTTP 接口 31
2.1.2 API 术语 . 33
2.1.3 Kubernetes API 版本 . 36
2.1.4 声明式状态管理 . 37
2.2 通过命令行使用API . 38
2.3 API 服务器是如何处理请求的 43
2.4 小结 47
第3 章 client-go 基础 49
3.1 代码仓库 49
3.1.1 客户端库. 49
3.1.2 Kubernetes API 类型 . 51
3.1.3 API Machinery . 52
3.1.4 创建并使用客户端对象 53
3.1.5 版本与兼容性 56
3.1.6 API 版本与兼容性保证 59
3.2 Go 语言中的Kubernetes 对象 62
3.2.1 TypeMeta 63
3.2.2 ObjectMeta 67
3.2.3 规格与状态 68
3.3 客户端集合 . 68
3.3.1 状态子资源:UpdateStatus 71
3.3.2 列表与删除 71
3.3.3 Watch 72
3.3.4 客户端扩展 73
3.3.5 客户端选项 73
3.4 Informer 和缓存 75
3.5 深入API Machinery 83
3.5.1 型别 83
3.5.2 资源 83
3.5.3 REST 映射 . 84
3.5.4 Scheme 86
3.6 Vendor 机制 88
3.6.1 glide 88
3.6.2 dep . 89
3.6.3 Go 模块 90
3.7 小结 92
第4 章 使用自定义资源 93
4.1 服务发现信息 95
4.2 类型定义 97
4.3 自定义资源的高级功能 . 100
4.3.1 自定义资源合法性验证 100
4.3.2 短名字与类别 103
4.3.3 打印列 104
4.3.4 子资源 106
4.4 开发者眼中的自定义资源 . 111
4.4.1 动态客户端 . 112
4.4.2 强类型客户端 114
4.4.3 Operator SDK 和Kubebuilder 的controller-runtime 客户端 121
4.5 小结 . 123
第5 章 自动代码生成 124
5.1 为何需要代码生成器 124
5.2 调用代码生成器 125
5.3 通过标签控制代码生成器行为 127
5.3.1 全局标签 128
5.3.2 局部标签 129
5.3.3 deepcopy-gen 标签 131
5.3.4 runtime.Object 与DeepCopyObject 131
5.3.5 client-gen 标签 133
5.3.6 informer-gen 和lister-gen 135
5.4 小结 . 136
第6 章 编写Operator 的方案 137
6.1 准备工作 138
6.2 基于sample-controller 138
6.2.1 引导 139
6.2.2 业务逻辑 140
6.3 Kubebuilder . 148
6.3.1 引导 149
6.3.2 业务逻辑 155
6.4 Operator SDK . 160
6.4.1 引导 161
6.4.2 业务逻辑 163
6.5 其他方案 167
6.6 应用和未来的方向 168
6.7 小结 . 169
第7 章 发布控制器和Operator 170
7.1 生命周期管理和打包 170
7.1.1 打包:挑战 . 171
7.1.2 Helm 172
7.1.3 Kustomize 174
7.1.4 其他打包方法 176
7.1.5 打包的实践 177
7.1.6 生命周期管理 178
7.2 准生产部署 179
7.2.1 将权限设置正确 179
7.2.2 自动构建与测试 183
7.2.3 自定义控制器和可观测性 184
7.3 小结 . 187
第8 章 自定义API 服务器 . 189
8.1 自定义API 服务器的适用场景 189
8.2 示例:一个披萨店 192
8.3 架构:聚合 193
8.3.1 API 服务 195
8.3.2 自定义API 服务器的内部结构 198
8.3.3 委托身份认证和信任机制 200
8.3.4 委托授权 201
8.4 开发自定义API 服务器 . 204
8.4.1 选项、配置模式和启动基础设施 204
8.4.2 次启动 . 213
8.4.3 内部类型和转换 214
8.4.4 编写API 类型 218
8.4.5 转换 220
8.4.6 默认值处理 . 224
8.4.7 双程测试 226
8.4.8 验证 228
8.4.9 注册表与策略 231
8.4.10 安装API 237
8.4.11 准入 . 242
8.5 部署自定义API 服务器 . 253
8.5.1 部署清单文件 254
8.5.2 设置RBAC . 257
8.5.3 不安全地运行自定义API 服务器 259
8.5.4 证书与信任 . 262
8.5.5 共享etcd 265
8.6 小结 . 266
第9 章 自定义资源进阶 . 268
9.1 自定义资源版本 268
9.1.1 改进披萨餐厅 269
9.1.2 转换Webhook 架构 273
9.1.3 实现转换Webhook . 277
9.1.4 搭建HTTPS 服务器 278
9.1.5 部署转换Webhook . 285
9.1.6 观察实际转换过程 286
9.2 准入Webhook . 290
9.2.1 餐馆示例中的准入需求 291
9.2.2 准入Webhook 架构 292
9.2.3 注册准入Webhook . 295
9.2.4 实现准入Webhook . 296
9.2.5 准入Webhook 实战 302
9.3 结构化Schema 与CRD 的未来 . 304
9.3.1 结构化Schema . 305
9.3.2 剪裁或保留不能识别的字段 307
9.3.3 控制剪裁 308
9.3.4 IntOrString 和RawExtensions 310
9.3.5 默认值 311
9.4 小结 . 313
附录 资源 . 315
作者介绍 319
封面介绍 319