无服务器计算的简便方法

无服务器计算本身(简称为“无服务器”)在2014年发布了AWS Lambda(首批无服务器平台之一)之后获得了广泛的普及。从那时起,无服务器方法的普及程度一直在增长,但是遗憾的是,工具的开发并没有跟上步伐。



我叫弗拉迪斯拉夫·坦科夫(Vladislav Tankov),在2018-2020年,我在ITMOJetBrains公司硕士课程学习,自2017年以来,我一直在JetBrains工作



在2018年夏天,在JetBrains黑客马拉松上,我和我的一些同事试图为Kotlin语言制作一个工具,该工具可以通过分析应用程序代码来简化无服务器应用程序的创建。



黑客马拉松之后,我已经在JetBrains公司硕士课程的科学工作框架内,我决定继续开发该项目。在过去的两年中,该工具已大大扩展并获得了功能,但保留了其名称-Kotless或Kotlin Serverless Framework。



什么是无服务器



首先,让我们记住最简单的无服务器计算平台的组成。该平台包括三个主要组件:



  • 无服务器功能的执行系统-处理某些事件的小型应用程序;
  • 从外部世界(或云平台,例如AWS)到平台的事件系统的一组不同接口,例如HTTP接口;
  • 事件系统本身,它提供事件从接口到函数的传递以及处理结果从函数到接口的传递。


这三个组件足以构建一个相当复杂的应用程序。例如,一个Web应用程序只是一个外部HTTP接口(在AWS中,它将是APIGateway),对于处理的每个资源(如/ route / my),它都有自己的Serverless处理函数。您可以构建一个更复杂的应用程序,该应用程序使用数据库并且本身调用其他无服务器功能,如图所示。



好的,您可以构建此类应用程序,但是为什么呢?



无服务器应用程序具有许多不可否认的优势,这些优势证明了架构的合理性。



  • 无服务器功能在不需要时不起作用。确实,该功能仅处理事件-如果没有事件,为什么要占用计算资源?
  • 无服务器功能可以并行处理相同类型的事件。也就是说,如果/ route / my变得非常流行,并且一千个用户一次请求它,那么无服务器平台可以简单地启动1000个处理程序,每个事件一个。


这些点加起来也许是最重要的无服务器的口头禅之一:无服务器应用程序从零扩展到无穷大。这样的应用程序在不需要时不会花钱,并且能够在需要时每秒处理数千个请求。



问题



让我们看一下Kotlin语言中的一个非常简单的示例:



@Get("/my/route")
fun handler() = "Hello World"


很明显,可以使用无服务器方法来实现这样的应用程序。乍一看,创建一个带有一些DNS地址的HTTP接口并将map / my / route映射fun处理程序()就足够了



实际上,创建这样的应用程序将比添加单个注释花费更多。例如,对于AWS:



  • 您将需要实现特定的事件处理程序接口,在这种情况下为RequestStreamHandler。
  • 您将需要描述无服务器应用程序的基础结构:描述应用程序的HTTP API,描述所有处理程序功能,并将它们的功能与接口相关联,仔细选择权限。
  • 最后,您将必须收集所有处理程序功能,加载到无服务器平台中,并部署适当的基础结构。


这样简单的应用程序没有那么几个步骤,对吗?



对于那些开始以代码为基础的圣礼的人来说,我当然会注意到其中的一部分过程可以自动化,但是这种自动化本身需要研究一种全新的方法(实际上是将基础设施描述为代码)和一种新的语言。对于想要部署基本应用程序的开发人员来说,这似乎是不必要的困难任务。



有可能做些简单的事情吗?在某些情况下(特别是在这种情况下)-是的!



代码基础架构



让我们看另一面:我们不是试图强迫用户描述基础结构,而是尝试从已经编写的用户代码中派生它。



再次考虑相同的示例:



@Get("/my/route")
fun handler() = "Hello World"


我们知道用户希望该功能处理/ my /路由的请求-因此,让我们综合一个基础结构,该基础结构将使用/ my / route创建一个HTTP API ,创建所需的Serverless函数,并进行所有必要的魔术连接!



在自动化软件工程2019年的文章中,我将此方法称为代码中的基础架构。实际上,我们从隐式定义基础结构的应用程序代码中提取了基础结构的描述,也就是说,它实际上包含在代码“内部”。



应当注意,在下文中,仅考虑HTTP API应用程序的合成。可以使用类似的方法来处理队列和处理云平台的事件,但这是Kotless进一步开发的问题。



实作



希望在这一点上思路清晰,剩下三个主要问题:



  • 如何从代码中提取信息?
  • 如何基于此信息创建基础结构?
  • 如何在云中运行应用程序?


