Kubernetes 弃用策略

Kubernetes 是一个拥有许多组件和许多贡献者的大型系统。对于这样的大型系统,其功能集会随时间不断地演变,有时也可能会删除一个功能。这可能包括删除一个 API、一个参数或者甚至是一整个功能。为了避免破坏现有用户的使用,Kubernetes 遵循一个弃用策略来移除系统的一些元素。

本文档详细描述系统各方面的弃用策略。

弃用部分 API

由于 Kubernetes 是一个 API 驱动的系统,为了反映对问题域的深化理解,API 也会随着时间不断演变。Kubernetes API 实际上是一个 API 集合,称作 “API 组”,并且每个 API 组都是独立的版本。API 版本 分为3个主要部分,每个都有不同的弃用策略:

示例 规划
v1 GA (基本可用, stable)
v1beta1 Beta (预发布)
v1alpha1 Alpha (实验性)

一个给定的 Kubernetes 发布版本支持任意数量的 API 组和 API 版本。

以下规则管理 API 元素的弃用。包括:

  • REST 资源 (也叫做 API 对象)
  • REST 资源的字段
  • 枚举或常量值
  • 组件配置结构

这些规则只适用于官方正式版本,不适用 master 的任意提交或者分支版本。

规则 #1: 只能通过递增的 API 组版本来删除 API 元素。

一旦把一个 API 元素添加到 API 组的某个特定版本中,那么就不能在没有规划的情况下从该版本中移除或者对它的行为做出重大的改变。

注意:由于历史原因,目前有两个 “庞大的” API 组 - “core” (没有组名)和 “extensions”。资源将会逐渐从这些遗留 API 组转移到特定领域的 API 组中。

规则 #2: API 对象必须能够在一个发布版本的不同 API 版本中切换,而且不能有信息丢失,除非整个 REST 资源在某些版本中不存在。

例如,一个对象可以写成 v1,然后回读为 v2 并且再转换为 v1,最终生成的 v1 资源必须和原来的 v1 相同。v2 中的表示可能与 v1 不同,但是系统知道如何在两个方向之间进行转换。另外,任何在 v2 中添加的新字段必须能够和 v1 相互转换,这意味着 v1 可能需要添加一个等效字段或将其表示为注解。

规则 #3: 一个已规划的 API 版本可能至少要等到新的 API 版本稳定并且发布后才会弃用。

GA API 版本能够替代另一个 GA API 版本或者 beta 和 alpha API 版本。Beta API 版本可能不能替代 GA API 版本。

规则 #4: 除了每个规划中的最新 API 版本,旧的 API 版本必须在宣布弃用后继续支持一段时间,时间不少于:

  • GA: 1年或者2个发布版本 (选择最长的一个)
  • Beta: 3个月或者1个发布版本 (选择最长的一个)
  • Alpha: 没有要求

这最好能够用一个例子来说明。想象有一个 Kubernetes 发布版本 X,其支持一个特定的 API 组。大约每3个月有一个新的 Kubernetes 发布版本(一年4次)。以下表格描述在一系列的后续发布版本中哪个 API 组仍被支持。

发布版本 API 版本 注意事项
X v1
X+1 v1, v2alpha1
X+2 v1, v2alpha2
  • 移除 v2alpha1, "action required" relnote
X+3 v1, v2beta1
  • 移除 v2alpha2, "action required" relnote
X+4 v1, v2beta1, v2beta2
  • 弃用 v2beta1, "action required" relnote
X+5 v1, v2, v2beta2
  • 移除 v2beta1, "action required" relnote
  • 弃用 v2beta2, "action required" relnote
  • 弃用 v1, "action required" relnote
X+6 v1, v2
  • 移除 v2beta2, "action required" relnote
X+7 v1, v2
X+8 v1, v2
X+9 v2
  • 移除 v1, "action required" relnote

REST 资源 (也叫做 API 对象)

假定现在有一个需要被弃用的 REST 资源,名为 Widget,在以上的时间线中提供在 API v1 版本中。我们在 X+1 的发布中 记录 并且 宣布 其弃用。那么 Widget 资源将会继续存在 API v1 版本(已被弃用)但是不在 v2alpha1 中。Widget 必须存在并且保持可用直到 X+8(包含 X+8)。只有在 X+9 发布版本中,当 API v1 已经老化,Widget 资源才会被删除,同时其行为也被移除。

REST 资源的字段

与整个 REST 资源一样,API v1 中单独的字段必须要保持可用直到 API v1 版本被删除。但是和整个 REST 资源不同的是,API v2 可能对这个字段有不同的表达,只是这个表达要可以相互转化。例如,v1 中将要被弃用的名为 “magnitude” 的字段可能在 API v2 中命名为 “deprecatedMagnitude”。当 v1 被最终移除后,这个弃用字段才能从 v2 中移除。

枚举或常量值

与整个 REST 资源及其字段一样,一个在 API v1 中支持的常量必须存在并且保持可用,直到 API v1 被移除。

组件配置结构

组件配置在版本和管理上和 RETS 资源是一样的。

未来的工作

随着时间的推移,Kubernetes 将会出现更多细粒度的 API 版本,到时这些规则也需要做相应的适配。

弃用一个参数或 CLI

Kubernetes 系统是由几个不同的部件相互协作组成的。有时一个 Kubernetes 发布版本可能会移除这些部件的一些参数或者 CLI 命令(统称 “CLI 元素”)。这些独立的部件自然被分为两个组 - 面向用户和面向管理员的组件,这两者在弃用策略上稍有不同。除非一个参数有明显的 “alpha” 或者 “beta” 前缀,或者被文档标识为 “alpha” 或者 “beta”,否则认为它是 GA 版本。

CLI 元素实际上是系统 API 的一部分,但是它们没有像 REST API 一样进行版本化,它们的弃用规则如下:

规则 #5a: 面向用户组件的 CLI 元素(例如 kubectl)在它们宣布弃用后至少要保持:

  • GA: 1年或2个发布版本 (选择最长的一个)
  • Beta: 3个月或者1个发布版本 (选择最长的一个)
  • Alpha: 没有要求

规则 #5b: 面向管理员组件的 CLI 元素(例如 kubelet)在它们宣布弃用后至少要保持:

  • GA: 6个月或者1个发布版本 (选择最长的一个)
  • Beta: 3个月或者1个发布版本 (选择最长的一个)
  • Alpha: 没有要求

规则 #6: 在使用弃用的 CLI 元素时必须要发出警告(可选择禁用)

弃用一个功能或者行为

有时一个 Kubernetes 发布版本需要弃用一些非 API 或者 CLI 控制的系统功能或者行为。在这种情况下,弃用策略如下:

规则 #7: 被弃用的行为在宣布弃用后至少要保持一年可用。

这并不表示对系统的所有改变都遵循这个策略。这只适用于重大的、用户可见的行为,这些行为将会影响 Kubernetes 应用的正确性或者影响 Kubernetes 集群的管理,这些行为也在彻底清除中。

例外

