GWT Web 应用程序与动态加载类的系统类路径
在我的 GWT Web 应用程序中,我将所有 jar 文件保留在项目之外,并使用类路径变量引用它们。这允许我链接到其他项目/团队的 jar,而不必将 jar 的副本放在我的 Web 应用程序 lib 目录中。托管模式会在此系统类路径中查找类,然后将它们添加到 Web 应用程序类路径中,警告我它正在这样做。当我部署构建系统时,只会引入我需要在网络应用程序中发送的 jar,这不是问题。
我遇到的问题是某些代码使用动态查找,在类路径中搜索实现。如果尚未将 jar 添加到 Web 应用程序类路径,因为尚未从该 jar 加载任何类,则它不会包含在搜索中。
我遇到的具体问题是持久性 - 它通过搜索 META-INF/services 文件来查找 EntityManagerFactory 实现。我对 Rome 及其模块扩展也遇到了类似的问题。
我有一个解决方法,在开发/托管模式下,我只需引用一个我知道位于我想要的 jar 中的类,这会导致它被添加到我的 Web 应用程序类路径中。 调用来完成此操作
private void devModeClassPathHack() {
Class<?> gwtDevModeHack1 = EntityManagerImpl.class;
}
我通过从我的开发模式 Guice 模块
。我的问题很简单 - 有没有“更好”的方法来做到这一点?
In my GWT web app I am keeping all my jar files outside of my project and referencing them using classpath variables. This allows me to link to jars from other projects/teams without having to put a copy of the jar in my web app lib directory. Hosted mode kindly looks up the classes in this system classpath and then adds them to the web-app classpath warning me that it is doing so. When I deploy my build system pulls in only the jars I need to ship in my web app and is not a problem.
The issue I have is that some code uses dynamic lookups, searching the classpath for implementations. If a jar has not yet been added to the web app classpath beacuse no classes have yet benn loaded from the jar it is not included in the search.
The particular problem I am having is with Persistence - it looks up EntityManagerFactory implementations by searching for META-INF/services files. I have also had a similar problem with Rome and its module extensions.
I have got a workaround, in the dev/hosted mode I simply refer to a class I know is in a jar I want and this causes it to be added to my web app classpath. I do this my by calling
private void devModeClassPathHack() {
Class<?> gwtDevModeHack1 = EntityManagerImpl.class;
}
from my development mode Guice module.
My question is simple - is there a "nicer" way of doing this?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
我不认为,有更好的方法 - 使用 GWT Jetty/dev 模式的这种临时“自我修复”机制已经是一种 hack :) 如果您需要运行服务器端 在开发期间在例如 JBoss 上编写代码(与客户端的 GWT 开发模式一起),这将停止工作。
(作为另一个问题,类加载的顺序 - 以及因此不同 jar 中存在多个版本的类的情况下的优先级 - 将取决于程序流程。这可能非常难以调试。)
您提到,您拉在所有来自外面的罐子里。在这种情况下,我要做的是将 WEB-INF/lib 目录中的 .svnignore (或 .gitignore/...) 设置为“*.jar”。然后,我将运行用于创建生产构建的相同构建步骤,以在启动服务器之前将 jar 复制到 lib 目录中。
I don't think, there's a nicer way - using this makeshift "self-healing" mechanism of the GWT Jetty/dev mode is already a hack :) If you ever have the need to run the server side code on e. g. JBoss during development (together with GWT dev mode for the client side), this will stop working.
(As an additional problem, the order of classloading - and consequently the precedence in cases when there are multiple versions of a class in different jars - will depend on program flow. This can be very nasty to debug.)
You mention, that you pull in all the jars from outside. What I would do in that case, is to set .svnignore (or .gitignore/...) to "*.jar" in the WEB-INF/lib dir. Then I'd run the same build step which is used to create the production build to copy the jars into the lib dir before starting the server.