一文带你看懂并优化AI应用的架构设计
AI技术现在很火,各大公司都开始朝着这个领域发力。他们不仅创建出很多出色成果,还通过一系列技术、工具和服务,帮助普通开发者也能轻而易举地开发出新颖的AI应用。
本文将告诉大家如何在Akamai云计算平台上优化一个基于Qwik和OpenAI服务的Web项目。具体来说,我们将通过本文详细剖析项目的整体架构和优化方式,从而为广大开发者带来启发。
基本架构
假设有这样的一个Web应用:
在两个文本框中输入两个“对手”,随后由AI来决定在战斗中谁会获胜。该应用还提供了一些解释决策原因以及创建图像的选项。该应用相当基础,用户提交两个对手,然后应用程序即时返回一个由AI生成的响应,从中得知哪个对手会在战斗中获胜。
架构也很简单:
客户端向服务器发送请求。
服务器构造提示并将提示转发给OpenAI。
OpenAI向服务器返回一个流式响应。
服务器对流式响应进行任何必要的调整,并将其转发给客户端。
该应用搭建在Akamai的云计算服务(以前的Linode)上,不过下文将要介绍的内容对任何云平台应该都适用。
看起来像是高级餐厅里的服务员, ️ ️则是“一只眼睛”,或者说是AI
从技术上讲,这是完全可行的,但存在一些问题,特别是当用户提交重复请求时。将响应存储在我们自己的服务器上,并且只针对唯一请求访问OpenAI,可能会让整个过程更快速,更具成本效益。
这就需要假设我们不需要每个请求都是非确定性的(即相同的输入产生不同的输出)。我们可以假设相同的输入产生相同的输出是可接受的。毕竟,谁会赢得一场战斗的预测结果可能并不会改变。
添加数据库架构
如果我们想要存储来自OpenAI的响应,一种实际的放置地点是某种类型的数据库,这种数据库应该能让我们围绕两个对手进行快速、简单的查找。这样,在收到请求时,就可以首先检查数据库:
客户端向服务器发送请求。
服务器检查数据库中是否存在与用户输入相匹配的条目。
如果存在匹配的记录,服务器使用该数据回复并完成请求。跳过后续步骤。
如果不存在匹配的记录,则服务器继续执行上一小节中流程的第三步(联系OpenAI)。
在关闭响应前,服务器将OpenAI的结果存储在数据库中。
虚线代表可选请求,而 看起来像是一个硬盘
有了这样的设置,任何重复的请求都将由数据库直接处理。通过将一些OpenAI请求设置为可选,我们还有可能降低用户体验的延迟,同时通过减少API请求的数量来节省费用。
这是一个很好的开始,特别是如果服务器和数据库位于同一个地区。这将比访问OpenAI的服务器快得多。
然而,随着应用程序变得更加受欢迎,我们可能会开始吸引来自世界各地的用户。数据库查询的速度自然是越快越好,但往返传输数据造成的延迟又该如何消除?
我们可以通过将应用移动到距离用户更近的地方来解决这个问题。
引入边缘计算
边缘(Edge)指一种让内容尽可能接近用户的方式。对一些应用场景来说,边缘可能意味着物联网设备或手机基站,但在Web应用之类的场景中,最典型的边缘往往是内容分发网络(CDN)。
CDN是一种全球分布的计算机网络,可以从网络中最近的节点响应用户请求。传统的CDN是为静态资产设计的,但近年来,CDN开始支持边缘计算。
有了边缘计算,我们可以将很多后端逻辑移动到距离用户非常近的地方,而且不仅限于计算!大多数边缘计算提供商还在同一边缘节点上提供某种最终一致的键值存储服务。
这会对我们的应用程序产生什么影响?
客户端向我们的后端发送请求。
边缘计算网络将请求路由到最近的边缘节点。
边缘节点检查与用户输入匹配的键值存储中是否存在现有记录。
如果存在匹配的记录,边缘节点将使用该数据回复,完成请求。跳过后续步骤。
如果不存在匹配的记录,则边缘节点将请求转发到源服务器,源服务器再将其传递给OpenAI……
在关闭响应前,服务器将OpenAI的结果存储在边缘键值存储中。
边缘节点是蓝色方框,用 表示;EdgeWorker是Akamai的边缘计算产品,用 表示;EdgeKV是Akamai的键值存储服务,用 表示。从物理距离来说,边缘节点比云中的源服务器更接近客户端
源服务器在这里可能并非绝对必要,但我们认为它的存在有一定必要性。基于数据、计算和逻辑流程考虑,这与先前的架构基本相同。主要区别在于先前存储的结果现在更接近用户,几乎可以立即返回。
注意:尽管数据被缓存在边缘,但响应仍然是动态构建的。如果不需要动态响应,将CDN放置在源服务器前并设置正确的HTTP头来缓存响应,可能是一种更简单的做法。
这样就完成了!任何重复请求几乎会立即得到响应,同时也节省了不必要的API请求。文本响应的架构问题顺利解决,但是别忘了,还有AI图像生成功能呢。
缓存图片
处理图片时,我们需要考虑内容的交付和存储。相信OpenAI有自己的解决方案,但一些企业出于安全、合规性或可靠性等原因的考虑,可能希望与图片交付和存储有关的整个基础设施都完全由自己掌控。一些情况下,企业甚至可能宁愿运行自己的图像生成服务,而不是使用OpenAI。
在当前的工作流程中,用户发出请求,最终请求传递到OpenAI。OpenAI生成图像,但不返回图像,而是返回一个JSON响应,其中包含图像的URL,该URL托管在OpenAI的基础设施上。使用此响应时,可以用URL将<img>标签添加到页面,从而启动另一个请求来获取对应的图像。
如果要将图像托管在自己的基础设施上,需要一个存储图像的地方。我们可以将图像写入源服务器的磁盘,但这可能会快速使用大量磁盘空间,并且必须升级服务器,这可能会很昂贵。对象存储是一种更便宜的解决方案,我们可以将图像上传到自己的对象存储实例,并使用该实例对应的URL。
这解决了存储问题,但对象存储桶通常都部署在单个区域,这与我们在数据库中存储文本时遇到的问题类似。单个区域可能距离用户很远,这可能会导致很高的延迟。
又到了边缘的用武之地了。为纯静态资产添加CDN功能其实非常简单。一旦配置完成,CDN将在初始请求时从对象存储中拉取图像,并将其缓存以供来自同一区域的后续访问者直接交付。
我们的图片处理流程如下:
客户端发送请求,根据对手生成图像。
边缘计算检查该请求的图像数据是否已存在。如果存在,则直接返回URL。
图像与URL一起添加到页面,并由浏览器请求图像。
如果图像已经缓存在CDN中,则浏览器几乎能立即加载。流程结束。
如果图像尚未被缓存,CDN将从对象存储位置拉取图像,缓存一份副本供未来的请求使用,并将图像返回给客户端。这是流程的另一个结尾。
如果图像数据不在边缘键值存储中,生成图像的请求将发送到服务器,然后传递到OpenAI,后者生成图像并返回URL信息。服务器启动任务将图像保存在对象存储桶中,将图像数据存储在边缘键值存储中,并将图像数据返回给边缘计算节点。
使用新的图像数据,客户端创建图像,生成新请求,并从步骤五继续。
内容交付网络以交付卡车()和网络信号()表示,对象存储以盒子里的袜子()或存储中的对象表示
诚然,最后这种架构稍微复杂了一些,但如果应用程序要处理大量流量,这种架构也是很有必要的。
大功告成
通过所有这些改变,我们已经为唯一请求创建了AI生成的文本和图像,并为重复请求提供了来自边缘的缓存内容。结果是更快的响应时间和更好的用户体验(当然,API调用也更少)。
上述内容完全以Akamai云计算平台为例,但其实所涉及的各种数据库、边缘计算、对象存储和CDN也适用于其他平台。这是一个有着广泛适用性的思路。只不过通过与Akamai的云计算和边缘计算服务整合不仅仅能改善性能,还可以获得很多非常酷的安全功能。
例如,在Akamai的网络上,我们可以使用诸如Web应用程序防火墙(WAF)、分布式拒绝服务(DDoS)防护、智能爬虫检测等功能,从而更好地保障应用程序、数据、客户信息的安全性。