分析



嵌入式Kotlin编译器将为我们提供帮助。



尽管示例实际上是关于注释的,但实际上,可以使用完全不同的方式来定义应用程序的HTTP API(取决于所使用的库),例如:



//ktor-like style
get("my-route") {
    "Hello World"
}


为了分析任意代码,事实证明Kotlin编译器可嵌入性更加熟悉和方便(由于示例众多)。



目前,Kotless可以分析三个主要框架:



  • Kotless DSL-Kotless自己的注释框架
  • Spring Boot是一个流行的Web框架,注释被解析;
  • Ktor是流行的Kotlin Web框架,分析了扩展功能。


在分析代码的过程中,将收集Kotless模式-这是无服务器应用程序的某些独立于平台的表示。它用于综合基础架构并使分析过程独立于特定的云平台。



合成



我们将合成Terraform代码。 Terraform被选为最受欢迎的“基础结构即代码”工具之一,具有广泛的受支持的云平台,这确保Kotless能够支持新的云平台并确保应用程序部署的稳定性。



综合从Kotless模式进行,该模式包含对应用程序的HTTP API及其功能的描述,以及一些其他数据(例如,所需的DNS名称)。



对于综合本身,使用了专门创建的Terraform DSL库。综合代码如下所示:



val resource = api_gateway_rest_api("tf_name") {
    name = "aws_name"
    binary_media_types = arrayOf(MimeType.PNG)
}


DSL保证了不同Terraform资源之间的格式设置和引用完整性,从而使扩展合成资源集变得更加容易。



使用简单的Terraform应用程序将合成的代码部署到云平台。



跑步



仍然可以在无服务器平台上运行该应用程序。如前所述,所有无服务器功能本质上都是某些事件的处理程序,在我们的例子中是HTTP请求。



必须将用于创建应用程序的框架(例如,Spring Boot)和无服务器平台连接起来。为此,在构建应用程序时,Kotless在应用程序代码中添加了一个特殊的“调度程序”-一个特定于平台的事件处理程序,充当应用程序中使用的框架和云平台之间的适配器。



工具



该工具本身(包括用于创建基础结构的整个描述管道)已作为Gradle构建系统的插件实现。而且,所有主要模块都是单独的库,这大大简化了对其他构建系统的支持。



使用插件非常简单。配置完成后,用户只有一个摇篮任务-部署,这需要所有必要的步骤来部署当前应用程序到云中。



从用户端进行定制也非常简单。插件本身首先被应用:



plugins {
  io("io.kotless") version "0.1.5" apply true
}


之后,用户添加他需要的框架:



dependencies {
  //Kotless DSL 
  implementation("io.kotless", "lang", "0.1.5")
}


最后,它设置对AWS的访问权限,以便Kotless可以部署:



kotless {
  config {
    bucket = "kotless.s3.example.com"

    terraform {
      profile = "example"
      region = "us-east-1"
    }
  }
}


本地发布



很容易看出,最后一点要求用户熟悉AWS并至少拥有一个AWS账户。这样的要求使想要在本地尝试该工具的用户感到恐惧。



这就是为什么Kotless支持本地启动模式的原因。使用所选框架的标准功能(Ktor,Spring Boot和Kotless DSL当然都可以在本地运行应用程序),Kotless会将应用程序部署到用户的计算机上。



此外,Kotless可以运行AWS仿真(由LocalStack使用),以便用户可以在本地检查应用程序的行为是否符合预期。



进一步的发展



在编写Kotless(以及我的硕士学位论文)时,我设法在ASE 2019,KotlinConf 2019和Talking Kotlin播客中进行介绍。总体而言,该工具受到好评,尽管到2019年底它似乎不再是一种新颖性了(到那时,Zappa,Claudia.js和AWS Chalice变得很流行)。



但是,目前,Kotless可能是Kotlin世界中同类产品中最著名的工具,我当然打算开发它。



我计划在不久的将来稳定当前的API和功能,准备教程和演示项目,以使新用户更轻松地学习该工具。



例如,我们计划准备一组有关如何使用Kotless创建聊天机器人的教程。似乎无服务器技术非常适合此用例(并且Kotless用户已经在编写Telegram机器人),但是缺少合适的工具显着阻碍了广泛使用。



最后,该工具整个体系结构最重要的方面之一是其平台独立性。在不久的将来,我希望支持Google Cloud Platform和Microsoft Azure,这将使应用程序实际上可以通过一个按钮在云之间迁移。



我希望Kotless和类似的工具能够真正帮助将无服务器技术引入大众,并且越来越多的应用程序仅在运行时才会消耗资源,从而略微减少了宇宙的熵:)



All Articles