2019独角兽企业重金招聘Python工程师标准>>>
换了新公司,一切也重新开始,接触到的第一个活就是可能需要将之前python写的一套数据传输的代码,改用Java实现,提高开发效率;
python代码结构很清晰,分为两部分:
- 抽取接口数据,pickle序列化后打包上传到云服务器;
- 从云服务器下载,解析入库;
我主要做的是先将解析入库这部分Java化,其中一个很大的问题就是解析pickle序列化后的数据,这个问题折磨我了2天。。
主要是好像这种问题网上很少解决方案,也不知道是不是我这操作太奇葩了。。度娘就别想了,只能借助梯子了。看过网上的示例都没有能正常跑的,或多或少都有些问题,不过也让我了解到了目前的解决方案,也主要分为两种:
- 借助Jython来做,引入jar包后,可以在Java里使用python的代码,当然这应该是对应的Java实现吧,但是感觉有点重,jar包有30多M
- 使用pyrolite包,这个包主要是用于与python通信,进行远程调用python的方法;
因为我们数据打包上传跟下载解析是分开部署的, 如果在解析那块还去单独部署个python用来解析数据,再用Java去远程调用去获取返回值,这就有点多此一举了。。所以我们这边使用的就是通过引入Jython来实现了,到时候数据打包如果也改成Java实现的话,那就再改造了。
先说说遇到的几个坑吧:
init: Bootstrapping class not in BootstrapTypesSingleton.getClassToType()[class=class org.python.core.PyBaseString]
解决这个问题花的时间最久,不解决的话使用pystring的时候会报空指针错误;之前从网上看到过类似的,需要在使用前先执行.gcMonitorGlobal方法,但是由于个人粗心。跑去调用pystring.gcMonitorGlobal,所以并没有卵用,最后仔细看错误发现是PyBaseString的问题,而PyString又是继承PyBaseString的,后来在代码中加入静态块解决该问题;
ValueError: insecure string pickle
不安全的值,原因是也是格式问题,python序列化后的格式是这样的
然后读取时,在每行尾部需要加上"\n"换行才可以
至此遇到的大问题都已经解决,其他问题的话就比较常见了(比如格式转换异常这种),主要是也没有搜到什么完整的解决方案,也是自己东拼西凑才搞定的,也是不容易,还是因为对python也不太了解吧,遇到没见过的报错有点懵,而且有时候报的错也不一定是真实的错。例如ValueError这个错,最开始报的是空指针,通过调试代码看,是Jython里的异常类toString的时候空指针,导致无法发现真实的错误,只能一步步调试,才发现。。有点坑
因为确实搜索过没有发现什么完整的解决方案或代码示例,所以整理出来希望能帮到大家!
参考网站:http://bugs.jython.org/issue2492
https://github.com/irmen/Pyrolite
https://nikoskatsanos.com/blog/2017/01/08/python-unpickling-in-java/
http://www.roman10.net/2012/10/10/loading-python-pickle-files-from-java/