基于Serverless架构的Python Blog开发(原生开发与Flask框架结合)

前言

Serverless架构是一个新的概念,也能够说是一个新的架构或者技术,可是不管他有多新,都不能一会儿完成现有都开发习惯到Serverless架构的过渡,让现有的工程师放弃现有的Express、Koa、Flask、Django等框架直接在Serverless架构上开发项目,显然是不可能,就算可能,这也须要时间进行适应和过渡。
那么在这个过渡的期间咱们是否能够考虑将现有的框架部署到Serverless架构上?接下来,咱们以Flask框架进行一个简单的测试:python

  • 测试四种接口:git

    • Get请求(可能涉及到经过路径传递参数)
    • Post请求(经过Formdata传递参数)
    • Get请求(经过url参数进行参数传递)
    • Get请求(带有jieba等计算功能)
  • 测试两种状况:github

    • 本地表现
    • 经过Flask-Component部署表现
  • 测试两种性能:flask

    • 传统云服务器上的性能表现
    • 云函数性能表现

首先是测试代码:api

from flask import Flask, redirect, url_for, request
import jieba
import jieba.analyse

app = Flask(__name__)


@app.route('/hello/<name>')
def success(name):
    return 'hello %s' % name


@app.route('/welcome/post', methods=['POST'])
def welcome_post():
    user = request.form['name']
    return 'POST %s' % user


@app.route('/welcome/get', methods=['GET'])
def welcome_get():
    user = request.args.get('name')
    return 'GET %s' % user


@app.route('/jieba/', methods=['GET'])
def jieba_test():
    str = "Serverless Framework 是业界很是受欢迎的无服务器应用框架,开发者无需关心底层资源便可部署完整可用的 Serverless 应用架构。Serverless Framework 具备资源编排、自动伸缩、事件驱动等能力,覆盖编码、调试、测试、部署等全生命周期,帮助开发者经过联动云资源,迅速构建 Serverless 应用。"
    print(", ".join(jieba.cut(str)))
    print(jieba.analyse.extract_tags(str, topK=20, withWeight=False, allowPOS=()))
    print(jieba.analyse.textrank(str, topK=20, withWeight=False, allowPOS=('ns', 'n', 'vn', 'v')))
    return 'success'


if __name__ == '__main__':
    app.run(debug=True)

这段测试代码是比较有趣的,它包括了最经常使用的请求方法、传参方法,也包括简单的接口和稍微复杂的接口。服务器

本地表现

本地运行以后,经过Postman进行三个接口简单测试:架构

  • Post参数传递:

  • Get参数传递:

经过Flask-Component部署表现

接下来,咱们将这个代码部署到云函数中:并发

经过Flask-Component部署,能够参考Tencent给予的文档,Github地址https://github.com/serverless...app

Yaml文档内容:框架

FlaskComponent:
  component: '@gosls/tencent-flask'
  inputs:
    region: ap-beijing
    functionName: Flask_Component
    code: ./flask_component
    functionConf:
      timeout: 10
      memorySize: 128
      environment:
        variables:
          TEST: vale
      vpcConfig:
        subnetId: ''
        vpcId: ''
    apigatewayConf:
      protocols:
        - http
      environment: release

部署完成

接下来测试咱们的目标三个接口

  • Get经过路径传参:

  • Post参数传递:

  • Get参数传递:

经过上面的测试,咱们能够看出,经过Flask-Component部署的云函数,也是能够具有经常使用的几种请求形式和传参形式。

能够这样说,通常状况下,用户的Flask项目能够直接经过腾讯云提供的Flask-component快速部署到Serverless架构上,能够获得比较良好的运行。

简单的性能测试

接下来对性能进行一波简单的测试,首先购买一个云服务器,将这个部分代码部署到云服务器上。
在云上购买服务器,保守一点买了1核2G


而后配置环境,到服务能够跑起来:


经过Post设置一下简单的Tests:

而后对接口进行测试:

很是顺利完成了接口测试:

能够经过接口测试结果进行部分可视化:

同时对数据进行统计:

能够看到,经过上图和上表,服务器测的总体响应时间都快于云函数的响应时间。并且能够看到函数存在冷启动,一按出现冷启动,其响应时间会增加20余倍。在因为上述测试,仅仅是很是简单的接口,接下来咱们来测试一下稍微复杂的接口,使用了jieba分词的接口,由于jieba分词接口存在:
测试结果:

可视化结果:

