嘉宾 | 霍秉杰 整顿 | 王新
出品 | CSDN 云原生
2022 年 5 月 10 日,在 CSDN 云原生系列在线峰会第 4 期“ApacheSkyWalking 峰会”上,青云科技资深架构师霍秉杰分享了 SkyWalkingv9 如何帮忙 OpenFunction 实现函数可观测。
Serverless: 下一波浪潮
随着技术的倒退,人们越来越少关注底层技术栈的一些细节,越来越多关注本人利用的商业逻辑。CNCF 公布的 Serverless 白皮书印证了这一点。
如上图所示,从下往上,最底层是 CaaS(Container as a Service),它向下形象和屏蔽了基础设施的差别,向上提供了一个利用运行的平台,用户对基础设施和利用有绝对全面和灵便的掌控。
中间层是 PaaS(Platform as a Service),次要分为两类,一类是传统的 PaaS 平台,例如 Cloud Foundry、Heroku; 另一类则是容器平台,例如 OpenShift、KubeSphere,它们能够提供 Kubernetes 没有的一些能力,比方用户的鉴权、认证与治理,可观测性包含监控、告警、日志、事件与审计,服务网格,还有 CI/CD 等。这使得用户能够更加关注于开发和部署利用,其余能够依赖平台提供的能力。
最上层是 FaaS(Function as a Service),包含云厂商的函数计算服务和开源的函数计算平台。在 FaaS 这层,用户更多关注本人利用的业务逻辑局部,其余的方面都交给平台去解决。
为什么须要一个云厂商中立的 FaaS 平台?
近几年咱们越来越多地听到多云、分布式云、混合云这样的提法,其中起因应该是 Kubernetes 带来了云厂商中立的可能性,于是很多公司开始基于 Kubernetes 去做多云、分布式云、混合云的计划或产品。然而在 FaaS 畛域却很难实现厂商中立,因为每个云厂商都有本人的 FaaS 平台,通常这些云厂商的 FaaS 平台都会和本人云上的后端服务绑定。CNCF Serverless 白皮书其实也提到了这一点:各个厂商因为编程模型,事件及音讯接口,还有后端服务的不同导致用了一个厂商的 FaaS 平台后,就很难迁徙到别的厂商的 FaaS 平台。
如何构建一个云厂商中立的 FaaS 平台?
那么有没有可能去构建一个云厂商中立的 FaaS 平台?如何去构建这样一个平台?首先不开源必定是不太可能做到厂商中立的,不开源就成了另一个厂商。
CNCF 的 Serverless 白皮书在 2018 年公布,外面提到 Serverless 不足标准化,成熟度方面也有所欠缺。四年过来了,其实这两个方面都有所改观。首先标准化方面,据 CNCF 2021 年的调查报告显示正在应用以及正在评估应用 Kubernetes 的受访者曾经达到创纪录的 96%,Kubernetes 逐步走向底层成为更下层平台和服务的基础设施;此外四年以来云原生 Serverless 畛域也有了很多停顿,其中最驰名的 Knative 就是在 2018 年开源的,四年以来 Knative 曾经公布了 v1.0 版并且当初曾经捐给了 CNCF。本文不会过多介绍 Knative,而是会着重介绍另外两个云原生 Serverless 畛域的技术,Dapr 和 KEDA。
KEDA 全称是 Kubernetes Event-driven Autoscaling。顾名思义 KEDA 次要用于 Kubernetes 上分布式应用的主动伸缩,其独特之处在于可依据泛滥事件源特有的指标进行伸缩,包含开源的中间件及各大云厂商的后端服务等事件源。咱们能够用 KEDA 来解耦事件源与分布式应用的主动伸缩,KEDA 使得利用能够依据应用中间件或服务的特有指标进行伸缩,无论该中间件或服务是云上托管的还是开源的。
Dapr 全称是分布式应用运行时,它是把分布式应用的各种能力形象成多个 Building Block,比方有的利用有状态治理的需要,须要存取一些状态,Dapr 有一个 State Management 的 Building Block 能够提供这方面的能力;有一些事件驱动的分布式应用,有公布订阅的需要,Dapr 有一个 pubsub 的 Building Block 能够提供这方面的能力;再比方很多利用都有输出和输入,于是 Dapr 提供了 Input/Output Binding 的 Building Block。总之,应用 Dapr 能够把分布式的利用和其依赖的后端服务进行解耦。
具体来说个别 FaaS 平台都须要反对多语言,通常须要和多种后端服务去打交道。咱们假如一个 FaaS 平台须要反对 5 种语言并且须要和 10 个 message queue 去对接。不必 Dapr 的状况下,每种语言都得用每个 message queue 该语言的 SDK 去对接这个 message queue,总共就会有 50 种实现;在应用 Dapr 的状况下,每种语言仅须要用 Dapr 的 SDK 去和 Dapr 对接,再由 Dapr 去和各个 message queue 对接,这时候只须要 5 种实现。能够看到在引入了 Dapr 之后,极大地升高了 FaaS 平台的复杂度。
相当于咱们在 Serverless 的 FaaS 和 BaaS 之间额定增加了一层 Dapr。
Dapr 相当于 FaaS 拜访 BaaS 的一个对立的接口。
几个星期之前咱们把如何在 OpenFunction 中应用 Dapr 和 Dapr 寰球社区做了一个分享,Dapr 的两位联结创始人 Mark 和 Yaron 对 OpenFunction 这种用法很观赏,也很快乐看到 Dapr 被利用到越来越多的 Serverless Function runtimes 中。
OpenFunction 简介
OpenFunction 次要由 3 个局部组成: Build,Serving 和 Events. 在 Build 和 Serving 之上还有一层形象 Function, 由 Function 来管制函数的 Build 和 Serving. Function 是用户和 OpenFunction 交互的对立接口,用户无需和 Build 以及 Serving 打交道。
Build 次要负责把函数的代码构建成函数的镜像。采纳的是 Cloud Native Buildpacks 技术,这也是最近几年涌现进去的一个云原生构建技术,它的特点就是不须要依赖 Dockerfile 就可能把函数的镜像给 build 进去。目前已被 Google Cloud,IBM Cloud,VMWare, Heroku 等公司采纳。当初 OpenFunction 也反对用另外三种依赖于 Dockerfile 的构建技术去 build 利用包含 buildah, BuildKit 和 Kaniko. 当前也会陆续反对用这些依赖于 Dockerfile 的构建技术去构建函数镜像。
Serving 应该是 OpenFunction 中最要害的局部,次要负责运行函数。目前 Serving 蕴含了同步和异步两个函数运行时。同步函数目前反对用 Knative 作为运行时,咱们也打算反对用 KEDA http-addon 作为另一个同步函数运行时,目前咱们曾经有 Maintainer 积极参与到了这个我的项目中。OpenFunction 比拟有特色的应该是它的异步函数运行时。很少看到在开源或者是云厂商的 FaaS 平台里有专门的异步函数运行时,如果有异步函数也多是通过把事件源的事件转换成一个 HTTP 的申请后再去解决。OpenFunction 的异步函数是间接对接事件源的,由 KEDA 和 Dapr 形成,这是 OpenFunction 所特有的。
OpenFunction Events 的作用相似 Knative Eventing. 然而 Knative Eventing 在设计与应用上都过于简单,于是 OpenFunction 受 Argo Events 的启发设计了本人的事件治理框架 OpenFunction Events,其由 EventSource, Sink, EventBus 和 Trigger 等局部组成。
OpenFunction Build
当一个函数创立后,Function 会创立一个 Builder,Builder 会创立 Shipwright 的 Build 和 BuildRun,联合 Shipwright 的 BuildStrategy, Shipwright 会生成 Tekton 的 TaskRun,TaskRun 中蕴含多个 Step,函数代码就是在这些 Step 的管制下构建成函数镜像。
OpenFunction Serving
如前所述,OpenFunction 当初反对 Knative 同步函数运行时和 OpenFunction 异步函数运行时。二者都能够和 Dapr 集成,区别在于 Knative 同步函数运行时因为输出来自 HTTP 申请,只用到了 Dapr 的 output binding 和 pubsub 的 publish 局部;而 OpenFunction 异步函数运行时的输出和输入都是通过 Dapr 对接中间件或云服务,所以用到了 Dapr 的 input 和 output binding 或 pubsub 的 publish 和 subscribe.
咱们将来打算反对 KEDA http-addon 作为另一个同步函数运行时,同时也将探讨通过 pool 的技术优化函数冷启动的工夫。
OpenFunction Events
OpenFunction Events 是受 Argo Events 启发,其和 Argo Events 的不同之处在于 OpenFunction 的 EventBus 因为应用了 Dapr 的 pubsub 与底层的 message queue 是解耦的,这意味着它并不会绑定到某个云平台或者开源软件上。当 EventSource 收到内部事件后,有两条门路:它能够间接触发一个同步函数,也能够将事件写入到 EventBus 进行长久化。事件写入 EventBus 后也有两种解决形式:它能够间接触发一个异步函数;也能够定义一个 Trigger 来对事件进行筛选,筛选出感兴趣事件后,可触发一个同步函数,或者将筛选出的事件写回到 EventBus 作为输入。
OpenFunction Functions Framework
Functions Framework 是 OpenFunction 的另一个重要组成部分,由 context、plugins、Runtime、Framework 这形成。Framework 读取 OpenFunction 的 Context,将 Function 的上下文读取进去,并且查看这个函数有没有插件,如果有的话则将插件注册进来,而后创立 Runtime 并且启动。当同步或者异步函数触发后,由 Runtime 管制函数运行的生命周期。首先会执行插件的 pre-phase hooks,再调用用户函数,之后调用插件的 post-phase hooks, 最初解决这个函数输入。
退出插件的机制的很大一部分起因是想在这个函数执行的前后,执行一些用户不须要关怀的自定义逻辑。比方 OpenFunction 和 SkyWalking 的集成,就须要在这个函数执行前后做一些解决,这个咱们稍后开展。
FaaS 可观测性: SkyWalking v9 助力 OpenFunction 实现函数可观测
函数的性能对用户来说比拟重要,于是通过和 SkyWalking 社区的充沛探讨和单干,OpenFunction 在 v0.6.0 实现了与 SkyWalking 的集成,用户通过简略的配置就能通过 SkyWalking v9 监测函数的性能。
以下面的同步函数触发异步函数为例,为了监测同步和异步函数的性能,用户只须要在函数的 annotation 做如下配置即可(也能够将配置放入 configmap 以对所有函数失效):
做好上述 tracing 的配置,部署函数后,用户将能够在 SkyWalking V9 的 FaaS 页面看到如下函数调用链及性能数据:
残缺示例详见:https://github.com/OpenFuncti...
SkyWalking 与 OpenFunction 集成 Demo 详见:http://demo.skywalking.apache...
Case Study: OpenFunction 在主动驾驶畛域的利用
OpenFunction 有个社区用户驭势科技是主动驾驶行业的,他们把 OpenFunction 利用于主动驾驶,上面咱们看看 OpenFunction 在驭势科技的利用。
驭势科技主动驾驶场景
如上图所示,主动驾驶的场景比较复杂,设计的模块比拟多包含车辆检测、调度命令散发、环境感知、行人躲避、路由布局、底盘管制、多车协同等等。
为什么主动驾驶厂商须要一个云厂商中立的 FaaS 平台?
起因有以下几点:
- 不同的客户要求部署到不同的云厂商
- 一些客户的车端数据比拟敏感,要求放到和私有云隔离的环境
- 数据处理逻辑多样,来自同一数据源的数据在不同场景下的解决逻辑不尽相同
- 数据处理逻辑常常变动
- 主动驾驶波及的模块较多,不同的模块由不同的团队负责,须要多语言反对
- 大量车端数据须要实时处理
- 主动驾驶车辆也有潮汐的个性,数据处理需要有顶峰和低谷
此外,不同的云厂商有不同的后端服务,如果没有一个云厂商中立的 FaaS 平台,对于同一解决逻辑则须要为对接的每一个云厂商都实现类似的实现。
应用 OpenFunction 同步与异步函数解决车辆数据
驭势科技应用 OpenFunction 解决车端数据的归档:
- 同步函数接管申请并合成工作并发送至音讯队列
- 音讯队列中的子工作触发异步函数运行
- 用不同语言编写的异步函数解决不同的子工作,并将处理结果发送至不同的后端服务
- 利用音讯队列解耦生产者和消费者函数
FaaS 利用场景概览
据 CNCF Serverless 白皮书所示,FaaS 能够利用到如下泛滥场景中去:
- HTTP REST APIs for web applications
- Mobile backends
- Executing logic in response to storage changes like S3, database (insert, update, trigger, delete)
- Performing analytics on IoT sensor input messages (such as MQTT messages)
- Stream processing at scale (ETL, analyzing or modifying data in motion)
- Business logic like order processing, stock trade processing
- Chatbot
- Serving machine learning and AI models
- Batch jobs or scheduled tasks: Jobs that require intense parallel computation, IO, or network for only a few minutes
- Continuous integration pipelines
概括地说,Serverless 架构次要解决 IaaS, PaaS, CaaS 无奈高效解决或解决不了的问题:
- 高效地解决新问题:Solved a brand new problem efficiently where an on-demand model wasn’t available
- 高效地解决老问题:Solved a traditional cloud problem much more efficiently (performance, cost)
- 解决“大”的问题:Showed a dimension of “largeness”, whether in size of data processed or requests handled
- 解决弹性的问题:Showed resilience by scaling automatically (up and down) with a low error rates
- 解决快的问题:Brought a solution to market much faster than previously possible (days to hours)
OpenFunction 社区
OpenFunction 曾经逐步被越来越多的公司采纳:
- 国内某电信公司采纳 OpenFunction 构建云函数计算平台
- 驭势科技 (UISEE) 采纳 OpenFunction 解决车端数据
- 全象低代码平台采纳 OpenFunction 实现插件机制
也有越来越多的社区贡献者参加到了 OpenFunction 我的项目中来:
- 次要 Maintainer 来自 KubeSphere 团队
- SkyWalking PMC 成员张伟 @arugal 实现了 SkyWalking 和 OpenFunction Go 版 Functions Framework 的集成
- 驭势科技 (UISEE) 正在参加 Nodejs 和 Python 版 Functions Framework 的开发
- 全象团队参加了命令行工具 ofn 的开发
- @Geffzhang 正在参加 dotNet 版 Functions Framework 的开发
OpenFunction 曾经在 2022 年 4 月 26 日经 CNCF 技术监督委员会(TOC)投票被正式接收为 CNCF 沙箱我的项目,欢送更多的社区贡献者参加到 OpenFunction 我的项目中来。
退出 OpenFunction 社区:
- 微信:搜寻并增加公众号 kubesphere , 回复 OpenFunction
- Slack: https://slack.cncf.io 注册并搜寻 #openfunction
- Discord: https://discord.gg/hG3yc6uAyC
OpenFunction 路线图
OpenFunction 将在之后的开发中,将重点放在如下性能上:
- 反对更多语言的异步函数框架包含 Nodejs, Python, Java 和 .NET
- 反对将 Java 函数编译成 Native 程序运行在 Quarkus 环境中
- 应用 KEDA 的 http-add-on 作为 Knative Serving 之外同步函数运行时的又一个抉择
- 反对 OpenTelemetry 生态作为 SkyWalking 之外的另一个函数 Tracing 的计划
- 减少 OpenFunction 控制台
- 实现 Serverless 工作流
- 对在边缘运行的函数有更好的反对
- 预研基于 Pool 的冷启动优化计划
- 应用 WebAssembly 作为更加轻量的运行时,联合 Rust 函数来减速冷启动速度
函数示例
上面是两个函数的例子,一个异步函数,一个同步函数触发异步函数。
异步函数示例
上面是用异步函数进行日志告警的例子,K8s 的日志被收集并发送到 Kafka 后能够触发异步函数,异步函数找到日志中的某些谬误后能够发送告警到 Notification Manager,最初 Notification Manager 会发告诉到 Slack。
函数的代码及定义详见:https://github.com/OpenFuncti...。
同步函数触发异步函数
上面是一个同步函数触发异步函数的例子,同步函数接管 HTTP 申请,解决后将处理结果通过 Dapr 发送到 Kafka,Kafka 中的 Event 进而会触发异步函数。
同步函数的代码及定义详见:https://github.com/OpenFuncti...。
异步函数的代码及定义详见:https://github.com/OpenFuncti...。
controller-manager 被重启后,同样会依据配置的变动,把局部资源类型主动转化成联邦资源的逻辑,也就是说,在 Host 集群创立的这部分资源会主动同步到所有成员集群,理论的多集群同步靠 kubefed-controller-manager 来执行。以下资源会被主动创立联邦资源下发:
本文由博客一文多发平台 OpenWrite 公布!