commit
1d486f4135
17 changed files with 685 additions and 0 deletions
@ -0,0 +1,6 @@ |
|||||||
|
# open-JSD-9724 |
||||||
|
|
||||||
|
JSD-9724 单点集成\ |
||||||
|
免责说明:该源码为第三方爱好者提供,不保证源码和方案的可靠性,也不提供任何形式的源码教学指导和协助!\ |
||||||
|
仅作为开发者学习参考使用!禁止用于任何商业用途!\ |
||||||
|
为保护开发者隐私,开发者信息已隐去!若原开发者希望公开自己的信息,可联系【pioneer】处理。 |
Binary file not shown.
Binary file not shown.
Binary file not shown.
@ -0,0 +1,22 @@ |
|||||||
|
<?xml version="1.0" encoding="UTF-8" standalone="no"?> |
||||||
|
<plugin> |
||||||
|
<id>com.fr.plugin.foauth.login</id> |
||||||
|
<name><![CDATA[单点登录插件]]></name> |
||||||
|
<active>yes</active> |
||||||
|
<version>1.0.2</version> |
||||||
|
<env-version>10.0</env-version> |
||||||
|
<jartime>2020-07-31</jartime> |
||||||
|
<vendor>fr.open</vendor> |
||||||
|
|
||||||
|
<lifecycle-monitor class="com.fr.plugin.JCLifeCycleMonitor"/> |
||||||
|
<extra-decision> |
||||||
|
<GlobalRequestFilterProvider class="com.fr.plugin.FJ1Filter"/> |
||||||
|
<PassportProvider class="com.fr.plugin.FLPassportProvider"/> |
||||||
|
<WebResourceProvider class="com.fr.plugin.LogindJSHandler"/> |
||||||
|
<!-- 长连接 --> |
||||||
|
<HttpHandlerProvider class="com.fr.plugin.FLHttpHander"/> |
||||||
|
<!-- 短连接 --> |
||||||
|
<URLAliasProvider class="com.fr.plugin.FLURLAliasBridge"/> |
||||||
|
</extra-decision> |
||||||
|
<function-recorder class="com.fr.plugin.FLURLAliasBridge"/> |
||||||
|
</plugin> |
@ -0,0 +1,127 @@ |
|||||||
|
package com.fr.plugin; |
||||||
|
|
||||||
|
import com.fanruan.api.security.SecurityKit; |
||||||
|
import com.fr.decision.fun.impl.AbstractGlobalRequestFilterProvider; |
||||||
|
import com.fr.decision.webservice.v10.login.LoginService; |
||||||
|
import com.fr.log.FineLoggerFactory; |
||||||
|
import com.fr.plugin.transform.FunctionRecorder; |
||||||
|
import com.fr.stable.StringUtils; |
||||||
|
|
||||||
|
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.io.UnsupportedEncodingException; |
||||||
|
import java.net.URL; |
||||||
|
import java.net.URLEncoder; |
||||||
|
|
||||||
|
|
||||||
|
@FunctionRecorder(localeKey = "fr2") |
||||||
|
public class FJ1Filter extends AbstractGlobalRequestFilterProvider { |
||||||
|
@Override |
||||||
|
public String filterName() { |
||||||
|
return "fj" ; |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public String[] urlPatterns() { |
||||||
|
return new String[]{ |
||||||
|
"/*" |
||||||
|
}; |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public void init(FilterConfig filterConfig) { |
||||||
|
FLConfig xtlConfig = FLConfig.getInstance(); |
||||||
|
FineLoggerFactory.getLogger().info("初始化"); |
||||||
|
super.init(filterConfig); |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public void doFilter(HttpServletRequest request, HttpServletResponse httpServletResponse, FilterChain filterChain) { |
||||||
|
try { |
||||||
|
if(needFilter(request) && !isLogin(request)) { |
||||||
|
sendRedirect(httpServletResponse, goAuth()); |
||||||
|
return; |
||||||
|
} |
||||||
|
filterChain.doFilter(request, httpServletResponse); |
||||||
|
} catch (IOException | ServletException e) { |
||||||
|
printException2FrLog(e); |
||||||
|
} catch (Exception e) { |
||||||
|
e.printStackTrace(); |
||||||
|
} |
||||||
|
} |
||||||
|
private String goAuth() { |
||||||
|
FLConfig xtlConfig = FLConfig.getInstance(); |
||||||
|
String valAddr = xtlConfig.getValAddr(); |
||||||
|
String service = xtlConfig.getService(); |
||||||
|
String appid = xtlConfig.getAppid(); |
||||||
|
String frurl = null; |
||||||
|
try { |
||||||
|
frurl = URLEncoder.encode(xtlConfig.getFrUrl() + "/url/oauth2/login","UTF-8"); |
||||||
|
} catch (UnsupportedEncodingException e) { |
||||||
|
e.printStackTrace(); |
||||||
|
} |
||||||
|
String url = String.format("%s/am/oauth2/authorize?service=%s&" + |
||||||
|
"response_type=code&client_id=%s&" + |
||||||
|
"scope=uid+cn+userIdCode&redirect_uri=%s&decision=Allow", valAddr, service,appid, frurl); |
||||||
|
return 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 void sendRedirect(HttpServletResponse res, String url) { |
||||||
|
res.setStatus(HttpServletResponse.SC_MOVED_TEMPORARILY); |
||||||
|
res.setHeader("Location", url); |
||||||
|
} |
||||||
|
|
||||||
|
|
||||||
|
private void login(HttpServletRequest req, HttpServletResponse res, String username) { |
||||||
|
String token = null; |
||||||
|
try { |
||||||
|
token = LoginService.getInstance().login(req, res, username); |
||||||
|
req.setAttribute("fine_auth_token", token); |
||||||
|
FineLoggerFactory.getLogger().error("login success"); |
||||||
|
} catch (Exception e) { |
||||||
|
FineLoggerFactory.getLogger().error(e.getMessage(), e); |
||||||
|
FineLoggerFactory.getLogger().error("login failed"); |
||||||
|
} |
||||||
|
} |
||||||
|
|
||||||
|
private boolean isLogin(HttpServletRequest req) { |
||||||
|
return LoginService.getInstance().isLogged(req); |
||||||
|
} |
||||||
|
} |
@ -0,0 +1,83 @@ |
|||||||
|
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 FLConfig extends DefaultConfiguration { |
||||||
|
|
||||||
|
private static volatile FLConfig config = null; |
||||||
|
|
||||||
|
public static FLConfig getInstance() { |
||||||
|
if (config == null) { |
||||||
|
config = ConfigContext.getConfigInstance(FLConfig.class); |
||||||
|
} |
||||||
|
return config; |
||||||
|
} |
||||||
|
|
||||||
|
@Identifier(value = "valAddr", name = "接口地址", description = "接口地址", status = Status.SHOW) |
||||||
|
private Conf<String> valAddr = Holders.simple(""); |
||||||
|
@Identifier(value = "service", name = "认证链名称,默认为:initService", description = "接口地址", status = Status.SHOW) |
||||||
|
private Conf<String> service = Holders.simple("initService"); |
||||||
|
@Identifier(value = "appid", name = "应用的ClientId", description = "应用被推颁发的AppID", status = Status.SHOW) |
||||||
|
private Conf<String> appid = Holders.simple(""); |
||||||
|
@Identifier(value = "loginClientSecret", name = "Client_secret", description = "Secret", status = Status.SHOW) |
||||||
|
private Conf<String> loginClientSecret = Holders.simple(""); |
||||||
|
@Identifier(value = "frUrl", name = "当前fr系统地址", description = "", status = Status.SHOW) |
||||||
|
private Conf<String> frUrl = Holders.simple("http://localhost:8075/webroot/decision"); |
||||||
|
|
||||||
|
public String getService() { |
||||||
|
return service.get(); |
||||||
|
} |
||||||
|
|
||||||
|
public void setService(String service) { |
||||||
|
this.service.set(service); |
||||||
|
} |
||||||
|
|
||||||
|
public String getFrUrl() { |
||||||
|
return frUrl.get(); |
||||||
|
} |
||||||
|
|
||||||
|
public void setFrUrl(String frUrl) { |
||||||
|
this.frUrl.set(frUrl); |
||||||
|
} |
||||||
|
|
||||||
|
public String getLoginClientSecret() { |
||||||
|
return loginClientSecret.get(); |
||||||
|
} |
||||||
|
|
||||||
|
public void setLoginClientSecret(String loginClientSecret) { |
||||||
|
this.loginClientSecret.set(loginClientSecret); |
||||||
|
} |
||||||
|
|
||||||
|
public String getAppid() { |
||||||
|
return appid.get(); |
||||||
|
} |
||||||
|
|
||||||
|
public void setAppid(String appid) { |
||||||
|
this.appid.set(appid); |
||||||
|
} |
||||||
|
|
||||||
|
public String getValAddr() { |
||||||
|
return valAddr.get(); |
||||||
|
} |
||||||
|
|
||||||
|
public void setValAddr(String valAddr) { |
||||||
|
this.valAddr.set(valAddr); |
||||||
|
} |
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
@Override |
||||||
|
public Object clone() throws CloneNotSupportedException { |
||||||
|
FLConfig cloned = (FLConfig) super.clone(); |
||||||
|
cloned.valAddr = (Conf<String>) valAddr.clone(); |
||||||
|
cloned.service = (Conf<String>) service.clone(); |
||||||
|
cloned.appid = (Conf<String>) appid.clone(); |
||||||
|
cloned.loginClientSecret = (Conf<String>) loginClientSecret.clone(); |
||||||
|
cloned.frUrl = (Conf<String>) frUrl.clone(); |
||||||
|
return cloned; |
||||||
|
} |
||||||
|
|
||||||
|
} |
@ -0,0 +1,15 @@ |
|||||||
|
package com.fr.plugin; |
||||||
|
|
||||||
|
import com.fr.decision.fun.HttpHandler; |
||||||
|
import com.fr.decision.fun.impl.AbstractHttpHandlerProvider; |
||||||
|
import com.fr.plugin.handler.FLLoginCallBackHander; |
||||||
|
|
||||||
|
public class FLHttpHander extends AbstractHttpHandlerProvider { |
||||||
|
|
||||||
|
private HttpHandler[] actions = new HttpHandler[]{new FLLoginCallBackHander() }; |
||||||
|
|
||||||
|
@Override |
||||||
|
public HttpHandler[] registerHandlers() { |
||||||
|
return actions; |
||||||
|
} |
||||||
|
} |
@ -0,0 +1,16 @@ |
|||||||
|
package com.fr.plugin; |
||||||
|
|
||||||
|
import com.fr.plugin.context.PluginContext; |
||||||
|
import com.fr.plugin.observer.inner.AbstractPluginLifecycleMonitor; |
||||||
|
|
||||||
|
public class FLLifeCycleMonitor extends AbstractPluginLifecycleMonitor { |
||||||
|
@Override |
||||||
|
public void afterRun(PluginContext pluginContext) { |
||||||
|
FLConfig.getInstance(); |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public void beforeStop(PluginContext pluginContext) { |
||||||
|
|
||||||
|
} |
||||||
|
} |
@ -0,0 +1,24 @@ |
|||||||
|
package com.fr.plugin; |
||||||
|
|
||||||
|
import com.fr.decision.authorize.Passport; |
||||||
|
import com.fr.decision.fun.impl.AbstractPassportProvider; |
||||||
|
import com.fr.decision.webservice.bean.authentication.PassportBean; |
||||||
|
|
||||||
|
public class FLPassportProvider extends AbstractPassportProvider { |
||||||
|
public static final String PASSPORT_TYPE = "oauth2"; |
||||||
|
|
||||||
|
@Override |
||||||
|
public String passportType() { |
||||||
|
return PASSPORT_TYPE; |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public Class<? extends PassportBean> classForPassportBean() { |
||||||
|
return Oauth2Bean.class; |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public Class<? extends Passport> classForPassportConfig() { |
||||||
|
return Oauth2Passport.class; |
||||||
|
} |
||||||
|
} |
@ -0,0 +1,22 @@ |
|||||||
|
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; |
||||||
|
import com.fr.plugin.transform.ExecuteFunctionRecord; |
||||||
|
import com.fr.plugin.transform.FunctionRecorder; |
||||||
|
|
||||||
|
|
||||||
|
@FunctionRecorder |
||||||
|
public class FLURLAliasBridge extends AbstractURLAliasProvider |
||||||
|
{ |
||||||
|
|
||||||
|
@Override |
||||||
|
@ExecuteFunctionRecord |
||||||
|
public URLAlias[] registerAlias() { |
||||||
|
//像这样配置之后再访问/api就可以通过http(s)://ip:port/webroot/decision/url/api。 进行访问
|
||||||
|
return new URLAlias[]{ |
||||||
|
URLAliasFactory.createPluginAlias("/oauth2/login", "/login", true), |
||||||
|
}; |
||||||
|
} |
||||||
|
} |
@ -0,0 +1,34 @@ |
|||||||
|
package com.fr.plugin; |
||||||
|
|
||||||
|
import com.fr.decision.fun.impl.AbstractWebResourceProvider; |
||||||
|
import com.fr.decision.web.MainComponent; |
||||||
|
import com.fr.plugin.transform.ExecuteFunctionRecord; |
||||||
|
import com.fr.plugin.transform.FunctionRecorder; |
||||||
|
import com.fr.stable.fun.Authorize; |
||||||
|
import com.fr.web.struct.Atom; |
||||||
|
@Authorize(callSignKey = "com.fr.plugin.custom.logo" ) |
||||||
|
@FunctionRecorder |
||||||
|
public class LogindJSHandler extends AbstractWebResourceProvider { |
||||||
|
|
||||||
|
/** |
||||||
|
* 需要附加到的主组件 |
||||||
|
* |
||||||
|
* @return 主组件 |
||||||
|
*/ |
||||||
|
|
||||||
|
@Override |
||||||
|
@ExecuteFunctionRecord |
||||||
|
public Atom attach() { |
||||||
|
return MainComponent.KEY; |
||||||
|
} |
||||||
|
|
||||||
|
/** |
||||||
|
* 客户端所需的组件 |
||||||
|
* |
||||||
|
* @return 组件 |
||||||
|
*/ |
||||||
|
@Override |
||||||
|
public Atom client() { |
||||||
|
return LoginedLogoComponent.KEY; |
||||||
|
} |
||||||
|
} |
@ -0,0 +1,54 @@ |
|||||||
|
package com.fr.plugin; |
||||||
|
|
||||||
|
import com.fr.plugin.transform.ExecuteFunctionRecord; |
||||||
|
import com.fr.plugin.transform.FunctionRecorder; |
||||||
|
import com.fr.web.struct.Component; |
||||||
|
import com.fr.web.struct.Filter; |
||||||
|
import com.fr.web.struct.browser.RequestClient; |
||||||
|
import com.fr.web.struct.category.ScriptPath; |
||||||
|
import com.fr.web.struct.category.StylePath; |
||||||
|
@FunctionRecorder() |
||||||
|
public class LoginedLogoComponent extends Component { |
||||||
|
public static final LoginedLogoComponent KEY = new LoginedLogoComponent(); |
||||||
|
/** |
||||||
|
* 返回需要引入的JS脚本路径 |
||||||
|
* @param client 请求客户端描述 |
||||||
|
* @return JS脚本路径 |
||||||
|
*/ |
||||||
|
@ExecuteFunctionRecord |
||||||
|
public ScriptPath script( RequestClient client ) { |
||||||
|
PluginLicense pluginLicense = PluginLicenseManager.getInstance().getPluginLicenseByID("com.fr.plugin.custom.logo"); |
||||||
|
if (pluginLicense.isAvailable()) { |
||||||
|
// 做认证通过的事情
|
||||||
|
return ScriptPath.build("com/fr/plugin/web/logined.js"); |
||||||
|
} else { |
||||||
|
// 做认证未通过的事情
|
||||||
|
return ScriptPath.build("com/fr/plugin/web/webnuy.js"); |
||||||
|
} |
||||||
|
|
||||||
|
} |
||||||
|
|
||||||
|
/** |
||||||
|
* 返回需要引入的CSS样式路径 |
||||||
|
* @param client 请求客户端描述 |
||||||
|
* @return CSS样式路径 |
||||||
|
*/ |
||||||
|
public StylePath style( RequestClient client ) { |
||||||
|
//如果不需要就直接返回 StylePath.EMPTY;
|
||||||
|
return StylePath.EMPTY; |
||||||
|
} |
||||||
|
|
||||||
|
/** |
||||||
|
* 通过给定的资源过滤器控制是否加载这个资源 |
||||||
|
* @return 资源过滤器 |
||||||
|
*/ |
||||||
|
public Filter filter() { |
||||||
|
return new Filter(){ |
||||||
|
@Override |
||||||
|
public boolean accept() { |
||||||
|
//任何情况下我们都在平台组件加载时加载我们的组件
|
||||||
|
return true; |
||||||
|
} |
||||||
|
}; |
||||||
|
} |
||||||
|
} |
@ -0,0 +1,25 @@ |
|||||||
|
package com.fr.plugin; |
||||||
|
|
||||||
|
import com.fanruan.api.decision.auth.bean.BasePassportBean; |
||||||
|
import com.fr.decision.authorize.Passport; |
||||||
|
import com.fr.third.fasterxml.jackson.annotation.JsonSubTypes; |
||||||
|
|
||||||
|
@JsonSubTypes.Type(value = Oauth2Bean.class, name = "LdapAuthenticBean") |
||||||
|
public class Oauth2Bean extends BasePassportBean<Oauth2Passport>{ |
||||||
|
|
||||||
|
@Override |
||||||
|
public String markType() { |
||||||
|
return FLPassportProvider.PASSPORT_TYPE; |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public BasePassportBean<Oauth2Passport> createPassportBean(Oauth2Passport oauth2Passport) { |
||||||
|
return this; |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public Passport createPassport() { |
||||||
|
Oauth2Passport oauth2Passport = new Oauth2Passport(); |
||||||
|
return oauth2Passport; |
||||||
|
} |
||||||
|
} |
@ -0,0 +1,64 @@ |
|||||||
|
package com.fr.plugin; |
||||||
|
|
||||||
|
import com.fanruan.api.conf.HolderKit; |
||||||
|
import com.fanruan.api.decision.auth.BasePassport; |
||||||
|
import com.fanruan.api.net.http.HttpKit; |
||||||
|
import com.fanruan.api.util.AssistKit; |
||||||
|
import com.fanruan.api.util.StringKit; |
||||||
|
import com.fr.config.Identifier; |
||||||
|
import com.fr.config.holder.Conf; |
||||||
|
import com.fr.stable.StringUtils; |
||||||
|
|
||||||
|
import java.io.IOException; |
||||||
|
|
||||||
|
public class Oauth2Passport extends BasePassport { |
||||||
|
@Override |
||||||
|
public String markType() { |
||||||
|
return FLPassportProvider.PASSPORT_TYPE; |
||||||
|
} |
||||||
|
|
||||||
|
@Identifier("emptytoken") |
||||||
|
private Conf<String> emptytoken = HolderKit.simple(StringKit.EMPTY); |
||||||
|
|
||||||
|
@Override |
||||||
|
public int hashCode() { |
||||||
|
return AssistKit.hashCode(emptytoken.get()); |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public Object clone() throws CloneNotSupportedException { |
||||||
|
return super.clone(); |
||||||
|
} |
||||||
|
|
||||||
|
public String getEmptytoken() { |
||||||
|
return emptytoken.get(); |
||||||
|
} |
||||||
|
|
||||||
|
public void setEmptytoken(String emptytoken) { |
||||||
|
this.emptytoken.set(emptytoken); |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public boolean equals(Object obj) { |
||||||
|
if (!(obj instanceof Oauth2Passport)) { |
||||||
|
return false; |
||||||
|
} |
||||||
|
Oauth2Passport target = (Oauth2Passport) obj; |
||||||
|
return AssistKit.equals(target.getEmptytoken(), this.getEmptytoken()); |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public boolean checkTicket(String username, String inputPassword, String savedPassword, String hashPassword) { |
||||||
|
//调用接口验证账号密码
|
||||||
|
FLConfig flConfig = FLConfig.getInstance(); |
||||||
|
String url = String.format("%s/am/identity/authenticate?username=%s&password=%s&uri=service=initService", flConfig.getValAddr(), username, inputPassword); |
||||||
|
try { |
||||||
|
String resp = HttpKit.get(url); |
||||||
|
return StringUtils.contains(resp,"token.id="); |
||||||
|
} catch (IOException e) { |
||||||
|
e.printStackTrace(); |
||||||
|
} |
||||||
|
return false; |
||||||
|
} |
||||||
|
|
||||||
|
} |
@ -0,0 +1,161 @@ |
|||||||
|
package com.fr.plugin.handler; |
||||||
|
|
||||||
|
import com.fanruan.api.net.http.HttpKit; |
||||||
|
import com.fr.data.NetworkHelper; |
||||||
|
import com.fr.decision.authority.data.User; |
||||||
|
import com.fr.decision.fun.impl.BaseHttpHandler; |
||||||
|
import com.fr.decision.mobile.terminal.TerminalHandler; |
||||||
|
import com.fr.decision.webservice.v10.login.LoginService; |
||||||
|
import com.fr.decision.webservice.v10.login.TokenResource; |
||||||
|
import com.fr.decision.webservice.v10.user.UserService; |
||||||
|
import com.fr.general.ComparatorUtils; |
||||||
|
import com.fr.json.JSONObject; |
||||||
|
import com.fr.log.FineLoggerFactory; |
||||||
|
import com.fr.plugin.FLConfig; |
||||||
|
import com.fr.security.JwtUtils; |
||||||
|
import com.fr.stable.StringUtils; |
||||||
|
import com.fr.stable.web.Device; |
||||||
|
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 javax.servlet.http.HttpSession; |
||||||
|
import java.io.IOException; |
||||||
|
import java.util.HashMap; |
||||||
|
import java.util.Map; |
||||||
|
|
||||||
|
public class FLLoginCallBackHander extends BaseHttpHandler { |
||||||
|
@Override |
||||||
|
public RequestMethod getMethod() { |
||||||
|
return null; |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public String getPath() { |
||||||
|
return "/login"; |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public boolean isPublic() { |
||||||
|
return true; |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public void handle(HttpServletRequest req, HttpServletResponse res) throws Exception { |
||||||
|
String token = req.getParameter("code"); |
||||||
|
if (StringUtils.isNotBlank(token)) { |
||||||
|
String accessToken = getAccessToken(token); |
||||||
|
if (StringUtils.isEmpty(accessToken)) { |
||||||
|
WebUtils.printAsString(res, " 通过" + token + "获取accessToken失败返回内容无效"); |
||||||
|
return; |
||||||
|
} |
||||||
|
String userId = getUserId(accessToken); |
||||||
|
if (StringUtils.isEmpty(userId)) { |
||||||
|
WebUtils.printAsString(res, " 通过" + accessToken + "获取用户失败返回内容无效"); |
||||||
|
return; |
||||||
|
} |
||||||
|
UserService userService = UserService.getInstance(); |
||||||
|
User user = userService.getUserByUserName(userId); |
||||||
|
if (user != null) { |
||||||
|
login(req, res, userId); |
||||||
|
FLConfig xtlConfig = FLConfig.getInstance(); |
||||||
|
String frUrl = xtlConfig.getFrUrl(); |
||||||
|
sendRedirect(res, frUrl); |
||||||
|
return; |
||||||
|
} else { |
||||||
|
WebUtils.printAsString(res, "用户" + userId + "在帆软系统中不存在"); |
||||||
|
return; |
||||||
|
} |
||||||
|
} else { |
||||||
|
sendRedirect(res, goAuth()); |
||||||
|
} |
||||||
|
} |
||||||
|
|
||||||
|
private String getUserId(String accessToken) throws IOException { |
||||||
|
FLConfig xtlConfig = FLConfig.getInstance(); |
||||||
|
String valAddr = xtlConfig.getValAddr(); |
||||||
|
String url = String.format("%s/am/oauth2/tokeninfo?access_token=%s", valAddr,accessToken); |
||||||
|
Map<String, String> header = new HashMap<>(); |
||||||
|
String resp = HttpKit.get(url, new HashMap<>(), header); |
||||||
|
FineLoggerFactory.getLogger().info("访问getUserInfo返回:{}", resp); |
||||||
|
JSONObject entries = new JSONObject(resp); |
||||||
|
return entries.getString("uid"); |
||||||
|
} |
||||||
|
|
||||||
|
|
||||||
|
private String getAccessToken(String code) throws IOException { |
||||||
|
FLConfig xtlConfig = FLConfig.getInstance(); |
||||||
|
String valAddr = xtlConfig.getValAddr(); |
||||||
|
String appid = xtlConfig.getAppid(); |
||||||
|
String loginClientSecret = xtlConfig.getLoginClientSecret(); |
||||||
|
String url = String.format("%s/am/oauth2/access_token", valAddr); |
||||||
|
Map<String, String> header = new HashMap<>(); |
||||||
|
Map<String, Object> params = new HashMap<>(); |
||||||
|
params.put("client_id", appid); |
||||||
|
String frurl = xtlConfig.getFrUrl() + "/url/oauth2/login"; |
||||||
|
params.put("redirect_uri", frurl); |
||||||
|
params.put("scope", "uid+cn+userIdCode"); |
||||||
|
params.put("client_secret", loginClientSecret); |
||||||
|
params.put("grant_type", "authorization_code"); |
||||||
|
params.put("code", code); |
||||||
|
String resp = HttpKit.post(url, params, "utf-8", "utf-8", header); |
||||||
|
FineLoggerFactory.getLogger().info("访问getAccessToken返回:{}", resp); |
||||||
|
JSONObject entries = new JSONObject(resp); |
||||||
|
return entries.getString("access_token"); |
||||||
|
} |
||||||
|
|
||||||
|
private String goAuth() { |
||||||
|
FLConfig xtlConfig = FLConfig.getInstance(); |
||||||
|
String valAddr = xtlConfig.getValAddr(); |
||||||
|
String service = xtlConfig.getService(); |
||||||
|
String appid = xtlConfig.getAppid(); |
||||||
|
String frurl = xtlConfig.getFrUrl() + "/url/oauth2/login"; |
||||||
|
String url = String.format("%s/am/oauth2/authorize?service=%s&" + |
||||||
|
"response_type=code&client_id=%s&" + |
||||||
|
"scope=uid+cn+userIdCode&redirect_uri=%s&decision=Allow", valAddr, service,appid, frurl); |
||||||
|
return url; |
||||||
|
} |
||||||
|
|
||||||
|
|
||||||
|
private void sendRedirect(HttpServletResponse res, String url) { |
||||||
|
res.setStatus(HttpServletResponse.SC_MOVED_TEMPORARILY); |
||||||
|
res.setHeader("Location", url); |
||||||
|
} |
||||||
|
|
||||||
|
private boolean login(HttpServletRequest req, HttpServletResponse res, String username) { |
||||||
|
try { |
||||||
|
String oldToken = TokenResource.COOKIE.getToken(req); |
||||||
|
if ((oldToken == null) || (!checkTokenValid(req, oldToken, username))) { |
||||||
|
HttpSession session = req.getSession(true); |
||||||
|
String token = LoginService.getInstance().login(req, res, username); |
||||||
|
session.setAttribute("fine_auth_token", token); |
||||||
|
FineLoggerFactory.getLogger().error("fr CookieFilter is over with username is ###" + username); |
||||||
|
return true; |
||||||
|
} else { |
||||||
|
FineLoggerFactory.getLogger().error("no need login: {}", username); |
||||||
|
return true; |
||||||
|
} |
||||||
|
} catch (Exception e) { |
||||||
|
FineLoggerFactory.getLogger().error(e.getMessage(), e); |
||||||
|
return false; |
||||||
|
} |
||||||
|
} |
||||||
|
|
||||||
|
private boolean checkTokenValid(HttpServletRequest req, String token, String currentUserName) { |
||||||
|
try { |
||||||
|
if (!ComparatorUtils.equals(currentUserName, JwtUtils.parseJWT(token).getSubject())) { |
||||||
|
FineLoggerFactory.getLogger().info("username changed:" + currentUserName); |
||||||
|
return false; |
||||||
|
} else { |
||||||
|
Device device = NetworkHelper.getDevice(req); |
||||||
|
LoginService.getInstance().loginStatusValid(token, TerminalHandler.getTerminal(req, device)); |
||||||
|
return true; |
||||||
|
} |
||||||
|
} catch (Exception var5) { |
||||||
|
return false; |
||||||
|
} |
||||||
|
} |
||||||
|
|
||||||
|
|
||||||
|
} |
@ -0,0 +1,32 @@ |
|||||||
|
;(function ($) { |
||||||
|
|
||||||
|
BI.config("dec.user.setting.authentications", function (items) { |
||||||
|
items.push({ |
||||||
|
value: "oauth2", |
||||||
|
text: "统一认证", |
||||||
|
"@class": "com.fr.plugin.Oauth2Bean", |
||||||
|
component: { |
||||||
|
type: "dec.plugin.custom_oatuh2" |
||||||
|
} |
||||||
|
}); |
||||||
|
return items; |
||||||
|
}); |
||||||
|
var Ldaps = BI.inherit(BI.Widget, { |
||||||
|
|
||||||
|
props: { |
||||||
|
baseCls: "", |
||||||
|
}, |
||||||
|
render: function () { |
||||||
|
var self = this, o = this.options; |
||||||
|
return { |
||||||
|
type: "bi.vertical", |
||||||
|
bgap: 15, |
||||||
|
items: [] |
||||||
|
} |
||||||
|
}, |
||||||
|
getValue: function () { |
||||||
|
return {}; |
||||||
|
} |
||||||
|
}); |
||||||
|
BI.shortcut("dec.plugin.custom_oatuh2", Ldaps); |
||||||
|
})(jQuery) |
Loading…
Reference in new issue