经过对Jieba接口的测试,能够看到虽然服务器也会有因分词组件进行初始化而产生比较慢的响应时间,可是总体而言,速度依旧是远远低于云函数。
那么问题来了,是函数自己的性能有问题,仍是增长了Flask框架+APIGW响应集成以后才有问题?
接下来,作一组新的接口测试,在函数中,直接返回内容,而不进行额外处理,看看函数+API网关性能和正常状况下的服务器性能对比

能够看出虽然最小和平均耗时的区别不是很大,可是最大耗时基本上是持平。能够看出来,框架的加载会致使函数冷启动时间长度变得异常可怕。
接下来经过Python代码,对Flask框架进行并发测试:
对函数进行3次压测,每次并发300:

===========task end===========
total:301,succ:301,fail:0,except:0
response maxtime: 1.2727971077
response mintime 0.573610067368

===========task end===========
total:301,succ:301,fail:0,except:0
response maxtime: 1.1745698452
response mintime 0.172255039215

===========task end===========
total:301,succ:301,fail:0,except:0
response maxtime: 1.2857568264
response mintime 0.157210826874

对服务器进行3次压测,一样是每次并发300:

===========task end===========
total:301,succ:301,fail:0,except:0
response maxtime: 3.41151213646
response mintime 0.255661010742

===========task end===========
total:301,succ:301,fail:0,except:0
response maxtime: 3.37784004211
response mintime 0.212490081787

===========task end===========
total:301,succ:301,fail:0,except:0
response maxtime: 3.39548277855
response mintime 0.439364910126

经过这一波压测,咱们能够看到这样一个奇怪现象,那就是在函数和服务器预热完成以后,连续三次并发301个请求。函数的总体表现,反而比服务器的要好。这也说明了在Serverless架构下,弹性伸缩的一个很是重要的表现。传统服务器,咱们若是出现了高并发现象,很容易会致使总体服务受到严重影响,例如响应时间变长,无响应,甚至是服务器直接挂掉,可是在Serverless架构下,这个弹性伸缩的能力是云厂商帮助咱们作的,因此在并发量达到必定的时候,其实Serverless架构的优点变得会更加明显。

总结:

  • Flask是能够经过很简单的方法上Serverless架构,用户基本上能够按照原生Flask开发习惯来开发Flask项目,尤为是使用Flask开发接口服务的项目,更是能够比较容易的迁移到Serverless架构。
  • 总体框架迁移上Serverless架构可能要要注意几个额外的点:
  1. 若是接口比较多,可能要按照资源消耗比较大的那个接口来设置内存大小,以我例子中的状况,非jieba接口使用的时候,可使用最小内存(64M),jieba接口使用的时候,须要256M的内存,而整个项目是一体的,只能设置一个内存,因此为了保证项目可用性,就会总体设置为256M的内存,这样一来若是另外三个接口访问比较多的前提下,可能资源消耗会相对增长比较大,因此,若是有条件的话,可考虑将资源消耗比较大的接口额外提取出来;
  2. 云函数+API网关的组合对静态资源以及文件上传等的支持可能并非十分友好,尤为是云函数+API网关的双重收费,因此这里建议将Flask中的一些静态资源统一放在对象存储中,同时将文件上传逻辑修改为优先上传到对象存储中,能够参考以前的文章:【实践与踩坑】用Serverless怎么上传文件?
  • 框架越大,或者框架内的资源越多函数冷启动的时间可能会越大。这一点是很是值得重视的。在刚才测试过程当中,非框架下,最高耗时是平均耗时的3倍,而在加载Flask框架和Jieba的前提下,最高耗时是平均的10+倍!若是能够保证函数都是热启动还好,一旦出现冷启动,可能会有必定的影响。
  • 因为用户发起请求是客户端到API网关再到函数,而后从函数回到API网关,再回到客户端,这个过程相对直接访问服务器得到结果的链路明显长了一些,因此在实际测试过程当中小用户量对的表现发而不是很好,几回测试,基本上1核2G的服务器都是优于函数表现。可是当并发量上来的以后能够看到函数的表现实现了大超车,一度超越这台1核2G的服务器。那么这里有一个有趣的结论:对于极小规模请求,函数是按量付费,虽然性能上有必定的劣势,可是按量付费在价格上有必定的优点;当流量逐渐变大以后,函数在性能上的优点也逐渐凸显。

我相信,Serverless架构会随着时间的发展,愈加的成熟,目前可能还有或多或少的问题,可是不久的未来,必定不负众望。


相关文章
相关标签/搜索