python 导入模型h20_Python Web应用程序中H20的内存泄漏

博主在使用Python Flask框架构建的决策引擎中遇到H2O 3.20.0.7版本内存泄漏问题。在每次HTTP请求时,H2O计分卡用于生成用户评分,导致内存逐渐增加并抛出'Cannot allocate memory'错误。尝试了通过Python的垃圾回收和定期服务重启来缓解问题,但效果有限。博主计划引入内存分析器和将H2O服务分离到独立服务器。建议是使用MOJO和轻量级MOJO运行时,以减少内存占用,并确保及时清理内存对象。
摘要由CSDN通过智能技术生成

我的决策引擎基于带有uWSGI和Nginx的python-flask框架构建。作为通过HTTP请求评估用户的一部分,我运行h2o == 3.20.0.7的计分卡来生成分数以对用户做出决策。下面给出一些有关我如何在应用程序中使用h2o的清晰说明

h2o.init() # initialize

predictions = h2o.mojo_predict_pandas(features_df, MODEL_MOJO_ZIP_FILE_PATH, MODEL_GENMODEL_JAR_PATH) # generate score

# features_df -> pandas DF

应用开始时的H2o详细信息

-------------------------- ----------------------------------------

H2O cluster uptime: 01 secs

H2O cluster timezone: Etc/UTC

H2O data parsing timezone: UTC

H2O cluster version: 3.20.0.7

H2O cluster version age: 1 year, 7 months and 10 days !!!

H2O cluster name: H2O_from_python_unknownUser_t8cqu9

H2O cluster total nodes: 1

H2O cluster free memory: 1.656 Gb

H2O cluster total cores: 4

H2O cluster allowed cores: 4

H2O cluster status: accepting new members, healthy

H2O connection url: http://localhost:54321

H2O connection proxy:

H2O internal security: False

H2O API Extensions: XGBoost, Algos, AutoML, Core V3, Core V4

-------------------------- ----------------------------------------

H2o(作为单独的服务运行)和flask应用程序都在同一服务器上运行(负载平衡器下的3至8台服务器)。

有时内存使用量在稳定增加并抛出Cannot allocate memory

在计算计分卡时。然后有时它会自动自行解决。记分卡与HTTP请求下的其他规则(顺序运行)一起运行,但该错误仅在计算记分卡时报告。假设,它涉及到h2o时需要更多的内存。在此周期内,流量看起来是相同的。所以我希望这不是由于人流量大。

根据我的调查,某些内存挂在某处,并且没有释放。

我做了以下变通办法来释放挂起的内存并减少影响

来自Python的h2o中的1个GC

没有经历积极的影响。

2计划的服务重新启动-用新服务器优雅地替换旧服务器。

经历了积极的影响。60-70%的错误消失了。

我想了解内部发生的情况,并介绍适当的修复方法而不是解决方法。帮助将不胜感激。

供您参考,

我没试过

1将H2o群集更新为新版本,因为当前版本太旧(1年,7个月和11天)-同意最好使用最新版本,但不能保证不会再出现相同版本,并且需要付出努力在验证分数,结果等方面也更多

2我没有通过使用来限制H2o的内存使用,min_mem_size因为我不希望记分卡评估失败。

我打算

1添加一个内存分析器,以轻松了解与我的应用相关的每个部分/进程的内存利用率

编辑

2从flask应用程序中分离出h2o并将其托管在不同的服务器中,以便轻松扩展。-尽管如此,同样的问题还是可能的。

我经过了一些内存分析器,但仍无法完成最适合我当前情况的分析器。我也想对此提出建议。

谢谢

解决方案

您描述的方法与我建议的方法不同。

为了简单起见(忽略多个服务器和负载平衡),我将绘制设置的架构图,如下所示:

[Client HTTP program] -> [python flask app] -> [java scoring backend]

这种高级架构很好,但是您已经实现了Java评分层部分,我将说这是最困难的方法,而不是预期的方法。

预期的方法是仅使用MOJO和轻量级的MOJO运行时。一种简单的方法是将MOJO包装在一个非常简单的最小Web服务中。

以下是MOJO的javadoc链接:

以及一个github回购,演示了如何在简单的Java servlet容器中使用MOJO:

另外,这是一个较旧的github存储库,您可能会发现使用POJO而不是MOJO很有用。MOJO更好。使用MOJO而不是POJO,但是您可以从阅读此版本库中的文档中找到帮助:

请注意,如果您以这种方式进行操作,则仍可以根据需要分别缩放/负载均衡[python flask app]和[java scoring backend]服务,尽管我希望Java的运行速度比python快得多,所以可能只需将python和java分成两个组就更容易,并使python向本地java发出请求。

好的,既然我已经讨论了最佳实践方法,那么让我指出一些我可以发现的问题(困难的方法)。

您没有提到是一次计分还是批量计分。使用完整的H2O-3服务器本身进行评分更适合于批处理评分,而一次只能对一行进行评分的效率极低。解析过程非常繁重,而计分过程一次仅占一行。这将影响延迟。

虽然您可以将MOJO对象本身读入完整的H2O-3服务器进程并将其用于批处理计分,但从来没有打算在实时HTTP工作流中执行此操作。(有趣的是,在H2O-3出现的头5年里,甚至不可能获得支持。)

如果您不自己清理,肯定会有内存泄漏。

Running the H2O-3 server process as a long-running service for scoring is not recommended. But if you really want to do it, take these steps:

The in-memory objects need to be cleaned out. You can find them with the h2o.ls() and remove them with the h2o.rm() calls in the R/python client APIs. Both the datasets and the scores would need to be cleaned up. You probably don't want to remove the model itself, though.

I don't expect you need to manually trigger garbage collections in the Java process, but you can if you want to. Personally, I only do that when I have turned on Java flags like -XX:+PrintGCDetails -XX:+PrintGCTimeStamps so I can see the effect of the compaction on how much free heap memory remains after a Full GC. I do this so I can see whether objects are really being retained, so I can confirm they are getting cleared out. I like to give those logs to http://gceasy.io and visualize them.

Do monitor the logs to see the free heap remaining after a Full GC.

Even if you are doing the right stuff in terms of cleaning up memory, give the H2O-3 server process lots of memory. I wouldn't even run it on my laptop with a smaller -Xmx than 5G. As such, I would characterize the original poster's Java heap as severely under-provisioned (H2O cluster free memory: 1.656 Gb).

If you see the free heap remaining after Full GC creeping up, restart the Java process, since this is not the standard use case and not something that gets thoroughly tested. The H2O-3 clusters are thought of by the development team as more as short-to-medium lifetime services (hours/days) than long-running services (months+, e.g. nginx/apache).

Hope that helps!

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值