在其他模块的 JSF ManagedBean 中通过 @EJB(lookup) 注入远程无状态 EJB

Posted

技术标签:

【中文标题】在其他模块的 JSF ManagedBean 中通过 @EJB(lookup) 注入远程无状态 EJB【英文标题】:Inject remote stateless EJB via @EJB(lookup) in a JSF ManagedBean in other module 【发布时间】:2015-07-11 13:43:04 【问题描述】:

不能将 EJB 从一个模块注入到另一个模块中的 EJB。单个 glassfish 实例上的两个模块。

主模块中的远程接口:

@Remote
public interface TestEJBLocal 
    String getMessage();


在主模块中的实现:

@Stateless
public class TestEJB implements TestEJBRemote 
    @Override
    public String getMessage() 
        return "Hello EJB World";
    

第 3 方模块中的远程接口(消费者):

@Remote
public interface TestEJBLocal 
    String getMessage();


3rdparty 模块中的消费者 bean:

@Named
@RequestScoped
public class testBean 

    @EJB(lookup="java:global/mavenproject3-ear/mavenproject3-ejb-1.0-SNAPSHOT/TestEJB!com.versetty.ejb.TestEJBRemote")
    private TestEJBRemote messageBean;

    public void doEJBCall() 
        System.out.println(messageBean.getMessage());
    


消费者 JSF 页面:

<?xml version='1.0' encoding='UTF-8' ?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml"
      xmlns:h="http://xmlns.jcp.org/jsf/html">
    <h:head>
        <title>Facelet Title</title>
    </h:head>
    <h:body>
        Hello from Facelets
        <h:form>
            <h:commandButton action="#testBean.doEJBCall()" title="call"/>
        </h:form>
    </h:body>
</html>

例外:

Caused by: java.lang.IllegalArgumentException: Can not set com.versetty.web.remote.TestEJBRemote field com.versetty.web.bean.testBean.messageBean to com.versetty.ejb._TestEJBRemote_Wrapper
at sun.reflect.UnsafeFieldAccessorImpl.throwSetIllegalArgumentException(UnsafeFieldAccessorImpl.java:167)
at sun.reflect.UnsafeFieldAccessorImpl.throwSetIllegalArgumentException(UnsafeFieldAccessorImpl.java:171)
at sun.reflect.UnsafeObjectFieldAccessorImpl.set(UnsafeObjectFieldAccessorImpl.java:81)
at java.lang.reflect.Field.set(Field.java:764)
at com.sun.enterprise.container.common.impl.util.InjectionManagerImpl._inject(InjectionManagerImpl.java:688)
... 59 more

【问题讨论】:

access a Local Session Bean from another EAR? 的可能重复项 当然,该错误表明您正在查找与您在注入点指定的不同的 bean 定义:com.versetty.web.remote.TestEJBRemote 和 com.versetty.ejb._TestEJBRemote_Wrapper 代理 bean将具有相同的包命名 它有效。非常感谢。 【参考方案1】:

您使用了@Local 接口,但您正尝试从不同的EJB 应用程序访问它——您应该为此使用@Remote。 This answer 很好地解释了原因。

【讨论】:

如果我使用远程接口:原因:java.lang.IllegalArgumentException:无法将 com.versetty.web.remote.TestEJBRemote 字段 com.versetty.web.bean.testBean.testRemote 设置为 com。 versetty.ejb._TestEJBRemote_Wrapper 好的,听起来您已经添加了一个远程接口TestEJBRemote 和一个字段“testRemote”,但该字段仍然是TestEJBLocal 类型?如果是这种情况,请尝试将其更改为 TestEJBRemote。如果没有,您能否将您所做的更改和您遇到的错误添加为“我也尝试过...”,以便我们进一步调试? 看,我改变了问题正文。 感谢您进行更新。从这个 (***.com/questions/28774739/…) 看来,您还需要 messageBean in testBean 中的公共 getter 和 setter? getter 和 setter 是否也在使用 TestEJBRemote,而不是 TestEJB? (同样,最好将此代码添加到问题中)。您能否再次检查二传手的姓名和签名是否正确? IAE 是一个反射问题,所以看起来 JEE 已经构建了 EJB,它只是无法将它注入您的领域。如果这不起作用,您可以尝试将 EJB 注释移动到 setter 方法吗?

以上是关于在其他模块的 JSF ManagedBean 中通过 @EJB(lookup) 注入远程无状态 EJB的主要内容,如果未能解决你的问题,请参考以下文章

如何在 JSF 2.0/2.1 中用 CDI 替换 @ManagedBean / @ViewScope

JSF 如何找到用@ManagedBean 注释的bean?

JSF2 - 由 EJB 或 ManagedBean 支持?

JSF2:从 Spring 向 managedbean 注入服务对象?

无法从xhtml文件,Jsf managedBean访问方法

如何从 JSF 中的另一个 bean 获取 managedbean 属性