java 警告:无法注册销毁回调
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/2077558/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
WARN: Could not register destruction callback
提问by Bozho
15:11:14,676 WARN FacesRequestAttributes:121 - Could not register destruction callback [org.springframework.beans.factory.support.DisposableBeanAdapter@1059fd6] for attribute 'purchaseController' because FacesRequestAttributes does not support such callbacks
15:11:14,676 警告 FacesRequestAttributes:121 - 无法为属性“purchaseController”注册销毁回调 [org.springframework.beans.factory.support.DisposableBeanAdapter@1059fd6] 因为 FacesRequestAttributes 不支持此类回调
This warn message appears in my log a lot. For every managed bean whenever it expires. It expires after a given time, because I'm using MyFaces Orchestra.
这个警告信息出现在我的日志很多。对于每个过期的托管 bean。它在给定时间后过期,因为我使用的是 MyFaces Orchestra。
I have defined the org.springframework.web.context.request.RequestContextListenerin my web.xml, and I don't have the spring jar only ones on my classpath (i.e. not a class-loading problem)
我已经org.springframework.web.context.request.RequestContextListener在我的 中定义了web.xml,并且我的类路径上没有只有 spring jar(即不是类加载问题)
The docs of FacesRequestAttribute says:
FacesRequestAttribute 的文档说:
NOTE: In contrast to ServletRequestAttributes, this variant does not support destruction callbacks for scoped attributes, neither for the request scope nor for the session scope. If you rely on such implicit destruction callbacks, consider defining a Spring RequestContextListener in your web.xml.
注意:与 ServletRequestAttributes 相比,此变体不支持作用域属性的销毁回调,无论是请求作用域还是会话作用域。如果您依赖此类隐式销毁回调,请考虑在您的 web.xml 中定义一个 Spring RequestContextListener。
The purchaseControlleris actually a simple managed bean (not extending anything an implementing only Serializable), annotated with @Controller.
这purchaseController实际上是一个简单的托管 bean(不扩展任何仅实现Serializable),用@Controller.
Update1:
更新1:
The beans in @Scope("request")and @Scope("session")seem to be affected.
So I wanted to know whether this warn poses any danger to the proper flow. I.e. if something really needs those callbacks. If not, I will just skip the warning with the lo4j config.
在豆类@Scope("request")和@Scope("session")似乎受到影响。所以我想知道这个警告是否对正常流程构成任何危险。即如果真的需要那些回调。如果没有,我将跳过 lo4j 配置的警告。
Update 2:
更新 2:
I digged a little further, and it seems that this happens only sometimes. IF the listener is used, then RequestContextHolder.currentRequestAttributes()returns the ServletRequestAttributes, rather than FacesRequestAttributes. So it appears that sometimes the listener doesn't work and doesn't set the current attributes in the RequestContextHolder.
我进一步挖掘了一下,似乎这种情况只是偶尔发生。如果使用侦听器,则RequestContextHolder.currentRequestAttributes()返回ServletRequestAttributes, 而不是FacesRequestAttributes。所以看起来有时侦听器不起作用并且没有在RequestContextHolder.
Update 3:
更新 3:
I turned debug on for RequestContextListener, and here's the result:
我为 开启了调试RequestContextListener,结果如下:
07:21:31,518 DEBUG RequestContextListener:69 - Bound request context to thread: org.apache.catalina.connector.RequestFacade@1190ae9
07:21:31,518 DEBUG RequestContextListener:89 - Cleared thread-bound request context: org.apache.catalina.connector.RequestFacade@1190ae9
07:21:31,538 WARN FacesRequestAttributes:121 - Could not register destruction callback [org.springframework.beans.factory.support.DisposableBeanAdapter@11aa152] for attribute 'org.apache.myfaces.orchestra.conversation.AccessScopeManager' because FacesRequestAttributes does not support such callbacks
07:21:31,541 WARN FacesRequestAttributes:121 - Could not register destruction callback [org.springframework.beans.factory.support.DisposableBeanAdapter@1552393] for attribute 'localeController' because FacesRequestAttributes does not support such callbacks
....and so on, other request and session beans
It appears that the request gets destroyed before access to the beans is attempted. Which is very odd. Could this be due to a problem in the servlet container implementation of the listener handling?
似乎在尝试访问 bean 之前请求已被破坏。这很奇怪。这可能是由于侦听器处理的 servlet 容器实现中的问题吗?
采纳答案by Pascal Thivent
In the javadoc of FacesRequestAttributes, we can read:
在 的 javadoc 中FacesRequestAttributes,我们可以阅读:
Note:In contrast to
ServletRequestAttributes, this variant does notsupport destruction callbacks for scoped attributes, neither for the request scope nor for the session scope. If you rely on such implicit destruction callbacks, consider defining a SpringRequestContextListenerin your web.xml.
注:相反
ServletRequestAttributes,这种变异并没有支持销毁回调范围属性,既不是请求范围,也不适用于会话范围。如果您依赖此类隐式销毁回调,请考虑RequestContextListener在您的 web.xml 中定义一个 Spring 。
And, indeed, the registerDestructionCallback()method of FacesRequestAttributesdoesn't do much things:
而且,确实, 的registerDestructionCallback()方法FacesRequestAttributes没有做太多事情:
public void registerDestructionCallback(String name, Runnable callback, int scope) {
if (logger.isWarnEnabled()) {
logger.warn("Could not register destruction callback [" + callback + "] for attribute '" + name +
"' because FacesRequestAttributes does not support such callbacks");
}
}
But my understanding is that the RequestContextListener(that you have declared) will take care of this job. Its requestDestroyed(ServletRequestEvent requestEvent)method is shown below:
但我的理解是RequestContextListener(您已声明)将负责这项工作。其requestDestroyed(ServletRequestEvent requestEvent)方法如下图所示:
public void requestDestroyed(ServletRequestEvent requestEvent) {
ServletRequestAttributes attributes =
(ServletRequestAttributes) requestEvent.getServletRequest().getAttribute(REQUEST_ATTRIBUTES_ATTRIBUTE);
ServletRequestAttributes threadAttributes =
(ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
if (threadAttributes != null) {
// We're assumably within the original request thread...
if (attributes == null) {
attributes = threadAttributes;
}
RequestContextHolder.resetRequestAttributes();
LocaleContextHolder.resetLocaleContext();
}
if (attributes != null) {
attributes.requestCompleted();
if (logger.isDebugEnabled()) {
logger.debug("Cleared thread-bound request context: " + requestEvent.getServletRequest());
}
}
}
And if you look at the javadoc of ServletRequestAttributes#requestCompleted():
如果您查看以下的 javadoc ServletRequestAttributes#requestCompleted():
Executes all request destruction callbacks and updates the session attributes that have been accessed during request processing.
执行所有请求销毁回调并更新在请求处理期间访问过的会话属性。
So, I think that you can safely skip the WARN with log4j configuration (maybe confirm this with a little debugging session though).
因此,我认为您可以安全地跳过带有 log4j 配置的 WARN(尽管可以通过一些调试会话来确认这一点)。
回答by Boon
I tried adding
我尝试添加
<listener>
<listener-class>org.springframework.web.context.request.RequestContextListener</listener-class>
</listener>
as suggested by erhan14 on this forum post.
正如 erhan14 在此论坛帖子上所建议的那样。
And that warning disappeared for me. Hope it helps.
那个警告对我来说消失了。希望能帮助到你。

