From 9ec1994dfc29f61d0cfa91a6c79b5bdf540c9567 Mon Sep 17 00:00:00 2001 From: dimengzhe Date: Sat, 7 Dec 2024 16:17:27 +0800 Subject: [PATCH] =?UTF-8?q?=E5=AF=B9=E5=A4=96?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- pom.xml | 14 +- .../yxt/ss/gateway/api/rest/Signature.java | 180 +++++++++++++++--- .../ss/gateway/api/utils/SignatureQuery.java | 25 +++ 3 files changed, 188 insertions(+), 31 deletions(-) create mode 100644 src/main/java/com/yxt/ss/gateway/api/utils/SignatureQuery.java diff --git a/pom.xml b/pom.xml index 2a789cd..691e8bf 100644 --- a/pom.xml +++ b/pom.xml @@ -20,10 +20,10 @@ org.springframework.cloud spring-cloud-starter-gateway - + org.projectlombok lombok @@ -35,6 +35,12 @@ spring-webmvc + + com.squareup.okhttp3 + okhttp + 4.11.0 + + diff --git a/src/main/java/com/yxt/ss/gateway/api/rest/Signature.java b/src/main/java/com/yxt/ss/gateway/api/rest/Signature.java index ee72d5d..89df505 100644 --- a/src/main/java/com/yxt/ss/gateway/api/rest/Signature.java +++ b/src/main/java/com/yxt/ss/gateway/api/rest/Signature.java @@ -1,18 +1,24 @@ package com.yxt.ss.gateway.api.rest; import com.yxt.ss.gateway.api.utils.ResultBean; +import com.yxt.ss.gateway.api.utils.SignatureQuery; import com.yxt.ss.gateway.api.utils.SignatureUtil; +import okhttp3.*; +import org.springframework.util.StringUtils; import org.springframework.web.bind.annotation.PostMapping; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RequestParam; import org.springframework.web.bind.annotation.RestController; +import java.io.IOException; import java.io.UnsupportedEncodingException; import java.net.URLEncoder; import java.security.MessageDigest; import java.security.NoSuchAlgorithmException; +import java.util.HashMap; import java.util.Map; import java.util.TreeMap; +import java.util.concurrent.TimeUnit; /** * @description: @@ -30,10 +36,102 @@ public class Signature { //获取签名 @PostMapping("/getSign") - ResultBean getSign(@RequestParam("parameters") Map parameters, @RequestParam("appKey") String appKey, @RequestParam("secret") String secret) throws UnsupportedEncodingException, NoSuchAlgorithmException { + ResultBean getSign(SignatureQuery query) { ResultBean rb = ResultBean.fireFail(); - String sign = SignatureUtil.generateSignature(parameters, appKey, secret); - return rb.success().setData(sign); + try { + Map formData = new HashMap<>(); + Map map = query.getParameters(); + formData.put("key1", map.getOrDefault("key1", "").toString()); + String appKey = query.getAppKey(); + String secret = query.getSecret(); + + // 生成签名 + String sign = SignatureUtil.generateSignature(formData, appKey, secret); + return rb.success().setData(sign); + } catch (UnsupportedEncodingException e) { + return rb.setMsg("Unsupported encoding: " + e.getMessage()); + } catch (NoSuchAlgorithmException e) { + return rb.setMsg("Algorithm not found: " + e.getMessage()); + } + } + + public static void main(String[] args) { + OkHttpClient client = new OkHttpClient.Builder() + .connectTimeout(10, TimeUnit.SECONDS) + .writeTimeout(10, TimeUnit.SECONDS) + .readTimeout(30, TimeUnit.SECONDS) + .build(); + + try { + // 构建URL + String endPoint = "http://127.0.0.1:9999"; + String path = "/signature/getSign"; + + // 假设data是一个包含所有参数的字典 + Map data = new HashMap<>(); + data.put("parameters[key1]", "value1"); + data.put("parameters[key2]", "value2"); + data.put("appKey", "testAppKey"); + data.put("secret", "testSecret"); + + // 创建FormData + FormBody.Builder formBuilder = new FormBody.Builder(); + for (Map.Entry entry : data.entrySet()) { + formBuilder.add(entry.getKey(), entry.getValue()); + } + RequestBody formBody = formBuilder.build(); + + // 构建POST请求 + String url = endPoint + path; + System.out.println("Request URL: " + url); + System.out.println("Request Data: " + data); + + Request request = new Request.Builder() + .url(url) + .post(formBody) + .build(); + + // 发送请求 + try (Response response = client.newCall(request).execute()) { + if (response.isSuccessful()) { + System.out.println("Response: " + response.body().string()); + } else { + System.err.println("Request failed: " + response.code()); + } + } + } catch (IOException e) { + System.err.println("Network error: " + e.getMessage()); + } catch (Exception e) { + System.err.println("Unexpected error: " + e.getMessage()); + } + } + + //获取签名 + @PostMapping("/getSign2") + ResultBean getSign2(@RequestParam("parameters") Map parameters, + @RequestParam("appKey") String appKey, + @RequestParam("secret") String secret) { + ResultBean rb = ResultBean.fireFail(); + try { + // 1. 参数校验 + if (parameters == null || parameters.isEmpty()) { + return rb.setMsg("Parameters cannot be empty."); + } + if (StringUtils.isEmpty(appKey)) { + return rb.setMsg("AppKey cannot be empty."); + } + if (StringUtils.isEmpty(secret)) { + return rb.setMsg("Secret cannot be empty."); + } + + // 生成签名 + String sign = SignatureUtil.generateSignature(parameters, appKey, secret); + return rb.success().setData(sign); + } catch (UnsupportedEncodingException e) { + return rb.setMsg("Unsupported encoding: " + e.getMessage()); + } catch (NoSuchAlgorithmException e) { + return rb.setMsg("Algorithm not found: " + e.getMessage()); + } } @@ -42,45 +140,73 @@ public class Signature { * 返回系统参数 */ @PostMapping("/getSignParameters") - public ResultBean> signParameters(@RequestParam("parameters") Map parameters, @RequestParam("appKey") String appKey, @RequestParam("secret") String secret) throws UnsupportedEncodingException, NoSuchAlgorithmException { + public ResultBean> signParameters(SignatureQuery query) { ResultBean> rb = ResultBean.fireFail(); - // 1. 使用 TreeMap 按照字典顺序对参数进行排序 - Map tree = new TreeMap<>(parameters); - tree.put("_app", appKey); - tree.putIfAbsent("_t", String.valueOf(System.currentTimeMillis())); - // 拼接参数串 - String content = SignatureUtil.joinParameters(tree); + try { + Map parameters = query.getParameters(); + + // 2. 使用 TreeMap 按照字典顺序对参数进行排序 + Map tree = new TreeMap<>(parameters); + tree.put("_app", query.getAppKey()); + tree.putIfAbsent("_t", String.valueOf(System.currentTimeMillis())); + + // 3. 拼接参数串 + String content = SignatureUtil.joinParameters(tree); + + // 4. 将参数串前后拼接密钥 + content = query.getSecret() + content + query.getSecret(); - // 将参数串前后拼上密钥 - content = secret + content + secret; + // 5. 计算 sign 值 + String sign = SignatureUtil.md5(content); - // 计算sign值并添加到参数集合中 - String sign = SignatureUtil.md5(content); - tree.put("_sign", sign); - tree.put("_s", ""); + // 6. 添加系统参数 + tree.put("_sign", sign); + tree.put("_s", ""); - return rb.success().setData(tree); + return rb.success().setData(tree); + + } catch (UnsupportedEncodingException e) { + return rb.setMsg("Encoding error: " + e.getMessage()); + } catch (NoSuchAlgorithmException e) { + return rb.setMsg("Algorithm error: " + e.getMessage()); + } catch (Exception e) { + return rb.setMsg("Unexpected error: " + e.getMessage()); + } } /** * 验证签名是否正确 * - * @param parameters 请求参数 - * @param appKey 应用的 AppKey - * @param secret 密钥 - * @param receivedSignature 请求中的签名 * @return 是否验证通过 */ @PostMapping("/validateSignature") - public ResultBean validateSignature(@RequestParam("parameters") Map parameters, @RequestParam("appKey") String appKey, @RequestParam("secret") String secret, @RequestParam("receivedSignature") String receivedSignature) throws UnsupportedEncodingException, NoSuchAlgorithmException { + public ResultBean validateSignature(SignatureQuery query) { ResultBean rb = ResultBean.fireFail(); - // 1. 重新生成签名 - String calculatedSignature = SignatureUtil.generateSignature(parameters, appKey, secret); - // 2. 比较计算出来的签名和请求中的签名 - boolean validd = calculatedSignature.equals(receivedSignature); - return rb.success().setData(validd); + try { + Map parameters = query.getParameters(); + String appKey = query.getAppKey(); + String secret = query.getSecret(); + + + // 2. 重新生成签名 + String calculatedSignature = SignatureUtil.generateSignature(parameters, appKey, secret); + + // 3. 使用固定时间比较方式验证签名 + boolean valid = MessageDigest.isEqual( + calculatedSignature.getBytes("UTF-8"), + query.getReceivedSignature().getBytes("UTF-8") + ); + + return rb.success().setData(valid); + } catch (UnsupportedEncodingException e) { + return rb.setMsg("Encoding error: " + e.getMessage()); + } catch (NoSuchAlgorithmException e) { + return rb.setMsg("Algorithm error: " + e.getMessage()); + } catch (Exception e) { + return rb.setMsg("Unexpected error: " + e.getMessage()); + } } diff --git a/src/main/java/com/yxt/ss/gateway/api/utils/SignatureQuery.java b/src/main/java/com/yxt/ss/gateway/api/utils/SignatureQuery.java new file mode 100644 index 0000000..a9c3255 --- /dev/null +++ b/src/main/java/com/yxt/ss/gateway/api/utils/SignatureQuery.java @@ -0,0 +1,25 @@ +package com.yxt.ss.gateway.api.utils; + +import lombok.Data; + +import java.util.HashMap; +import java.util.Map; + +/** + * @description: + * @author: dimengzhe + * @date: 2024/12/7 + **/ +@Data +public class SignatureQuery { + + private String appKey; + + private String secret; + + //业务参数 + private Map parameters = new HashMap<>(); + + + private String receivedSignature; +}