什么会导致原始 'OAuth2' 状态参数在 org.springframework.social.connect.web.ConnectSupport 中为空?
What could cause the original 'OAuth2' state parameter to be null in org.springframework.social.connect.web.ConnectSupport?
我正在尝试在我的应用程序上使用 Spring Social,我在调试时注意到原始 'OAuth2' 状态参数在我的应用程序上始终为 null。
请参阅下面 org.springframework.social.connect.web.ConnectSupport
的 Spring 社交源代码:
private void verifyStateParameter(NativeWebRequest request) {
String state = request.getParameter("state");
String originalState = extractCachedOAuth2State(request);//Always null...
if (state == null || !state.equals(originalState)) {
throw new IllegalStateException("The OAuth2 'state' parameter is missing or doesn't match.");
}
}
private String extractCachedOAuth2State(WebRequest request) {
String state = (String) sessionStrategy.getAttribute(request, OAUTH2_STATE_ATTRIBUTE);
sessionStrategy.removeAttribute(request, OAUTH2_STATE_ATTRIBUTE);
return state;
}
有人可以帮忙吗?
编辑:我确实看到状态参数被 facebook 传回:
Request URL:https://www.facebook.com/v2.5/dialog/oauth?client_id=414113641982912&response_type=code&redirect_uri=http%3A%2F%2Flocalhost%3A8080%2Fconnect%2Ffacebook&scope=public_profile&state=0b7a97b5-b8d1-4f97-9b60-e3242c9c7eb9
Request Method:GET
Status Code:302
Remote Address:179.60.192.36:443
edit 2:顺便说一下,我得到的异常如下:
Exception while handling OAuth2 callback (The OAuth2 'state' parameter is missing or doesn't match.). Redirecting to facebook connection status page.
您从 Facebook 获得的不是请求属性,而是请求参数。
您应该通过以下方式获取它:
request.getParameter("state")
原来这个问题是由于我 依赖 headers - 而不是 cookies - 来管理 session .
通过注释掉下面的springsession配置bean:
@Bean
public HttpSessionStrategy sessionStrategy(){
return new HeaderHttpSessionStrategy();
}
oauth2 状态参数问题已解决。
P.S. 现在我必须找到一种方法让 Spring Social 与我当前的 [配置一起工作=37=] Session...
编辑:我设法保留了 HeaderHttpSession 策略(在 spring session 方面)并通过实施我自己的 Session 策略(在 spring 社交方面)如下:
public class CustomSessionStrategy implements SessionStrategy {
public void setAttribute(RequestAttributes request, String name, Object value) {
request.setAttribute(name, value, RequestAttributes.SCOPE_SESSION);
}
public Object getAttribute(RequestAttributes request, String name) {
ServletWebRequest servletWebRequest = (ServletWebRequest) request;
return servletWebRequest.getParameter(name);
}
public void removeAttribute(RequestAttributes request, String name) {
request.removeAttribute(name, RequestAttributes.SCOPE_SESSION);
}
}
试试这个解决方法,看看它是否适合你:
令我惊讶的是,我在 'incognito' 浏览器中打开了应用程序,一切正常。就这样。我认为在某些内容被缓存并导致问题之前。
我今天 运行 解决了这个问题,我的应用程序运行得非常好。我刚休息了几个小时,当我再次 运行 时,它开始抱怨“OAuth2 'state' 参数丢失或不匹配。”
状态参数首先放入会话中,然后请求发送到 facebook,请求返回相同的状态参数,但是当 spring 正在寻找会话对象以获取状态参数时,它没有找到会话.我认为它没有找到会话,因为当请求返回时它认为它是一个不同的客户端(或主机),即使旧的 HttpSession 对象仍然存在。容器为每个客户端维护一个 HttpSession。
我正在尝试在我的应用程序上使用 Spring Social,我在调试时注意到原始 'OAuth2' 状态参数在我的应用程序上始终为 null。
请参阅下面 org.springframework.social.connect.web.ConnectSupport
的 Spring 社交源代码:
private void verifyStateParameter(NativeWebRequest request) {
String state = request.getParameter("state");
String originalState = extractCachedOAuth2State(request);//Always null...
if (state == null || !state.equals(originalState)) {
throw new IllegalStateException("The OAuth2 'state' parameter is missing or doesn't match.");
}
}
private String extractCachedOAuth2State(WebRequest request) {
String state = (String) sessionStrategy.getAttribute(request, OAUTH2_STATE_ATTRIBUTE);
sessionStrategy.removeAttribute(request, OAUTH2_STATE_ATTRIBUTE);
return state;
}
有人可以帮忙吗?
编辑:我确实看到状态参数被 facebook 传回:
Request URL:https://www.facebook.com/v2.5/dialog/oauth?client_id=414113641982912&response_type=code&redirect_uri=http%3A%2F%2Flocalhost%3A8080%2Fconnect%2Ffacebook&scope=public_profile&state=0b7a97b5-b8d1-4f97-9b60-e3242c9c7eb9
Request Method:GET
Status Code:302
Remote Address:179.60.192.36:443
edit 2:顺便说一下,我得到的异常如下:
Exception while handling OAuth2 callback (The OAuth2 'state' parameter is missing or doesn't match.). Redirecting to facebook connection status page.
您从 Facebook 获得的不是请求属性,而是请求参数。
您应该通过以下方式获取它:
request.getParameter("state")
原来这个问题是由于我 依赖 headers - 而不是 cookies - 来管理 session .
通过注释掉下面的springsession配置bean:
@Bean
public HttpSessionStrategy sessionStrategy(){
return new HeaderHttpSessionStrategy();
}
oauth2 状态参数问题已解决。
P.S. 现在我必须找到一种方法让 Spring Social 与我当前的 [配置一起工作=37=] Session...
编辑:我设法保留了 HeaderHttpSession 策略(在 spring session 方面)并通过实施我自己的 Session 策略(在 spring 社交方面)如下:
public class CustomSessionStrategy implements SessionStrategy {
public void setAttribute(RequestAttributes request, String name, Object value) {
request.setAttribute(name, value, RequestAttributes.SCOPE_SESSION);
}
public Object getAttribute(RequestAttributes request, String name) {
ServletWebRequest servletWebRequest = (ServletWebRequest) request;
return servletWebRequest.getParameter(name);
}
public void removeAttribute(RequestAttributes request, String name) {
request.removeAttribute(name, RequestAttributes.SCOPE_SESSION);
}
}
试试这个解决方法,看看它是否适合你:
令我惊讶的是,我在 'incognito' 浏览器中打开了应用程序,一切正常。就这样。我认为在某些内容被缓存并导致问题之前。
我今天 运行 解决了这个问题,我的应用程序运行得非常好。我刚休息了几个小时,当我再次 运行 时,它开始抱怨“OAuth2 'state' 参数丢失或不匹配。” 状态参数首先放入会话中,然后请求发送到 facebook,请求返回相同的状态参数,但是当 spring 正在寻找会话对象以获取状态参数时,它没有找到会话.我认为它没有找到会话,因为当请求返回时它认为它是一个不同的客户端(或主机),即使旧的 HttpSession 对象仍然存在。容器为每个客户端维护一个 HttpSession。