Spring MVC 拦截器方式示例
客户端直接通过拦截器的方式与服务端进行交互,当请求中没有access_token 信息, 则进入统一身份认证授权登录界面,登录完成后,会重定向回传递的redirect_uri地址,来完成交互
1、判断请求是否包含 access_token 信息,没有则拦截到授权页面
2、授权成功后将会重定向 https://my_server_url/callback#token=access_token
编写登录回调接口 /callback ,存储 access_token(可前端存储)
3、认证回调接口获取到 access_token 后,可获取当前登陆人信息
根据 accesstoken 获取用户信息:https://cas_server_url/oauth2.0/profile?access_token=xxxxx
正确时返回:
{
"service" : "service_url",
"attributes" : {
"credentialType" : "LoginCredential"
},
"id" : "admin",
"client_id" : "client"
}
响应参数
参数名称 | 参数说明 | 类型 | schema |
---|---|---|---|
service | 应用地址 | string | |
attributes | 用户属性值 | integer(int64) | |
id | 用户唯一ID | string | |
client_id | 应用客户端ID | string |
代码示例
import com.alibaba.fastjson2.JSONObject;
import lombok.extern.slf4j.Slf4j;
import okhttp3.OkHttpClient;
import okhttp3.Request;
import okhttp3.Response;
import org.apache.http.NameValuePair;
import org.apache.http.client.utils.URLEncodedUtils;
import org.springframework.util.StringUtils;
import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.ModelAndView;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.net.URI;
import java.net.URISyntaxException;
import java.nio.charset.Charset;
import java.util.List;
import java.util.Optional;
@Slf4j
public class CasAuthInterceptor implements HandlerInterceptor {
/**
* HTTP Authorization Param, equal to <code>accessToken</code>
*/
public static final String AUTHORIZATION_PARAM = "access_token";
public OkHttpClient okhttp3Client;
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
System.out.println("preHandle......");
// 1、获取请求中的accessToken
String accessToken = this.obtainaAccessToken(request);
if(StringUtils.hasText(accessToken)){
// 2、创建Request.Builder对象
long startTime = System.currentTimeMillis();
Request.Builder builder = new Request.Builder().url("https://cas_server_url/oauth2.0/profile?access_token=" + accessToken);
// 2.创建一个call对象, 参数就是Request请求对象
try {
Response okResponse = okhttp3Client.newCall(builder.get().build()).execute();
if (okResponse.isSuccessful()) {
log.info("OkHttp3 >> Request Success : code : {}, use time : {} ", okResponse.code(), System.currentTimeMillis() - startTime);
/**
{
"service" : "service_url",
"attributes" : {
"credentialType" : "LoginCredential"
},
"id" : "admin",
"client_id" : "client"
}
*/
String body = okResponse.body().string();
JSONObject jsonObject = JSONObject.parseObject(body);
// 接入的客户端ID
String clientId = jsonObject.getString("client_id");
// 当前认证用户信息
JSONObject attributes = jsonObject.getJSONObject("attributes");
} else {
log.error("OkHttp3 >> Request Failure : code : {}, message : {}, use time : {} ", okResponse.code(), okResponse.message(), System.currentTimeMillis() - startTime);
}
} catch (Exception e) {
log.error("OkHttp3 Request Error : {}, use time : {}", e.getMessage(), System.currentTimeMillis() - startTime);
}
return true;
}
response.sendRedirect("https://cas_server_url/oauth2.0/authorize?response_type=token&client_id=clientxxx&redirect_uri=https://my_server_url/callback");
return false;
}
@Override
public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
System.out.println("postHandle......");
}
@Override
public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
System.out.println("afterCompletion......");
}
protected String obtainaAccessToken(HttpServletRequest request) throws URISyntaxException {
// 从header中获取AcessToken
URI uri = new URI(request.getRequestURL().toString());
// https://my_server_url/callback#token=access_token
System.out.println(uri.getFragment());
List<NameValuePair> valuePairList = URLEncodedUtils.parse(uri.getFragment(), Charset.defaultCharset());
Optional<NameValuePair> optional = valuePairList.stream().filter(nameValuePair -> nameValuePair.getName().equals("token")).findFirst();
if(optional.isPresent()){
return optional.get().getValue();
}
String accessToken = request.getParameter(AUTHORIZATION_PARAM);
return accessToken;
}
}
作者:Jeebiz 创建时间:2022-10-23 20:28
最后编辑:Jeebiz 更新时间:2024-05-07 20:29
最后编辑:Jeebiz 更新时间:2024-05-07 20:29