没有策略能够覆盖所有可能的情况。本文档的策略会随着时间不断演变。实际上,存在并不是完全契合本策略的情况,或者有时本策略变成了一个严重的阻碍。这些情况需要和 SIG 或者项目负责人进行讨论,以找到最好的解决方案。需要时刻记住,Kubernetes 致力于成为一个尽最大可能不破坏用户使用的稳定的系统。例外情况将会在相关的发布公告中宣布。

译者:tianshapjq / 原文链接

K8S中文社区微信公众号

使用联邦服务进行跨集群服务发现

本文介绍了如何使用 Kubernetes 联邦服务跨多个 Kubernetes 集群部署通用服务。 这使您可以轻松地为 Kubernetes 应用程序实现跨集群服务发现和可用区容错。

前提要求

本指南假定您有一个已安装运行的 Kubernetes 集群联邦,如果没有,请转到集群联邦管理指南 以了解如何启动一个集群联邦(或让您的集群管理员安装一个)。其他教程, 例如 Kelsey Hightower 的这个教程也可以帮助您。

一般来说,你应对 Kubernetes 的工作原理有一个基本了解,特别是服务

概览

联邦服务的创建方式和传统Kubernetes Services非常相似, 只需进行一次 API 调用即可指定所需的服务属性。在联邦服务环境下,此API调用将定向到联邦API端点, 而不是 Kubernetes 集群 API 端点,联邦服务的API与传统 Kubernetes Services 的API 100%兼容

一旦创建,联邦服务自动:

  1. 在集群联邦底层的每个集群中创建对应的 Kubernetes 服务,
  2. 监视那些服务 “shards” (以及它们所在的集群)的健康状况,
  3. 在公共 DNS 提供商(例如 Google Cloud DNS 或 AWS Route 53 )中管理一组 DNS 记录, 从而确保您的联邦服务的客户端可以随时无缝地找到合适的健康服务端点,即使在集群可用区或区域中断的情况下也是如此。

在集群联邦内部的客户端(即 Pods ),如果集群联邦存在且健康,会自动在所在集群中找到集群联邦的本地分片, 如果不存在,将会寻找最接近健康的分片。

混合云功能

Kubernetes 集群联邦可以包含运行在不同云提供商(例如 Google Cloud ,AWS )中的集群,以及本地私有云(例如在 OpenStack 上)。 只需在适当的云提供商 和/或 地区创建您需要的所有集群,并且向联邦 API Server 注册每个集群的API端点和凭证(参考集群联邦管理指南了解详细信息)。

之后,您的应用程序和服务可以跨越不同的集群和云提供商,详情如下所述。

创建联邦服务

通常这样完成,例如:

kubectl --context=federation-cluster create -f services/nginx.yaml

’–context=federation-cluster’参数告诉 kubectl 使用合适的凭证将请求提交给联邦 API 端点。 如果你还没有配置这样的上下文,访问集群联邦管理指南或管理教程 其中之一了解如何做到这一点。

如上所述,联邦服务将自动在联邦底层的所有集群中创建和维护对应的 Kubernetes 服务。

您可以通过检查每个基础集群来验证这一点,例如:

kubectl --context=gce-asia-east1a get services nginx
NAME      CLUSTER-IP     EXTERNAL-IP      PORT(S)   AGE
nginx     10.63.250.98   104.199.136.89   80/TCP    9m

上面假定您的客户端中为您的集群在该区域中配置了一个名为’gce-asia-east1a’的上下文, 底层服务的名称和命名空间将自动匹配上面创建的联邦服务的名称和命名空间( 如果碰巧在这些集群中有已经存在的相同名称和命名空间的服务, 它们将被联邦自动采用并更新以符合您联邦服务的规范 - 无论哪种方式,最终结果都将一样)。

联邦服务的状态将自动反映底层 Kubernetes 服务的实时状态,例如:

$kubectl --context=federation-cluster describe services nginx

Name:                   nginx
Namespace:              default
Labels:                 run=nginx
Selector:               run=nginx
Type:                   LoadBalancer
IP:                     10.63.250.98
LoadBalancer Ingress:   104.197.246.190, 130.211.57.243, 104.196.14.231, 104.199.136.89, ...
Port:                   http    80/TCP
Endpoints:              <none>
Session Affinity:       None
No events.

请注意,联邦服务的’LoadBalancer Ingress’地址与所有基础 Kubernetes 服务的’LoadBalancer Ingress’地址相对应( 一旦这些被分配 - 这可能需要几秒钟)。为了集群间和提供商间服务分片的网络正常工作, 您的服务需要有一个外部可见的IP地址。Service Type:Loadbalancer 通常用于此, 尽管也有其他选项(例如 External IP’s)存在。

还要注意,我们还没有配置任何后端 Pod 来接收指向这些地址的网络流量(即’Service Endpoints’), 所以联邦服务还没有认为这些服务是健康的服务分片,因此还没有将这些服务添加到这个联邦服务的 DNS 记录中(后面更多关于这方面的内容)。

添加后端 pods

为了使底层服务分片健康,我们需要在服务后面添加后端 Pod 。 这目前是直接针对底层集群的API端点完成的(尽管将来联邦服务器将能够使用单个命令为您完成所有这些工作,以节省您的麻烦)。 例如,要在13个基础集群中创建后端 Pod :

for CLUSTER in asia-east1-c asia-east1-a asia-east1-b \
                        europe-west1-d europe-west1-c europe-west1-b \
                        us-central1-f us-central1-a us-central1-b us-central1-c \
                        us-east1-d us-east1-c us-east1-b
do
  kubectl --context=$CLUSTER run nginx --image=nginx:1.11.1-alpine --port=80
done

请注意,kubectl run会自动添加run = nginx标签,从而将后端Pod与对应的service相关联。

验证公共 DNS 记录

一旦上面的 Pods 成功启动,并开始监听连接,Kubernetes 将报告 Pods 作为在该集群服务的健康端点(通过自动健康检查)。 集群联邦将依次考虑这些服务“分片”中的每一个都是健康的,并通过自动配置相应的公共 DNS 记录以将其放置在服务中。 您可以使用您的首选接口到您配置的 DNS 提供商来验证这一点。例如,如果您的联邦配置为使用Google Cloud DNS, 并且托管 DNS 域名为’example.com’:

