commit
ed2852d75e
12 changed files with 677 additions and 0 deletions
@ -0,0 +1,7 @@ |
|||||||
|
|
||||||
|
# open-JSD-9647 |
||||||
|
|
||||||
|
JSD-9647 派拉集成\ |
||||||
|
免责说明:该源码为第三方爱好者提供,不保证源码和方案的可靠性,也不提供任何形式的源码教学指导和协助!\ |
||||||
|
仅作为开发者学习参考使用!禁止用于任何商业用途!\ |
||||||
|
为保护开发者隐私,开发者信息已隐去!若原开发者希望公开自己的信息,可联系【pioneer】处理。 |
Binary file not shown.
@ -0,0 +1,21 @@ |
|||||||
|
<?xml version="1.0" encoding="UTF-8" standalone="no"?><plugin> |
||||||
|
<id>com.eco.plugin.zzl.ijf.iam</id> |
||||||
|
<name><![CDATA[解放IAM单点登录]]></name> |
||||||
|
<active>yes</active> |
||||||
|
<version>1.0.4</version> |
||||||
|
<env-version>10.0</env-version> |
||||||
|
<jartime>2020-07-31</jartime> |
||||||
|
<vendor>fr.open</vendor> |
||||||
|
<description><![CDATA[oauth2]]></description> |
||||||
|
<change-notes><![CDATA[ |
||||||
|
add 9880 |
||||||
|
]]></change-notes> |
||||||
|
<extra-decision> |
||||||
|
<GlobalRequestFilterProvider class="com.fr.plugin.IAMloginFilter"/> |
||||||
|
<!-- 长连接 --> |
||||||
|
<HttpHandlerProvider class="com.fr.plugin.TCauth2HandlerProvider"/> |
||||||
|
<!-- 短连接 --> |
||||||
|
<URLAliasProvider class="com.fr.plugin.TCauth2URLAliasBridge"/> |
||||||
|
</extra-decision> |
||||||
|
<function-recorder class="com.fr.plugin.TCauth2HandlerProvider"/> |
||||||
|
</plugin> |
@ -0,0 +1,113 @@ |
|||||||
|
package com.fr.plugin; |
||||||
|
|
||||||
|
import com.fanruan.api.net.http.HttpKit; |
||||||
|
import com.fr.decision.authority.data.User; |
||||||
|
import com.fr.decision.fun.impl.BaseHttpHandler; |
||||||
|
import com.fr.decision.webservice.v10.login.LoginService; |
||||||
|
import com.fr.decision.webservice.v10.user.UserService; |
||||||
|
import com.fr.json.JSONObject; |
||||||
|
import com.fr.log.FineLoggerFactory; |
||||||
|
import com.fr.plugin.context.PluginContexts; |
||||||
|
import com.fr.third.org.apache.commons.codec.digest.DigestUtils; |
||||||
|
import com.fr.third.org.apache.commons.lang3.StringUtils; |
||||||
|
import com.fr.third.springframework.web.bind.annotation.RequestMethod; |
||||||
|
import com.fr.web.utils.WebUtils; |
||||||
|
import org.dom4j.DocumentException; |
||||||
|
|
||||||
|
import javax.servlet.http.HttpServletRequest; |
||||||
|
import javax.servlet.http.HttpServletResponse; |
||||||
|
import java.io.IOException; |
||||||
|
import java.net.URLEncoder; |
||||||
|
import java.nio.charset.StandardCharsets; |
||||||
|
import java.util.Base64; |
||||||
|
import java.util.HashMap; |
||||||
|
import java.util.Map; |
||||||
|
|
||||||
|
public class GetTicket extends BaseHttpHandler { |
||||||
|
@Override |
||||||
|
public RequestMethod getMethod() { |
||||||
|
return null; |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public String getPath() { |
||||||
|
return "/getToken"; |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public boolean isPublic() { |
||||||
|
return true; |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public void handle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse) throws Exception { |
||||||
|
JSONObject entries = new JSONObject(); |
||||||
|
if (!PluginContexts.currentContext().isAvailable()) { |
||||||
|
entries.put("code", "1"); |
||||||
|
entries.put("msg", "授权过期请联系销售人员"); |
||||||
|
WebUtils.printAsJSON(httpServletResponse, entries); |
||||||
|
return; |
||||||
|
} |
||||||
|
String accessToken = WebUtils.getHTTPRequestParameter(httpServletRequest, "accessToken"); |
||||||
|
if (StringUtils.isBlank(accessToken)) { |
||||||
|
entries.put("code", "1"); |
||||||
|
entries.put("msg", "accessToken码不存在"); |
||||||
|
WebUtils.printAsJSON(httpServletResponse, entries); |
||||||
|
return; |
||||||
|
} |
||||||
|
|
||||||
|
String uid = getUserInfo(accessToken); |
||||||
|
User user = UserService.getInstance().getUserByUserName(uid); |
||||||
|
if (user == null) { |
||||||
|
entries.put("code", "1"); |
||||||
|
entries.put("msg", "登录失败:" + uid + " 在帆软用户体系不存在,请联系管理员添加"); |
||||||
|
WebUtils.printAsJSON(httpServletResponse, entries); |
||||||
|
return; |
||||||
|
} |
||||||
|
String token = login(httpServletRequest, httpServletResponse, uid); |
||||||
|
entries.put("code", "0"); |
||||||
|
entries.put("data", token); |
||||||
|
WebUtils.printAsJSON(httpServletResponse, entries); |
||||||
|
} |
||||||
|
|
||||||
|
private String getAccessToken(String code) throws IOException { |
||||||
|
Oauth2Config config = Oauth2Config.getInstance(); |
||||||
|
String valAddr = config.getValAddr(); |
||||||
|
String appId = config.getAppId(); |
||||||
|
String clientSecret = config.getClientSecret(); |
||||||
|
String frUrl = Oauth2Config.getInstance().getFrUrl(); |
||||||
|
String redirectUrl = String.format("%s/url/iam/authCallBack", frUrl); |
||||||
|
Map<String, String> params = new HashMap<>(); |
||||||
|
String tokenUrl = String.format("%s/oauth2/rest/token", valAddr); |
||||||
|
params.put("redirect_uri", redirectUrl); |
||||||
|
params.put("grant_type", "AUTHORIZATION_CODE"); |
||||||
|
params.put("code", code); |
||||||
|
Map<String, String> header = new HashMap<>(); |
||||||
|
header.put("X-OAUTH-IDENTITY-DOMAIN-NAME", "IdmDomain"); |
||||||
|
header.put("Authorization", "Basic " + Base64.getEncoder().encodeToString(String.format("%s:%s", appId, clientSecret).getBytes(StandardCharsets.UTF_8))); |
||||||
|
String json = HttpKit.post(tokenUrl, params, "utf-8", "utf-8", header); |
||||||
|
FineLoggerFactory.getLogger().info("获取AccessToken 请求返回:{}", json); |
||||||
|
JSONObject obj = new JSONObject(json); |
||||||
|
return obj.getString("access_token"); |
||||||
|
} |
||||||
|
|
||||||
|
public static String getUserInfo(String accessToken) throws DocumentException, IOException { |
||||||
|
Map<String, String> header = new HashMap<>(); |
||||||
|
Oauth2Config config = Oauth2Config.getInstance(); |
||||||
|
String valAddr = config.getValAddr(); |
||||||
|
String url = String.format("%s/oauth2/rest/userinfo?access_token=%s", valAddr, accessToken); |
||||||
|
header.put("Authorization", "Bearer " + accessToken); |
||||||
|
String json = HttpKit.get(url, new HashMap<>(), header); |
||||||
|
FineLoggerFactory.getLogger().info("获取userinfo 请求返回:{}", json); |
||||||
|
JSONObject obj = new JSONObject(json); |
||||||
|
return obj.getString("sub"); |
||||||
|
} |
||||||
|
|
||||||
|
private String login(HttpServletRequest req, HttpServletResponse res, String username) throws Exception { |
||||||
|
String token = LoginService.getInstance().login(req, res, username); |
||||||
|
req.setAttribute("fine_auth_token", token); |
||||||
|
FineLoggerFactory.getLogger().info("fr FrFilter is over with username is ###" + username); |
||||||
|
return token; |
||||||
|
} |
||||||
|
|
||||||
|
} |
@ -0,0 +1,63 @@ |
|||||||
|
package com.fr.plugin; |
||||||
|
|
||||||
|
import com.fr.decision.fun.impl.BaseHttpHandler; |
||||||
|
import com.fr.decision.webservice.v10.login.LoginService; |
||||||
|
import com.fr.third.org.apache.commons.codec.digest.DigestUtils; |
||||||
|
import com.fr.third.org.apache.commons.lang3.StringUtils; |
||||||
|
import com.fr.third.springframework.web.bind.annotation.RequestMethod; |
||||||
|
import com.fr.web.utils.WebUtils; |
||||||
|
|
||||||
|
import javax.servlet.http.HttpServletRequest; |
||||||
|
import javax.servlet.http.HttpServletResponse; |
||||||
|
import java.io.IOException; |
||||||
|
import java.net.URLEncoder; |
||||||
|
import java.util.HashMap; |
||||||
|
import java.util.Map; |
||||||
|
|
||||||
|
public class GoAuthApi extends BaseHttpHandler { |
||||||
|
@Override |
||||||
|
public RequestMethod getMethod() { |
||||||
|
return null; |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public String getPath() { |
||||||
|
return "/goAuth"; |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public boolean isPublic() { |
||||||
|
return true; |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public void handle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse) throws Exception { |
||||||
|
if (isLogin(httpServletRequest)) { |
||||||
|
sendRedirect(httpServletResponse, HttpUtils.getDefaultUrl(httpServletRequest)); |
||||||
|
return; |
||||||
|
} else { |
||||||
|
String valAddr = Oauth2Config.getInstance().getValAddr(); |
||||||
|
String appId = Oauth2Config.getInstance().getAppId(); |
||||||
|
String frUrl = Oauth2Config.getInstance().getFrUrl(); |
||||||
|
String redirectUrl = String.format("%s/url/iam/authCallBack", frUrl); |
||||||
|
redirectUrl = URLEncoder.encode(redirectUrl, "utf-8"); |
||||||
|
String goUrl = String.format("%s/oauth2/rest/authz?response_type=code&client_id=%s&domain=IdmDomain&state=xyz&scope=IdmResServer.UserProfile.me openid email phone profile&redirect_uri=%s", valAddr, appId, redirectUrl); |
||||||
|
sendRedirect(httpServletResponse, goUrl); |
||||||
|
} |
||||||
|
} |
||||||
|
|
||||||
|
|
||||||
|
private void sendRedirect(HttpServletResponse res, String url) throws IOException { |
||||||
|
Map<String, String> params = new HashMap<>(); |
||||||
|
params.put("callBack", url); |
||||||
|
WebUtils.writeOutTemplate("com/fr/plugin/redirect.html", res, params); |
||||||
|
} |
||||||
|
|
||||||
|
private boolean isLogin(HttpServletRequest req) { |
||||||
|
return LoginService.getInstance().isLogged(req); |
||||||
|
} |
||||||
|
|
||||||
|
private String md5(String str) { |
||||||
|
return DigestUtils.md5Hex(str); |
||||||
|
} |
||||||
|
} |
@ -0,0 +1,52 @@ |
|||||||
|
package com.fr.plugin; |
||||||
|
|
||||||
|
import com.fr.base.FRContext; |
||||||
|
import com.fr.base.ServerConfig; |
||||||
|
import com.fr.base.TemplateUtils; |
||||||
|
import com.fr.log.FineLoggerFactory; |
||||||
|
import com.fr.stable.StringUtils; |
||||||
|
import com.fr.third.org.apache.commons.io.IOUtils; |
||||||
|
|
||||||
|
import javax.servlet.http.HttpServletRequest; |
||||||
|
import java.io.*; |
||||||
|
import java.net.HttpURLConnection; |
||||||
|
import java.net.URL; |
||||||
|
import java.net.URLEncoder; |
||||||
|
import java.nio.charset.StandardCharsets; |
||||||
|
import java.util.Base64; |
||||||
|
import java.util.Iterator; |
||||||
|
import java.util.Map; |
||||||
|
import java.util.Set; |
||||||
|
|
||||||
|
/** |
||||||
|
* http请求工具类 |
||||||
|
* |
||||||
|
* @author 0246 |
||||||
|
*/ |
||||||
|
public class HttpUtils { |
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
/** |
||||||
|
* 返回当前系统的根路径 |
||||||
|
* |
||||||
|
* @return |
||||||
|
*/ |
||||||
|
public static String getDefaultUrl(HttpServletRequest req) { |
||||||
|
StringBuilder url = new StringBuilder(); |
||||||
|
try { |
||||||
|
url.append(req.getScheme()); |
||||||
|
url.append("://"); |
||||||
|
url.append(req.getServerName()); |
||||||
|
if (req.getServerPort() != 80) { |
||||||
|
url.append(":"); |
||||||
|
url.append(req.getServerPort()); |
||||||
|
} |
||||||
|
url.append(TemplateUtils.render("${fineServletURL}")); |
||||||
|
} catch (Exception e) { |
||||||
|
FineLoggerFactory.getLogger().error(e.getMessage(), e); |
||||||
|
} |
||||||
|
return url.toString(); |
||||||
|
} |
||||||
|
|
||||||
|
} |
@ -0,0 +1,166 @@ |
|||||||
|
package com.fr.plugin; |
||||||
|
|
||||||
|
import com.fr.base.ServerConfig; |
||||||
|
import com.fr.base.TemplateUtils; |
||||||
|
import com.fr.data.NetworkHelper; |
||||||
|
import com.fr.decision.fun.impl.AbstractGlobalRequestFilterProvider; |
||||||
|
import com.fr.decision.webservice.utils.DecisionStatusService; |
||||||
|
import com.fr.decision.webservice.v10.login.LoginService; |
||||||
|
import com.fr.json.JSONObject; |
||||||
|
import com.fr.log.FineLoggerFactory; |
||||||
|
import com.fr.plugin.transform.ExecuteFunctionRecord; |
||||||
|
import com.fr.plugin.transform.FunctionRecorder; |
||||||
|
import com.fr.stable.StringUtils; |
||||||
|
import com.fr.store.StateHubService; |
||||||
|
import com.fr.web.utils.WebUtils; |
||||||
|
|
||||||
|
import javax.servlet.FilterChain; |
||||||
|
import javax.servlet.FilterConfig; |
||||||
|
import javax.servlet.ServletException; |
||||||
|
import javax.servlet.http.HttpServletRequest; |
||||||
|
import javax.servlet.http.HttpServletResponse; |
||||||
|
import java.io.IOException; |
||||||
|
import java.io.PrintWriter; |
||||||
|
import java.io.StringWriter; |
||||||
|
import java.net.URLEncoder; |
||||||
|
import java.util.Iterator; |
||||||
|
import java.util.Map; |
||||||
|
|
||||||
|
@FunctionRecorder(localeKey = "fds") |
||||||
|
public class IAMloginFilter extends AbstractGlobalRequestFilterProvider { |
||||||
|
@Override |
||||||
|
public String filterName() { |
||||||
|
return "oauth2"; |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public String[] urlPatterns() { |
||||||
|
return new String[]{ |
||||||
|
"/*" |
||||||
|
}; |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public void init(FilterConfig filterConfig) { |
||||||
|
Oauth2Config.getInstance(); |
||||||
|
super.init(filterConfig); |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
@ExecuteFunctionRecord |
||||||
|
public void doFilter(HttpServletRequest request, HttpServletResponse httpServletResponse, FilterChain filterChain) { |
||||||
|
try { |
||||||
|
if (isLogOut(request)) { |
||||||
|
delLoginOut(request, httpServletResponse); |
||||||
|
return; |
||||||
|
} |
||||||
|
if (needFilter(request) && !isLogin(request)) { |
||||||
|
//跳转到登录界面
|
||||||
|
String originalURL =getOriginalUrlIgnoreCode(request); |
||||||
|
String frUrl = Oauth2Config.getInstance().getFrUrl(); |
||||||
|
String valAddr = Oauth2Config.getInstance().getValAddr(); |
||||||
|
String appId = Oauth2Config.getInstance().getAppId(); |
||||||
|
StateHubService stateHubService = DecisionStatusService.originUrlStatusService(); |
||||||
|
stateHubService.put("loginCallBack", originalURL); |
||||||
|
String redirectUrl = String.format("%s/url/iam/authCallBack", frUrl); |
||||||
|
redirectUrl = URLEncoder.encode(redirectUrl, "utf-8"); |
||||||
|
String goUrl = String.format("%s/oauth2/rest/authz?response_type=code&client_id=%s&domain=IdmDomain&state=xyz&scope=IdmResServer.UserProfile.me openid email phone profile&redirect_uri=%s", valAddr, appId, redirectUrl); |
||||||
|
sendRedirect(httpServletResponse, goUrl); |
||||||
|
return; |
||||||
|
} |
||||||
|
filterChain.doFilter(request, httpServletResponse); |
||||||
|
} catch (IOException | ServletException e) { |
||||||
|
printException2FrLog(e); |
||||||
|
} catch (Exception e) { |
||||||
|
printException2FrLog(e); |
||||||
|
} |
||||||
|
} |
||||||
|
|
||||||
|
public String getOriginalUrlIgnoreCode(HttpServletRequest request) throws Exception { |
||||||
|
StringBuffer url = new StringBuffer(request.getRequestURI()); |
||||||
|
Map parameterMap = request.getParameterMap(); |
||||||
|
Iterator iterator = parameterMap.entrySet().iterator(); |
||||||
|
boolean notFirst = url.toString().indexOf("?") == -1; |
||||||
|
while (iterator.hasNext()) { |
||||||
|
Map.Entry entry = (Map.Entry) iterator.next(); |
||||||
|
if (StringUtils.equals("code", entry.getKey().toString())) { |
||||||
|
continue; |
||||||
|
} |
||||||
|
if (notFirst) { |
||||||
|
url.append('?'); |
||||||
|
notFirst = false; |
||||||
|
} else { |
||||||
|
url.append('&'); |
||||||
|
} |
||||||
|
|
||||||
|
url.append(entry.getKey().toString()); |
||||||
|
url.append('='); |
||||||
|
url.append( URLEncoder.encode(request.getParameter(entry.getKey().toString()),"utf-8")); |
||||||
|
} |
||||||
|
FineLoggerFactory.getLogger().info("重定向到:" + url.toString()); |
||||||
|
return url.toString(); |
||||||
|
} |
||||||
|
|
||||||
|
private void delLoginOut(HttpServletRequest req, HttpServletResponse res) { |
||||||
|
try { |
||||||
|
//执行帆软内部的退出
|
||||||
|
LoginService.getInstance().logout(req, res); |
||||||
|
Oauth2Config oauth2Config = Oauth2Config.getInstance(); |
||||||
|
JSONObject jsonObject = new JSONObject(); |
||||||
|
String url = String.format("%s/FawIdmCommonUtils/ssoLoginService/goLogout", oauth2Config.getValAddr()); |
||||||
|
jsonObject.put("data", url); |
||||||
|
//调用外部接口注销accessToken
|
||||||
|
FineLoggerFactory.getLogger().error("登出成功: ----------------"); |
||||||
|
//指定退出之后到他们登录页面
|
||||||
|
WebUtils.printAsJSON(res, jsonObject); |
||||||
|
} catch (Exception var4) { |
||||||
|
} |
||||||
|
} |
||||||
|
|
||||||
|
private boolean isLogOut(HttpServletRequest req) { |
||||||
|
String url = WebUtils.getOriginalURL(req); |
||||||
|
String servletNamePrefix = "/" + ServerConfig.getInstance().getServletName() + "/logout"; |
||||||
|
return url.contains(servletNamePrefix) && req.getMethod().equals("POST"); |
||||||
|
} |
||||||
|
|
||||||
|
private void sendRedirect(HttpServletResponse res, String url) { |
||||||
|
res.setStatus(HttpServletResponse.SC_MOVED_TEMPORARILY); |
||||||
|
res.setHeader("Location", url); |
||||||
|
} |
||||||
|
|
||||||
|
private boolean needFilter(HttpServletRequest request) { |
||||||
|
String requestURI = request.getRequestURI(); |
||||||
|
String isAdmin = request.getParameter("isAdmin"); |
||||||
|
if (StringUtils.equals(isAdmin, "1")) { |
||||||
|
return false; |
||||||
|
} |
||||||
|
if (StringUtils.isNotBlank(requestURI) && request.getMethod().equals("GET")) { |
||||||
|
if (requestURI.endsWith("decision")) { |
||||||
|
return true; |
||||||
|
} |
||||||
|
if (requestURI.endsWith("/view/form") || requestURI.endsWith("/view/report")) { |
||||||
|
if (StringUtils.isNotBlank(request.getParameter("viewlet"))) { |
||||||
|
return true; |
||||||
|
} |
||||||
|
} |
||||||
|
if (requestURI.contains("/v10/entry/access/") && request.getMethod().equals("GET")) { |
||||||
|
return true; |
||||||
|
} |
||||||
|
if (requestURI.contains("/v5/design/report") && (requestURI.endsWith("/edit") || requestURI.endsWith("/view"))) { |
||||||
|
return true; |
||||||
|
} |
||||||
|
} |
||||||
|
return false; |
||||||
|
} |
||||||
|
|
||||||
|
public static void printException2FrLog(Throwable e) { |
||||||
|
StringWriter writer = new StringWriter(); |
||||||
|
e.printStackTrace(new PrintWriter(writer)); |
||||||
|
String s = writer.toString(); |
||||||
|
FineLoggerFactory.getLogger().error("错误:{}", s); |
||||||
|
} |
||||||
|
|
||||||
|
private boolean isLogin(HttpServletRequest req) { |
||||||
|
return LoginService.getInstance().isLogged(req); |
||||||
|
} |
||||||
|
} |
@ -0,0 +1,70 @@ |
|||||||
|
package com.fr.plugin; |
||||||
|
|
||||||
|
import com.fr.config.*; |
||||||
|
import com.fr.config.holder.Conf; |
||||||
|
import com.fr.config.holder.factory.Holders; |
||||||
|
|
||||||
|
@Visualization(category = "单点登录配置") |
||||||
|
public class Oauth2Config extends DefaultConfiguration { |
||||||
|
|
||||||
|
private static volatile Oauth2Config config = null; |
||||||
|
|
||||||
|
public static Oauth2Config getInstance() { |
||||||
|
if (config == null) { |
||||||
|
config = ConfigContext.getConfigInstance(Oauth2Config.class); |
||||||
|
} |
||||||
|
return config; |
||||||
|
} |
||||||
|
|
||||||
|
@Identifier(value = "valAddr", name = "接口地址", description = "接口地址", status = Status.SHOW) |
||||||
|
private Conf<String> valAddr = Holders.simple(""); |
||||||
|
@Identifier(value = "frUrl", name = "报表地址", description = "报表地址", status = Status.SHOW) |
||||||
|
private Conf<String> frUrl = Holders.simple("http://localhost:8075/webroot/decision"); |
||||||
|
@Identifier(value = "appId", name = "clientId", description = "clientId", status = Status.SHOW) |
||||||
|
private Conf<String> appId = Holders.simple(""); |
||||||
|
@Identifier(value = "clientSecret", name = "clientSecret", description = "clientSecret", status = Status.SHOW) |
||||||
|
private Conf<String> clientSecret = Holders.simple(""); |
||||||
|
|
||||||
|
public String getFrUrl() { |
||||||
|
return frUrl.get(); |
||||||
|
} |
||||||
|
|
||||||
|
public void setFrUrl(String frUrl) { |
||||||
|
this.frUrl.set(frUrl); |
||||||
|
} |
||||||
|
|
||||||
|
public String getAppId() { |
||||||
|
return appId.get(); |
||||||
|
} |
||||||
|
|
||||||
|
public void setAppId(String appId) { |
||||||
|
this.appId.set(appId); |
||||||
|
} |
||||||
|
|
||||||
|
public String getClientSecret() { |
||||||
|
return clientSecret.get(); |
||||||
|
} |
||||||
|
|
||||||
|
public void setClientSecret(String clientSecret) { |
||||||
|
this.clientSecret.set(clientSecret); |
||||||
|
} |
||||||
|
|
||||||
|
public String getValAddr() { |
||||||
|
return valAddr.get(); |
||||||
|
} |
||||||
|
|
||||||
|
public void setValAddr(String valAddr) { |
||||||
|
this.valAddr.set(valAddr); |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public Object clone() throws CloneNotSupportedException { |
||||||
|
Oauth2Config cloned = (Oauth2Config) super.clone(); |
||||||
|
cloned.valAddr = (Conf<String>) valAddr.clone(); |
||||||
|
cloned.appId = (Conf<String>) appId.clone(); |
||||||
|
cloned.clientSecret = (Conf<String>) clientSecret.clone(); |
||||||
|
cloned.frUrl = (Conf<String>) frUrl.clone(); |
||||||
|
return cloned; |
||||||
|
} |
||||||
|
|
||||||
|
} |
@ -0,0 +1,122 @@ |
|||||||
|
package com.fr.plugin; |
||||||
|
|
||||||
|
import com.fanruan.api.net.http.HttpKit; |
||||||
|
import com.fr.decision.authority.data.User; |
||||||
|
import com.fr.decision.fun.impl.BaseHttpHandler; |
||||||
|
import com.fr.decision.webservice.utils.DecisionStatusService; |
||||||
|
import com.fr.decision.webservice.v10.login.LoginService; |
||||||
|
import com.fr.decision.webservice.v10.user.UserService; |
||||||
|
import com.fr.json.JSONObject; |
||||||
|
import com.fr.log.FineLoggerFactory; |
||||||
|
import com.fr.store.StateHubService; |
||||||
|
import com.fr.third.jodd.util.StringUtil; |
||||||
|
import com.fr.third.org.apache.commons.lang3.StringUtils; |
||||||
|
import com.fr.third.springframework.web.bind.annotation.RequestMethod; |
||||||
|
import com.fr.web.utils.WebUtils; |
||||||
|
import org.dom4j.Document; |
||||||
|
import org.dom4j.DocumentException; |
||||||
|
import org.dom4j.DocumentHelper; |
||||||
|
import org.dom4j.Element; |
||||||
|
|
||||||
|
import javax.servlet.http.HttpServletRequest; |
||||||
|
import javax.servlet.http.HttpServletResponse; |
||||||
|
import java.io.IOException; |
||||||
|
import java.nio.charset.StandardCharsets; |
||||||
|
import java.util.Base64; |
||||||
|
import java.util.HashMap; |
||||||
|
import java.util.Map; |
||||||
|
|
||||||
|
public class TCAuthCallbackApi extends BaseHttpHandler { |
||||||
|
@Override |
||||||
|
public RequestMethod getMethod() { |
||||||
|
return null; |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public String getPath() { |
||||||
|
return "/authCallBack"; |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public boolean isPublic() { |
||||||
|
return true; |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public void handle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse) throws Exception { |
||||||
|
String code = WebUtils.getHTTPRequestParameter(httpServletRequest, "code"); |
||||||
|
if (StringUtils.isBlank(code)) { |
||||||
|
WebUtils.printAsString(httpServletResponse, "code授权码不存在"); |
||||||
|
return; |
||||||
|
} |
||||||
|
//第一步获取token
|
||||||
|
|
||||||
|
String accessToken = getAccessToken(code); |
||||||
|
if (StringUtils.isBlank(accessToken)) { |
||||||
|
WebUtils.printAsString(httpServletResponse, "授权码无效,请重新授权"); |
||||||
|
return; |
||||||
|
} |
||||||
|
String uid = getUserInfo(accessToken); |
||||||
|
User user = UserService.getInstance().getUserByUserName(uid); |
||||||
|
if (user == null) { |
||||||
|
WebUtils.printAsString(httpServletResponse, "登录失败:" + uid + " 在帆软用户体系不存在,请联系管理员添加"); |
||||||
|
return; |
||||||
|
} |
||||||
|
login(httpServletRequest, httpServletResponse, uid); |
||||||
|
StateHubService stateHubService = DecisionStatusService.originUrlStatusService(); |
||||||
|
Object callback = stateHubService.get("loginCallBack"); |
||||||
|
if (callback != null) { |
||||||
|
sendRedirect(httpServletResponse, callback.toString()); |
||||||
|
return; |
||||||
|
} |
||||||
|
sendRedirect(httpServletResponse, HttpUtils.getDefaultUrl(httpServletRequest)); |
||||||
|
} |
||||||
|
|
||||||
|
private String getAccessToken(String code) throws IOException { |
||||||
|
Oauth2Config config = Oauth2Config.getInstance(); |
||||||
|
String valAddr = config.getValAddr(); |
||||||
|
String appId = config.getAppId(); |
||||||
|
String clientSecret = config.getClientSecret(); |
||||||
|
String frUrl = Oauth2Config.getInstance().getFrUrl(); |
||||||
|
String redirectUrl = String.format("%s/url/iam/authCallBack", frUrl); |
||||||
|
Map<String, String> params = new HashMap<>(); |
||||||
|
String tokenUrl = String.format("%s/oauth2/rest/token", valAddr); |
||||||
|
params.put("redirect_uri", redirectUrl); |
||||||
|
params.put("grant_type", "AUTHORIZATION_CODE"); |
||||||
|
params.put("code", code); |
||||||
|
Map<String, String> header = new HashMap<>(); |
||||||
|
header.put("X-OAUTH-IDENTITY-DOMAIN-NAME", "IdmDomain"); |
||||||
|
header.put("Authorization", "Basic " + Base64.getEncoder().encodeToString(String.format("%s:%s", appId, clientSecret).getBytes(StandardCharsets.UTF_8))); |
||||||
|
String json = HttpKit.post(tokenUrl, params, "utf-8", "utf-8", header); |
||||||
|
FineLoggerFactory.getLogger().info("获取AccessToken 请求返回:{}", json); |
||||||
|
JSONObject obj = new JSONObject(json); |
||||||
|
return obj.getString("access_token"); |
||||||
|
} |
||||||
|
|
||||||
|
public static String getUserInfo(String accessToken) throws DocumentException, IOException { |
||||||
|
Map<String, String> header = new HashMap<>(); |
||||||
|
Oauth2Config config = Oauth2Config.getInstance(); |
||||||
|
String valAddr = config.getValAddr(); |
||||||
|
String url = String.format("%s/oauth2/rest/userinfo?access_token=%s", valAddr, accessToken); |
||||||
|
header.put("Authorization", "Bearer " + accessToken); |
||||||
|
String json = HttpKit.get(url, new HashMap<>(), header); |
||||||
|
FineLoggerFactory.getLogger().info("获取userinfo 请求返回:{}", json); |
||||||
|
JSONObject obj = new JSONObject(json); |
||||||
|
return obj.getString("sub"); |
||||||
|
} |
||||||
|
|
||||||
|
|
||||||
|
private String login(HttpServletRequest req, HttpServletResponse res, String username) throws Exception { |
||||||
|
String token = LoginService.getInstance().login(req, res, username); |
||||||
|
req.setAttribute("fine_auth_token", token); |
||||||
|
FineLoggerFactory.getLogger().info("fr FrFilter is over with username is ###" + username); |
||||||
|
return token; |
||||||
|
} |
||||||
|
|
||||||
|
private void sendRedirect(HttpServletResponse res, String url) throws IOException { |
||||||
|
Map<String, String> params = new HashMap<>(); |
||||||
|
params.put("callBack", url); |
||||||
|
WebUtils.writeOutTemplate("com/fr/plugin/redirect.html", res, params); |
||||||
|
} |
||||||
|
|
||||||
|
} |
@ -0,0 +1,25 @@ |
|||||||
|
package com.fr.plugin; |
||||||
|
|
||||||
|
import com.fr.decision.fun.HttpHandler; |
||||||
|
import com.fr.decision.fun.impl.AbstractHttpHandlerProvider; |
||||||
|
import com.fr.plugin.transform.ExecuteFunctionRecord; |
||||||
|
import com.fr.plugin.transform.FunctionRecorder; |
||||||
|
import com.fr.stable.fun.Authorize; |
||||||
|
|
||||||
|
@FunctionRecorder |
||||||
|
/** |
||||||
|
* url处理器需要在这里注册 |
||||||
|
*/ |
||||||
|
@Authorize |
||||||
|
public class TCauth2HandlerProvider extends AbstractHttpHandlerProvider { |
||||||
|
@Override |
||||||
|
@ExecuteFunctionRecord |
||||||
|
public HttpHandler[] registerHandlers() { |
||||||
|
return new HttpHandler[]{ |
||||||
|
new GoAuthApi(), |
||||||
|
new GetTicket(), |
||||||
|
new TCAuthCallbackApi() |
||||||
|
}; |
||||||
|
} |
||||||
|
|
||||||
|
} |
@ -0,0 +1,27 @@ |
|||||||
|
package com.fr.plugin; |
||||||
|
|
||||||
|
import com.fr.decision.fun.impl.AbstractURLAliasProvider; |
||||||
|
import com.fr.decision.webservice.url.alias.URLAlias; |
||||||
|
import com.fr.decision.webservice.url.alias.URLAliasFactory; |
||||||
|
|
||||||
|
/** |
||||||
|
* 将长连接转换为短连接 |
||||||
|
* 参考文档: |
||||||
|
* https://wiki.fanruan.com/display/PD/com.fr.decision.fun.URLAliasProvider
|
||||||
|
*/ |
||||||
|
public class TCauth2URLAliasBridge extends AbstractURLAliasProvider |
||||||
|
{ |
||||||
|
public TCauth2URLAliasBridge() { |
||||||
|
Oauth2Config.getInstance(); |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public URLAlias[] registerAlias() { |
||||||
|
//像这样配置之后再访问/api就可以通过http(s)://ip:port/webroot/decision/url/api。 进行访问
|
||||||
|
return new URLAlias[]{ |
||||||
|
URLAliasFactory.createPluginAlias("/goAuth", "/goAuth", true), |
||||||
|
URLAliasFactory.createPluginAlias("/getToken", "/getToken", true), |
||||||
|
URLAliasFactory.createPluginAlias("/iam/authCallBack", "/authCallBack", true), |
||||||
|
}; |
||||||
|
} |
||||||
|
} |
Loading…
Reference in new issue