在一些场景下,运行在CloudFoundry
和Kubernetes
等平台上的Cloud Native应用需要使用各种各样的外部服务,如数据库,消息队列等。但应用开发者并不想关心这些服务的配置、管理和位置等信息,以便将精力集中在业务逻辑开发上。为了满足这种需要,CloudFoundry
及Google
等一系列公司创建了Open Service Broker API(OSBAPI)
项目,致力于将外部服务的生命周期管理,应用平台与服务代理的交互,服务实例的访问等内容标准化。
OSBAPI
规范定义了高度抽象的应用平台与外部服务代理的交互逻辑,规范化外部服务的使用,主要包括:
- 注册服务代理: 应用平台会获取服务代理提供的服务列表及相应规格,
OSBAPI
使用术语Plan
来表示规格。 Provision
服务实例:OSBAPI
使用术语Provision
来统一指定服务资源的供应。在外部服务具体实现上,可以是创建虚拟机实例,也可以是分配资源,也可以是创建SaaS帐号等等。- 绑定应用及服务实例: 当服务实例创建完成后,开发者想要其应用与该服务实例进行交互。从服务代理的角度来看,就是将应用与服务实例进行绑定。具体实现逻辑可以非常灵活,一般情况下,会生成访问该服务实例所需的新凭证。比如,生成数据库实例的IP、端口、用户名、密码等等。这些凭证会被返回给应用平台以提供给具体应用使用。
OSBAPI
的具体工作模式如下图:
Kubernetes的Service Catalog项目实现了OSBAPI
规范,Kubernetes平台的应用通过service catalog来使用外部服务。
大体实现架构如图:
Service catalog实现将service catalog资源对象的管理映射到OSBAPI
相应资源的操作, 架构上主要包括两部分:
- API Server:
它基于API-aggregation实了一个扩展API Server, 使用etcd做为后端存储。
Kubernetes用户和service catalog controller通过与API Server交互完成Service Catalog资源的CRUD操作。 - Controller:
Controller实现了OSBAPI
规范。它监控API Server上资源对象的事件,并完成与OSBAPI
对应的操作。比如,当用户创建一个ClusterServiceBroker对象, API Server会存储该资源并产生一个事件。Controller会接收到该事件,接着去请求指定的服务代理获取该服务代理所提供的资源。
Service catalog的API组为: servicecatalog.k8s.io
, 当前的API资源版本为: v1beta1
,提供的主要资源有:
- ClusterServiceBroker:
Service Broker在Kubernetes集群内的表示, 包含Service Broker的相关信息。 - ClusterServiceClass:
表示特定ServiceBroker所提供的外部服务,ClusterServiceBroker创建后,controller会自动从ClusterServiceBroker所提供的URL拉取服务列表,为每个外部服务创建一个ClusterServiceClass。 - ClusterServicePlan:
表示外部服务的规格,ClusterServiceBroker创建后,controller也会自动创建ClusterServicePlan对象。 - ServiceInstance:
外部服务的服务实例,创建该对象时,controller会发送OSBAPI
Provision
请求。 - ServiceBinding:
创建该对象后,controller发送OSBAPI
的Binding请求,并将返回的凭证信息存储在kubernetes的Secret对象中。该Secret对象需要被挂载到需要使用该服务的Pod中。
其他的一些资源具体可参考: https://svc-cat.io/docs/resources/
当存储有相关凭证信息的Secret
对象挂载到特定应用的Pod
中,该应用则可以使用这些信息与外部服务进行交互, 如下图所示:
下面通过一个实例来说明Kubernetes与外部服务的交互。
首先,我们基于python的openbrokerapi来实现一个demo broker, 它只是简单的返回服务信息,并不真实分配服务资源。
源码broker.py
内容如下:
1 | from openbrokerapi import api |
运行该broker:
1 | python broker.py |
该虚拟机IP为10.0.0.231
,它监听5000
端口。
我们假定Kubernetes集群搭建和Service Catalog已经安装完成。
首先,在Kubernetest集群创建ClusterServiceBroker:
demo-broker.yaml
的内容如下:
1 | apiVersion: servicecatalog.k8s.io/v1beta1 |
创建demo-broker:
1 | [root@fg-t1 yaml]# kubectl create -f demo-broker.yaml |
查看clusterservicebrokers
列表:
1 | [root@fg-t1 yaml]# kubectl get clusterservicebrokers |
查看clusterserviceclasses
列表, 可以看到demo-broker所提供的demo-service:
1 | [root@fg-t1 yaml]# kubectl get clusterserviceclasses |
查看clusterserviceplans
列表:
1 | [root@fg-t1 yaml]# kubectl get clusterserviceplans |
接下来,创建服务实例。demo-instance.yaml
内容如下:
1 | apiVersion: servicecatalog.k8s.io/v1beta1 |
创建ServiceInstance对象:
1 | [root@fg-t1 yaml]# kubectl create -f demo-instance.yaml |
查看实例列表,可以看到新创建的demo-instance实例:
1 | [root@fg-t1 yaml]# kubectl get serviceinstances |
接着,创建Binding:demo-binding.yaml
内容如下:
1 | apiVersion: servicecatalog.k8s.io/v1beta1 |
创建ServiceBinding对象:
1 | [root@fg-t1 yaml]# kubectl create -f demo-binding.yaml |
查看ServiceBindings列表可以看到demo-binding创建成功:
1 | [root@fg-t1 yaml]# kubectl get servicebindings |
我们在demo-binding.yaml
中指定凭证信息存储在Secret对象demo-instance-credentials
中,我们来查看这个Secret对象:
1 | [root@fg-t1 yaml]# kubectl get secret demo-instance-credentials -o yaml |
1 | [root@fg-t1 yaml]# echo 'aHR0cDovL2RlbW8ubG9jYWwvYmY2YWRlZTItYmJkNC0xMWU5LWFhYmYtMDI0MmFjMTEwMDA3' | base64 --decode |
可以看到,返回的内容正是我们在broker.py
中所指定的内容。
最后,我们清理掉这些实例内容:
1 | [root@fg-t1 yaml]# kubectl delete servicebindings demo-binding |