$ gcloud dns managed-zones describe example-dot-com
creationTime: '2016-06-26T18:18:39.229Z'
description: Example domain for Kubernetes Cluster Federation
dnsName: example.com.
id: '3229332181334243121'
kind: dns#managedZone
name: example-dot-com
nameServers:
- ns-cloud-a1.googledomains.com.
- ns-cloud-a2.googledomains.com.
- ns-cloud-a3.googledomains.com.
- ns-cloud-a4.googledomains.com.
$ gcloud dns record-sets list --zone example-dot-com
NAME                                                            TYPE      TTL     DATA
example.com.                                                    NS        21600   ns-cloud-e1.googledomains.com., ns-cloud-e2.googledomains.com.
example.com.                                                    OA        21600   ns-cloud-e1.googledomains.com. cloud-dns-hostmaster.google.com. 1 21600 3600 1209600 300
nginx.mynamespace.myfederation.svc.example.com.                 A         180     104.197.246.190, 130.211.57.243, 104.196.14.231, 104.199.136.89,...
nginx.mynamespace.myfederation.svc.us-central1-a.example.com.   A         180     104.197.247.191
nginx.mynamespace.myfederation.svc.us-central1-b.example.com.   A         180     104.197.244.180
nginx.mynamespace.myfederation.svc.us-central1-c.example.com.   A         180     104.197.245.170
nginx.mynamespace.myfederation.svc.us-central1-f.example.com.   CNAME     180     nginx.mynamespace.myfederation.svc.us-central1.example.com.
nginx.mynamespace.myfederation.svc.us-central1.example.com.     A         180     104.197.247.191, 104.197.244.180, 104.197.245.170
nginx.mynamespace.myfederation.svc.asia-east1-a.example.com.    A         180     130.211.57.243
nginx.mynamespace.myfederation.svc.asia-east1-b.example.com.    CNAME     180     nginx.mynamespace.myfederation.svc.asia-east1.example.com.
nginx.mynamespace.myfederation.svc.asia-east1-c.example.com.    A         180     130.211.56.221
nginx.mynamespace.myfederation.svc.asia-east1.example.com.      A         180     130.211.57.243, 130.211.56.221
nginx.mynamespace.myfederation.svc.europe-west1.example.com.    CNAME     180     nginx.mynamespace.myfederation.svc.example.com.
nginx.mynamespace.myfederation.svc.europe-west1-d.example.com.  CNAME     180     nginx.mynamespace.myfederation.svc.europe-west1.example.com.
... etc.

注意:如果您的联邦配置为使用 AWS Route53,则可以使用其中一个等效的AWS工具,例如:

$ aws route53 list-hosted-zones

$ aws route53 list-resource-record-sets --hosted-zone-id Z3ECL0L9QLOVBX

无论您使用哪种 DNS 服务程序,任何 DNS 查询工具(例如’dig’或’nslookup’)允许您查看联邦为您创建的记录。 请注意,您应该直接在您的 DNS 提供商处指出这些工具(例如dig @ns-cloud-e1.googledomains.com ...), 或者根据您配置的 TTL 预计延迟(默认为180秒)看到更新,由于中间 DNS 服务器的缓存.

关于上面的例子的一些说明

  1. 请注意,每个至少有一个健康后端端点的服务分片有一个正常(‘A’)记录。 例如,在 us-central1-a 中,104.197.247.191是该区域中服务分片的外部IP地址, 而在 asia-east1-a 中,地址是130.211.56.221。
  2. 同样,还有区域’A’记录,包括该地区所有健康的分片。 例如,’us-central1’。这些区域记录对于不具有特定区域首选项的客户端以及下述局部自动化和故障转移机制的构建块非常有用。
  3. 对于当前没有健康后端端点的区域,使用CNAME(‘Canonical Name’)记录将这些查询别名(自动重定向)到下一个最接近的健康区域。 在本例中,us-central1-f 中的服务分片当前没有健康的后端端点(即 Pods ), 因此已创建CNAME记录自动将查询重定向到该区域中的其他分片(本例中为 us-central1 )。
  4. 同样,如果封闭区域内没有健康的碎片, 搜索就会进一步扩展。在 europe-west1-d 可用性区域,没有健康的后端, 所以查询被重定向到更广泛的 europe-west1 (其也没有健康的后端Pods), 并且继续到全局健康的地址(‘nginx.mynamespace .myfederation.svc.example.com。’)。

上述 DNS 记录集自动保持与联邦服务系统全局所有服务分片的当前健康状态同步。 DNS 解析器库(由所有客户端调用)自动遍历 ‘CNAME’ 和 ‘A’ 记录的层次结构, 以返回正确的健康 IP 地址集。然后, 客户端可以选择任何一个返回的地址来启动网络连接(如果需要,可以自动切换到其他等效地址之一)。

发现联邦服务

从联邦集群内部的 pods

默认情况下,Kubernetes 集群预先配置了集群本地DNS服务器(‘KubeDNS’),以及智能构建的DNS搜索路径, 这些路径一起确保您在 Pod 内运行的软件发出的“myservice”,“myservice.mynamespace”, “bobsservice.othernamespace”等DNS查询会自动扩展并正确解析到在本地集群中运行的服务相应的服务IP。

