当前位置: 首页 > 知识库问答 >
问题:

如何将CDI SessionScoped bean注入请求范围bean

焦宁
2023-03-14

我试图用jsf和CDI编写一个简单的登录表单。问题是当我注入我的SessionScoped bean时,它不像我期望的那样工作。这是我的豆子

@Named
@SessionScoped
public class LoginInfo implements Serializable {
    private String uname;
    private String pass;
    private String pagename;
    private int count;

    public LoginInfo() {
    }

    public void increment() {
        count++;
    }
}

这是我的控制器:

@Named
@RequestScoped
public class LoginPageMg {
    @Inject
    LoginInfo lo;

    public LoginPageMg() {
    }


    public void login() {
        lo.increment();
        lo.setPagename("aaa");
        int x = 8;
    }
}

还有一个简单的Jsf表单,它调用login函数并显示LoginInfo类的计数器字段。

<h:form prependId="false" id="mainform" styleClass="login-box">
                        <p:inputText value="#{loginPageMg.uname}"/>
                        <p:password value="#{loginPageMg.pass}"/>

                        <h:outputLabel id="counter" value="#{loginInfo.count}"></h:outputLabel>

                        <p:commandButton update="counter"
                                         action="#{loginPageMg.login}"
                                         value="login"></p:commandButton>
</h:form>

通过单击登录按钮和调试变量,我可以看到“lo”是这样的:

lo={LoginInfo$Proxy$_$$_WeldClientProxy@16688}“com.mg。LoginInfo@703ec5d5"

在intx=8行中,我可以看到“lo”变量根本没有改变,但在我的jsf页面中,我可以看到每次按下login按钮时计数器都会增加,bean在刷新页面后会保留该值。

  1. 什么是WeldClientProxy
  2. 为什么有两个不同的SessionScoped bean实例?这是正常的还是我做错了什么
  3. 如何注入jsf所做的相同实例

我正在使用Wildfly 15 Jsf 2.3.4 CDI 1.1

共有1个答案

谷光誉
2023-03-14

我正在使用Wildfly 15 Jsf 2.3.4 CDI 1.1

WildFly 15意味着EE8兼容性,因此它附带了CDI2.0。

现在我尽可能多地回答你的问题:

什么是WeldClientProxy?

Weld是大多数EE服务器(包括WildFly)使用的CDI参考实现WeldClientProxy是一个内部构造,它用于注入正常范围的bean(除了@Dependent),其他几乎都是这样。它不是bean的实际实例,您可以将其视为一个“包装器”,它知道如何检索实际的上下文实例并委托对它的调用。这样,您可以重用代理实例,同时仍然指向引擎盖下的正确实例(因此引用不需要更改)。

为什么有两个不同的SessionScoped bean实例?这正常吗还是我做错了什么?

只有一个,客户端代理不是实际的实例。您基本上是通过看到计数每次都在增加并保持请求之间的状态来验证这一点的。

如何注入与jsf相同的实例?

JSF实际上没有注入任何东西,而是使用表达式语言根据bean的名称来查找bean。CDI允许您通过@命名来定义此名称。然后,JSF可以再次通过代理使用您正在注射的相同bean。

 类似资料:
  • 问题内容: 我正在尝试在Spring中建立一个请求范围的bean。 我已经成功设置好了,所以每个请求创建一次bean。现在,它需要访问HttpServletRequest对象。 由于该bean是每个请求创建一次的,所以我认为容器可以轻松地将请求对象注入到我的bean中。我怎样才能做到这一点 ? 问题答案: 可以将请求范围的Bean与请求对象自动连接。

  • 我有一个spring AOP方面类,它在每次调用服务时都会记录日志,我计划在日志中打印更多信息,这次每个请求都会有唯一的标识符,该标识符存储在请求范围的对象中,直到服务返回。我尝试将请求对象注入到@方面,但似乎效果不佳。 如果只有一个建议,它在我调用该服务时起作用,如果我添加更多建议,它会出错。(问题结束) 日志错误

  • 我已经看了很多帖子,似乎没有什么能像我喜欢的那样工作。 我想将一个对象从一个过滤器注入到ContainerRequestContext属性中,然后在其他类中检索它。 这是我的过滤器: 下面是我想要访问ContainerRequestContext的类: 我的spring配置: 如果我将容器请求上下文注入到我的 Web 资源中,一切都按预期工作。但是,如果调用我的提供程序类容器请求上下文始终为空。

  • 本文解释了可以将RequestScoped Bean注入ApplicationScoped Bean中,并且客户机代理将在请求期间指向正确的实例:在CDI中,较短范围的Bean实例注入较大范围的Bean实例中-它是如何工作的? 当使用一个单独的生产者类进行额外处理并生成RequestScoped bean时,这是如何工作的?在部署到应用服务器时,由于不明确的依赖关系,我得到一个Deployment

  • 我得到的错误是: 我检查的内容: > 已启用批注处理,否则AnyService根本不会实例化 AnyBean不是最终的 请求作用域在AnyBean中与AspectJ代理(ScopedProxyMode.target_class)一起定义 存在EnableAspectJAutoproxy批注 类路径上有以下JAR: Web XML还包含RequestContextListener: 当我向org.s

  • 问题内容: 我有灰熊提供的球衣。 我有一个实现类。但是,为所有传入请求创建一次此类。因此,这样做: 该为空。我可以将上下文注入到被调用的实际端点中,但这相当粗陋和丑陋,对我来说真的没有用;因为我希望记录各种请求。理想情况下,希望在请求的ResponseFilter端获取此对象。 必须有一种简单的方法来执行此操作。到目前为止,我所看到的所有问题/答案都不适用于Grizzly,也无法插入REST端点调