feat:打标回调通知接口

This commit is contained in:
苏竹红
2025-11-17 14:14:47 +08:00
parent fcef86762d
commit 04b5a4e7bc
9 changed files with 194 additions and 3 deletions

View File

@@ -5,7 +5,9 @@ import com.cool.store.constants.CommonConstants;
import com.cool.store.enums.ErrorCodeEnum;
import com.cool.store.exception.ServiceException;
import com.cool.store.response.ResponseResult;
import com.cool.store.response.bigdata.ApiResponse;
import com.cool.store.utils.OpenSignatureUtil;
import com.cool.store.utils.RsaSignUtil;
import com.cool.store.utils.UUIDUtils;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.core.type.TypeReference;
@@ -42,6 +44,8 @@ public class OpenApiValidateFilter implements Filter {
private String coolAppKey;
@Value("${cool.api.secret}")
private String coolAppSecret;
@Value("${cool.api.rsa.private.key}")
private String coolPrivateKey;
private static final Set<String> WHITELIST_URIS = new HashSet<>(Arrays.asList(
"/zxjp/open/v1/statusRefresh",
"/zxjp/open/v1/getStoreUser",
@@ -52,6 +56,8 @@ public class OpenApiValidateFilter implements Filter {
"/zxjp/open/v1/getYlsToken", "/zxjp/open/v1/getStoreList",
"/zxjp/open/v1/changeReceiptStatus", "/zxjp/open/v1/getStoreUser"));
// 添加钱包接口路径前缀常量
private static final String WALLET_API_PATTERN = "^/zxjp/open/v\\d+/wallet/.*$";
@Override
public void init(FilterConfig filterConfig) throws ServletException {
}
@@ -70,6 +76,11 @@ public class OpenApiValidateFilter implements Filter {
filterChain.doFilter(servletRequest, response);
return;
}
// 针对钱包接口的专用验签处理 所有符合 /zxjp/open/v{版本号}/wallet/ 格式的接口都会走钱包专用的验签流程。
if (uri.matches(WALLET_API_PATTERN)) {
handleWalletApiValidation(request, response, filterChain);
return;
}
HttpServletResponse res = (HttpServletResponse) response;
// 1. 验证时间戳
@@ -186,4 +197,90 @@ public class OpenApiValidateFilter implements Filter {
@Override
public void destroy() {
}
private void handleWalletApiValidation(HttpServletRequest request, ServletResponse response, FilterChain filterChain) throws IOException, ServletException {
HttpServletResponse res = (HttpServletResponse) response;
try {
// 读取请求体
StringBuilder requestBody = new StringBuilder();
try (BufferedReader reader = request.getReader()) {
String line;
while ((line = reader.readLine()) != null) {
requestBody.append(line);
}
}
String jsonBody = requestBody.toString();
// 1. 验证时间戳
String timestampStr = extractTimestampFromJson(jsonBody);
if (timestampStr == null) {
writeErrorResponse(res, ErrorCodeEnum.SIGN_FAIL, "缺少timestamp参数");
return;
}
long timestamp = Long.parseLong(timestampStr) / 1000;
long currentTime = System.currentTimeMillis() / 1000;
long timeDiff = Math.abs(currentTime - timestamp);
if (timeDiff > 600) {
writeErrorResponse(res, ErrorCodeEnum.SIGN_FAIL, "请求已过期请保证timestamp时间在10分钟之内");
return;
}
// 2. 钱包接口专用验签逻辑
if (!verifyWalletSignatureFromBody(jsonBody)) {
writeErrorResponse(res, ErrorCodeEnum.SIGN_FAIL, "签名校验失败");
return;
}
filterChain.doFilter(request, response);
} catch (Exception e) {
log.error("钱包接口验签异常: ", e);
writeErrorResponse(res, ErrorCodeEnum.SIGN_FAIL, "验签异常");
}
}
/**
* 从JSON中提取timestamp字段
*/
private String extractTimestampFromJson(String jsonBody) {
try {
ObjectMapper objectMapper = new ObjectMapper();
Map<String, Object> params = objectMapper.readValue(jsonBody, new TypeReference<Map<String, Object>>() {});
Object timestamp = params.get("timestamp");
return timestamp != null ? timestamp.toString() : null;
} catch (Exception e) {
log.error("提取timestamp失败: ", e);
return null;
}
}
/**
* 钱包接口签名验证方法 - 签名在请求体中
*/
private boolean verifyWalletSignatureFromBody(String jsonBody) {
try {
// 解析请求参数
ObjectMapper objectMapper = new ObjectMapper();
Map<String, Object> params = objectMapper.readValue(jsonBody, new TypeReference<Map<String, Object>>() {});
// 使用RsaSignUtil.verifyWalletSign进行验签
return RsaSignUtil.verifyWalletSign(params, coolPrivateKey);
} catch (Exception e) {
log.error("钱包接口签名验证失败: ", e);
return false;
}
}
/**
* 写入错误响应
*/
private void writeErrorResponse(HttpServletResponse response, ErrorCodeEnum errorCode, String message) throws IOException {
response.setStatus(HttpStatus.OK.value());
response.setCharacterEncoding("UTF-8");
response.getWriter().write(JSON.toJSONString(ApiResponse.fail(errorCode, message)));
}
}

View File

@@ -11,11 +11,13 @@ import com.cool.store.request.StoreCodeDTO;
import com.cool.store.request.*;
import com.cool.store.request.notice.ThirdHandleMessageRequest;
import com.cool.store.request.notice.ThirdMatterRequest;
import com.cool.store.request.wallet.AddTagCallbackNoticeRequest;
import com.cool.store.request.xgj.FranchiseFeeCallBackRequest;
import com.cool.store.request.xgj.ReceiptCallBackRequest;
import com.cool.store.response.ResponseResult;
import com.cool.store.response.bigdata.ApiResponse;
import com.cool.store.service.*;
import com.cool.store.service.wallet.WalletService;
import com.cool.store.utils.poi.StringUtils;
import com.github.pagehelper.PageInfo;
import io.swagger.annotations.Api;
@@ -57,6 +59,8 @@ public class OpenApiController {
WechatMiniAppService wechatMiniAppService;
@Autowired
WeChatHandler weChatHandler;
@Resource
WalletService walletService;
@PostMapping("/statusRefresh")
public ApiResponse<Boolean> statusRefresh(@RequestBody StatusRefreshDTO statusRefreshDTO){
@@ -214,4 +218,10 @@ public class OpenApiController {
}
return echostr;
}
@ApiOperation("打标回调通知接口")
@PostMapping("/wallet/addTagCallback")
public ApiResponse<Boolean> addTagCallback(@RequestBody @Validated AddTagCallbackNoticeRequest request) {
return ApiResponse.successByWallet(walletService.addTagCallback(request));
}
}