diff --git a/sa-token-core/src/main/java/cn/dev33/satoken/config/SaSignConfig.java b/sa-token-core/src/main/java/cn/dev33/satoken/config/SaSignConfig.java index eb099707..6e83f5ad 100644 --- a/sa-token-core/src/main/java/cn/dev33/satoken/config/SaSignConfig.java +++ b/sa-token-core/src/main/java/cn/dev33/satoken/config/SaSignConfig.java @@ -74,6 +74,19 @@ public class SaSignConfig { } } + /** + * 复制对象 + * @return / + */ + public SaSignConfig copy() { + SaSignConfig obj = new SaSignConfig(); + obj.secretKey = this.secretKey; + obj.timestampDisparity = this.timestampDisparity; + obj.digestAlgo = this.digestAlgo; + obj.digestMethod = this.digestMethod; + return obj; + } + // -------------- 策略函数 diff --git a/sa-token-demo/sa-token-demo-sso/sa-token-demo-sso-server/src/main/resources/application.yml b/sa-token-demo/sa-token-demo-sso/sa-token-demo-sso-server/src/main/resources/application.yml index 08f103e2..dcea68c8 100644 --- a/sa-token-demo/sa-token-demo-sso/sa-token-demo-sso-server/src/main/resources/application.yml +++ b/sa-token-demo/sa-token-demo-sso/sa-token-demo-sso-server/src/main/resources/application.yml @@ -4,6 +4,9 @@ server: # Sa-Token 配置 sa-token: + # 打印操作日志 + is-log: true + # ------- SSO-模式一相关配置 (非模式一不需要配置) # cookie: # 配置 Cookie 作用域 @@ -15,22 +18,27 @@ sa-token: ticket-timeout: 300 # 所有允许的授权回调地址 allow-url: "*" + # API 接口调用秘钥 (默认) + secret-key: kQwIOrYvnXmSDkwEiFngrKidMcdrgKor + # 是否启用匿名 client + allow-anon-client: false # ------- SSO-模式三相关配置 (下面的配置在使用SSO模式三时打开) # 是否打开模式三 is-http: true - allow-anon-client: false clients: + # 应用 sso-client2,采用模式二对接 (跨域、同Redis) sso-client2: client: sso-client2 - allow-url: http://sa-sso-client1.com:9002/sso/login + allow-url: "*" + # 应用 sso-client3,采用模式三对接 (跨域、跨Redis) + sso-client3: + client: sso-client3 + secret-key: SSO-C3-kQwIOrYvnXmSDkwEiFngrKidMcdrgKor + allow-url: "*" - sign: - # API 接口调用秘钥 - secret-key: kQwIOrYvnXmSDkwEiFngrKidMcdrgKor - # ---- 除了以上配置项,你还需要为 Sa-Token 配置http请求处理器(文档有步骤说明) spring: diff --git a/sa-token-demo/sa-token-demo-sso/sa-token-demo-sso2-client/src/main/resources/application.yml b/sa-token-demo/sa-token-demo-sso/sa-token-demo-sso2-client/src/main/resources/application.yml index 716c130c..0a80bc8a 100644 --- a/sa-token-demo/sa-token-demo-sso/sa-token-demo-sso2-client/src/main/resources/application.yml +++ b/sa-token-demo/sa-token-demo-sso/sa-token-demo-sso2-client/src/main/resources/application.yml @@ -15,7 +15,7 @@ sa-token: sign: # API 接口调用秘钥 - secret-key: kQwIOrYvnXmSDkwEiFngrKidMcdrgKor + secret-key: SSO-C2-kQwIOrYvnXmSDkwEiFngrKidMcdrgKor # 配置Sa-Token单独使用的Redis连接 (此处需要和SSO-Server端连接同一个Redis) alone-redis: diff --git a/sa-token-demo/sa-token-demo-sso/sa-token-demo-sso3-client/src/main/resources/application.yml b/sa-token-demo/sa-token-demo-sso/sa-token-demo-sso3-client/src/main/resources/application.yml index f0c2c6f8..b52db6ab 100644 --- a/sa-token-demo/sa-token-demo-sso/sa-token-demo-sso3-client/src/main/resources/application.yml +++ b/sa-token-demo/sa-token-demo-sso/sa-token-demo-sso3-client/src/main/resources/application.yml @@ -4,16 +4,19 @@ server: # sa-token配置 sa-token: + # 打印操作日志 + is-log: true + # sso-client 相关配置 sso-client: + # 应用标识 + client: sso-client3 # sso-server 端主机地址 server-url: http://sa-sso-server.com:9000 # 使用 Http 请求校验ticket (模式三) is-http: true - - sign: # API 接口调用秘钥 - secret-key: kQwIOrYvnXmSDkwEiFngrKidMcdrgKor + secret-key: SSO-C3-kQwIOrYvnXmSDkwEiFngrKidMcdrgKor spring: # 配置 Redis 连接 (此处与SSO-Server端连接不同的Redis) diff --git a/sa-token-plugin/sa-token-sso/src/main/java/cn/dev33/satoken/sso/config/SaSsoClientConfig.java b/sa-token-plugin/sa-token-sso/src/main/java/cn/dev33/satoken/sso/config/SaSsoClientConfig.java index dd7d4a3d..1e6abd9f 100644 --- a/sa-token-plugin/sa-token-sso/src/main/java/cn/dev33/satoken/sso/config/SaSsoClientConfig.java +++ b/sa-token-plugin/sa-token-sso/src/main/java/cn/dev33/satoken/sso/config/SaSsoClientConfig.java @@ -89,6 +89,11 @@ public class SaSsoClientConfig implements Serializable { */ public Boolean isHttp = false; + /** + * API 调用签名秘钥 + */ + public String secretKey; + /** * 是否校验参数签名(方便本地调试用的一个配置项,生产环境请务必为true) */ @@ -274,6 +279,26 @@ public class SaSsoClientConfig implements Serializable { return this; } + /** + * 获取 API 调用签名秘钥 + * + * @return / + */ + public String getSecretKey() { + return this.secretKey; + } + + /** + * 设置 API 调用签名秘钥 + * + * @param secretKey / + * @return 对象自身 + */ + public SaSsoClientConfig setSecretKey(String secretKey) { + this.secretKey = secretKey; + return this; + } + /** * 获取 是否校验参数签名(方便本地调试用的一个配置项,生产环境请务必为true) * @@ -307,6 +332,7 @@ public class SaSsoClientConfig implements Serializable { + ", currSsoLogoutCall=" + currSsoLogoutCall + ", isSlo=" + isSlo + ", isHttp=" + isHttp + + ", secretKey=" + secretKey + ", isCheckSign=" + isCheckSign + "]"; } diff --git a/sa-token-plugin/sa-token-sso/src/main/java/cn/dev33/satoken/sso/config/SaSsoClientModel.java b/sa-token-plugin/sa-token-sso/src/main/java/cn/dev33/satoken/sso/config/SaSsoClientModel.java index ca4ad286..d907f23d 100644 --- a/sa-token-plugin/sa-token-sso/src/main/java/cn/dev33/satoken/sso/config/SaSsoClientModel.java +++ b/sa-token-plugin/sa-token-sso/src/main/java/cn/dev33/satoken/sso/config/SaSsoClientModel.java @@ -47,7 +47,10 @@ public class SaSsoClientModel implements Serializable { */ public Boolean isSlo = true; - + /** + * API 调用签名秘钥 + */ + public String secretKey; // 额外方法 @@ -61,7 +64,6 @@ public class SaSsoClientModel implements Serializable { return this; } - // get set /** @@ -116,12 +118,33 @@ public class SaSsoClientModel implements Serializable { return this; } + /** + * 获取 API 调用签名秘钥 + * + * @return / + */ + public String getSecretKey() { + return this.secretKey; + } + + /** + * 设置 API 调用签名秘钥 + * + * @param secretKey / + * @return 对象自身 + */ + public SaSsoClientModel setSecretKey(String secretKey) { + this.secretKey = secretKey; + return this; + } + @Override public String toString() { return "SaSsoClientModel [" + "client=" + client + ", allowUrl=" + allowUrl + ", isSlo=" + isSlo + + ", secretKey=" + secretKey + "]"; } diff --git a/sa-token-plugin/sa-token-sso/src/main/java/cn/dev33/satoken/sso/config/SaSsoServerConfig.java b/sa-token-plugin/sa-token-sso/src/main/java/cn/dev33/satoken/sso/config/SaSsoServerConfig.java index 971ab578..cedde8fb 100644 --- a/sa-token-plugin/sa-token-sso/src/main/java/cn/dev33/satoken/sso/config/SaSsoServerConfig.java +++ b/sa-token-plugin/sa-token-sso/src/main/java/cn/dev33/satoken/sso/config/SaSsoServerConfig.java @@ -94,6 +94,11 @@ public class SaSsoServerConfig implements Serializable { */ public Boolean isCheckSign = true; + /** + * API 调用签名秘钥 + */ + public String secretKey; + /** * Client 信息配置列表 */ @@ -298,6 +303,26 @@ public class SaSsoServerConfig implements Serializable { return this; } + /** + * 获取 API 调用签名秘钥 + * + * @return / + */ + public String getSecretKey() { + return this.secretKey; + } + + /** + * 设置 API 调用签名秘钥 + * + * @param secretKey / + * @return 对象自身 + */ + public SaSsoServerConfig setSecretKey(String secretKey) { + this.secretKey = secretKey; + return this; + } + /** * 获取 Client 信息配置列表 * @@ -331,6 +356,7 @@ public class SaSsoServerConfig implements Serializable { + ", maxRegClient=" + maxRegClient + ", isCheckSign=" + isCheckSign + ", allowAnonClient=" + allowAnonClient + + ", secretKey=" + secretKey + ", clients=" + clients + "]"; } diff --git a/sa-token-plugin/sa-token-sso/src/main/java/cn/dev33/satoken/sso/template/SaSsoClientTemplate.java b/sa-token-plugin/sa-token-sso/src/main/java/cn/dev33/satoken/sso/template/SaSsoClientTemplate.java index 8418f482..bbfe80d4 100644 --- a/sa-token-plugin/sa-token-sso/src/main/java/cn/dev33/satoken/sso/template/SaSsoClientTemplate.java +++ b/sa-token-plugin/sa-token-sso/src/main/java/cn/dev33/satoken/sso/template/SaSsoClientTemplate.java @@ -16,6 +16,8 @@ package cn.dev33.satoken.sso.template; import cn.dev33.satoken.SaManager; +import cn.dev33.satoken.config.SaSignConfig; +import cn.dev33.satoken.sign.SaSignTemplate; import cn.dev33.satoken.sso.SaSsoManager; import cn.dev33.satoken.sso.config.SaSsoClientConfig; import cn.dev33.satoken.sso.error.SaSsoErrorCode; @@ -191,6 +193,25 @@ public class SaSsoClientTemplate extends SaSsoTemplate { return SaFoxUtil.joinParam(url, signParamsStr); } + /** + * 获取底层使用的 API 签名对象 + * @param client 指定客户端标识,填 null 代表获取默认的 + * @return / + */ + @Override + public SaSignTemplate getSignTemplate(String client) { + SaSignConfig signConfig = SaManager.getSaSignTemplate().getSignConfigOrGlobal().copy(); + + // 使用 secretKey 的优先级:SSO 模块全局配置 > sign 模块默认配置 + String secretKey = getClientConfig().getSecretKey(); + if(SaFoxUtil.isEmpty(secretKey)) { + secretKey = signConfig.getSecretKey(); + } + signConfig.setSecretKey(secretKey); + + return new SaSignTemplate(signConfig); + } + // ------------------- 发起请求 ------------------- diff --git a/sa-token-plugin/sa-token-sso/src/main/java/cn/dev33/satoken/sso/template/SaSsoServerTemplate.java b/sa-token-plugin/sa-token-sso/src/main/java/cn/dev33/satoken/sso/template/SaSsoServerTemplate.java index c872032f..f24f5caf 100644 --- a/sa-token-plugin/sa-token-sso/src/main/java/cn/dev33/satoken/sso/template/SaSsoServerTemplate.java +++ b/sa-token-plugin/sa-token-sso/src/main/java/cn/dev33/satoken/sso/template/SaSsoServerTemplate.java @@ -16,7 +16,10 @@ package cn.dev33.satoken.sso.template; import cn.dev33.satoken.SaManager; +import cn.dev33.satoken.config.SaSignConfig; +import cn.dev33.satoken.context.model.SaRequest; import cn.dev33.satoken.session.SaSession; +import cn.dev33.satoken.sign.SaSignTemplate; import cn.dev33.satoken.sso.SaSsoManager; import cn.dev33.satoken.sso.config.SaSsoClientModel; import cn.dev33.satoken.sso.config.SaSsoServerConfig; @@ -260,12 +263,8 @@ public class SaSsoServerTemplate extends SaSsoTemplate { */ public SaSsoClientModel getClientNotNull(String client) { if(SaFoxUtil.isEmpty(client)) { - SaSsoServerConfig serverConfig = getServerConfig(); - if(serverConfig.getAllowAnonClient()) { - SaSsoClientModel scm = new SaSsoClientModel(); - scm.setAllowUrl(serverConfig.getAllowUrl()); - scm.setIsSlo(serverConfig.getIsSlo()); - return scm; + if(getServerConfig().getAllowAnonClient()) { + return getAnonClient(); } else { throw new SaSsoException("client 标识不可为空"); } @@ -278,6 +277,23 @@ public class SaSsoServerTemplate extends SaSsoTemplate { } } + /** + * 获取匿名 client 信息 + * + * @return / + */ + public SaSsoClientModel getAnonClient() { + SaSsoServerConfig serverConfig = getServerConfig(); + SaSsoClientModel scm = new SaSsoClientModel(); + scm.setAllowUrl(serverConfig.getAllowUrl()); + scm.setIsSlo(serverConfig.getIsSlo()); + scm.setSecretKey(serverConfig.getSecretKey()); + if(SaFoxUtil.isEmpty(scm.getSecretKey())) { + scm.setSecretKey(SaManager.getSaSignTemplate().getSignConfigOrGlobal().getSecretKey()); + } + return scm; + } + /** * 获取应用信息,无效 client 返回 null * @@ -558,6 +574,39 @@ public class SaSsoServerTemplate extends SaSsoTemplate { // ---------------------- 重构 ---------------------- + /** + * 校验 Ticket 码,获取账号id,如果此ticket是有效的,则立即删除 + * @param ticket Ticket码 + * @param client client 标识 + */ + public void checkTicketVerifySign(SaRequest req, String ticket, String client) { + SaSignTemplate signTemplate = getSignTemplate(client); + signTemplate.checkRequest(req, paramName.client, paramName.ticket, paramName.ssoLogoutCall); + } + + + /** + * 获取底层使用的 API 签名对象 + * @param client 指定客户端标识,填 null 代表获取默认的 + * @return / + */ + @Override + public SaSignTemplate getSignTemplate(String client) { + SaSignConfig signConfig = SaManager.getSaSignTemplate().getSignConfigOrGlobal().copy(); + SaSsoClientModel clientModel = getClientNotNull(client); + + // 使用 secretKey 的优先级:client 单独配置 > SSO 模块全局配置 > sign 模块默认配置 + String secretKey = clientModel.getSecretKey(); + if (SaFoxUtil.isEmpty(secretKey) && SaFoxUtil.isNotEmpty(client)) { + secretKey = getServerConfig().getSecretKey(); + } + if(SaFoxUtil.isEmpty(secretKey)) { + secretKey = signConfig.getSecretKey(); + } + signConfig.setSecretKey(secretKey); + + return new SaSignTemplate(signConfig); + }