随着联邦服务和跨集群服务发现的引入,此概念将扩展到涵盖在全局范围内跨集群联邦的任何其他集群中运行的 Kubernetes 服务。 要充分利用此扩展范围,请使用稍微不同的 DNS 名称(形式” <服务名称>.<命名空间>.<联邦名称>", 例如 myservice.mynamespace.myfederation )来解析联邦服务。 你没有明确地选择这种行为时使用不同的 DNS 名称还可避免现有应用程序意外地穿越跨区域或跨区域网络, 并且您因此可能会收到不必要的网络费用或延迟。

因此,使用我们的NGINX演示上面的服务,以及刚刚描述的联邦服务DNS名称表单,我们来看一个例子: us-central1-f可用区中的集群中的Pod需要连接我们的 NGINX 服务。现在可以使用服务的联邦 DNS 名称

而不是使用服务在传统集群本地的 DNS (```"nginx.mynamespace"```, 将自动扩展到
```"nginx.mynamespace.svc.cluster.local"```)名称,
这将自动扩展,并解析到我的 NGINX 服务的最接近健康的分片,无论在世界任何地方。
如果在本地集群中存在健康的分片,该服务的集群本地(通常 10.x.y.z)IP地址将被返回(由集群本地 KubeDNS ),
这几乎完全等同于非联邦服务解决方案(接近因为 KubeDNS 实际上为本地联邦服务返回一个 CNAME 和一个 A 记录,
但是应用程序会忽略这个小的技术差异)。


但是如果这个服务在本地集群中不存在的话(或者服务存在,但是没有健康的后端 pods ),那么 DNS 查询会自动扩展为
```"nginx.mynamespace.myfederation.svc.us-central1-f.example.com”```
(即逻辑上"找到离我的可用区域最近的其中一个分片的外部 IP "),这个扩展是由 KubeDNS 自动执行的,它返回相关的 CNAME 记录。
在上面的例子中,这导致了自动遍历 DNS 记录的层次结构,并且在本地 us-central1 区域的联邦服务的外部IP之一处结束
(即 104.197.247.191,104.197.244.180 or 104.197.245.170)。 


当然,可以通过明确指定适当的DNS名称,而不是依靠DNS的自动扩展,
明确地定位可用区域和Pod以外的区域中的服务分片,而不是依靠自动 DNS 扩展。例如,
"nginx.mynamespace.myfederation.svc.europe-west1.example.com" 将解析欧洲所有目前健康的服务分片,
即使发布查询的 Pod 位于美国,也不管在美国是否有健康的服务碎片。这对于远程监控和其他类似的应用是有用的。


### 来自集群联邦之外的其他客户端


上述讨论大部分同样适用于外部客户端,只是所述的自动 DNS 扩展已不再可用。
因此,外部客户端需要指定联邦服务的完全限定的 DNS 名称之一,是区域名称,
地区名称或全球名称。出于方便的原因,在服务中手动配置其他静态 CNAME 记录通常是一个好主意,例如:

``` shell
eu.nginx.acme.com        CNAME nginx.mynamespace.myfederation.svc.europe-west1.example.com.
us.nginx.acme.com        CNAME nginx.mynamespace.myfederation.svc.us-central1.example.com.
nginx.acme.com           CNAME nginx.mynamespace.myfederation.svc.example.com.

这样,您的客户就可以使用左侧的简短表格,并且可以自动将其路由到本国最近的健康分片。 Kubernetes 集群联邦自动处理所有必需的故障转移。未来的版本将进一步改善。

处理后端 pods 和整个集群的失败

标准 Kubernetes 服务 cluster-IP 已经确定无响应的单独Pod端点自动以低延迟(几秒钟)退出服务。 此外,如上所述,Kubernetes 集群联邦系统会自动监控集群的健康状况, 以及您的联邦服务的所有分片背后的端点,根据需要采取分片进入和退出服务(例如当服务后面的所有端点, 或者整个集群或可用区域都停止运行时,或者相反,从停机状态恢复)。由于 DNS 缓存固有的延迟( 默认情况下,联邦服务 DNS 记录的缓存超时或 TTL 配置为3分钟,但可以进行调整)。 在灾难性失败的情况下,所有客户可能需要花费很长时间才能完全故障切换到另一个集群。 但是,考虑到每个区域服务端点可以返回的离散IP地址的数量(例如上面 us-central1,有三个选择) 许多客户端将自动故障切换到其中一个替代IP的时间少于给定的适当配置。

故障排查

我无法连接到我的集群联邦 API

检查你的:

  1. 客户端(通常为 kubectl )配置正确(包括 API 端点和登录证书)。
  2. 集群联邦 API 服务器正在运行并且网络可达。

请参阅集群联邦管理指南了解如何正确启动集群联邦身份验证 (或让集群管理员为您执行此操作),以及如何正确配置客户端

我可以通过集群联邦 API 成功创建一个联邦服务,但在我的底层集群中没有创建对应的服务

检查:

  1. 您的集群在集群联邦 API (kubectl describe clusters)中正确注册。
  2. 你的集群都是 ‘Active’ 的。这意味着集群联邦系统能够连接和验证集群端点。如果不是,请查阅 federation-controller-manager pod 的日志以确定可能发生的故障。 kubectl --namespace=federation logs $(kubectl get pods --namespace=federation -l module=federation-controller-manager -o name)
  3. 该集群提供给集群联邦 API 的登录凭证具有正确的授权和配额,以在集群中的相关命名空间中创建服务。如果不是这种情况,您应该再次看到相关的错误消息提供了上述日志文件中的更多细节。
  4. 是否有其他错误阻止了服务创建操作的成功(在kubectl logs federation-controller-manager --namespace federation'的输出中查找'service-controller错误)。

我可以成功创建联邦服务,但是在我的 DNS 提供程序中没有创建匹配的DNS记录

检查:

1.您的联邦名称,DNS 提供程序,DNS 域名配置正确。请参阅联邦集群管理指南教程以了解 如何配置集群联邦身份验证系统的 DNS 提供程序(或让您的集群管理员为您执行此操作)。 2.确认集群联邦的服务控制器已经成功连接到所选的 DNS 提供程序并进行身份验证(在kubectl logs federation-controller-manager --namespace federation的输出中查找service-controller errors 或 successes)。

匹配到我在 DNS 提供商中创建的 DNS 记录,但客户端无法解析这些记录

检查:

  1. 管理您的联邦 DNS 域的 DNS 注册管理器已正确配置到指向您配置的DNS提供商的域名服务器。 例如,请参阅 Google Domains文档 和 Google云端DNS文档 ,或从您的域名注册商或 DNS 提供商获得同样的指导。

此故障排除指南并没有帮助我解决我的问题

  1. 请使用我们的支持渠道寻求帮助。

译者:du2016 / 原文链接

K8S中文社区微信公众号

使用 Salt 配置 Kubernetes 集群

Kubernetes 集群可以使用 Salt 进行配置

这些 Salt 脚本可以跨多个托管提供商共享,这取决于您在何处托管 Kubernetes 集群,您可能正在使用多种不同的操作系统和多种不同的网络配置。因此,在做修改 Salt 配置之前了解一些背景信息是很重要的,以便在使用其他主机托管提供商时降低集群配置失败的可能。

创建 Salt 集群

salt-master 服务运行在 kubernetes-master 节点 (除了在默认的 GCE 环境和 OpenStack-Heat 环境)

salt-minion 服务运行在 kubernetes-master 节点和每个 kubernetes-node 节点。

每个 salt-minion 服务在 master.conf 文件中配置与 kubernetes-master 节点上的 salt-master 服务进行交互 (除了 GCE 环境和 OpenStack-Heat 环境)

[root@kubernetes-master] $ cat /etc/salt/minion.d/master.conf
master: kubernetes-master

每个 salt-minion 都会与 salt-master 联系,根据其提供的机器信息,salt-master 会向其提供作为 kubernetes-master 或 kubernetes-node 用于运行 Kubernetes 所需要的能力。

如果您正使用基于 Vagrant 的环境,salt-api 服务运行在 kubernetes-master 节点。它被配置为使 Vagrant 用户能够对 Salt 集群进行内省,以便通过 REST API 了解 Vagrant 环境中的机器的信息。

在 GCE 和其它环境下独立配置 Salt

在 GCE 和 OpenStack 环境,使用 Openstack-Heat 提供商,master 和 node 节点被配置为 standalone minions。每个 VM 的配置都源于它的 instance metadata 并被保存在 Salt grains (/etc/salt/minion.d/grains.conf) 和本地 Salt 用于保存执行状态的 pillars (/srv/salt-overlay/pillar/cluster-params.sls) 中。

对于 GCE 和 OpenStack ,所有引用 master/minion 设置的其余部分都应该被忽略。这种设置的一个后果是,Salt 不存在 - 节点之间不存在配置共享。

Salt 安全

(不适用于 默认的 GCE 和 OpenStack-Heat 配置环境。)

salt-master 没有启用安全功能,salt-master 被配置为自动接受所有来自 minion 的接入请求。在深入研究之前,不推荐在生产环境中启用安全配置。(在某些环境中,如果 salt-master 端口不能从外部访问,并且您信任您的网络上的每个节点,这并不像它看起来那么糟糕)

[root@kubernetes-master] $ cat /etc/salt/master.d/auto-accept.conf
open_mode: True
auto_accept: True

配置 Salt minion

Salt 集群中的每个 minion 都有一个相关的配置,它指示 salt-master 如何在机器上提供所需的资源。

下面是一个基于 Vagrant 环境的示例文件:

[root@kubernetes-master] $ cat /etc/salt/minion.d/grains.conf
grains:
  etcd_servers: $MASTER_IP
  cloud: vagrant
  roles:
    - kubernetes-master

每个托管环境都使用了略微不同的 grains.conf 文件,用于在需要的 Salt 文件中构建条件逻辑。

下面列举了目前支持的定义键/值对的集合。如果你添加了新的,请确保更新这个列表。

键 | 值 ———————————–|—————————————————————-

api_servers (可选) IP 地址/主机名 ,kubelet 用其访问 kube-apiserver
cbr-cidr (可选) docker 容器网桥分配给 minion 节点的 IP 地址范围
cloud (可选) 托管 Kubernetes 的 IaaS 平台, gce, azure, aws, vagrant
etcd_servers (可选) 以逗号分隔的 IP 地址列表,kube-apiserver 和 kubelet 使用其访问 etcd。kubernetes_master 角色的节点使用第一个机器的 IP ,在 GCE 环境上使用 127.0.0.1。
hostnamef (可选) 机器的完整主机名,即:uname -n
node_ip (可选)用于定位本节点的 IP 地址
hostname_override (可选)对应 kubelet 的 hostname-override 参数
network_mode (可选)节点间使用的网络模型:openvswitch
networkInterfaceName (可选)用于绑定地址的网络接口,默认值 eth0
publicAddressOverride (可选)kube-apiserver 用于绑定外部只读访问的IP地址
roles (必选)1、kubernetes-master 表示本节点是 Kubernetes 集群的 master。2、kubernetes-pool 表示本节点是一个 kubernetes-node。根据角色,Salt 脚本会在机器上提供不同的资源

Salt sls 文件可以应用这些键到分支行为。

此外,一个集群可能运行在基于 Debian 的操作系统或基于 Red Hat 的操作系统(Centos、Fedora、RHEL等)。因此,有时区分基于操作系统的行为(如果像下面这样的分支)是很重要的。

{% if grains['os_family'] == 'RedHat' %}
// something specific to a RedHat environment (Centos, Fedora, RHEL) where you may use yum, systemd, etc.
{% else %}
// something specific to Debian environment (apt-get, initd)
{% endif %}

最佳实践

在为进程配置默认参数时,最好避免使用环境文件( Red Hat 环境中的 Systemd )或 init.d 文件( Debian 发行版)以保留在操作系统环境中应该通用的默认值。这有助于保持我们的 Salt 模板文件易于理解,因为管理员可能不熟悉每个发行版的细节。

未来的增强(网络)

每个 pod IP 配置都是特定于提供商的,因此在进行网络更改时,必须将这些设置为沙箱,因为不同的提供商可能不会使用相同的机制( iptables 、openvswitch 等)。

我们应该定义一个 grains.conf 键,这样能更明确地捕获正在使用的网络环境配置,以避免将来在不同的提供商之间产生混淆。

进一步阅读

cluster/saltbase 项目有更多关于当前 SaltStack 配置的详细信息。

译者:linyouchong / 原文链接

K8S中文社区微信公众号

在 CenturyLink Cloud 上运行 Kubernetes

这些脚本处理 CenturyLink Cloud 上 Kubernetes 集群的创建,删除和扩展。

您可以使用单个命令完成所有这些任务。我们已经可以使用 Ansible playbooks 执行这些任务,请参考 这里

寻求帮助

如果遇到任何问题或需要任何帮助,我们都会帮助您。您可以通过以下任何方式联系我们:

您可以任意选择虚拟机或物理服务器组成集群。

  • 无论虚拟机还是物理服务器均支持 Kubernetes 集群。如果工作节点(minion)使用物理服务器,请使用 –minion_type=bareMetal 标志。
  • 有关物理服务器的更多信息,请访问:https://www.ctl.io/bare-metal/
  • 物理服务仅在 VA1 和 GB3 数据中心提供。
  • 所有13个公有云位置均提供虚拟机

要求

运行这个脚本的要求是:

运行这个脚本的要求是:

  • 一个 Linux 管理主机(在 Ubuntu 和 OSX 测试过)
  • python 2(在 2.7.11 上测试过)
    • pip(安装 Python 2.7.9)
  • git
  • 具有创建新主机权限的 CenturyLink Cloud 帐户
  • 从您的 Linux 主机到 CenturyLink Cloud 的 VPN 连接

脚本安装

满足所有要求后,请按照以下说明运行安装脚本。

1) 克隆这个仓库,并 cd 到这个目录中。

git clone https://github.com/CenturyLinkCloud/adm-kubernetes-on-clc

2) 安装所有要求,包括

  • Ansible
  • CenturyLink Cloud SDK
  • Ansible模块
sudo pip install -r ansible/requirements.txt

3) 从模板创建凭证文件,并使用它来设置您的ENV变量

cp ansible/credentials.sh.template ansible/credentials.sh
vi ansible/credentials.sh
source ansible/credentials.sh

4) 使用网络内的虚拟机或 配置连接到 CenturyLink Cloud 网络的 VPN 来从您的机器访问 CenturyLink Cloud 网络。

脚本安装示例:Ubuntu 14 演练

如果您使用的是 Ubuntu 14,方便起见,我们已经提供了一个安装依赖和脚本的分步指导。

# system
apt-get update
apt-get install -y git python python-crypto
curl -O https://bootstrap.pypa.io/get-pip.py
python get-pip.py

# installing this repository
mkdir -p ~home/k8s-on-clc
cd ~home/k8s-on-clc
git clone https://github.com/CenturyLinkCloud/adm-kubernetes-on-clc.git
cd adm-kubernetes-on-clc/
pip install -r requirements.txt

# getting started
cd ansible
cp credentials.sh.template credentials.sh; vi credentials.sh
source credentials.sh

集群创建

要创建一个新的 Kubernetes 集群,只需运行 kube-up.sh 脚本。以下列出了脚本选项和一些示例的完整列表。

CLC_CLUSTER_NAME=[name of kubernetes cluster]
cd ./adm-kubernetes-on-clc
bash kube-up.sh -c="$CLC_CLUSTER_NAME"

大约需要15分钟来创建集群。一旦脚本完成,它会输出一些命令来帮助您在机器上设置 kubectl 以指向新的集群。

集群创建完成后,会将其配置文件本地保存在您管理主机的以下目录中

> CLC_CLUSTER_HOME=$HOME/.clc_kube/$CLC_CLUSTER_NAME/

集群创建:脚本选项

Usage: kube-up.sh [OPTIONS]
Create servers in the CenturyLinkCloud environment and initialize a Kubernetes cluster
Environment variables CLC_V2_API_USERNAME and CLC_V2_API_PASSWD must be set in
order to access the CenturyLinkCloud API

All options (both short and long form) require arguments, and must include "="
between option name and option value.

     -h (--help)                   display this help and exit
     -c= (--clc_cluster_name=)     set the name of the cluster, as used in CLC group names
     -t= (--minion_type=)          standard -> VM (default), bareMetal -> physical]
     -d= (--datacenter=)           VA1 (default)
     -m= (--minion_count=)         number of kubernetes minion nodes
     -mem= (--vm_memory=)          number of GB ram for each minion
     -cpu= (--vm_cpu=)             number of virtual cps for each minion node
     -phyid= (--server_conf_id=)   physical server configuration id, one of
                                      physical_server_20_core_conf_id
                                      physical_server_12_core_conf_id
                                      physical_server_4_core_conf_id (default)
     -etcd_separate_cluster=yes    create a separate cluster of three etcd nodes,
                                   otherwise run etcd on the master node

集群扩展

要扩展现有的 Kubernetes 集群,运行 add-kube-node.sh 脚本。脚本选项和一些例子的完整列表在 下面 列出。 此脚本必须从创建集群的同一台主机(或者在 ~/.clc_kube/$cluster_name 路径保存了集群 artifact 文件的主机)运行。

cd ./adm-kubernetes-on-clc
bash add-kube-node.sh -c="name_of_kubernetes_cluster" -m=2

集群扩展:脚本选项

Usage: add-kube-node.sh [OPTIONS]
Create servers in the CenturyLinkCloud environment and add to an
existing CLC kubernetes cluster

Environment variables CLC_V2_API_USERNAME and CLC_V2_API_PASSWD must be set in
order to access the CenturyLinkCloud API

     -h (--help)                   display this help and exit
     -c= (--clc_cluster_name=)     set the name of the cluster, as used in CLC group names
     -m= (--minion_count=)         number of kubernetes minion nodes to add

集群删除

有两种方法可以删除现有的集群:

1) 使用我们的 Python 脚本:

python delete_cluster.py --cluster=clc_cluster_name --datacenter=DC1

2) 使用 CenturyLink Cloud 用户界面。 要删除集群,请登录到 CenturyLink Cloud 控制门户并删除包含该的父服务器组 Kubernetes 集群。 我们希望添加一个脚本化的选项来尽快做到这一点。

例子

在 VA1 中创建名称为 k8s_1,1个 master 节点和3个 worker(在物理机上)的集群

bash kube-up.sh --clc_cluster_name=k8s_1 --minion_type=bareMetal --minion_count=3 --datacenter=VA1

在 VA1 中创建一个名为 k8s_2 的集群,一个在3个虚拟机和6个 worker minion(在虚拟机上)的 HA etcd 集群

bash kube-up.sh --clc_cluster_name=k8s_2 --minion_type=standard --minion_count=6 --datacenter=VA1 --etcd_separate_cluster=yes

在 UC1 中创建一个名为 k8s_3,1个 master 节点和10个具有更高 mem/cpu 的 worker minion(在VM上)的集群:

bash kube-up.sh --clc_cluster_name=k8s_3 --minion_type=standard --minion_count=10 --datacenter=VA1 -mem=6 -cpu=4

集群功能和体系结构

我们使用以下功能配置 Kubernetes 集群:

  • KubeDNS:DNS 解析和服务发现
  • Heapster/InfluxDB:用于 metric 收集。需要 Grafana 和 auto-scaling。
  • Grafana:Kubernetes/Docker metric 面板
  • KubeUI:简单的界面来查看 Kubernetes 状态
  • Kube Dashboard:新的用于与您的集群交互的 Web 界面

我们使用这些组件创建 Kubernetes 集群:

  • Kubernetes 1.1.7
  • Ubuntu 14.04
  • Flannel 0.5.4
  • Docker 1.9.1-0~trusty
  • Etcd 2.2.2

可选插件

  • 日志记录:我们提供一个集成的集中日志记录 ELK 平台,以便所有 Kubernetes 和 docker 日志被发送到 ELK 堆栈。要安装 ELK 堆栈并配置 Kubernetes 发送日志, 遵循 日志聚合文档。 注意:我们不会默认安装这个,因为它占用的空间并不小。

集群管理

管理 Kubernetes 集群的最广泛使用的工具是命令行 kubectl。 如果您的管理主机上还没有这个二进制文件,可以运行 install_kubectl.sh,这个脚本会将它下载并安装到 /usr/bin/local 中。

该脚本要求定义环境变量 CLC_CLUSTER_NAME

install_kubectl.sh 也写一个配置文件,它将嵌入必要的特定集群的身份验证证书。 配置文件会写到 ${CLC_CLUSTER_HOME}/kube 目录

export KUBECONFIG=${CLC_CLUSTER_HOME}/kube/config
kubectl version
kubectl cluster-info

以编程方式访问集群

可以使用本地存储的客户端证书来访问 apiserver。例如,您可能希望使用任何 Kubernetes API 客户端库 ,并以您选择的编程语言对您的 Kubernetes 集群进行编程。

为了演示如何使用这些本地存储的证书,我们提供了以下例子,使用 ```curl`` 通过 https 与主 apiserver 进行通信:

curl \
   --cacert ${CLC_CLUSTER_HOME}/pki/ca.crt  \
   --key ${CLC_CLUSTER_HOME}/pki/kubecfg.key \
   --cert ${CLC_CLUSTER_HOME}/pki/kubecfg.crt  https://${MASTER_IP}:6443

但请注意,这不适用于 OSX 版本的 curl 二进制文件。

使用浏览器访问集群

我们在 Kubernetes 上安装两个 UI。原来的 KubeUI 和 新的 Kube dashboard。 当你创建一个集群时,脚本应该输出这些接口 URL ,像这样:

KubeUI is running at https://${MASTER_IP}:6443/api/v1/namespaces/kube-system/services/kube-ui/proxy.

kubernetes-dashboard is running at https://${MASTER_IP}:6443/api/v1/namespaces/kube-system/services/kubernetes-dashboard/proxy.

关于用户界面身份验证的注意事项:集群设置为使用基本用户 admin 的身份验证。打在网址 https://${MASTER_IP}:6443 需要接受 apiserver 的自签名证书,然后提交管理员密码文件,位于:

> _${CLC_CLUSTER_HOME}/kube/admin_password.txt_

配置文件

各种配置文件被写入主目录 CLC_CLUSTER_HOME 下的 .clc_kube/${CLC_CLUSTER_NAME} 几个子目录中。 你可以使用这些文件从您创建集群的位置以外的机器访问集群。

  • config/: Ansible变量文件,包含描述主控和主控主机的参数
  • hosts/: 主机文件列出了可靠的剧本的访问信息
  • kube/: kubectl 配置文件,以及管理员访问 Kubernetes API 的基本认证密码
  • pki/: 在集群中启用 TLS 通信的公共基础设施文件
  • ssh/: 用于 root 访问主机的 SSH 密钥

kubectl 使用例子

kubectl 有很多功能。下面是一些例子

列出所有名称空间中的现有 node、Pod、service 等等,或者只列出一个:

kubectl get nodes
kubectl get --all-namespaces services
kubectl get --namespace=kube-system replicationcontrollers

Kubernetes API 服务器在 web URL 上提供服务,通过校验客户证书保护这些 URL 。 如果你在本地运行一个 kubectl 代理,kubectl 将会提供必要的证书并通过 http 服务于本地。

kubectl proxy -p 8001

然后,您可以在浏览器中访问像 http://127.0.0.1:8001/api/v1/namespaces/kube-system/services/kube-ui/proxy/ 这样的 URL 而不需要客户端证书。

这些是在 CenturyLink Cloud 上不起作用的已知项,但可以在其他云上工作:

  • 目前没有 LoadBalancer 类型的支持服务。我们正在积极努力,希望在2016年4月左右发布这些变化。
  • 目前,CenturyLink Cloud 不支持持久性存储卷。但是,客户可以使用自己选中的持久存储。我们自己使用 Gluster。

Ansible 文件

如果你想了解更多有关我们 Ansible 文件的信息,请 阅读此文件

更多信息

有关管理和使用 Kubernetes 集群的更多详细信息,请参阅 Kubernetes 文档

译者:zhangqx2010 / 原文链接

K8S中文社区微信公众号

Kubernetes 联邦 Deployment

本指南说明了如何在联邦控制平面中使用 Deployment。

联邦控制平面中的 Deployment(在本指南中称为 “联邦 Deployment”)与传统的 Kubernetes Deployment 非常类似, 并提供相同的功能。 在联邦控制平面中创建联邦 Deployment 确保所需的副本数存在于注册的群集中。

到 Kubernetes 1.5 版本为止,联邦 Deployment 还是一个 Alpha 特性。 Deployment 的核心功能已经提供, 但一些特性(例如完整的 rollout 兼容性)仍在开发中。

Before you begin

  • This guide assumes that you have a running Kubernetes Cluster Federation installation. If not, then head over to the federation admin guide to learn how to bring up a cluster federation (or have your cluster administrator do this for you). Other tutorials, such as Kelsey Hightower’s Federated Kubernetes Tutorial, might also help you create a Federated Kubernetes cluster.
  • 通常您还应当拥有基本的 Kubernetes 应用知识,特别是 Deployment 相关的应用知识。

创建联邦 Deployment

联邦 Deployment 的 API 和传统的 Kubernetes Deployment API 是兼容的。 您可以通过向联邦 apiserver 发送请求来创建一个 Deployment。

您可以通过使用 kubectl 运行下面的指令来创建联邦 Deployment:

kubectl --context=federation-cluster create -f mydeployment.yaml

--context=federation-cluster 参数告诉 kubectl 发送请求到联邦 apiserver 而不是某个 Kubernetes 集群。

一旦联邦 Deployment 被创建,联邦控制平面会在所有底层 Kubernetes 集群中创建一个 Deployment。 您可以通过检查底层每个集群来对其进行验证,例如:

kubectl --context=gce-asia-east1a get deployment mydep

上面的命令假定您在客户端中配置了一个叫做 ‘gce-asia-east1a’ 的上下文,用于向相应区域的集群发送请求。

底层集群中的这些 Deployment 会匹配联邦 Deployment 中副本数和修订版本(revision)相关注解_之外_的信息。 联邦控制平面确保所有集群中的副本总数与联邦 Deployment 中请求的副本数量匹配。

在底层集群中分布副本

默认情况下,副本会被平均分布到所有的底层集群中。 例如: 如果您有3个注册的集群并且创建了一个副本数为 9 (spec.replicas = 9)的联邦 Deployment,那么这 3 个集群中的每个 Deployment 都将有 3 个副本 (spec.replicas=3)。

为修改每个集群中的 副本数,您可以在联邦 Deployment 中以注解的形式指定 FederatedReplicaSetPreference, 其中注解的键为 federation.kubernetes.io/deployment-preferences。

更新联邦 Deployment

您可以像更新 Kubernetes Deployment 一样更新联邦 Deployment。 但是,对于联邦 Deployment, 您必须发送请求到联邦 apiserver 而不是某个特定的 Kubernetes 集群。 联邦控制平面会确保每当联邦 Deployment 更新时,它会更新所有底层集群中相应的 Deployment 来和更新后的内容保持一致。 所以如果(在联邦 Deployment 中)选择了滚动更新,那么底层集群会独立地进行滚动更新,并且联邦 Deployment 中的 maxSurge and maxUnavailable 只会应用于独立的集群中。 将来这种行为可能会改变。

如果您的更新包括副本数量的变化,联邦控制平面会改变底层集群中的副本数量,以确保它们的总数等于联邦 Deployment 中请求的数量。

删除联邦 Deployment

您可以像删除 Kubernetes Deployment 一样删除联邦 Deployment。但是,对于联邦 Deployment,您必须发送请求到联邦 apiserver 而不是某个特定的 Kubernetes 集群。

例如,您可以使用 kubectl 运行下面的命令来删除联邦 Deployment:

kubectl --context=federation-cluster delete deployment mydep

译者:lichuqiang / 原文链接

K8S中文社区微信公众号

Kubernetes on Mesos

关于 Kubernetes on Mesos

Mesos 支持 Kubernetes 和其他 Mesos 一级框架如 HDFSSpark, 和 Chronos 的集群资源动态共享。 同时 Mesos 保证了集群中不同框架中应用间合理的资源分配与隔离。

Mesos 集群可以部署在几乎所有IaaS云供应商的基础设施上或您自己的物理数据中心中。Kubernetes on Mesos 可以让您可以更容易地把 Kubernetes 的工作负载从其中一个环境迁移至其他环境中。

本教程将带您在 Mesos 集群上安装 Kubernetes。将会告诉您如何一步一步地添加 Kubernetes 到 Mesos 集群并启动第一个 nginx web 服务器 pod。

注意:  当前步骤中的已知问题 以及不支持集中日志和监控. 如果您在以下步骤中遇到问题,请 在 kubernetes-mesos 提出 issue .

更多信息请参阅 Kubernetes on Mesos 贡献目录.

先决条件

- 了解Apache Mesos

- 支持 Go 语言 (点击 这里 查看版本要求)

  • make (i.e. build-essential)
  • Docker

注意: 您 可以, 但是您不一定要 将 Kubernetes-Mesos 和 Mesos 的Master 节点部署在同一台机器上.

部署 Kubernetes-Mesos

使用 SSH 登录到 Kubernetes 的 master 节点 , 将以下占位符替换为相应的IP地址.

ssh jclouds@${ip_address_of_master_node}

构建 Kubernetes-Mesos

git clone https://github.com/kubernetes-incubator/kube-mesos-framework
cd kube-mesos-framework
make

设置环境变量。Set some environment variables. 使用 hostname -i 命令来获取 master 的内部 IP 地址.

export KUBERNETES_MASTER_IP=$(hostname -i)
export KUBERNETES_MASTER=http://${KUBERNETES_MASTER_IP}:8888

请注意,KUBERNETES_MASTER 被用来作为 api endpoint. 如果您已经定义了这个文件 ~/.kube/config 并且指向了其他终端,您需要在后面步骤中在 kubectl 命令后加上 --server=${KUBERNETES_MASTER} .

部署 etcd

启动 etcd 并验证运行状况:

sudo docker run -d --hostname $(uname -n) --name etcd \
  -p 4001:4001 -p 7001:7001 quay.io/coreos/etcd:v2.2.1 \
  --listen-client-urls http://0.0.0.0:4001 \
  --advertise-client-urls http://${KUBERNETES_MASTER_IP}:4001
$ sudo docker ps
CONTAINER ID   IMAGE                        COMMAND   CREATED   STATUS   PORTS                NAMES
fd7bac9e2301   quay.io/coreos/etcd:v2.2.1   "/etcd"   5s ago    Up 3s    2379/tcp, 2380/...   etcd

同时最好用以下代码测试您的 etcd 实例,保证可达

curl -L http://${KUBERNETES_MASTER_IP}:4001/v2/keys/

如果连接正常,您会看到数据库中的 键 列表(如果有的话)

启动 Kubernetes-Mesos 服务

将 Kubernetes-Mesos 添加到环境变量 PATH 里面

export PATH="$(pwd)/_output/local/go/bin:$PATH"

确认您的 Mesos master 节点:取决于您的安装方式,可能是 host:port 形式,就像 mesos-master:5050;或者是 ZooKeeper URL 的形式,就像 zk://zookeeper:2181/mesos。为了让 Kubernetes 在 Mesos master 节点的更改时运行良好,在生产环境中推荐使用 ZooKeeper URL 的形式。

export MESOS_MASTER=<host:port or zk:// url>

使用下列语句在当前路径创建一个 cloud 配置文件 mesos-cloud.conf

$ cat <<EOF >mesos-cloud.conf
[mesos-cloud]
        mesos-master        = ${MESOS_MASTER}
EOF

现在,在 master 节点上启动下列组件 kubernetes-mesos API server, controller manager, 以及 scheduler:

$ km apiserver \
  --address=${KUBERNETES_MASTER_IP} \
  --etcd-servers=http://${KUBERNETES_MASTER_IP}:4001 \
  --service-cluster-ip-range=10.10.10.0/24 \
  --port=8888 \
  --cloud-provider=mesos \
  --cloud-config=mesos-cloud.conf \
  --secure-port=0 \
  --v=1 >apiserver.log 2>&1 &

$ km controller-manager \
  --master=${KUBERNETES_MASTER_IP}:8888 \
  --cloud-provider=mesos \
  --cloud-config=./mesos-cloud.conf  \
  --v=1 >controller.log 2>&1 &

$ km scheduler \
  --address=${KUBERNETES_MASTER_IP} \
  --mesos-master=${MESOS_MASTER} \
  --etcd-servers=http://${KUBERNETES_MASTER_IP}:4001 \
  --mesos-user=root \
  --api-servers=${KUBERNETES_MASTER_IP}:8888 \
  --cluster-dns=10.10.10.10 \
  --cluster-domain=cluster.local \
  --v=2 >scheduler.log 2>&1 &

运行 disown 命令,保证后台任务在您登出后保持运行.

disown -a

验证 KM 服务

通过 kubectl 与 kubernetes-mesos 框架进行交互:

$ kubectl get pods
NAME      READY     STATUS    RESTARTS   AGE
# NOTE: your service IPs will likely differ
$ kubectl get services
NAME             CLUSTER-IP       EXTERNAL-IP     PORT(S)        AGE
k8sm-scheduler   10.10.10.113     <none>          10251/TCP      1d
kubernetes       10.10.10.1       <none>          443/TCP        1d

最后,使用浏览器访问 Mesos web GUI 所在地址 http://<mesos-master-ip:port>. 确保您有 VPN 连接正在运行. 在 Frameworks 选项卡中找到运行中的框架 “Kubernetes”.

启动 pod

在本地文件中创建一个 JSON 格式的 pod 描述文件:

$ cat <<EOPOD >nginx.yaml
apiVersion: v1
kind: Pod
metadata:
  name: nginx
spec:
  containers:
  - name: nginx
    image: nginx
    ports:
    - containerPort: 80
EOPOD

使用 kubectl CLI 向 Kubernetes 发送 pod 描述文件:

$ kubectl create -f ./nginx.yaml
pod "nginx" created

耐心等待一到两分钟,dockerd 下载镜像。我们可以用 kubectl 查看 pod 运行状态

$ kubectl get pods
NAME      READY     STATUS    RESTARTS   AGE
nginx     1/1       Running   0          14s

通过浏览器访问 Mesos web GUI 检查 pod 运行状态. 点击 Kubernetes 框架. 接下来将会显示启动 Kubernetes pod 的 Mesos 任务.

启动 kube-dns 组件

Kube-dns 是一个 Kubernetes 组件,给集群增加了基于DNS的服务发现. 详情请见 DNS in Kubernetes.

Kube-dns 组件作为一个pod运行在集群中,这个 pod 包含了三个同时运行的容器:

  • 一个本地etcd实例
  •  kube-dns DNS服务器

kube-dns 的默认参数

  • service IP 10.10.10.10
  • 和 cluster.local domain.

请注意我们已经把以上两个参数传入了上述 apiserver.

我们提供了一个 replication controller 模板,用来启动上述 pod ,可以通过这个链接进行下载 cluster/addons/dns/kubedns-controller.yaml.in . 接下来我们来创建可用的 replication controller yaml 文件:

  • 将 {{ pillar['dns_replicas'] }} 替换为 1
  • 将 {{ pillar['dns_domain'] }} 替换为 cluster.local.
  • 向 kube2sky container command 添加 --kube_master_url=${KUBERNETES_MASTER} 参数.

另外, cluster/addons/dns/kubedns-controller.yaml.in 中的 service 模板需要做如下替换:

  • {{ pillar['dns_server'] }} with 10.10.10.10.

以下是上述操作的自动脚本:

sed -e "s/{{ pillar\['dns_replicas'\] }}/1/g;"\
"s,\(command = \"/kube2sky\"\),\\1\\"$'\n'"        - --kube_master_url=${KUBERNETES_MASTER},;"\
"s/{{ pillar\['dns_domain'\] }}/cluster.local/g" \
  cluster/addons/dns/kubedns-controller.yaml.in > kubedns-controller.yaml
sed -e "s/{{ pillar\['dns_server'\] }}/10.10.10.10/g" \
  cluster/addons/dns/kubedns-svc.yaml.in > kubedns-svc.yaml

现在 kube-dns 的 pod 和 service 已经准备完毕,下面是启动指令

kubectl create -f ./kubedns-controller.yaml
kubectl create -f ./kubedns-svc.yaml

运行 kubectl get pods --namespace=kube-system 确认 3/3 也就是这个pod的所有容器都是 running 状态. 需要注意,kube-dns 的 pod 运行在 kube-system namespace, 而不是 default 下.

为了确认新的 DNS 服务正在运行,我们在集群中启动一个 busybox pod 进行 DNS 检索. 首先创建一个 busybox.yaml pod 定义文件:

cat <<EOF >busybox.yaml
apiVersion: v1
kind: Pod
metadata:
  name: busybox
  namespace: default
spec:
  containers:
  - image: busybox
    command:
      - sleep
      - "3600"
    imagePullPolicy: IfNotPresent
    name: busybox
  restartPolicy: Always
EOF

然后启动 pod:

kubectl create -f ./busybox.yaml

Pod 启动之后,通过以下命令尝试解析 Kubernetes master service,默认返回值应该为 10.10.10.1.

kubectl  exec busybox -- nslookup kubernetes

如果一切正常,将会看到如下结果

Server:    10.10.10.10
Address 1: 10.10.10.10

Name:      kubernetes
Address 1: 10.10.10.1

支持

IaaS层 Config. Mgmt OS Networking 网络 Docs 文档 Conforms 支持
Mesos/GCE docs Community (Kubernetes-Mesos Authors)

查看解决方法,请参阅 解决方法

延伸阅读

试试标准例子 Kubernetes examples.

看看 Kubernetes on Mesos 架构 contrib directory.

注意: 有些例子需要在集群中预先安装 Kubernetes DNS . 以后会在本指南中加入 Kubernetes DNS 的激活方法.

注意: 以下是一些 当前 Kubernetes-Mesos 实践中的已知问题.

译者:jiaj12 / 原文链接

K8S中文社区微信公众号