我正在使用带有SparkContext的Jupyter笔记本和Python内核。一位同事编写了一些Python代码,用于通过ipykernel事件连接Spark事件。当我们从笔记本单元导入他的模块时,它适用于我们需要支持的所有组合:Python 2.7和3.5,Spark 1.6和2.x,仅限Linux。
现在我们要为所有Python内核自动启用该代码。我把导入到我们的sitecustomize.py
。这适用于Spark 2.x,但不适用于Spark 1.6。使用Spark 1.6的内核不再获得sc
,并且有些东西如此搞砸,以至于像matplotlib.cbook
之类的无关导入失败了。当我使用计时器延迟导入几秒钟时,它可以工作。
显然,sitecustomize.py
中的代码执行得太早,无法导入连接Spark和ipykernel的模块。
我正在寻找一种方法来延迟导入,直到Spark和/或ipykernel完全初始化。但在任何笔记本单元执行之前,它仍应作为内核启动的一部分执行。
我发现this trick延迟了代码执行,直到sys.argv
被初始化。但我认为它不能用于像sc
这样的全局变量,因为Python全局变量仍然是模块的本地变量。到目前为止,我能想到的最好的方法是使用计时器每秒检查sys.modules
中是否存在某些模块。但这不是很可靠,因为我不知道如何区分完全初始化的模块和仍在加载过程中的模块。
关于如何挂钩在启动期间执行较晚的启动代码的任何想法?特定于pyspark和/或ipykernel的解决方案将满足我的需求。
答案 0 :(得分:2)
嗯,你并没有详细说明你遇到的错误。
我认为为ipython内核定制启动行为的规范方法是设置配置文件并设置exec_lines
选项。
例如,您可以放入~/.ipython/profile_default/ipython_config.py
# sample ipython_config.py
c = get_config()
c.InteractiveShellApp.exec_lines = [
'import numpy',
'import scipy'
]
c.InteractiveShellApp.exec_files = [
'mycode.py',
'fancy.ipy'
]