package com.yeshi.fanli.aspect;
|
|
import java.io.IOException;
|
import java.io.PrintWriter;
|
import java.lang.reflect.Method;
|
import java.util.ArrayList;
|
import java.util.Collections;
|
import java.util.Iterator;
|
import java.util.List;
|
import java.util.Map;
|
|
import javax.servlet.http.HttpServletRequest;
|
|
import org.aspectj.lang.ProceedingJoinPoint;
|
import org.aspectj.lang.Signature;
|
import org.aspectj.lang.annotation.Around;
|
import org.aspectj.lang.annotation.Aspect;
|
import org.aspectj.lang.reflect.MethodSignature;
|
import org.springframework.stereotype.Component;
|
import org.springframework.web.context.request.RequestContextHolder;
|
import org.springframework.web.context.request.ServletRequestAttributes;
|
import org.yeshi.utils.JsonUtil;
|
|
import com.yeshi.fanli.log.LogHelper;
|
import com.yeshi.fanli.util.StringUtil;
|
import com.yeshi.fanli.util.annotation.RequestNoSignValidate;
|
|
import net.sf.json.JSONObject;
|
|
//客户端接口签名验证
|
@Component
|
@Aspect
|
public class H5SignValidateAspect {
|
|
public static final String EDP = "execution(* com.yeshi.fanli.controller.apph5.*.*(..))";
|
|
public static String KEY = "thisWarning";
|
|
@Around(EDP)
|
public Object appH5Around(ProceedingJoinPoint joinPoint) throws IOException {
|
|
ServletRequestAttributes servletContainer = (ServletRequestAttributes) RequestContextHolder
|
.getRequestAttributes();
|
HttpServletRequest request = servletContainer.getRequest();
|
|
Signature signature = joinPoint.getSignature();
|
MethodSignature methodSignature = (MethodSignature) signature;
|
Method targetMethod = methodSignature.getMethod();
|
Method realMethod = null;
|
try {
|
realMethod = joinPoint.getTarget().getClass().getDeclaredMethod(joinPoint.getSignature().getName(),
|
targetMethod.getParameterTypes());
|
} catch (NoSuchMethodException e2) {
|
e2.printStackTrace();
|
} catch (SecurityException e2) {
|
e2.printStackTrace();
|
}
|
|
Object[] args = joinPoint.getArgs();
|
// 判断是否有忽略验证的注解
|
if (realMethod != null && realMethod.isAnnotationPresent(RequestNoSignValidate.class)) {
|
try {
|
return joinPoint.proceed(args);
|
} catch (Throwable e) {
|
LogHelper.errorDetailInfo(e, getHttpServletParams(request), request.getRequestURI().toString());
|
}
|
}
|
|
PrintWriter out = servletContainer.getResponse().getWriter();
|
String callback = request.getParameter("callback");
|
|
String sign = request.getParameter("sign");
|
Map<String, String> parameterMap = request.getParameterMap();
|
// 参数-、sign 均不能为空
|
if (parameterMap == null || StringUtil.isNullOrEmpty(sign)) {
|
JsonUtil.printMode(out, callback, JsonUtil.loadFalseResult("签名错误"));
|
return null;
|
}
|
|
boolean isRight = signIsRight(sign, parameterMap);
|
|
// 签名是否正确
|
if (isRight) {
|
Object obj = null;
|
try {
|
obj = joinPoint.proceed(args);
|
} catch (Throwable e) {
|
e.printStackTrace();
|
try {
|
LogHelper.errorDetailInfo(e, getHttpServletParams(request), request.getRequestURI().toString());
|
} catch (Exception e1) {
|
e1.printStackTrace();
|
}
|
}
|
return obj;
|
} else {
|
JsonUtil.printMode(out, callback, JsonUtil.loadFalseResult("签名错误"));
|
out.close();
|
LogHelper.error("H5签名错误:" + getHttpServletParams(request));
|
return null;
|
}
|
}
|
|
/**
|
* 获取请求参数
|
*
|
* @param request
|
* @return
|
*/
|
private String getHttpServletParams(HttpServletRequest request) {
|
if (request == null) {
|
return "";
|
}
|
Map map = request.getParameterMap();
|
if (map != null) {
|
Iterator<String> its = map.keySet().iterator();
|
JSONObject json = new JSONObject();
|
while (its.hasNext()) {
|
String next = its.next();
|
if (map.get(next) != null) {
|
Object[] objects = (Object[]) map.get(next);
|
if (objects != null && objects.length > 0) {
|
json.put(next, objects[0].toString());
|
}
|
}
|
}
|
return json.toString();
|
}
|
return "";
|
}
|
|
/**
|
* 验证是否正确
|
*
|
* @param sign
|
* @param parameterMap
|
* @return
|
*/
|
@SuppressWarnings("unchecked")
|
private boolean signIsRight(String sign, Map<String, String> map) {
|
int i = 0;
|
|
List<String> list = new ArrayList<>();
|
|
Iterator<String> iterator = map.keySet().iterator();
|
|
while (iterator.hasNext()) {
|
String key = iterator.next();
|
|
if ("sign".equalsIgnoreCase(key) || "callback".equalsIgnoreCase(key) || "_".equalsIgnoreCase(key)) {
|
continue;
|
}
|
|
Object value = map.get(key);
|
Object[] values = (Object[]) value;
|
list.add(values[0].toString());
|
}
|
Collections.sort(list);
|
|
StringBuffer sb = new StringBuffer();
|
|
for (String val : list) {
|
sb.append(val);
|
sb.append("###");
|
}
|
|
String md5 = StringUtil.Md5(sb.toString() + KEY);
|
|
if (!md5.equalsIgnoreCase(sign)) {
|
return false;
|
} else {
|
return true;
|
}
|
}
|
|
}
|