无法从Jython模块导入Java类

13 投票
2 回答
8384 浏览
提问于 2025-04-17 15:53

注意:我找到了问题的解决办法,并且自己回答了。不过,我还是不明白为什么那个设置是错的,导致了这个问题。我仍然希望能有一个关于Jython导入系统如何工作的好解释;如果有人愿意回答这个问题,我会很感激。


我正在一个现有的Java EE项目上工作,需要用Python进行一些计算。我现在处于集成测试的初期阶段,但已经遇到了问题。我读过Jython书的第10章,但还是找不到解决办法。我也看过第8章(关于代码重用的模块和包),但对我来说还是不太清楚。

如果能解释一下Jython的导入系统是怎么工作的,以及如何配置它,我会非常感激。

问题:

$ jython -v
import: 'exceptions' as org.python.core.exceptions in builtin modules
Jython 2.5.3 (2.5:c56500f08d34+, Aug 13 2012, 14:54:35) 
[Java HotSpot(TM) Server VM (Oracle Corporation)] on java1.7.0_10
import: import site # precompiled from /home/me/jython/2.5.3/Lib/site$py.class
import: 'sys' as sys in builtin modules
import: import os # precompiled from /home/me/jython/2.5.3/Lib/os$py.class
import: 'errno' as org.python.modules.errno in builtin modules
import: 'posix' as org.python.modules.posix.PosixModule in builtin modules
import: import posixpath # precompiled from /home/me/jython/2.5.3/Lib/posixpath$py.class
import: import stat # precompiled from /home/me/jython/2.5.3/Lib/stat$py.class
import: 'java' as java package
import: 'File' as java class
import: 'IOException' as java class
import: 'org' as java package
import: 'Py' as java class
Type "help", "copyright", "credits" or "license" for more information.

>>> import pendulum.generator.BuildingType
import: import pendulum # precompiled from /path/to/project/build/classes/pendulum/__init__$py.class
import: import pendulum.generator # precompiled from /path/to/project/build/classes/pendulum/generator/__init__$py.class
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
ImportError: No module named BuildingType

我的问题是:我哪里做错了,怎么才能成功导入BuildingType接口?也许问题出在CLASSPATH上,但我不知道应该设置成什么值。


代码组织:

$ tree build/classes/pendulum/generator/ src/pendulum/generator/
build/classes/pendulum/generator/
├── BuildingType.class
├── __init__.py
└── __init__$py.class

src/pendulum/generator/
├── BuildingType.java
└── __init__.py

私有Jython注册文件定义的导入路径:

$ cat ~/.jython 
python.path=\
/path/to/project/build/classes:\
/path/to/project/src:\
/home/me/jdevel/extras/2.5.3/Lib:\
/home/me/jdevel/extras/2.5.3/Lib/site-packages

我确定Jython能够找到这些路径,因为我在Jython提示符下用sys.path检查过。

BuildingType.java

package pendulum.generator;

public interface BuildingType {
    public String getBuildingName();
    public String getBuildingAddress();
    public String getBuildingId();
}

2 个回答

4

你需要设置 CLASSPATH 和 python.path。

在相同的目录结构下,这样做对我有效:

jython10$ CLASSPATH=build/classes/  jython -v Building.py
import: 'exceptions' as org.python.core.exceptions in builtin modules
import: import site # precompiled from /usr/local/Java/jython2.5.3/Lib/site$py.class
import: 'sys' as sys in builtin modules
import: import os # precompiled from /usr/local/Java/jython2.5.3/Lib/os$py.class
import: 'errno' as org.python.modules.errno in builtin modules
import: 'posix' as org.python.modules.posix.PosixModule in builtin modules
import: import posixpath # precompiled from /usr/local/Java/jython2.5.3/Lib/posixpath$py.class
import: import stat # precompiled from /usr/local/Java/jython2.5.3/Lib/stat$py.class
import: java package as '/Users/sdm7g/jaxp/jython10/build/classes/pendulum'
import: 'pendulum' as java package
import: 'pendulum' as java package
import: java package as '/Users/sdm7g/jaxp/jython10/build/classes/pendulum/generator'
import: 'pendulum.generator' as java package
import: 'BuildingType' as java class

参考资料:使用 CLASSPATH(Jython 书籍)。

4

经过很多时间的尝试和错误,我终于自己找到了答案。

.jython 应该像这样写:

python.path=\
/path/to/project/build:\
/path/to/project/src:\
/home/me/jdevel/extras/2.5.3/Lib:\
/home/me/jdevel/extras/2.5.3/Lib/site-packages

而不是这样:

python.path=\
/path/to/project/build/classes:\
/path/to/project/src:\
/home/me/jdevel/extras/2.5.3/Lib:\
/home/me/jdevel/extras/2.5.3/Lib/site-packages

特别要注意的是,/path/to/project/build/classes 加到导入路径是错误的(即使它看起来符合文件系统的结构),而 /path/to/project/build 是正确的,这样就解决了问题。

撰写回答