GWT & Java EE SessionScoped bean 不持久
GWT & Java EE SessionScoped bean not persisting
我正在玩 EE 并希望保留用户会话状态。我这里有会话 bean:
@Stateful(mappedName = "UserSessionState")
@Named("UserSessionState")
@SessionScoped
@StatefulTimeout(value = 5, unit = TimeUnit.MINUTES)
public class UserSessionState implements Serializable
{
private boolean hasPlayerId = false;
private String playerId = "";
public void setRandomPlayerId()
{
playerId = UUID.uuid();
hasPlayerId = true;
}
public boolean hasPlayerId()
{
return hasPlayerId;
}
public String getPlayerId()
{
return playerId;
}
}
这里是一个 servlet(GameState 是一个按预期工作的 Application Scoped bean,CustomExtendedHttpServlet 只是 HttpServlet 的简单扩展)
public class NewUserJoined extends CustomExtendedHttpServlet
{
@Inject
protected GameState gameState;
@Inject
protected UserSessionState user;
@Override
protected String doGetImpl(HttpServletRequest request, HttpServletResponse response, UserContext userLoginContext)
{
if (!user.hasPlayerId())
{
user.setRandomPlayerId();
}
String userId = user.getPlayerId();
if (!gameState.hasUser(userId))
{
gameState.addUser(userId, user);
return "Hi, your ID is: " + user.getPlayerId() + ", there are " + gameState.getUserCount() + " other players here";
}
else
{
return user.getPlayerId() + " you're already in the game, there are: " + gameState.getUserCount() + " other players here";
}
}
}
我不确定发生了什么,但每当我从同一个 HTTP 会话调用新用户加入 servlet 时,我都会在第一次调用时收到此响应(如预期的那样):
"Hi, your ID is: , there are 1 other players here"
在同一个会话中重复同一个 servlet 调用会给我同样的信息:
"Hi, your ID is: , there are 2 other players here"
...
看起来用户会话状态的新实例被一遍又一遍地创建。我这样做正确吗?
编辑 1:这是我用来发送请求的代码。我似乎在每次请求时都获得了一个新的会话 ID,这可能是什么原因造成的?
RequestCallback callback = new RequestCallback()
{
@Override
public void onResponseReceived(Request request, Response response)
{
log(response.getText());
}
@Override
public void onError(Request request, Throwable exception)
{
log(
"Response Error | "
+ "Exception: " + exception);
}
};
RequestBuilder rb = new RequestBuilder(RequestBuilder.GET, SERVLET_URL);
rb.setCallback(callback);
try
{
rb.send();
}
catch (RequestException e)
{
log("Response Error | "
+ "Exception: " + e);
}
您是否尝试调用 request.getSession(true) 以确保此处建立了 EE HTTPSession?
解决了问题,
原来我在 GWT 客户端中有一个旧的解决方法,它正在更改主机以解决 CORS 问题。因为响应与源不匹配,所以 cookie 没有通过未来的 servlet GET 调用发送。
我正在玩 EE 并希望保留用户会话状态。我这里有会话 bean:
@Stateful(mappedName = "UserSessionState")
@Named("UserSessionState")
@SessionScoped
@StatefulTimeout(value = 5, unit = TimeUnit.MINUTES)
public class UserSessionState implements Serializable
{
private boolean hasPlayerId = false;
private String playerId = "";
public void setRandomPlayerId()
{
playerId = UUID.uuid();
hasPlayerId = true;
}
public boolean hasPlayerId()
{
return hasPlayerId;
}
public String getPlayerId()
{
return playerId;
}
}
这里是一个 servlet(GameState 是一个按预期工作的 Application Scoped bean,CustomExtendedHttpServlet 只是 HttpServlet 的简单扩展)
public class NewUserJoined extends CustomExtendedHttpServlet
{
@Inject
protected GameState gameState;
@Inject
protected UserSessionState user;
@Override
protected String doGetImpl(HttpServletRequest request, HttpServletResponse response, UserContext userLoginContext)
{
if (!user.hasPlayerId())
{
user.setRandomPlayerId();
}
String userId = user.getPlayerId();
if (!gameState.hasUser(userId))
{
gameState.addUser(userId, user);
return "Hi, your ID is: " + user.getPlayerId() + ", there are " + gameState.getUserCount() + " other players here";
}
else
{
return user.getPlayerId() + " you're already in the game, there are: " + gameState.getUserCount() + " other players here";
}
}
}
我不确定发生了什么,但每当我从同一个 HTTP 会话调用新用户加入 servlet 时,我都会在第一次调用时收到此响应(如预期的那样):
"Hi, your ID is: , there are 1 other players here"
在同一个会话中重复同一个 servlet 调用会给我同样的信息: "Hi, your ID is: , there are 2 other players here" ...
看起来用户会话状态的新实例被一遍又一遍地创建。我这样做正确吗?
编辑 1:这是我用来发送请求的代码。我似乎在每次请求时都获得了一个新的会话 ID,这可能是什么原因造成的?
RequestCallback callback = new RequestCallback()
{
@Override
public void onResponseReceived(Request request, Response response)
{
log(response.getText());
}
@Override
public void onError(Request request, Throwable exception)
{
log(
"Response Error | "
+ "Exception: " + exception);
}
};
RequestBuilder rb = new RequestBuilder(RequestBuilder.GET, SERVLET_URL);
rb.setCallback(callback);
try
{
rb.send();
}
catch (RequestException e)
{
log("Response Error | "
+ "Exception: " + e);
}
您是否尝试调用 request.getSession(true) 以确保此处建立了 EE HTTPSession?
解决了问题,
原来我在 GWT 客户端中有一个旧的解决方法,它正在更改主机以解决 CORS 问题。因为响应与源不匹配,所以 cookie 没有通过未来的 servlet GET 调用发送。