HttpSession setAttribute并不总是插入新对象 [英] HttpSession setAttribute doesn't always insert new object
问题描述
我正在从WLS10g和JavaEE6升级到WLS12c和JavaEE7。
I am working on an upgrade from WLS10g and JavaEE6 to WLS12c and JavaEE7.
我注意到 HttpSession.setAttribute <的差异/ code>有效。在WLS10中,任何已存储在某个键下的对象都将被替换。
I have noticed a difference on how HttpSession.setAttribute
works. In WLS10, any object already stored under a certain key would always be replaced.
在WLS12中,如果 newObject.equals(oldObject)
,则不会替换该对象。
In WLS12 the object is not replaced if newObject.equals(oldObject)
.
这对我们来说是一个问题,因为应用程序有这样的对象:
This is a problem for us, because the applications have objects like this:
class ValueObject {
int key;
String data;
@Override
public int hashCode()
{
return key;
}
boolean equals(Object o) {
if (o == null || (o instanceof ValueObject) == false) {
return false;
}
ValueObject otherObject = (ValueObject)o;
/* Return true if the keys are equal, even though the data may differ */
return key == otherObject.key;
}
}
ValueObject通过跨越多个web的工作流程进行修改页面。中间值存储在 HTTPSession
中,在工作流结束时,修改后的值将写入数据库。
The ValueObject gets modified through a workflow that spans several web pages. The intermediate values are stored in the HTTPSession
and at the end of the workflow the modified value is written to the database.
在servlet中有这样的代码(成员实际上是通过getter / setter修改的,但我正在简化以减少问题中的代码量):
In the servlets there is code like this (the members are actually modified through getters/setters, but I am simplifying to reduce the amount of code in the question):
public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException {
HttpSession session = request.getSession();
ValueObject newValue = new ValueObject();
newValue.key = Integer.parseInt(request.getParameter("key"));
newValue.data = request.getParameter("data");
session.setAttribute("value", newValue);
...
newValue.key
未修改,而 newValue.data
有一个新值。
newValue.key
is unmodified while newValue.data
has a new value.
<$ c $的修改行为WLS12中的HttpSession 打破了这种模式 - 当从会话中检索到对象时,我们从第一步开始获得数据
,因为对象是'n'当我们尝试存储更新版本时,t会被替换。
The modified behaviour of the HttpSession
in WLS12 breaks this pattern - when the object is retrieved from the session we get the data
from the first step since the object isn't replaced when we try to store updated versions.
我们可以通过更改所有更新来解决此问题:
We could solve this by changing all updates from:
session.setAttribute("value", newValue);
到
session.removeAttribute("value");
session.setAttribute("value", newValue);
但是,有超过100个servlet因此需要做很多工作。解决方法既丑陋又容易出错,因为程序员在编写代码时需要再跟踪一件事。
However, there are more than 100 servlets so it is a lot of work. And the workaround is both ugly and prone to errors because the programmers need to keep track of one more thing when writing code.
有没有办法配置WLS12c来使用对象总是被替换的旧行为HttpSession.setAttribute()
?
Is there any way to configure WLS12c to use the old behaviour where the object always is replaced by HttpSession.setAttribute()
?
更新2015-09 -30 :
向Oracle提交的错误报告。我尝试过wero建议的过滤器想法。似乎Weblogic期望从过滤器链下来的对象是类 weblogic.server.internal.ServletRequestImpl
,因为当我包装它并将包装器发送到过滤器链时我从内部Weblogic类获得了ClassCastException。
Bug report filed with Oracle. I've tried the filter idea suggested by wero. It seems Weblogic expects the object coming down the filter chain to be of class weblogic.server.internal.ServletRequestImpl
, because when I wrapped it and sent the wrapper down the filter chain I got a ClassCastException from an internal Weblogic class.
我还检查了Gimby建议的配置选项。我找不到会议的任何适用选项。我们部署到单个服务器并使用 memory
作为会话持久性设置。
I have also checked the configuration options as suggested by Gimby. I could not find any applicable option for the Session. We deploy to a single server and use memory
as session persistence setting.
更新2016-02-03 :
Oracle已关闭错误报告作为不是错误。
Oracle has closed the bug report as "Not a bug".
推荐答案
由于Oracle将错误报告关闭为不是错误,我决定实施变通办法。
Since Oracle closed the bug report as "not a bug" I decided to implement the workaround.
我经历了对 HttpSession.setAttribute
的所有调用,并确定哪些调用使用了可能触发的对象错误。
I went through all calls to HttpSession.setAttribute
and identified which calls used an object that potentially could trigger the bug.
在我替换的那些地方
session.setAttribute(key, newValue);
with
session.removeAttribute(key);
session.setAttribute(key, newValue);
以及解释为何需要额外行的评论。
along with a comment explaining why the extra line was needed.
这篇关于HttpSession setAttribute并不总是插入新对象的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!