对之前写的flask的debug和优化

上次写到的那个flask做的api应用,很快出现了问题

too many open files

这个报错。。。首先环境是Linux,众所周知linux会把一切都当作文件处理。所以很明显是什么资源打开了没有关闭,但我看了一下,网络流都是好好关上了的。从本地打开的文件也全部用with包装,会自动关闭,不至于没关上。而且我调用频率很低,觉得真的很奇怪,简单粗暴的用到ulimit -n去调整最大使用的文件数量,当然在高并发环境下确实需要调整,但我调整后仍旧出现了这个问题,说明已经不是单纯的并发了,这是什么代码自己把自己的性能给吃没了的情况。

 

害,实际上,就是因为我只是一个新手的原因,BytesIO也是IO呀,不关闭就会一直打开,和文件一样的性质,只不过是存在内存中的。而且flask return之后也不会自动帮我执行它的close()方法

代码片段是这样的:

try:
result: BytesIO= loop.run_until_complete(make_image(cmd, users[0], users, args=args))
except download.DownloadError:
return “不支持带有&符号的图床”
try:
resp = Response(result.getvalue(), mimetype=”image/” + cmd.format)
except AttributeError:
return “args中可能出现错误”
return resp


命名不规范很随意,没有以json返回错误代码这种细节就忽略吧,反正这个API只有我用而已(笑


可以看到第二排从协程中得到了BytesIO,可是直到return 都没有关闭
所以修改方法就是在resp构造完成后,也就是第六排后加上result.close()

到这里看起来就算是完成了,但是。。。有没有注意到,这样写既没有用到线程模版来调用方法,也完全没有异步也没用缓存,每次访问都会做一次图片合成。这样显然是不行的,迟早会跑到某一次阻塞耗死。

所以得要对flask应用本身代码进行优化?不,我懒得。。。

这里可以用ngnix反向代理,但我讨厌单独弄容器,所以用到Python的gunicorn启动,自动托管,指定进程线程数都不需要我自己考虑,它会调度,而我只需要实现功能就可以了。

网上的gunicorn的教程非常多,但ubuntu多python版本环境实在是很痛苦,很多问题很难顶,所以有些诸如使用配置文件什么的,基本上对我这种小白,在ubuntu下是不可能完成的事情…

于是乎我采用手动启动的方式去弄的

pip安装好之后

gunicorn app:app –bind=0.0.0.0:5000

就完了咯,你以为很复杂么?捏嘿嘿!