├── .gitignore ├── README.md ├── pom.xml ├── src └── main │ ├── java │ └── com │ │ └── dfs │ │ ├── annotation │ │ ├── AppAndApplet.java │ │ ├── AppAndBoss.java │ │ ├── AppAppletBoss.java │ │ ├── AppSecurity.java │ │ ├── AppletSecurity.java │ │ ├── BossSecurity.java │ │ └── IgnoreSecurity.java │ │ ├── aspect │ │ ├── ExceptionAspect.java │ │ └── SecurityAspect.java │ │ ├── authorization │ │ └── TokenManager.java │ │ ├── controller │ │ ├── app │ │ │ └── AppLoginController.java │ │ ├── applite │ │ │ └── LoginController.java │ │ ├── boss │ │ │ └── BossLoginController.java │ │ └── common │ │ │ └── FileController.java │ │ ├── entity │ │ ├── SenseAgroAdmin.java │ │ ├── SenseAgroMember.java │ │ ├── SenseAgroSpecialist.java │ │ └── SenseAgroUser.java │ │ ├── exception │ │ └── TokenException.java │ │ ├── filter │ │ ├── CorsFilter.java │ │ └── SenseAgroRequestWrapper.java │ │ ├── job │ │ ├── JiguangPushJob.java │ │ ├── MessageSendJob.java │ │ └── OrderRefundJob.java │ │ ├── jpush │ │ ├── JiguangPush.java │ │ └── JiguangPushBySDK.java │ │ ├── mapper │ │ ├── SenseAgroAdminMapper.java │ │ ├── SenseAgroMemberMapper.java │ │ ├── SenseAgroSpecialistMapper.java │ │ └── SenseAgroUserMapper.java │ │ ├── model │ │ ├── AliyunMessageConfig.java │ │ ├── ApiCodeEnum.java │ │ ├── JiguangConfig.java │ │ ├── RedisConfig.java │ │ ├── SystemVariableEnum.java │ │ └── WechatConfig.java │ │ ├── response │ │ ├── AnalysisResult.java │ │ └── Response.java │ │ ├── service │ │ ├── SenseAgroAdminService.java │ │ ├── SenseAgroAppService.java │ │ ├── SenseAgroMemberService.java │ │ └── SenseAgroSpecialistService.java │ │ ├── utils │ │ ├── Captcha.java │ │ ├── CheckSumBuilder.java │ │ ├── CodecUtil.java │ │ ├── CollectionUtil.java │ │ ├── Constants.java │ │ ├── DesUtil.java │ │ ├── EmojiUtil.java │ │ ├── FileUploadUtil.java │ │ ├── FileUtil.java │ │ ├── HtmlToText.java │ │ ├── ImageUtil.java │ │ ├── JsonUtils.java │ │ ├── MarkImageUtils.java │ │ ├── Md5.java │ │ ├── MessageUtils.java │ │ ├── PayUtil.java │ │ ├── RedisSingletonUtil.java │ │ ├── RequestBodyUtils.java │ │ ├── ResourceUtil.java │ │ ├── ResponseUtil.java │ │ ├── RunPyUtil.java │ │ ├── SerializeUtil.java │ │ ├── StringUtil.java │ │ ├── WebContextUtil.java │ │ ├── ZipUtils.java │ │ └── pay │ │ │ └── wechat │ │ │ ├── AESUtil.java │ │ │ ├── Base64Util.java │ │ │ ├── MessageUtil.java │ │ │ ├── P12Request.java │ │ │ ├── PayUtil.java │ │ │ ├── PaymentPo.java │ │ │ ├── QueryPo.java │ │ │ ├── RefundPo.java │ │ │ ├── TransferPo.java │ │ │ └── UUIDHexGenerator.java │ │ └── websocket │ │ ├── CacheConstant.java │ │ ├── Constants.java │ │ ├── HttpSessionIdHandshakeInterceptor.java │ │ ├── MsgWeixin.java │ │ ├── PresenceChannelInterceptor.java │ │ ├── StompSubscribeEventListener.java │ │ └── WebSocketConfig.java │ ├── resources │ ├── applicationContext.xml │ ├── com │ │ └── dfs │ │ │ ├── SenseAgroAdminMapper.xml │ │ │ ├── SenseAgroMemberMapper.xml │ │ │ ├── SenseAgroSpecialistMapper.xml │ │ │ └── SenseAgroUserMapper.xml │ ├── mybatis-config.xml │ └── springmvc.xml │ └── webapp │ ├── WEB-INF │ ├── plugins │ │ ├── sockjs.js │ │ └── stomp.js │ └── web.xml │ └── index.html └── taoxy.sql /.gitignore: -------------------------------------------------------------------------------- 1 | /.idea 2 | *.iml 3 | /src/main/resources/environment/ 4 | /target 5 | /src/main/resources/*.properties 6 | *.properties -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | #### Spring4+SpringMVC4+Mybatis3+IDEA+REST风格框架(微信小程序+APP+Boss后台) 2 | 3 | - 纯REST风格,是微信小程序、APP、后台管理系统的统一后台,前后端分离 4 | 5 | - ResponseUtil类统一响应结构 6 | 7 | - ExceptionAspect类统一异常处理 8 | 9 | - SecurityAspect类统一验证 10 | 11 | - JsonUtils统一处理请求参数json 12 | 13 | - FileUploadUtil统一文件上传 14 | 15 | - JiguangPush集成极光推送 16 | 17 | - MessageUtils集成阿里大鱼短信 18 | 19 | - MarkimageUtils类集成图片水印 20 | 21 | - HtmlToText类集成富文本转文本 22 | 23 | - EmojiUtil类集成emoji表情转换存储(数据库如果为utf-8mb4也不用转) 24 | 25 | - RedisSingletonUtil类集成redis默认端口3991,密码www.taoxy.online 26 | 27 | - 数据库采用mysql,innodb+utf-8mb4 28 | 29 | - CorsFilter类解决跨域请求问题 30 | 31 | - SenseAgroRequestWrapper类缓存post方法的body数据 32 | 33 | - 集成网易IM聊天 34 | 35 | - 集成amr音频转mp3 36 | 37 | - 集成文件压缩和打包下载 38 | 39 | - 集成websocket 40 | 41 | - 集成maven Profiles三种打包配置 42 | 43 | - 集成微信支付,退款,消息模版推送 44 | 45 | - 数据库方面 46 | 47 | > ``` 48 | > sense_agro_admin表用于boss后台用户管理 49 | > sense_agro_member表用于微信用户登录小程序后存储信息和openid 50 | > sense_agro_specialist用于专家app端登录,uname是登录名不是name,uname必须是手机号 51 | > 且做了手机号的唯一输入,异常是在代码里处理的 52 | > sense_agro_user表示是记录specialist的登录操作的,可有可无 53 | > ``` 54 | 55 | - 接口格式 56 | 57 | ##### 微信小程序登录 58 | 59 | - ##### 请求url 60 | 61 | > applet/user/login/ 62 | 63 | - ##### 请求方式 64 | 65 | > post+json 66 | 67 | - ##### 请求参数 68 | 69 | > | 请求参数 | 参数类型 | 参数说明 | 70 | > | -------- | -------- | -------- | 71 | > | code | String | 微信code | 72 | 73 | - ##### 参数格式 74 | 75 | > ``` 76 | > { 77 | > "code":"xxxxxx" 78 | > } 79 | > ``` 80 | 81 | - ##### 返回参数 82 | 83 | > | 返回参数 | 参数类型 | 参数说明 | 84 | > | --------- | -------- | ------------------------------------------------------------ | 85 | > | status | int | 0:失败,1:成功 | 86 | > | msg | String | 成功时为空,失败为具体原因 | 87 | > | content | Map | | 88 | > | sessionId | String | 成功为sessionId值,失败为空,之后所有的接口前端都需要带上此参数 | 89 | 90 | - ##### 返回格式 91 | 92 | > ``` 93 | > { 94 | > "status": 1, 95 | > "msg": "", 96 | > "content": { 97 | > "sessionId": "xxxxxxxxxx" 98 | > } 99 | > } 100 | > ``` 101 | 102 | ##### Boss后台登录 103 | 104 | - ##### 请求url 105 | 106 | > taoxy/boss/login/ 107 | 108 | - ##### 请求方式 109 | 110 | > post+json 111 | 112 | - ##### 请求参数 113 | 114 | > | 请求参数 | 参数类型 | 参数说明 | 115 | > | -------- | -------- | -------- | 116 | > | name | String | 用户名 | 117 | > | passwd | String | 密码 | 118 | 119 | - ##### 参数格式 120 | 121 | > ``` 122 | > { 123 | > "name":"xxx", 124 | > "passwd":"xxx" 125 | > } 126 | > ``` 127 | 128 | - ##### 返回参数 129 | 130 | > | 返回参数 | 参数类型 | 参数说明 | 131 | > | -------- | -------- | ------------------------------------------------------------ | 132 | > | status | String | 0账号/密码错误,1登录成功 | 133 | > | msg | String | 登录成功/登录失败 | 134 | > | content | map | 成功/失败都返回空 | 135 | > | token | String | http的请求头里面,之后所有的接口前端都需要带上此参数,且参数名前端需要改为sessionId | 136 | 137 | - ##### 返回格 138 | 139 | > ``` 140 | > { 141 | > "status":"xxx", 142 | > "msg":"", 143 | > "content":{ 144 | > } 145 | > } 146 | > ``` 147 | 148 | ##### 专家APP登录 149 | 150 | #### 1.1 用户登录 151 | 152 | - ##### 请求url 153 | 154 | > taoxy/specialist/login/ 155 | 156 | - ##### 请求方式 157 | 158 | > post+json 159 | 160 | - ##### 请求参数 161 | 162 | > | 请求参数 | 参数类型 | 参数说明 | 163 | > | -------- | -------- | -------- | 164 | > | uname | String | 手机号 | 165 | > | passwd | String | 密码 | 166 | 167 | - ##### 参数格式 168 | 169 | > ``` 170 | > { 171 | > "uname":"xxxxxx", 172 | > "passwd":"xxxxx" 173 | > } 174 | > ``` 175 | 176 | - ##### 返回参数 177 | 178 | > | 返回参数 | 参数类型 | 参数说明 | 179 | > | -------- | -------- | --------------------------------------------------- | 180 | > | status | int | 0:失败,1:成功 | 181 | > | msg | String | 成功时为空,失败为具体原因 | 182 | > | content | Map | | 183 | > | token | String | http的请求头里面,之后所有的接口前端都需要带上此参数 | 184 | 185 | - ##### 返回格式 186 | 187 | > ``` 188 | > { 189 | > "status": 1, 190 | > "msg": "", 191 | > "content": { 192 | > } 193 | > } 194 | > ``` -------------------------------------------------------------------------------- /src/main/java/com/dfs/annotation/AppAndApplet.java: -------------------------------------------------------------------------------- 1 | package com.dfs.annotation; 2 | 3 | import java.lang.annotation.*; 4 | 5 | 6 | /** 7 | * @author taoxy 2019/1/3 8 | */ 9 | @Target(ElementType.METHOD) 10 | @Retention(RetentionPolicy.RUNTIME) 11 | @Documented 12 | public @interface AppAndApplet { 13 | 14 | } 15 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/annotation/AppAndBoss.java: -------------------------------------------------------------------------------- 1 | package com.dfs.annotation; 2 | 3 | import java.lang.annotation.*; 4 | 5 | 6 | /** 7 | * @author taoxy 2019/1/3 8 | */ 9 | @Target(ElementType.METHOD) 10 | @Retention(RetentionPolicy.RUNTIME) 11 | @Documented 12 | public @interface AppAndBoss { 13 | 14 | } 15 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/annotation/AppAppletBoss.java: -------------------------------------------------------------------------------- 1 | package com.dfs.annotation; 2 | 3 | import java.lang.annotation.*; 4 | 5 | 6 | /** 7 | * @author taoxy 2019/1/3 8 | */ 9 | @Target(ElementType.METHOD) 10 | @Retention(RetentionPolicy.RUNTIME) 11 | @Documented 12 | public @interface AppAppletBoss { 13 | 14 | } 15 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/annotation/AppSecurity.java: -------------------------------------------------------------------------------- 1 | package com.dfs.annotation; 2 | 3 | import java.lang.annotation.*; 4 | 5 | 6 | /** 7 | * @author taoxy 2019/1/3 8 | */ 9 | @Target(ElementType.METHOD) 10 | @Retention(RetentionPolicy.RUNTIME) 11 | @Documented 12 | public @interface AppSecurity { 13 | 14 | } 15 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/annotation/AppletSecurity.java: -------------------------------------------------------------------------------- 1 | package com.dfs.annotation; 2 | 3 | import java.lang.annotation.*; 4 | 5 | 6 | /** 7 | * @author taoxy 2019/1/3 8 | */ 9 | @Target(ElementType.METHOD) 10 | @Retention(RetentionPolicy.RUNTIME) 11 | @Documented 12 | public @interface AppletSecurity { 13 | 14 | } -------------------------------------------------------------------------------- /src/main/java/com/dfs/annotation/BossSecurity.java: -------------------------------------------------------------------------------- 1 | package com.dfs.annotation; 2 | 3 | import java.lang.annotation.*; 4 | 5 | 6 | /** 7 | * @author taoxy 2019/1/3 8 | */ 9 | @Target(ElementType.METHOD) 10 | @Retention(RetentionPolicy.RUNTIME) 11 | @Documented 12 | public @interface BossSecurity { 13 | 14 | } 15 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/annotation/IgnoreSecurity.java: -------------------------------------------------------------------------------- 1 | package com.dfs.annotation; 2 | 3 | import java.lang.annotation.Documented; 4 | import java.lang.annotation.ElementType; 5 | import java.lang.annotation.Retention; 6 | import java.lang.annotation.RetentionPolicy; 7 | import java.lang.annotation.Target; 8 | 9 | 10 | /** 11 | * @author taoxy 2019/1/3 12 | */ 13 | @Target(ElementType.METHOD) 14 | @Retention(RetentionPolicy.RUNTIME) 15 | @Documented 16 | public @interface IgnoreSecurity { 17 | 18 | } 19 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/aspect/ExceptionAspect.java: -------------------------------------------------------------------------------- 1 | package com.dfs.aspect; 2 | 3 | import com.dfs.exception.TokenException; 4 | import com.dfs.model.ApiCodeEnum; 5 | import com.dfs.utils.ResponseUtil; 6 | import org.apache.log4j.Logger; 7 | import org.springframework.http.HttpStatus; 8 | import org.springframework.http.converter.HttpMessageNotReadableException; 9 | import org.springframework.web.HttpMediaTypeNotSupportedException; 10 | import org.springframework.web.HttpRequestMethodNotSupportedException; 11 | import org.springframework.web.bind.MethodArgumentNotValidException; 12 | import org.springframework.web.bind.annotation.ControllerAdvice; 13 | import org.springframework.web.bind.annotation.ExceptionHandler; 14 | import org.springframework.web.bind.annotation.ResponseBody; 15 | import org.springframework.web.bind.annotation.ResponseStatus; 16 | 17 | /** 18 | * @author taoxy 2019/1/3 19 | */ 20 | @ControllerAdvice // 控制器增强 21 | @ResponseBody 22 | public class ExceptionAspect { 23 | 24 | /** 25 | * Log4j日志处理 26 | */ 27 | private static final Logger log = Logger.getLogger(ExceptionAspect.class); 28 | 29 | /** 30 | * 400 - Bad Request 31 | */ 32 | @ResponseStatus(HttpStatus.BAD_REQUEST) 33 | @ExceptionHandler(HttpMessageNotReadableException.class) 34 | public String handleHttpMessageNotReadableException(HttpMessageNotReadableException e) { 35 | log.error("could_not_read_json...", e); 36 | return ResponseUtil.getResponse(ApiCodeEnum.FAIL.getCode(), "could_not_read_json..."); 37 | } 38 | 39 | /** 40 | * 400 - Bad Request 41 | */ 42 | @ResponseStatus(HttpStatus.BAD_REQUEST) 43 | @ExceptionHandler({MethodArgumentNotValidException.class}) 44 | public String s(MethodArgumentNotValidException e) { 45 | log.error("parameter_validation_exception...", e); 46 | return ResponseUtil.getResponse(ApiCodeEnum.FAIL.getCode(), "parameter_validation_exception..."); 47 | } 48 | 49 | /** 50 | * 405 - Method Not Allowed。HttpRequestMethodNotSupportedException 51 | * 是ServletException的子类,需要Servlet API支持 52 | */ 53 | @ResponseStatus(HttpStatus.METHOD_NOT_ALLOWED) 54 | @ExceptionHandler(HttpRequestMethodNotSupportedException.class) 55 | public String handleHttpRequestMethodNotSupportedException(HttpRequestMethodNotSupportedException e) { 56 | log.error("request拦截...request_method_not_supported...", e); 57 | return ResponseUtil.getResponse(ApiCodeEnum.FAIL.getCode(), "request拦截...request_method_not_supported..."); 58 | } 59 | 60 | 61 | /** 62 | * 415 - Unsupported Media Type。HttpMediaTypeNotSupportedException 63 | * 是ServletException的子类,需要Servlet API支持 64 | */ 65 | @ResponseStatus(HttpStatus.UNSUPPORTED_MEDIA_TYPE) 66 | @ExceptionHandler({HttpMediaTypeNotSupportedException.class}) 67 | public String handleHttpMediaTypeNotSupportedException(Exception e) { 68 | log.error("content_type_not_supported...", e); 69 | return ResponseUtil.getResponse(ApiCodeEnum.FAIL.getCode(), "content_type_not_supported..."); 70 | } 71 | 72 | /** 73 | * 401 - Token is invaild 74 | */ 75 | @ResponseStatus(HttpStatus.UNAUTHORIZED) 76 | @ExceptionHandler(TokenException.class) 77 | public String handleTokenException(Exception e) { 78 | log.error("Token is invaild...", e); 79 | return ResponseUtil.getResponse("401", "content_type_not_supported..."); 80 | 81 | } 82 | 83 | /** 84 | * 500 - Internal Server Error 85 | */ 86 | @ResponseStatus(HttpStatus.INTERNAL_SERVER_ERROR) 87 | @ExceptionHandler(Exception.class) 88 | public String handleException(Exception e) { 89 | log.error("Internal Server Error...", e); 90 | return ResponseUtil.getResponse(ApiCodeEnum.FAIL.getCode(), "Internal Server Error..."); 91 | 92 | } 93 | } 94 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/aspect/SecurityAspect.java: -------------------------------------------------------------------------------- 1 | package com.dfs.aspect; 2 | 3 | import com.dfs.annotation.*; 4 | import com.dfs.authorization.TokenManager; 5 | import com.dfs.exception.TokenException; 6 | import com.dfs.entity.SenseAgroMember; 7 | import com.dfs.entity.SenseAgroUser; 8 | import com.dfs.model.ApiCodeEnum; 9 | import com.dfs.service.SenseAgroAppService; 10 | import com.dfs.service.SenseAgroMemberService; 11 | import com.dfs.utils.*; 12 | import org.apache.log4j.Logger; 13 | import org.aspectj.lang.ProceedingJoinPoint; 14 | import org.aspectj.lang.annotation.Around; 15 | import org.aspectj.lang.annotation.Aspect; 16 | import org.aspectj.lang.reflect.MethodSignature; 17 | import org.springframework.beans.factory.annotation.Autowired; 18 | import org.springframework.stereotype.Component; 19 | 20 | import javax.servlet.http.HttpServletRequest; 21 | import java.io.BufferedReader; 22 | import java.io.InputStreamReader; 23 | import java.lang.reflect.Method; 24 | import java.util.Date; 25 | import java.util.List; 26 | 27 | 28 | /** 29 | * @author taoxy 2019/1/3 30 | */ 31 | @Component 32 | @Aspect 33 | public class SecurityAspect { 34 | /** 35 | * Log4j日志处理 36 | */ 37 | private static final Logger log = Logger.getLogger(SecurityAspect.class); 38 | 39 | @Autowired 40 | private SenseAgroMemberService senseAgroMemberService; 41 | @Autowired 42 | private SenseAgroAppService senseAgroAppService; 43 | 44 | @Around("@annotation(org.springframework.web.bind.annotation.RequestMapping)") 45 | public Object execute(ProceedingJoinPoint pjp) throws Throwable { 46 | // 从切点上获取目标方法 47 | MethodSignature methodSignature = (MethodSignature) pjp.getSignature(); 48 | log.debug("methodSignature : " + methodSignature); 49 | Method method = methodSignature.getMethod(); 50 | log.debug("Method : " + method.getName() + " : " + method.isAnnotationPresent(IgnoreSecurity.class)); 51 | // 若目标方法忽略了安全性检查,则直接调用目标方法 52 | if (method.isAnnotationPresent(IgnoreSecurity.class)) { 53 | return pjp.proceed(); 54 | } 55 | //小程序端和APP端登录验证 56 | if (method.isAnnotationPresent(AppAndApplet.class)) { 57 | HttpServletRequest req = WebContextUtil.getRequest(); 58 | BufferedReader reader = new BufferedReader(new InputStreamReader(req.getInputStream(), "utf-8")); 59 | String param = RequestBodyUtils.read(reader); 60 | String sessionId; 61 | log.info("param is " + param); 62 | if (StringUtil.isEmpty(param)) { 63 | sessionId = req.getParameter("sessionId"); 64 | } else { 65 | sessionId = JsonUtils.getJsonStringParam(param, "sessionId"); 66 | } 67 | String openId; 68 | try { 69 | openId = DesUtil.decrypt(sessionId); 70 | } catch (Exception e) { 71 | openId = ""; 72 | } 73 | log.info("openid is " + openId); 74 | SenseAgroMember senseAgroMember = senseAgroMemberService.findMember(openId); 75 | log.info("select SenseAgroMember success"); 76 | List listUserSession = senseAgroAppService.findAppUserByToken((int) (new Date().getTime() / 1000), sessionId); 77 | if (senseAgroMember == null && listUserSession.size() == 0) { 78 | return ResponseUtil.getResponse(ApiCodeEnum.RELOGIN); 79 | } 80 | return pjp.proceed(); 81 | } 82 | //小程序登录验证 83 | if (method.isAnnotationPresent(AppletSecurity.class)) { 84 | HttpServletRequest req = WebContextUtil.getRequest(); 85 | BufferedReader reader = new BufferedReader(new InputStreamReader(req.getInputStream(), "utf-8")); 86 | String param = RequestBodyUtils.read(reader); 87 | String sessionId; 88 | if (StringUtil.isEmpty(param)) { 89 | sessionId = req.getParameter("sessionId"); 90 | } else { 91 | sessionId = JsonUtils.getJsonStringParam(param, "sessionId"); 92 | } 93 | String openId; 94 | try { 95 | openId = DesUtil.decrypt(sessionId); 96 | } catch (Exception e) { 97 | openId = ""; 98 | } 99 | log.info("openid is " + openId); 100 | SenseAgroMember senseAgroMember = senseAgroMemberService.findMember(openId); 101 | log.info("select SenseAgroMember success"); 102 | if (senseAgroMember == null) { 103 | return ResponseUtil.getResponse(ApiCodeEnum.RELOGIN); 104 | } 105 | return pjp.proceed(); 106 | } 107 | //Boss后台登录验证 108 | if (method.isAnnotationPresent(BossSecurity.class)) { 109 | String token = WebContextUtil.getRequest().getHeader("Token"); 110 | // redis检查 token 有效性 111 | if (!TokenManager.checkToken(token)) { 112 | String message = String.format("token [%s] is invalid", token); 113 | log.debug("message : " + message); 114 | throw new TokenException(message); 115 | } 116 | return pjp.proceed(); 117 | } 118 | //App端登录验证 119 | if (method.isAnnotationPresent(AppSecurity.class)) { 120 | HttpServletRequest req = WebContextUtil.getRequest(); 121 | BufferedReader reader = new BufferedReader(new InputStreamReader(req.getInputStream(), "utf-8")); 122 | String param = RequestBodyUtils.read(reader); 123 | String sessionId; 124 | if (StringUtil.isEmpty(param)) { 125 | sessionId = req.getParameter("sessionId"); 126 | } else { 127 | sessionId = JsonUtils.getJsonStringParam(param, "sessionId"); 128 | } 129 | List listUserSession = senseAgroAppService.findAppUserByToken((int) (new Date().getTime() / 1000), sessionId); 130 | if (listUserSession.size() == 0) {//size大小为当前有效登录次数 131 | throw new TokenException("认证已过期"); 132 | } 133 | return pjp.proceed(); 134 | } 135 | //App端和BOSS端登录验证 136 | if (method.isAnnotationPresent(AppAndBoss.class)) { 137 | HttpServletRequest req = WebContextUtil.getRequest(); 138 | BufferedReader reader = new BufferedReader(new InputStreamReader(req.getInputStream(), "utf-8")); 139 | String param = RequestBodyUtils.read(reader); 140 | String sessionId; 141 | if (StringUtil.isEmpty(param)) { 142 | sessionId = req.getParameter("sessionId"); 143 | } else { 144 | sessionId = JsonUtils.getJsonStringParam(param, "sessionId"); 145 | } 146 | List listUserSession = senseAgroAppService.findAppUserByToken((int) (new Date().getTime() / 1000), sessionId); 147 | String token = req.getHeader("Token"); 148 | if (!TokenManager.checkToken(token) && listUserSession.size() == 0) { 149 | throw new TokenException("认证已过期"); 150 | } 151 | return pjp.proceed(); 152 | } 153 | //三端登录验证 154 | if (method.isAnnotationPresent(AppAppletBoss.class)) { 155 | HttpServletRequest req = WebContextUtil.getRequest(); 156 | BufferedReader reader = new BufferedReader(new InputStreamReader(req.getInputStream(), "utf-8")); 157 | String param = RequestBodyUtils.read(reader); 158 | String sessionId; 159 | if (StringUtil.isEmpty(param)) { 160 | sessionId = req.getParameter("sessionId"); 161 | } else { 162 | sessionId = JsonUtils.getJsonStringParam(param, "sessionId"); 163 | } 164 | List listUserSession = senseAgroAppService.findAppUserByToken((int) (new Date().getTime() / 1000), sessionId); 165 | String token = req.getHeader("Token"); 166 | String openId; 167 | try { 168 | openId = DesUtil.decrypt(sessionId); 169 | } catch (Exception e) { 170 | openId = ""; 171 | } 172 | log.info("openid is " + openId); 173 | SenseAgroMember senseAgroMember = senseAgroMemberService.findMember(openId); 174 | if (!TokenManager.checkToken(token) && listUserSession.size() == 0 && senseAgroMember == null) { 175 | return ResponseUtil.getResponse(ApiCodeEnum.RELOGIN); 176 | } 177 | return pjp.proceed(); 178 | } 179 | throw new TokenException("类型不支持"); 180 | } 181 | } 182 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/authorization/TokenManager.java: -------------------------------------------------------------------------------- 1 | package com.dfs.authorization; 2 | 3 | import com.dfs.utils.CodecUtil; 4 | import com.dfs.utils.DesUtil; 5 | import com.dfs.utils.RedisSingletonUtil; 6 | import com.dfs.utils.StringUtil; 7 | import org.apache.log4j.Logger; 8 | 9 | import java.util.Date; 10 | 11 | 12 | /** 13 | * @author taoxy 2019/1/3 14 | */ 15 | public class TokenManager { 16 | 17 | private static final Logger log = Logger.getLogger(TokenManager.class); 18 | private static final RedisSingletonUtil redisUtil = new RedisSingletonUtil(); 19 | /** 20 | * @description 利用UUID创建boss Token(用户登录时 , 创建Token) 21 | */ 22 | public static String createToken(int id,int minute) { 23 | //String token = CodecUtil.createUUID(); 24 | String token = DesUtil.encrypt(id+"-"+new Date().getTime()/1000); 25 | redisUtil.setString(token, token, minute); 26 | return token; 27 | } 28 | /** 29 | * @description 利用UUID创建boss Token(用户登录时 , 创建Token) 30 | */ 31 | public static String createAppToken() { 32 | String token = "app"+CodecUtil.createUUID(); 33 | redisUtil.setString(token, token, 24); 34 | return token; 35 | } 36 | /** 37 | * @description Token验证(用户登录验证) 38 | */ 39 | public static boolean checkToken(String token) { 40 | try { 41 | log.info("Token is "+token); 42 | return StringUtil.isNotEmpty(token) && redisUtil.get(token).equals(token); 43 | } catch (Exception e) { 44 | e.printStackTrace(); 45 | } 46 | return false; 47 | } 48 | 49 | /** 50 | * @description Token删除(用户登出时 , 删除Token) 51 | */ 52 | public static void deleteToken(String token) { 53 | try { 54 | redisUtil.remove(token); 55 | } catch (Exception e) { 56 | e.printStackTrace(); 57 | } 58 | } 59 | } 60 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/controller/app/AppLoginController.java: -------------------------------------------------------------------------------- 1 | package com.dfs.controller.app; 2 | 3 | import com.dfs.annotation.IgnoreSecurity; 4 | import com.dfs.entity.SenseAgroSpecialist; 5 | import com.dfs.entity.SenseAgroUser; 6 | import com.dfs.model.ApiCodeEnum; 7 | import com.dfs.service.SenseAgroSpecialistService; 8 | import com.dfs.utils.*; 9 | import org.apache.log4j.Logger; 10 | import org.springframework.beans.factory.annotation.Autowired; 11 | import org.springframework.web.bind.annotation.RequestBody; 12 | import org.springframework.web.bind.annotation.RequestMapping; 13 | import org.springframework.web.bind.annotation.RequestMethod; 14 | import org.springframework.web.bind.annotation.RestController; 15 | 16 | import javax.servlet.http.HttpServletRequest; 17 | import javax.servlet.http.HttpServletResponse; 18 | import java.util.Date; 19 | import java.util.HashMap; 20 | import java.util.Map; 21 | 22 | /** 23 | * @author taoxy 2019/2/1 24 | */ 25 | @RestController 26 | @RequestMapping("/specialist") 27 | public class AppLoginController { 28 | @Autowired 29 | private SenseAgroSpecialistService senseAgroSpecialistService; 30 | private static final Logger log = Logger.getLogger(AppLoginController.class); 31 | 32 | @RequestMapping(value = "/login", method = RequestMethod.POST, produces = "application/json;charset=utf-8") 33 | @IgnoreSecurity 34 | public String appLogin(@RequestBody String param, HttpServletResponse resp, HttpServletRequest req) { 35 | String name = JsonUtils.getJsonStringParam(param, "name"); 36 | String passwd = JsonUtils.getJsonStringParam(param, "passwd"); 37 | Map map = new HashMap<>(); 38 | log.info("查询开始"); 39 | try { 40 | SenseAgroSpecialist senseAgroSpecialist = senseAgroSpecialistService.login(name, Md5.GetMD5Code(passwd)); 41 | if (senseAgroSpecialist != null) { 42 | int setSpecialistId = senseAgroSpecialist.getId();//专家id 43 | int nowTime = (int) (new Date().getTime() / 1000);//时间以秒存储 44 | int valid = nowTime + 2 * 24 * 60 * 60;//超时时间2天 45 | //String token = TokenManager.createToken(senseAgroSpecialist.getId(),flag,minute); 46 | String token = DesUtil.encrypt(setSpecialistId + "-" + nowTime); 47 | log.debug("**** Generate app Token **** : " + token); 48 | SenseAgroUser senseAgroUser = new SenseAgroUser(); 49 | senseAgroUser.setSpecialistId(setSpecialistId); 50 | senseAgroUser.setValidTime(valid); 51 | senseAgroUser.setAddTime(nowTime); 52 | senseAgroUser.setSessionid(token); 53 | senseAgroSpecialistService.addSenseAgroUser(senseAgroUser); 54 | resp.setHeader("Token", token); 55 | map.put("specialistId", setSpecialistId); 56 | return ResponseUtil.getResponse(map, ApiCodeEnum.SUCCESS); 57 | } 58 | } catch (Exception e) { 59 | e.printStackTrace(); 60 | } 61 | return ResponseUtil.getResponse(ApiCodeEnum.FAIL.getCode(), "帐号或密码错误"); 62 | } 63 | } 64 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/controller/applite/LoginController.java: -------------------------------------------------------------------------------- 1 | package com.dfs.controller.applite; 2 | 3 | 4 | import com.dfs.annotation.IgnoreSecurity; 5 | import com.dfs.model.ApiCodeEnum; 6 | import com.dfs.model.WechatConfig; 7 | import com.dfs.service.SenseAgroMemberService; 8 | import com.dfs.utils.*; 9 | import org.apache.http.HttpEntity; 10 | import org.apache.http.HttpResponse; 11 | import org.apache.http.client.methods.HttpGet; 12 | import org.apache.http.impl.client.CloseableHttpClient; 13 | import org.apache.http.impl.client.HttpClients; 14 | import org.apache.http.util.EntityUtils; 15 | import org.slf4j.Logger; 16 | import org.slf4j.LoggerFactory; 17 | import org.springframework.beans.factory.annotation.Autowired; 18 | import org.springframework.web.bind.annotation.*; 19 | 20 | import javax.servlet.http.HttpServletResponse; 21 | import java.io.IOException; 22 | import java.util.HashMap; 23 | import java.util.Map; 24 | 25 | 26 | /** 27 | * @author taoxy 2018/12/12 28 | */ 29 | 30 | @RestController 31 | @RequestMapping("/user") 32 | public class LoginController { 33 | @Autowired 34 | private SenseAgroMemberService memberService; 35 | private static final Logger logger = LoggerFactory.getLogger(LoginController.class); 36 | private static final RedisSingletonUtil redisUtil = new RedisSingletonUtil(); 37 | 38 | @RequestMapping(value = "/login", method = RequestMethod.POST, produces = "application/json;charset=utf-8") 39 | @IgnoreSecurity 40 | public String loginIn(@RequestBody String param, HttpServletResponse res) { 41 | Map map = new HashMap(); 42 | map.put("sessionId", ""); 43 | try { 44 | String code = JsonUtils.getJsonStringParam(param, "code"); 45 | String url = WechatConfig.openid_url + WechatConfig.appid + "&secret=" + WechatConfig.appsecret + "&js_code=" + code + "&grant_type=authorization_code"; 46 | CloseableHttpClient httpclient = HttpClients.createDefault(); 47 | HttpGet httpget = new HttpGet(url); 48 | String response = null; 49 | HttpResponse resp = httpclient.execute(httpget); 50 | HttpEntity entity = resp.getEntity(); 51 | if (entity != null) { 52 | response = EntityUtils.toString(entity, "UTF-8").trim(); 53 | } 54 | String sessionKey = JsonUtils.getJsonStringParam(response, "session_key"); 55 | String openId = JsonUtils.getJsonStringParam(response, "openid"); 56 | logger.debug("sessionKey is ", sessionKey); 57 | if (StringUtil.isNotEmpty(openId) && StringUtil.isNotEmpty(sessionKey)) { 58 | String desKey = DesUtil.encrypt(openId); 59 | map.put("sessionId", desKey); 60 | ResponseUtil.getResponse(map, ApiCodeEnum.SUCCESS); 61 | return ResponseUtil.getResponse(map, ApiCodeEnum.SUCCESS); 62 | } else { 63 | return ResponseUtil.getResponse(ApiCodeEnum.SUCCESS.getCode(), JsonUtils.getJsonStringParam(response, "errmsg")); 64 | } 65 | } catch (IOException e) { 66 | return ResponseUtil.getResponse(ApiCodeEnum.RELOGIN); 67 | } 68 | } 69 | } 70 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/controller/boss/BossLoginController.java: -------------------------------------------------------------------------------- 1 | package com.dfs.controller.boss; 2 | 3 | import com.dfs.annotation.IgnoreSecurity; 4 | import com.dfs.authorization.TokenManager; 5 | import com.dfs.entity.SenseAgroAdmin; 6 | import com.dfs.model.ApiCodeEnum; 7 | import com.dfs.service.SenseAgroAdminService; 8 | import com.dfs.utils.*; 9 | import org.apache.log4j.Logger; 10 | import org.springframework.beans.factory.annotation.Autowired; 11 | import org.springframework.web.bind.annotation.RequestBody; 12 | import org.springframework.web.bind.annotation.RequestMapping; 13 | import org.springframework.web.bind.annotation.RequestMethod; 14 | import org.springframework.web.bind.annotation.RestController; 15 | 16 | import javax.servlet.http.HttpServletRequest; 17 | import javax.servlet.http.HttpServletResponse; 18 | import javax.servlet.http.HttpSession; 19 | 20 | /** 21 | * @author taoxy 2019/1/3 22 | */ 23 | @RestController 24 | @RequestMapping("/boss") 25 | public class BossLoginController { 26 | @Autowired 27 | private SenseAgroAdminService userService; 28 | private static final Logger log = Logger.getLogger(BossLoginController.class); 29 | 30 | @RequestMapping(value = "/login", method = RequestMethod.POST, produces = "application/json;charset=utf-8") 31 | @IgnoreSecurity 32 | public String login(@RequestBody String param, HttpServletResponse response, HttpServletRequest request) { 33 | String name = JsonUtils.getJsonStringParam(param, "name"); 34 | String passwd = JsonUtils.getJsonStringParam(param, "passwd"); 35 | 36 | log.info("查询开始"); 37 | SenseAgroAdmin senseAgroAdmin = userService.login(name, Md5.GetMD5Code(passwd)); 38 | if (senseAgroAdmin != null) { 39 | int minute = 120;//超时时间,分钟 40 | String token = TokenManager.createToken(senseAgroAdmin.getId(), minute); 41 | log.debug("**** Generate Token **** : " + token); 42 | response.setHeader("Token", token); 43 | HttpSession session = request.getSession(true); 44 | //为了读取当前用户 45 | session.setAttribute("userId", senseAgroAdmin.getId()); 46 | return ResponseUtil.getResponse(ApiCodeEnum.SUCCESS); 47 | } 48 | return ResponseUtil.getResponse(ApiCodeEnum.FAIL.getCode(), "帐号或者密码错误"); 49 | } 50 | } 51 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/controller/common/FileController.java: -------------------------------------------------------------------------------- 1 | package com.dfs.controller.common; 2 | 3 | 4 | import com.dfs.annotation.IgnoreSecurity; 5 | import com.dfs.model.ApiCodeEnum; 6 | import com.dfs.utils.FileUploadUtil; 7 | import com.dfs.utils.ResourceUtil; 8 | import com.dfs.utils.ResponseUtil; 9 | import org.apache.commons.lang.StringUtils; 10 | import org.apache.log4j.Logger; 11 | import org.springframework.web.bind.annotation.RequestMapping; 12 | import org.springframework.web.bind.annotation.RequestMethod; 13 | import org.springframework.web.bind.annotation.RequestParam; 14 | import org.springframework.web.bind.annotation.RestController; 15 | import org.springframework.web.multipart.MultipartFile; 16 | 17 | import java.io.IOException; 18 | import java.util.HashMap; 19 | import java.util.Map; 20 | 21 | /** 22 | * @author taoxy 2019/1/3 23 | */ 24 | @RestController 25 | @RequestMapping("/file") 26 | public class FileController { 27 | 28 | private static final Logger logger = Logger.getLogger(FileController.class); 29 | 30 | /** 31 | * 表单需要enctype="multipart/form-data",名字为image 32 | */ 33 | @RequestMapping(value = "/uploadAdvertImg", method = RequestMethod.POST, produces = "application/json;charset=utf-8") 34 | @IgnoreSecurity 35 | public String uploadAdvertImg(@RequestParam(required = false, value = "image") MultipartFile image) { 36 | logger.info("开始上传广告图片:{}" + image); 37 | String path = ""; 38 | if (image != null) { 39 | try { 40 | path = FileUploadUtil.uploadImage(image, ResourceUtil.advertImageDir()); 41 | } catch (IOException e) { 42 | logger.error("上传图片失败:", e); 43 | } 44 | } 45 | Map content = new HashMap(); 46 | // 上传失败 47 | if (StringUtils.isBlank(path)) { 48 | return ResponseUtil.getResponse(content, ApiCodeEnum.FAIL); 49 | } 50 | // 上传成功 51 | content.put("path", path); 52 | return ResponseUtil.getResponse(content, ApiCodeEnum.SUCCESS); 53 | } 54 | } 55 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/entity/SenseAgroAdmin.java: -------------------------------------------------------------------------------- 1 | package com.dfs.entity; 2 | 3 | import lombok.ToString; 4 | 5 | import java.io.Serializable; 6 | /** 7 | * @author taoxy 2018/12/15 8 | */ 9 | @ToString 10 | public class SenseAgroAdmin implements Serializable { 11 | private static final long serialVersionUID = 1L; 12 | private Integer id; 13 | 14 | private String memberName; 15 | 16 | private String memberPassword; 17 | 18 | private Integer registerTime; 19 | 20 | private Integer updateTime; 21 | 22 | private Integer isBanned; 23 | 24 | public Integer getId() { 25 | return id; 26 | } 27 | 28 | public void setId(Integer id) { 29 | this.id = id; 30 | } 31 | 32 | public String getMemberName() { 33 | return memberName; 34 | } 35 | 36 | public void setMemberName(String memberName) { 37 | this.memberName = memberName == null ? null : memberName.trim(); 38 | } 39 | 40 | public String getMemberPassword() { 41 | return memberPassword; 42 | } 43 | 44 | public void setMemberPassword(String memberPassword) { 45 | this.memberPassword = memberPassword == null ? null : memberPassword.trim(); 46 | } 47 | 48 | public Integer getRegisterTime() { 49 | return registerTime; 50 | } 51 | 52 | public void setRegisterTime(Integer registerTime) { 53 | this.registerTime = registerTime; 54 | } 55 | 56 | public Integer getUpdateTime() { 57 | return updateTime; 58 | } 59 | 60 | public void setUpdateTime(Integer updateTime) { 61 | this.updateTime = updateTime; 62 | } 63 | 64 | public Integer getIsBanned() { 65 | return isBanned; 66 | } 67 | 68 | public void setIsBanned(Integer isBanned) { 69 | this.isBanned = isBanned; 70 | } 71 | } -------------------------------------------------------------------------------- /src/main/java/com/dfs/entity/SenseAgroMember.java: -------------------------------------------------------------------------------- 1 | package com.dfs.entity; 2 | 3 | import com.dfs.utils.EmojiUtil; 4 | import lombok.ToString; 5 | 6 | import java.io.Serializable; 7 | 8 | /** 9 | * @author taoxy 2018/12/15 10 | */ 11 | @ToString 12 | public class SenseAgroMember implements Serializable { 13 | private static final long serialVersionUID = 1L; 14 | private Integer memberId; 15 | 16 | private String memberName; 17 | 18 | private String memberPassword; 19 | 20 | private String memberAvatar; 21 | 22 | private String memberModifyAvatar; 23 | 24 | private Integer memberSex = 0; 25 | 26 | private String memberNickname; 27 | 28 | private String memberCountry; 29 | 30 | private String memberProvince; 31 | 32 | private String memberCity; 33 | 34 | private String memberArea; 35 | 36 | private String memberMobile; 37 | 38 | private String memberOpenid; 39 | 40 | private String memberUnionid; 41 | 42 | private Integer registerTime; 43 | 44 | private Integer updateTime; 45 | 46 | private Integer isBanned; 47 | 48 | private String registerFrom; 49 | 50 | public Integer getMemberId() { 51 | return memberId; 52 | } 53 | 54 | public void setMemberId(Integer memberId) { 55 | this.memberId = memberId; 56 | } 57 | 58 | public String getMemberName() { 59 | return memberName; 60 | } 61 | 62 | public void setMemberName(String memberName) { 63 | this.memberName = memberName == null ? null : memberName.trim(); 64 | } 65 | 66 | public String getMemberPassword() { 67 | return memberPassword; 68 | } 69 | 70 | public void setMemberPassword(String memberPassword) { 71 | this.memberPassword = memberPassword == null ? null : memberPassword.trim(); 72 | } 73 | 74 | public String getMemberAvatar() { 75 | return memberAvatar; 76 | } 77 | 78 | public void setMemberAvatar(String memberAvatar) { 79 | this.memberAvatar = memberAvatar == null ? null : memberAvatar.trim(); 80 | } 81 | 82 | public String getMemberModifyAvatar() { 83 | return memberModifyAvatar; 84 | } 85 | 86 | public void setMemberModifyAvatar(String memberModifyAvatar) { 87 | this.memberModifyAvatar = memberModifyAvatar == null ? null : memberModifyAvatar.trim(); 88 | } 89 | 90 | public Integer getMemberSex() { 91 | return memberSex; 92 | } 93 | 94 | public void setMemberSex(Integer memberSex) { 95 | this.memberSex = memberSex; 96 | } 97 | 98 | public String getMemberNickname() { 99 | return EmojiUtil.emojiRecovery(memberNickname); 100 | } 101 | 102 | public void setMemberNickname(String memberNickname) { 103 | this.memberNickname = memberNickname == null ? null : EmojiUtil.emojiConvert(memberNickname.trim()); 104 | } 105 | 106 | public String getMemberCountry() { 107 | return memberCountry; 108 | } 109 | 110 | public void setMemberCountry(String memberCountry) { 111 | this.memberCountry = memberCountry == null ? null : memberCountry.trim(); 112 | } 113 | 114 | public String getMemberProvince() { 115 | return memberProvince; 116 | } 117 | 118 | public void setMemberProvince(String memberProvince) { 119 | this.memberProvince = memberProvince == null ? null : memberProvince.trim(); 120 | } 121 | 122 | public String getMemberCity() { 123 | return memberCity; 124 | } 125 | 126 | public void setMemberCity(String memberCity) { 127 | this.memberCity = memberCity == null ? null : memberCity.trim(); 128 | } 129 | 130 | public String getMemberArea() { 131 | return memberArea; 132 | } 133 | 134 | public void setMemberArea(String memberArea) { 135 | this.memberArea = memberArea == null ? null : memberArea.trim(); 136 | } 137 | 138 | public String getMemberMobile() { 139 | return memberMobile; 140 | } 141 | 142 | public void setMemberMobile(String memberMobile) { 143 | this.memberMobile = memberMobile == null ? null : memberMobile.trim(); 144 | } 145 | 146 | public String getMemberOpenid() { 147 | return memberOpenid; 148 | } 149 | 150 | public void setMemberOpenid(String memberOpenid) { 151 | this.memberOpenid = memberOpenid == null ? null : memberOpenid.trim(); 152 | } 153 | 154 | public String getMemberUnionid() { 155 | return memberUnionid; 156 | } 157 | 158 | public void setMemberUnionid(String memberUnionid) { 159 | this.memberUnionid = memberUnionid == null ? null : memberUnionid.trim(); 160 | } 161 | 162 | public Integer getRegisterTime() { 163 | return registerTime; 164 | } 165 | 166 | public void setRegisterTime(Integer registerTime) { 167 | this.registerTime = registerTime; 168 | } 169 | 170 | public Integer getUpdateTime() { 171 | return updateTime; 172 | } 173 | 174 | public void setUpdateTime(Integer updateTime) { 175 | this.updateTime = updateTime; 176 | } 177 | 178 | public Integer getIsBanned() { 179 | return isBanned; 180 | } 181 | 182 | public void setIsBanned(Integer isBanned) { 183 | this.isBanned = isBanned; 184 | } 185 | 186 | public String getRegisterFrom() { 187 | return registerFrom; 188 | } 189 | 190 | public void setRegisterFrom(String registerFrom) { 191 | this.registerFrom = registerFrom == null ? null : registerFrom.trim(); 192 | } 193 | } -------------------------------------------------------------------------------- /src/main/java/com/dfs/entity/SenseAgroSpecialist.java: -------------------------------------------------------------------------------- 1 | package com.dfs.entity; 2 | 3 | import lombok.ToString; 4 | 5 | import java.math.BigDecimal; 6 | 7 | /** 8 | * @author taoxy 2019/02/02 9 | */ 10 | @ToString 11 | public class SenseAgroSpecialist { 12 | private Integer id; 13 | 14 | private String name; 15 | 16 | private String avater; 17 | 18 | private String coverImage; 19 | 20 | private String mark; 21 | 22 | private Integer visit; 23 | 24 | private String cropName; 25 | 26 | private Integer workAge; 27 | 28 | private String area; 29 | 30 | private BigDecimal originPrice; 31 | 32 | private BigDecimal adjustPrice; 33 | 34 | private Integer addTime; 35 | 36 | private String uname; 37 | 38 | private String passwd; 39 | 40 | private String description; 41 | 42 | private String skill; 43 | 44 | private Integer timeShow; 45 | 46 | private byte isOnline; 47 | 48 | public Integer getId() { 49 | return id; 50 | } 51 | 52 | public void setId(Integer id) { 53 | this.id = id; 54 | } 55 | 56 | public String getName() { 57 | return name; 58 | } 59 | 60 | public void setName(String name) { 61 | this.name = name; 62 | } 63 | 64 | public String getAvater() { 65 | return avater; 66 | } 67 | 68 | public void setAvater(String avater) { 69 | this.avater = avater; 70 | } 71 | 72 | public String getMark() { 73 | return mark; 74 | } 75 | 76 | public void setMark(String mark) { 77 | this.mark = mark; 78 | } 79 | 80 | public Integer getVisit() { 81 | return visit; 82 | } 83 | 84 | public void setVisit(Integer visit) { 85 | this.visit = visit; 86 | } 87 | 88 | public String getCropName() { 89 | return cropName; 90 | } 91 | 92 | public void setCropName(String cropName) { 93 | this.cropName = cropName; 94 | } 95 | 96 | public Integer getWorkAge() { 97 | return workAge; 98 | } 99 | 100 | public void setWorkAge(Integer workAge) { 101 | this.workAge = workAge; 102 | } 103 | 104 | public String getArea() { 105 | return area; 106 | } 107 | 108 | public void setArea(String area) { 109 | this.area = area; 110 | } 111 | 112 | public BigDecimal getOriginPrice() { 113 | return originPrice; 114 | } 115 | 116 | public void setOriginPrice(BigDecimal originPrice) { 117 | this.originPrice = originPrice; 118 | } 119 | 120 | public BigDecimal getAdjustPrice() { 121 | return adjustPrice; 122 | } 123 | 124 | public void setAdjustPrice(BigDecimal adjustPrice) { 125 | this.adjustPrice = adjustPrice; 126 | } 127 | 128 | public Integer getAddTime() { 129 | return addTime; 130 | } 131 | 132 | public void setAddTime(Integer addTime) { 133 | this.addTime = addTime; 134 | } 135 | 136 | public String getUname() { 137 | return uname; 138 | } 139 | 140 | public void setUname(String uname) { 141 | this.uname = uname; 142 | } 143 | 144 | public String getPasswd() { 145 | return passwd; 146 | } 147 | 148 | public void setPasswd(String passwd) { 149 | this.passwd = passwd; 150 | } 151 | 152 | public String getDescription() { 153 | if (description == null) { 154 | return ""; 155 | } 156 | return description; 157 | } 158 | 159 | public void setDescription(String description) { 160 | this.description = description; 161 | } 162 | 163 | public String getCoverImage() { 164 | return coverImage; 165 | } 166 | 167 | public void setCoverImage(String coverImage) { 168 | this.coverImage = coverImage; 169 | } 170 | 171 | public String getSkill() { 172 | return skill; 173 | } 174 | 175 | public void setSkill(String skill) { 176 | this.skill = skill; 177 | } 178 | 179 | public Integer getTimeShow() { 180 | return timeShow; 181 | } 182 | 183 | public void setTimeShow(Integer timeShow) { 184 | this.timeShow = timeShow; 185 | } 186 | 187 | public byte getIsOnline() { 188 | return isOnline; 189 | } 190 | 191 | public void setIsOnline(byte isOnline) { 192 | this.isOnline = isOnline; 193 | } 194 | } -------------------------------------------------------------------------------- /src/main/java/com/dfs/entity/SenseAgroUser.java: -------------------------------------------------------------------------------- 1 | package com.dfs.entity; 2 | 3 | import lombok.ToString; 4 | 5 | /** 6 | * @author taoxy 2019/02/02 7 | */ 8 | @ToString 9 | public class SenseAgroUser { 10 | private Integer id; 11 | 12 | private Integer specialistId; 13 | 14 | private Integer addTime; 15 | 16 | private Integer validTime; 17 | 18 | private String sessionid; 19 | 20 | public Integer getId() { 21 | return id; 22 | } 23 | 24 | public void setId(Integer id) { 25 | this.id = id; 26 | } 27 | 28 | public Integer getSpecialistId() { 29 | return specialistId; 30 | } 31 | 32 | public void setSpecialistId(Integer specialistId) { 33 | this.specialistId = specialistId; 34 | } 35 | 36 | public Integer getAddTime() { 37 | return addTime; 38 | } 39 | 40 | public void setAddTime(Integer addTime) { 41 | this.addTime = addTime; 42 | } 43 | 44 | public Integer getValidTime() { 45 | return validTime; 46 | } 47 | 48 | public void setValidTime(Integer validTime) { 49 | this.validTime = validTime; 50 | } 51 | 52 | public String getSessionid() { 53 | return sessionid; 54 | } 55 | 56 | public void setSessionid(String sessionid) { 57 | this.sessionid = sessionid == null ? null : sessionid.trim(); 58 | } 59 | } -------------------------------------------------------------------------------- /src/main/java/com/dfs/exception/TokenException.java: -------------------------------------------------------------------------------- 1 | package com.dfs.exception; 2 | 3 | /** 4 | * @author taoxy 2019/1/3 5 | */ 6 | public class TokenException extends RuntimeException { 7 | 8 | private static final long serialVersionUID = 1L; 9 | 10 | private String msg; 11 | 12 | public TokenException(String msg) { 13 | super(); 14 | this.msg = msg; 15 | } 16 | 17 | public String getMsg() { 18 | return msg; 19 | } 20 | 21 | public void setMsg(String msg) { 22 | this.msg = msg; 23 | } 24 | 25 | } 26 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/filter/CorsFilter.java: -------------------------------------------------------------------------------- 1 | package com.dfs.filter; 2 | 3 | import java.io.IOException; 4 | import java.util.Arrays; 5 | import java.util.List; 6 | 7 | import javax.servlet.Filter; 8 | import javax.servlet.FilterChain; 9 | import javax.servlet.FilterConfig; 10 | import javax.servlet.ServletException; 11 | import javax.servlet.ServletRequest; 12 | import javax.servlet.ServletResponse; 13 | import javax.servlet.http.HttpServletRequest; 14 | import javax.servlet.http.HttpServletResponse; 15 | 16 | import com.dfs.utils.CollectionUtil; 17 | import com.dfs.utils.StringUtil; 18 | import org.apache.log4j.Logger; 19 | 20 | 21 | /** 22 | * @author taoxy 2019/1/3 23 | */ 24 | public class CorsFilter implements Filter { 25 | 26 | private static final Logger log = Logger.getLogger(CorsFilter.class); 27 | 28 | private String allowOrigin; 29 | private String allowMethods; 30 | private String allowCredentials; 31 | private String allowHeaders; 32 | private String exposeHeaders; 33 | 34 | @Override 35 | public void init(FilterConfig filterConfig) throws ServletException { 36 | allowOrigin = filterConfig.getInitParameter("allowOrigin"); 37 | allowMethods = filterConfig.getInitParameter("allowMethods"); 38 | allowCredentials = filterConfig.getInitParameter("allowCredentials"); 39 | allowHeaders = filterConfig.getInitParameter("allowHeaders"); 40 | exposeHeaders = filterConfig.getInitParameter("exposeHeaders"); 41 | } 42 | 43 | @Override 44 | public void doFilter(ServletRequest req, ServletResponse res, FilterChain chain) throws IOException, ServletException { 45 | if(req instanceof HttpServletRequest){ 46 | req = new SenseAgroRequestWrapper((HttpServletRequest) req); 47 | //res = new SenseAgroRequestWrapper((HttpServletResponse)res); 48 | } 49 | HttpServletRequest request = (HttpServletRequest) req; 50 | HttpServletResponse response = (HttpServletResponse) res; 51 | String currentOrigin = request.getHeader("Origin"); 52 | log.debug("currentOrigin : " + currentOrigin); 53 | if (StringUtil.isNotEmpty(allowOrigin)) { 54 | List allowOriginList = Arrays.asList(allowOrigin.split(",")); 55 | log.debug("allowOriginList : " + allowOrigin); 56 | if (CollectionUtil.isNotEmpty(allowOriginList)) { 57 | if (allowOriginList.contains(currentOrigin)) { 58 | response.setHeader("Access-Control-Allow-Origin", currentOrigin); 59 | }else { 60 | log.info("Not allowed "+currentOrigin); 61 | } 62 | } 63 | } 64 | if (StringUtil.isNotEmpty(allowMethods)) { 65 | response.setHeader("Access-Control-Allow-Methods", allowMethods); 66 | } 67 | if (StringUtil.isNotEmpty(allowCredentials)) { 68 | response.setHeader("Access-Control-Allow-Credentials", allowCredentials); 69 | } 70 | if (StringUtil.isNotEmpty(allowHeaders)) { 71 | response.setHeader("Access-Control-Allow-Headers", allowHeaders); 72 | } 73 | if (StringUtil.isNotEmpty(exposeHeaders)) { 74 | response.setHeader("Access-Control-Expose-Headers", exposeHeaders); 75 | } 76 | chain.doFilter(req, res); 77 | } 78 | 79 | @Override 80 | public void destroy() { 81 | } 82 | } -------------------------------------------------------------------------------- /src/main/java/com/dfs/filter/SenseAgroRequestWrapper.java: -------------------------------------------------------------------------------- 1 | package com.dfs.filter; 2 | 3 | import org.apache.log4j.Logger; 4 | import org.springframework.util.StreamUtils; 5 | 6 | import javax.servlet.ReadListener; 7 | import javax.servlet.ServletInputStream; 8 | import javax.servlet.http.HttpServletRequest; 9 | import javax.servlet.http.HttpServletRequestWrapper; 10 | import java.io.*; 11 | import java.util.Enumeration; 12 | import java.util.Map; 13 | import java.util.Vector; 14 | 15 | /** 16 | * @author taoxy 2019/02/5 17 | */ 18 | public class SenseAgroRequestWrapper extends HttpServletRequestWrapper { 19 | private static final Logger logger = Logger.getLogger(SenseAgroRequestWrapper.class); 20 | 21 | private Map parameterMap; // get方法 22 | private byte[] requestBody = null; // post 方法body数据 23 | 24 | public SenseAgroRequestWrapper(HttpServletRequest request) { 25 | super(request); 26 | //缓存请求body 27 | try { 28 | parameterMap = request.getParameterMap(); 29 | requestBody = StreamUtils.copyToByteArray(request.getInputStream()); 30 | } catch (IOException e) { 31 | e.printStackTrace(); 32 | } 33 | } 34 | 35 | /** 36 | * 获取所有参数名, get相关方法重写 37 | * 38 | * @return 返回所有参数名 39 | */ 40 | @Override 41 | public Enumeration getParameterNames() { 42 | Vector vector = new Vector<>(parameterMap.keySet()); 43 | return vector.elements(); 44 | } 45 | 46 | /** 47 | * 获取指定参数名的值,如果有重复的参数名,则返回第一个的值 接收一般变量 ,如text类型 48 | * 49 | * @param name 指定参数名 50 | * @return 指定参数名的值 51 | */ 52 | @Override 53 | public String getParameter(String name) { 54 | String[] results = parameterMap.get(name); 55 | if (results == null || results.length <= 0) 56 | return null; 57 | else { 58 | System.out.println("modify before:" + results[0]); 59 | return modify(results[0]); 60 | } 61 | } 62 | 63 | /** 64 | * 获取指定参数名的所有值的数组,如:checkbox的所有数据 65 | * 接收数组变量 ,如checkobx类型 66 | */ 67 | @Override 68 | public String[] getParameterValues(String name) { 69 | String[] results = parameterMap.get(name); 70 | if (results == null || results.length <= 0) 71 | return null; 72 | else { 73 | int length = results.length; 74 | for (int i = 0; i < length; i++) { 75 | results[i] = modify(results[i]); 76 | } 77 | return results; 78 | } 79 | } 80 | 81 | /** 82 | * 自定义的一个简单修改原参数的方法,即:给原来的参数值前面添加了一个修改标志的字符串 83 | * 84 | * @param string 原参数值 85 | * @return 修改之后的值 ,这里并不进行改变 86 | */ 87 | private String modify(String string) { 88 | return string; 89 | } 90 | 91 | 92 | /** 93 | * 重写 getReader() 94 | */ 95 | @Override 96 | public BufferedReader getReader() throws IOException { 97 | return new BufferedReader(new InputStreamReader(getInputStream())); 98 | } 99 | 100 | /** 101 | * 重写 getInputStream() 102 | */ 103 | @Override 104 | public ServletInputStream getInputStream() throws IOException { 105 | logger.info("modify before post"); 106 | if (requestBody == null) { 107 | requestBody = new byte[0]; 108 | } 109 | final ByteArrayInputStream bais = new ByteArrayInputStream(requestBody); 110 | MyServletInputStream myServletInputStream = new MyServletInputStream(bais); 111 | return myServletInputStream; 112 | } 113 | 114 | // 定义自己的ServletInputStream 115 | class MyServletInputStream extends ServletInputStream { 116 | private InputStream inputStream; 117 | 118 | public MyServletInputStream(InputStream inputStream) { 119 | super(); 120 | this.inputStream = inputStream; 121 | } 122 | 123 | @Override 124 | public boolean isFinished() { 125 | return false; 126 | } 127 | 128 | @Override 129 | public boolean isReady() { 130 | return false; 131 | } 132 | 133 | @Override 134 | public void setReadListener(ReadListener readListener) { 135 | return; 136 | } 137 | 138 | @Override 139 | public int read() throws IOException { 140 | return inputStream.read(); 141 | } 142 | } 143 | } -------------------------------------------------------------------------------- /src/main/java/com/dfs/job/JiguangPushJob.java: -------------------------------------------------------------------------------- 1 | package com.dfs.job; 2 | 3 | import com.dfs.jpush.JiguangPush; 4 | import org.springframework.scheduling.annotation.Scheduled; 5 | import org.springframework.stereotype.Component; 6 | 7 | /** 8 | * @author taoxy 2019/2/28 9 | */ 10 | @Component 11 | public class JiguangPushJob { 12 | private static final String message = "茕茕白兔,东走西顾,衣不如新,人不如故"; 13 | 14 | @Scheduled(cron = "* 0/5 * * * ?") 15 | public void run() { 16 | synchronized (JiguangPushJob.class) { 17 | JiguangPush jiguangPush = new JiguangPush(); 18 | //jiguangPush.jiguangPush("1993","www.taoxy.online","0701"); 19 | } 20 | 21 | } 22 | } 23 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/job/MessageSendJob.java: -------------------------------------------------------------------------------- 1 | package com.dfs.job; 2 | 3 | 4 | import org.apache.log4j.Logger; 5 | import org.springframework.scheduling.annotation.Scheduled; 6 | import org.springframework.stereotype.Component; 7 | 8 | /** 9 | * @author taoxy 2019/2/28 10 | */ 11 | @Component 12 | public class MessageSendJob { 13 | 14 | private static final Logger logger = Logger.getLogger(MessageSendJob.class); 15 | 16 | //@Autowired 17 | //private SenseAgroMessageService senseAgroMessageService; 18 | 19 | @Scheduled(cron = "* 0/5 * * * ?") 20 | public void message() { 21 | // 执行批量消息推送操作 22 | //senseAgroMessageService.messageAll(); 23 | } 24 | } 25 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/job/OrderRefundJob.java: -------------------------------------------------------------------------------- 1 | package com.dfs.job; 2 | 3 | 4 | import org.apache.log4j.Logger; 5 | import org.springframework.scheduling.annotation.Scheduled; 6 | import org.springframework.stereotype.Component; 7 | 8 | /** 9 | * @author taoxy 2019/2/28 10 | */ 11 | @Component 12 | public class OrderRefundJob { 13 | 14 | private static final Logger logger = Logger.getLogger(OrderRefundJob.class); 15 | 16 | //@Autowired 17 | //private SenseAgroRefundService senseAgroRefundService; 18 | 19 | 20 | @Scheduled(cron = "* 0/15 * * * ?") 21 | public void refund() { 22 | // 微信支付宝执行批量退款操作 23 | //senseAgroRefundService.refundAll(); 24 | } 25 | } 26 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/jpush/JiguangPush.java: -------------------------------------------------------------------------------- 1 | package com.dfs.jpush; 2 | 3 | import com.dfs.model.JiguangConfig; 4 | import net.sf.json.JSONArray; 5 | import org.apache.http.HttpResponse; 6 | import org.apache.http.client.HttpClient; 7 | import org.apache.http.client.methods.HttpPost; 8 | import org.apache.http.entity.StringEntity; 9 | import org.apache.http.impl.client.DefaultHttpClient; 10 | import org.apache.http.util.EntityUtils; 11 | import net.sf.json.JSONObject; 12 | import org.apache.log4j.Logger; 13 | import sun.misc.BASE64Encoder; 14 | 15 | /** 16 | * @author taoxy 2019/2/27 17 | */ 18 | 19 | /** 20 | * java后台极光推送方式一:使用Http API 21 | * 此种方式需要自定义http请求发送客户端:HttpClient 22 | */ 23 | @SuppressWarnings({"deprecation", "restriction"}) 24 | public class JiguangPush { 25 | private static final Logger log = Logger.getLogger(JiguangPush.class); 26 | 27 | /** 28 | * 极光推送 29 | */ 30 | public void jiguangPush(String alias, String message, String title) { 31 | try { 32 | String result = push(JiguangConfig.pushUrl, alias, message, title, JiguangConfig.appKey, JiguangConfig.masterSecret, JiguangConfig.apns_production, JiguangConfig.time_to_live); 33 | JSONObject resData = JSONObject.fromObject(result); 34 | if (resData.containsKey("error")) { 35 | log.info("针对别名为" + alias + "的信息推送失败!"); 36 | JSONObject error = JSONObject.fromObject(resData.get("error")); 37 | log.info("错误信息为:" + error.get("message").toString()); 38 | } else { 39 | log.info("针对别名为" + alias + "的信息推送成功!"); 40 | } 41 | } catch (Exception e) { 42 | log.error("针对别名为" + alias + "的信息推送失败!", e); 43 | } 44 | } 45 | 46 | /** 47 | * 组装极光推送专用json串 48 | * 49 | * @param alias 50 | * @param alert 51 | * @return json 52 | */ 53 | public static JSONObject generateJson(String alias, String alert, String title, boolean apns_production, int time_to_live) { 54 | JSONObject json = new JSONObject(); 55 | JSONArray platform = new JSONArray();//平台 56 | platform.add("android"); 57 | platform.add("ios"); 58 | 59 | JSONObject audience = new JSONObject();//推送目标 60 | JSONArray alias1 = new JSONArray(); 61 | alias1.add(alias); 62 | audience.put("alias", alias1); 63 | JSONObject notification = new JSONObject();//通知内容 64 | JSONObject android = new JSONObject();//android通知内容 65 | android.put("alert", alert); 66 | android.put("title", title); 67 | android.put("builder_id", 1); 68 | android.put("style", 1); 69 | android.put("priority", 0); 70 | android.put("alert_type", 1); 71 | //android.put("big_text", "big text content"); 72 | JSONObject android_extras = new JSONObject();//android额外参数 73 | android_extras.put("type", "infomation"); 74 | android_extras.put("time", (int) (System.currentTimeMillis() / 1000)); 75 | android.put("extras", android_extras); 76 | 77 | JSONObject ios = new JSONObject();//ios通知内容 78 | ios.put("alert", alert); 79 | ios.put("sound", "default"); 80 | ios.put("badge", "+1"); 81 | JSONObject ios_extras = new JSONObject();//ios额外参数 82 | ios_extras.put("type", "infomation"); 83 | ios.put("extras", ios_extras); 84 | notification.put("android", android); 85 | notification.put("ios", ios); 86 | 87 | JSONObject options = new JSONObject();//设置参数 88 | options.put("time_to_live", Integer.valueOf(time_to_live)); 89 | options.put("apns_production", apns_production); 90 | 91 | json.put("platform", platform); 92 | json.put("audience", audience); 93 | json.put("notification", notification); 94 | json.put("options", options); 95 | return json; 96 | 97 | } 98 | 99 | /** 100 | * 推送方法-调用极光API 101 | * 102 | * @param reqUrl 103 | * @param alias 104 | * @param alert 105 | * @return result 106 | */ 107 | public static String push(String reqUrl, String alias, String alert, String title, String appKey, String masterSecret, boolean apns_production, int time_to_live) { 108 | String base64_auth_string = encryptBASE64(appKey + ":" + masterSecret); 109 | String authorization = "Basic " + base64_auth_string; 110 | return sendPostRequest(reqUrl, generateJson(alias, alert, title, apns_production, time_to_live).toString(), "UTF-8", authorization); 111 | } 112 | 113 | /** 114 | * 发送Post请求(json格式) 115 | * 116 | * @param reqURL 117 | * @param data 118 | * @param encodeCharset 119 | * @param authorization 120 | * @return result 121 | */ 122 | @SuppressWarnings({"resource"}) 123 | public static String sendPostRequest(String reqURL, String data, String encodeCharset, String authorization) { 124 | HttpPost httpPost = new HttpPost(reqURL); 125 | HttpClient client = new DefaultHttpClient(); 126 | HttpResponse response = null; 127 | String result = ""; 128 | try { 129 | StringEntity entity = new StringEntity(data, encodeCharset); 130 | entity.setContentType("application/json"); 131 | httpPost.setEntity(entity); 132 | httpPost.setHeader("Authorization", authorization.trim()); 133 | response = client.execute(httpPost); 134 | result = EntityUtils.toString(response.getEntity(), encodeCharset); 135 | } catch (Exception e) { 136 | log.error("请求通信[" + reqURL + "]时偶遇异常,堆栈轨迹如下", e); 137 | } finally { 138 | client.getConnectionManager().shutdown(); 139 | } 140 | return result; 141 | } 142 | 143 | /** 144 | *     * BASE64加密工具 145 | */ 146 | public static String encryptBASE64(String str) { 147 | byte[] key = str.getBytes(); 148 | BASE64Encoder base64Encoder = new BASE64Encoder(); 149 | String strs = base64Encoder.encodeBuffer(key); 150 | return strs; 151 | } 152 | } -------------------------------------------------------------------------------- /src/main/java/com/dfs/jpush/JiguangPushBySDK.java: -------------------------------------------------------------------------------- 1 | package com.dfs.jpush; 2 | 3 | import cn.jiguang.common.ClientConfig; 4 | import cn.jiguang.common.resp.APIConnectionException; 5 | import cn.jiguang.common.resp.APIRequestException; 6 | import cn.jpush.api.JPushClient; 7 | import cn.jpush.api.push.PushResult; 8 | import cn.jpush.api.push.model.Options; 9 | import cn.jpush.api.push.model.Platform; 10 | import cn.jpush.api.push.model.PushPayload; 11 | import cn.jpush.api.push.model.audience.Audience; 12 | import cn.jpush.api.push.model.notification.AndroidNotification; 13 | import cn.jpush.api.push.model.notification.IosNotification; 14 | import cn.jpush.api.push.model.notification.Notification; 15 | import org.apache.log4j.Logger; 16 | 17 | 18 | /** 19 | * java后台极光推送方式二:使用Java SDK 20 | */ 21 | @SuppressWarnings({"deprecation", "restriction"}) 22 | public class JiguangPushBySDK { 23 | private static final Logger log = Logger.getLogger(JiguangPush.class); 24 | private static String masterSecret = "b717a7993d82b6e6fa259b8a"; 25 | private static String appKey = "3365d0e31f413fedc4af13a1"; 26 | 27 | /** 28 | * 极光推送 29 | */ 30 | public void jiguangPush(String alias, String message) { 31 | log.info("对别名" + alias + "的用户推送信息"); 32 | PushResult result = push(String.valueOf(alias), message); 33 | if (result != null && result.isResultOK()) { 34 | log.info("针对别名" + alias + "的信息推送成功!"); 35 | } else { 36 | log.info("针对别名" + alias + "的信息推送失败!"); 37 | } 38 | } 39 | 40 | /** 41 | * 生成极光推送对象PushPayload(采用java SDK) 42 | * 43 | * @param alias 44 | * @param alert 45 | * @return PushPayload 46 | */ 47 | public static PushPayload buildPushObject_android_ios_alias_alert(String alias, String alert) { 48 | return PushPayload.newBuilder() 49 | .setPlatform(Platform.android_ios()) 50 | .setAudience(Audience.alias(alias)) 51 | .setNotification(Notification.newBuilder() 52 | .addPlatformNotification(AndroidNotification.newBuilder() 53 | .addExtra("type", "infomation") 54 | .setAlert(alert) 55 | .build()) 56 | .addPlatformNotification(IosNotification.newBuilder() 57 | .addExtra("type", "infomation") 58 | .setAlert(alert) 59 | .build()) 60 | .build()) 61 | .setOptions(Options.newBuilder() 62 | .setApnsProduction(false)//true-推送生产环境 false-推送开发环境(测试使用参数) 63 | .setTimeToLive(90)//消息在JPush服务器的失效时间(测试使用参数) 64 | .build()) 65 | .build(); 66 | } 67 | 68 | /** 69 | * 极光推送方法(采用java SDK) 70 | * 71 | * @param alias 72 | * @param alert 73 | * @return PushResult 74 | */ 75 | public static PushResult push(String alias, String alert) { 76 | ClientConfig clientConfig = ClientConfig.getInstance(); 77 | JPushClient jpushClient = new JPushClient(masterSecret, appKey, null, clientConfig); 78 | PushPayload payload = buildPushObject_android_ios_alias_alert(alias, alert); 79 | try { 80 | return jpushClient.sendPush(payload); 81 | } catch (APIConnectionException e) { 82 | log.error("Connection error. Should retry later. ", e); 83 | return null; 84 | } catch (APIRequestException e) { 85 | log.error("Error response from JPush server. Should review and fix it. ", e); 86 | log.info("HTTP Status: " + e.getStatus()); 87 | log.info("Error Code: " + e.getErrorCode()); 88 | log.info("Error Message: " + e.getErrorMessage()); 89 | log.info("Msg ID: " + e.getMsgId()); 90 | return null; 91 | } 92 | } 93 | } -------------------------------------------------------------------------------- /src/main/java/com/dfs/mapper/SenseAgroAdminMapper.java: -------------------------------------------------------------------------------- 1 | package com.dfs.mapper; 2 | 3 | import com.dfs.entity.SenseAgroAdmin; 4 | import org.apache.ibatis.annotations.Param; 5 | 6 | /** 7 | * @author taoxy 2018/12/15 8 | */ 9 | public interface SenseAgroAdminMapper { 10 | 11 | SenseAgroAdmin findUserBynameAndPasswd(@Param("memberName") String name, @Param("memberPassword") String passwd); 12 | } -------------------------------------------------------------------------------- /src/main/java/com/dfs/mapper/SenseAgroMemberMapper.java: -------------------------------------------------------------------------------- 1 | package com.dfs.mapper; 2 | 3 | import com.dfs.entity.SenseAgroMember; 4 | import org.apache.ibatis.annotations.Param; 5 | 6 | import java.util.List; 7 | 8 | /** 9 | * @author taoxy 2018/12/15 10 | */ 11 | public interface SenseAgroMemberMapper { 12 | SenseAgroMember selectByOpenId(@Param("memberOpenid") String memberOpenid); 13 | } -------------------------------------------------------------------------------- /src/main/java/com/dfs/mapper/SenseAgroSpecialistMapper.java: -------------------------------------------------------------------------------- 1 | package com.dfs.mapper; 2 | 3 | import com.dfs.entity.SenseAgroSpecialist; 4 | import org.apache.ibatis.annotations.Param; 5 | 6 | public interface SenseAgroSpecialistMapper { 7 | 8 | SenseAgroSpecialist findUserBynameAndPasswd(@Param("uname") String uname, @Param("passwd") String passwd); 9 | 10 | } -------------------------------------------------------------------------------- /src/main/java/com/dfs/mapper/SenseAgroUserMapper.java: -------------------------------------------------------------------------------- 1 | package com.dfs.mapper; 2 | 3 | import com.dfs.entity.SenseAgroUser; 4 | import org.apache.ibatis.annotations.Param; 5 | 6 | import java.util.List; 7 | 8 | public interface SenseAgroUserMapper { 9 | 10 | int insertSelective(SenseAgroUser record); 11 | 12 | List findUserByToken(@Param("nowTime") int nowTime, @Param("sessionId") String sessionId); 13 | } -------------------------------------------------------------------------------- /src/main/java/com/dfs/model/AliyunMessageConfig.java: -------------------------------------------------------------------------------- 1 | package com.dfs.model; 2 | 3 | public class AliyunMessageConfig { 4 | public static final String product = "Dysmsapi"; 5 | public static final String domain = "dysmsapi.aliyuncs.com"; 6 | public static final String accessKeyId = "xxxxxxxxxxxxxxx"; 7 | public static final String accessKeySecret = "xxxxxxxxxxxxxxx"; 8 | public static final String defaultConnectTimeout = "sun.net.client.defaultConnectTimeout"; 9 | public static final String defaultReadTimeout = "sun.net.client.defaultReadTimeout"; 10 | public static final String time = "10000"; 11 | } 12 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/model/ApiCodeEnum.java: -------------------------------------------------------------------------------- 1 | package com.dfs.model; 2 | 3 | /** 4 | * API接口响应码枚举 5 | * 6 | * @author zjj 7 | * @date 2019-02-13 8 | */ 9 | public enum ApiCodeEnum { 10 | 11 | SUCCESS("1", "操作成功"), 12 | FAIL("0", "操作失败"), 13 | EXCEPTION("0", "程序出现异常"), 14 | RELOGIN("2", "登录失效"), 15 | DUPLICATE_RECORD("10001", "重复记录"); 16 | 17 | 18 | private String code; 19 | private String msg; 20 | 21 | private ApiCodeEnum(String code, String msg) { 22 | this.code = code; 23 | this.msg = msg; 24 | } 25 | 26 | public String getCode() { 27 | return code; 28 | } 29 | 30 | public String getMsg() { 31 | return msg; 32 | } 33 | 34 | public static String getDescByValue(String code) { 35 | for (ApiCodeEnum enums : ApiCodeEnum.values()) { 36 | if (enums.getCode().equals(code)) { 37 | return enums.getMsg(); 38 | } 39 | } 40 | return ""; 41 | } 42 | 43 | } 44 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/model/JiguangConfig.java: -------------------------------------------------------------------------------- 1 | package com.dfs.model; 2 | 3 | public class JiguangConfig { 4 | public static final String masterSecret = "xxxxxxxxxxxxxxx"; 5 | public static final String appKey = "xxxxxxxxxxxxxxx"; 6 | public static final String pushUrl = "https://api.jpush.cn/v3/push"; 7 | public static final boolean apns_production = true; 8 | public static final int time_to_live = 86400; 9 | } 10 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/model/RedisConfig.java: -------------------------------------------------------------------------------- 1 | package com.dfs.model; 2 | 3 | public class RedisConfig { 4 | public static final Integer maxTotal = 100; 5 | public static final Integer maxIdle = 50; 6 | public static final Integer maxWaitMillis = 120; 7 | public static final Boolean testOnBorrow = true; 8 | public static final Boolean testOnReturn = true; 9 | public static final String host = "127.0.0.1"; 10 | public static final Integer port = 3991; 11 | public static final String passwd = "www.taoxy.online"; 12 | } 13 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/model/SystemVariableEnum.java: -------------------------------------------------------------------------------- 1 | package com.dfs.model; 2 | /** 3 | * 系统参数枚举 4 | * @author taoxy 2019/1/3 5 | */ 6 | public enum SystemVariableEnum { 7 | 8 | SUCCESS("1", "操作成功"), 9 | FAIL("0", "操作失败"); 10 | 11 | private String code; 12 | private String msg; 13 | 14 | private SystemVariableEnum(String code, String msg) { 15 | this.code = code; 16 | this.msg = msg; 17 | } 18 | 19 | public String getCode() { 20 | return code; 21 | } 22 | 23 | public String getMsg() { 24 | return msg; 25 | } 26 | 27 | public static String getDescByValue(String code) { 28 | for (SystemVariableEnum enums : SystemVariableEnum.values()) { 29 | if (enums.getCode().equals(code)) { 30 | return enums.getMsg(); 31 | } 32 | } 33 | return ""; 34 | } 35 | 36 | } 37 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/model/WechatConfig.java: -------------------------------------------------------------------------------- 1 | package com.dfs.model; 2 | 3 | import com.dfs.utils.ResourceUtil; 4 | 5 | /** 6 | * @ author ezra 7 | * @ date 2019/1/28 10:50 8 | */ 9 | public class WechatConfig { 10 | //小程序appid 11 | public static final String appid = "xxxxxxxxxxxxxxx"; 12 | //小程序appsecret 13 | public static final String appsecret = "xxxxxxxxxxxxxxx"; 14 | //微信支付的商户id 15 | public static final String mch_id = "1525341361"; 16 | //微信支付的商户密钥 17 | public static final String key = "xxxxxxxxxxxxxxx"; 18 | //支付成功后的服务器回调url,这里填PayController里的回调函数地址 19 | public static final String notify_url = ResourceUtil.imageServer() + "/taoxy/pay/wxNotify"; 20 | //签名方式,固定值 21 | public static final String SIGNTYPE = "MD5"; 22 | //交易类型,小程序支付的固定值为JSAPI 23 | public static final String TRADETYPE = "JSAPI"; 24 | //微信统一下单接口地址 25 | public static final String pay_url = "https://api.mch.weixin.qq.com/pay/unifiedorder"; 26 | //微信统一查询接口地址 27 | public static final String pay_query = "https://api.mch.weixin.qq.com/pay/orderquery"; 28 | // 微信退款接口地址 29 | public static final String REFUND_URL = "https://api.mch.weixin.qq.com/secapi/pay/refund"; 30 | // 微信查询退款信息地址 31 | public static final String REFUND_QUERY_URL = "https://api.mch.weixin.qq.com/pay/refundquery"; 32 | // 微信退款回调地址 33 | public static final String REFUND_NOTIFY_URL = ResourceUtil.imageServer() + "/taoxy/boss/refund/refundWechatCallback"; 34 | // P12证书存放路径 35 | public static final String CERT_P12_PATH = "/home/cert/wechat/taoxy/apiclient_cert.p12"; 36 | 37 | public static final String openid_url = "https://api.weixin.qq.com/sns/jscode2session?appid="; 38 | 39 | } 40 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/response/AnalysisResult.java: -------------------------------------------------------------------------------- 1 | package com.dfs.response; 2 | 3 | import java.io.Serializable; 4 | import java.math.BigDecimal; 5 | import java.util.List; 6 | 7 | /** 8 | * 算法分析结果 9 | * @author taoxy 2018/12/21 10 | */ 11 | public class AnalysisResult implements Serializable { 12 | private String content; 13 | private String imageUrl; 14 | private String result; 15 | private int score; 16 | private int wikiId; 17 | private List box; 18 | public String getContent() { 19 | return content; 20 | } 21 | 22 | public void setContent(String content) { 23 | this.content = content; 24 | } 25 | 26 | public String getImageUrl() { 27 | return imageUrl; 28 | } 29 | 30 | public void setImageUrl(String imageUrl) { 31 | this.imageUrl = imageUrl; 32 | } 33 | 34 | public String getResult() { 35 | return result; 36 | } 37 | 38 | public void setResult(String result) { 39 | this.result = result; 40 | } 41 | 42 | public int getScore() { 43 | return score; 44 | } 45 | public void setScore(int score) { 46 | this.score = score; 47 | } 48 | 49 | public int getWikiId() { 50 | return wikiId; 51 | } 52 | 53 | public void setWikiId(int wikiId) { 54 | this.wikiId = wikiId; 55 | } 56 | 57 | public List getBox() { 58 | return box; 59 | } 60 | 61 | public void setBox(List box) { 62 | this.box = box; 63 | } 64 | } 65 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/response/Response.java: -------------------------------------------------------------------------------- 1 | package com.dfs.response; 2 | 3 | /** 4 | * @author taoxy 2019/1/3 5 | */ 6 | public class Response { 7 | private String status; 8 | private String msg; 9 | private Object content; 10 | 11 | public String getStatus() { 12 | return status; 13 | } 14 | 15 | public void setStatus(String status) { 16 | this.status = status; 17 | } 18 | 19 | public String getMsg() { 20 | return msg; 21 | } 22 | 23 | public void setMsg(String msg) { 24 | this.msg = msg; 25 | } 26 | 27 | public Object getContent() { 28 | return content; 29 | } 30 | 31 | public void setContent(Object content) { 32 | this.content = content; 33 | } 34 | } 35 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/service/SenseAgroAdminService.java: -------------------------------------------------------------------------------- 1 | package com.dfs.service; 2 | 3 | import com.dfs.mapper.SenseAgroAdminMapper; 4 | import com.dfs.entity.SenseAgroAdmin; 5 | import org.springframework.beans.factory.annotation.Autowired; 6 | import org.springframework.stereotype.Service; 7 | import org.springframework.transaction.annotation.Isolation; 8 | import org.springframework.transaction.annotation.Propagation; 9 | import org.springframework.transaction.annotation.Transactional; 10 | 11 | /** 12 | * Title: UserService.java 13 | * Description: 对用户相关的业务逻辑的抽象(面向接口编程) 14 | */ 15 | 16 | /** 17 | * @author taoxy 2019/01/02 18 | */ 19 | @Service 20 | @Transactional(propagation = Propagation.REQUIRED, isolation = Isolation.DEFAULT) 21 | public class SenseAgroAdminService { 22 | 23 | @Autowired 24 | private SenseAgroAdminMapper senseAgroAdminMapper; 25 | 26 | /** 27 | * @description 用户登录逻辑 28 | */ 29 | public SenseAgroAdmin login(String name, String passwd) { 30 | return senseAgroAdminMapper.findUserBynameAndPasswd(name, passwd); 31 | } 32 | } 33 | 34 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/service/SenseAgroAppService.java: -------------------------------------------------------------------------------- 1 | package com.dfs.service; 2 | 3 | import com.dfs.mapper.SenseAgroUserMapper; 4 | import com.dfs.entity.SenseAgroUser; 5 | import org.springframework.beans.factory.annotation.Autowired; 6 | import org.springframework.stereotype.Service; 7 | import org.springframework.transaction.annotation.Isolation; 8 | import org.springframework.transaction.annotation.Propagation; 9 | import org.springframework.transaction.annotation.Transactional; 10 | 11 | import java.util.List; 12 | 13 | /** 14 | * @author taoxy 2019/02/02 15 | */ 16 | @Service 17 | @Transactional(propagation = Propagation.REQUIRED, isolation = Isolation.DEFAULT) 18 | public class SenseAgroAppService { 19 | @Autowired 20 | private SenseAgroUserMapper senseAgroUserMapper; 21 | 22 | //判断登录是否有效 23 | public synchronized List findAppUserByToken(int nowTime, String sessionId) { 24 | return senseAgroUserMapper.findUserByToken(nowTime, sessionId); 25 | } 26 | } 27 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/service/SenseAgroMemberService.java: -------------------------------------------------------------------------------- 1 | package com.dfs.service; 2 | 3 | import com.dfs.mapper.SenseAgroMemberMapper; 4 | import com.dfs.entity.SenseAgroMember; 5 | import com.dfs.utils.RedisSingletonUtil; 6 | import com.dfs.utils.StringUtil; 7 | import org.springframework.beans.factory.annotation.Autowired; 8 | import org.springframework.stereotype.Service; 9 | import org.springframework.transaction.annotation.Isolation; 10 | import org.springframework.transaction.annotation.Propagation; 11 | import org.springframework.transaction.annotation.Transactional; 12 | 13 | import java.util.List; 14 | 15 | /** 16 | * @author taoxy 2018/12/13 17 | */ 18 | @Service 19 | @Transactional(propagation = Propagation.REQUIRED, isolation = Isolation.DEFAULT) 20 | public class SenseAgroMemberService { 21 | 22 | private static final RedisSingletonUtil redisUtil = new RedisSingletonUtil(); 23 | 24 | @Autowired 25 | private SenseAgroMemberMapper senseAgroMemberMapper; 26 | 27 | public SenseAgroMember findMember(String openid) { 28 | if (StringUtil.isEmpty(openid)) return null; 29 | SenseAgroMember senseAgroMember = null; 30 | try { 31 | senseAgroMember = redisUtil.getSenseAgroMember(openid); 32 | if (senseAgroMember != null) { 33 | return senseAgroMember; 34 | } 35 | senseAgroMember = senseAgroMemberMapper.selectByOpenId(openid); 36 | redisUtil.setSenseAgroMember(openid, senseAgroMember, 1); 37 | return senseAgroMember; 38 | } catch (Exception e) { 39 | senseAgroMember = senseAgroMemberMapper.selectByOpenId(openid); 40 | redisUtil.setSenseAgroMember(openid, senseAgroMember, 1); 41 | return senseAgroMember; 42 | } 43 | } 44 | } 45 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/service/SenseAgroSpecialistService.java: -------------------------------------------------------------------------------- 1 | package com.dfs.service; 2 | 3 | import com.dfs.mapper.SenseAgroSpecialistMapper; 4 | import com.dfs.mapper.SenseAgroUserMapper; 5 | import com.dfs.entity.SenseAgroSpecialist; 6 | import com.dfs.entity.SenseAgroUser; 7 | import org.apache.log4j.Logger; 8 | import org.springframework.beans.factory.annotation.Autowired; 9 | import org.springframework.dao.DataAccessException; 10 | import org.springframework.dao.DuplicateKeyException; 11 | import org.springframework.stereotype.Service; 12 | import org.springframework.transaction.annotation.Isolation; 13 | import org.springframework.transaction.annotation.Propagation; 14 | import org.springframework.transaction.annotation.Transactional; 15 | 16 | import java.sql.SQLIntegrityConstraintViolationException; 17 | 18 | /** 19 | * @author taoxy 2019/01/30 20 | */ 21 | @Service 22 | @Transactional(propagation = Propagation.REQUIRED, isolation = Isolation.DEFAULT) 23 | public class SenseAgroSpecialistService { 24 | @Autowired 25 | private SenseAgroSpecialistMapper senseAgroSpecialistMapper; 26 | @Autowired 27 | private SenseAgroUserMapper senseAgroUserMapper; 28 | 29 | private static final Logger logger = Logger.getLogger(SenseAgroSpecialistService.class); 30 | 31 | /** 32 | * @description 用户登录逻辑 33 | */ 34 | public SenseAgroSpecialist login(String name, String passwd) { 35 | return senseAgroSpecialistMapper.findUserBynameAndPasswd(name, passwd); 36 | } 37 | public int addSenseAgroUser(SenseAgroUser senseAgroUser) { 38 | return senseAgroUserMapper.insertSelective(senseAgroUser); 39 | } 40 | 41 | } 42 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/Captcha.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils; 2 | 3 | import java.awt.*; 4 | import java.awt.image.BufferedImage; 5 | import java.io.OutputStream; 6 | import java.util.HashMap; 7 | import java.util.Map; 8 | import java.util.Random; 9 | 10 | /** 11 | * @author taoxy 2018/12/17 12 | */ 13 | public class Captcha { 14 | private static char mapTable[] = { 15 | '0', '1', '2', '3', '4', '5', 16 | '6', '7', '8', '9', '0', '1', 17 | '2', '3', '4', '5', '6', '7', 18 | '8', '9'}; 19 | public static Map getImageCode(int width, int height) { 20 | Map returnMap = new HashMap(); 21 | if (width <= 0) width = 60; 22 | if (height <= 0) height = 20; 23 | BufferedImage image = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB); 24 | // 获取图形上下文 25 | Graphics g = image.getGraphics(); 26 | //生成随机类 27 | Random random = new Random(); 28 | // 设定背景色 29 | g.setColor(getRandColor(200, 250)); 30 | g.fillRect(0, 0, width, height); 31 | //设定字体 32 | g.setFont(new Font("Times New Roman", Font.PLAIN, 18)); 33 | // 随机产生168条干扰线,使图象中的认证码不易被其它程序探测到 34 | g.setColor(getRandColor(160, 200)); 35 | for (int i = 0; i < 168; i++) { 36 | int x = random.nextInt(width); 37 | int y = random.nextInt(height); 38 | int xl = random.nextInt(12); 39 | int yl = random.nextInt(12); 40 | g.drawLine(x, y, x + xl, y + yl); 41 | } 42 | //取随机产生的码 43 | String strEnsure = ""; 44 | //4代表4位验证码,如果要生成更多位的认证码,则加大数值 45 | for (int i = 0; i < 4; ++i) { 46 | strEnsure += mapTable[(int) (mapTable.length * Math.random())]; 47 | // 将认证码显示到图象中 48 | g.setColor(new Color(20 + random.nextInt(110), 20 + random.nextInt(110), 20 + random.nextInt(110))); 49 | // 直接生成 50 | String str = strEnsure.substring(i, i + 1); 51 | // 设置随便码在背景图图片上的位置 52 | g.drawString(str, 13 * i + 20, 25); 53 | } 54 | // 释放图形上下文 55 | g.dispose(); 56 | returnMap.put("image",image); 57 | returnMap.put("strEnsure",strEnsure); 58 | return returnMap; 59 | } 60 | //给定范围获得随机颜色 61 | static Color getRandColor(int fc, int bc) { 62 | Random random = new Random(); 63 | if (fc > 255) fc = 255; 64 | if (bc > 255) bc = 255; 65 | int r = fc + random.nextInt(bc - fc); 66 | int g = fc + random.nextInt(bc - fc); 67 | int b = fc + random.nextInt(bc - fc); 68 | return new Color(r, g, b); 69 | } 70 | } 71 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/CheckSumBuilder.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils; 2 | 3 | import java.security.MessageDigest; 4 | /** 5 | * @author taoxy 2019/03/14 6 | */ 7 | public class CheckSumBuilder { 8 | // 计算并获取CheckSum 9 | public static String getCheckSum(String appSecret, String nonce, String curTime) { 10 | return encode("sha1", appSecret + nonce + curTime); 11 | } 12 | 13 | // 计算并获取md5值 14 | public static String getMD5(String requestBody) { 15 | return encode("md5", requestBody); 16 | } 17 | 18 | private static String encode(String algorithm, String value) { 19 | if (value == null) { 20 | return null; 21 | } 22 | try { 23 | MessageDigest messageDigest 24 | = MessageDigest.getInstance(algorithm); 25 | messageDigest.update(value.getBytes()); 26 | return getFormattedText(messageDigest.digest()); 27 | } catch (Exception e) { 28 | throw new RuntimeException(e); 29 | } 30 | } 31 | private static String getFormattedText(byte[] bytes) { 32 | int len = bytes.length; 33 | StringBuilder buf = new StringBuilder(len * 2); 34 | for (int j = 0; j < len; j++) { 35 | buf.append(HEX_DIGITS[(bytes[j] >> 4) & 0x0f]); 36 | buf.append(HEX_DIGITS[bytes[j] & 0x0f]); 37 | } 38 | return buf.toString(); 39 | } 40 | private static final char[] HEX_DIGITS = { '0', '1', '2', '3', '4', '5', 41 | '6', '7', '8', '9', 'a', 'b', 'c', 'd', 'e', 'f' }; 42 | } -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/CodecUtil.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils; 2 | 3 | import java.util.UUID; 4 | 5 | 6 | /** 7 | * @author taoxy 2019/1/3 8 | */ 9 | public class CodecUtil { 10 | 11 | public static String createUUID(){ 12 | return UUID.randomUUID().toString(); 13 | } 14 | } 15 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/CollectionUtil.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils; 2 | 3 | import java.util.Collection; 4 | 5 | 6 | /** 7 | * @author taoxy 2019/1/3 8 | */ 9 | public class CollectionUtil { 10 | public static boolean isNotEmpty(Collection c){ 11 | if (c != null && c.size() != 0 ) { 12 | return true; 13 | } 14 | return false; 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/Constants.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils; 2 | 3 | /** 4 | * @author taoxy 2019/1/3 5 | */ 6 | public class Constants { 7 | 8 | /** 9 | * 存储当前登录用户id的字段名 10 | */ 11 | public static final String CURRENT_USER_ID = "CURRENT_USER_ID"; 12 | 13 | /** 14 | * token有效期(小时) 15 | */ 16 | public static final int TOKEN_EXPIRES_HOUR = 6; 17 | 18 | /** 19 | * 存放Token的header字段 20 | */ 21 | public static final String DEFAULT_TOKEN_NAME = "token"; 22 | /** 23 | * 密码正则 24 | * 不能全部是数字 25 | * 不能全部是字母 26 | * 必须是数字或字母 27 | */ 28 | public static final String regex = "^(?![0-9]+$)(?![a-zA-Z]+$)[0-9A-Za-z]{8,16}$"; 29 | } 30 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/DesUtil.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils; 2 | 3 | import java.io.IOException; 4 | import java.io.UnsupportedEncodingException; 5 | import java.security.*; 6 | import javax.crypto.*; 7 | import javax.crypto.spec.DESKeySpec; 8 | import javax.crypto.spec.SecretKeySpec; 9 | 10 | /** 11 | * DES加密工具类 12 | * 13 | * @author 陶星袁 14 | * @date 2018-9-12 15 | */ 16 | public class DesUtil { 17 | private static final String KEY = "19930701329455536senseagrocomccc"; 18 | 19 | // private static final String KEY ="inspur_OTA-upgrade~!@#$%^&*()"; 20 | public static String encrypt(String strDataToEncrypt) { 21 | byte[] key = KEY.getBytes(); 22 | Provider sunJCE = new com.sun.crypto.provider.SunJCE(); 23 | Security.addProvider(sunJCE); 24 | String strAlgorithm = "DES"; 25 | SecretKeySpec keySpec = null; 26 | DESKeySpec deskey = null; 27 | String strResult = ""; 28 | try { 29 | deskey = new DESKeySpec(key); 30 | keySpec = new SecretKeySpec(deskey.getKey(), "DES"); 31 | Cipher cipher = Cipher.getInstance(strAlgorithm); 32 | cipher.init(Cipher.ENCRYPT_MODE, keySpec); 33 | byte[] utf8 = strDataToEncrypt.getBytes("UTF8"); 34 | byte[] enc = cipher.doFinal(utf8); 35 | strResult = new sun.misc.BASE64Encoder().encode(enc); 36 | } catch (NoSuchAlgorithmException e) { 37 | e.printStackTrace(); 38 | } catch (NoSuchPaddingException e) { 39 | e.printStackTrace(); 40 | } catch (InvalidKeyException e) { 41 | e.printStackTrace(); 42 | } catch (UnsupportedEncodingException e) { 43 | e.printStackTrace(); 44 | } catch (IllegalBlockSizeException e) { 45 | e.printStackTrace(); 46 | } catch (BadPaddingException e) { 47 | e.printStackTrace(); 48 | } 49 | return strResult; 50 | } 51 | 52 | public static String decrypt(String strDataToDecrypt) throws IOException { 53 | byte[] key = KEY.getBytes(); 54 | Provider sunJCE = new com.sun.crypto.provider.SunJCE(); 55 | Security.addProvider(sunJCE); 56 | String strAlgorithm = "DES"; 57 | SecretKeySpec keySpec = null; 58 | DESKeySpec deskey = null; 59 | String strResult = ""; 60 | try { 61 | deskey = new DESKeySpec(key); 62 | keySpec = new SecretKeySpec(deskey.getKey(), "DES"); 63 | Cipher cipher = Cipher.getInstance(strAlgorithm); 64 | cipher.init(Cipher.DECRYPT_MODE, keySpec); 65 | byte[] dec = new sun.misc.BASE64Decoder().decodeBuffer(strDataToDecrypt); 66 | byte[] utf8 = cipher.doFinal(dec); 67 | return new String(utf8, "UTF8"); 68 | } catch (NoSuchAlgorithmException e) { 69 | e.printStackTrace(); 70 | } catch (NoSuchPaddingException e) { 71 | e.printStackTrace(); 72 | } catch (InvalidKeyException e) { 73 | e.printStackTrace(); 74 | } catch (IllegalBlockSizeException e) { 75 | e.printStackTrace(); 76 | } catch (BadPaddingException e) { 77 | e.printStackTrace(); 78 | } 79 | return strResult; 80 | 81 | } 82 | } 83 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/EmojiUtil.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils; 2 | 3 | import java.io.UnsupportedEncodingException; 4 | import java.net.URLDecoder; 5 | import java.util.regex.Matcher; 6 | import java.util.regex.Pattern; 7 | import java.net.URLEncoder; 8 | 9 | /** 10 | * @author taoxy 2019/1/9 11 | */ 12 | public class EmojiUtil { 13 | 14 | 15 | public static String filterEmoji(String source) { 16 | if(source != null) 17 | { 18 | Pattern emoji = Pattern.compile ("[\ud83c\udc00-\ud83c\udfff]|[\ud83d\udc00-\ud83d\udfff]|[\u2600-\u27ff]",Pattern.UNICODE_CASE | Pattern. CASE_INSENSITIVE ) ; 19 | Matcher emojiMatcher = emoji.matcher(source); 20 | if ( emojiMatcher.find()) 21 | { 22 | source = emojiMatcher.replaceAll("*"); 23 | return source ; 24 | } 25 | return source; 26 | } 27 | return source; 28 | } 29 | public static String emojiConvert(String str) { 30 | String patternString = "([\\x{10000}-\\x{10ffff}\ud800-\udfff])"; 31 | Pattern pattern = Pattern.compile(patternString); 32 | Matcher matcher = pattern.matcher(str); 33 | StringBuffer sb = new StringBuffer(); 34 | while(matcher.find()) { 35 | try { 36 | matcher.appendReplacement(sb, "[[EMOJI:" + URLEncoder.encode(matcher.group(1),"UTF-8") + "]]"); 37 | } catch(UnsupportedEncodingException e) { 38 | return str; 39 | } 40 | } 41 | matcher.appendTail(sb); 42 | return sb.toString(); 43 | } 44 | 45 | public static String emojiRecovery(String str) { 46 | String patternString = "\\[\\[EMOJI:(.*?)\\]\\]"; 47 | Pattern pattern = Pattern.compile(patternString); 48 | Matcher matcher = pattern.matcher(str); 49 | StringBuffer sb = new StringBuffer(); 50 | while (matcher.find()) { 51 | try { 52 | matcher.appendReplacement(sb, URLDecoder.decode(matcher.group(1), "UTF-8")); 53 | } catch (UnsupportedEncodingException e) { 54 | e.printStackTrace(); 55 | } 56 | } 57 | matcher.appendTail(sb); 58 | return sb.toString(); 59 | } 60 | } 61 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/FileUploadUtil.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils; 2 | 3 | import java.io.File; 4 | import java.io.IOException; 5 | import java.text.SimpleDateFormat; 6 | import java.util.Date; 7 | 8 | import org.apache.log4j.Logger; 9 | import org.springframework.web.multipart.MultipartFile; 10 | 11 | /** 12 | * @author taoxy 2019/1/9 13 | */ 14 | public class FileUploadUtil { 15 | 16 | private static final Logger logger = Logger.getLogger(FileUploadUtil.class); 17 | 18 | /** 19 | * 上传图片 20 | * 21 | * @param multipartFile 22 | * @return 23 | * @throws IOException 24 | */ 25 | public static String uploadImage(MultipartFile multipartFile) throws IOException { 26 | String dirPath = (ResourceUtil.chat() + new SimpleDateFormat("yyyyMMdd").format(new Date())); 27 | File dir = new File(ResourceUtil.dataDir() + File.separator + dirPath); 28 | if (!dir.exists()) { 29 | dir.mkdirs(); 30 | } 31 | Runtime.getRuntime().exec("chmod -R 777 " + dir); 32 | String filePath = dirPath + File.separator + StringUtil.createUUID() + ".jpg"; 33 | File file = new File(ResourceUtil.dataDir() + File.separator + filePath); 34 | if (!file.exists()) { 35 | file.createNewFile(); 36 | } 37 | Runtime.getRuntime().exec("chmod -R 777 " + file); 38 | multipartFile.transferTo(file); 39 | return filePath; 40 | } 41 | 42 | /** 43 | * 上传文件 44 | * 45 | * @param multipartFile 46 | * @return 47 | * @throws IOException 48 | */ 49 | public static String uploadImage(MultipartFile multipartFile, String businessName) throws IOException { 50 | String dirPath = (businessName + "/" + new SimpleDateFormat("yyyyMMdd").format(new Date())); 51 | File dir = new File(ResourceUtil.dataDir() + "/" + dirPath); 52 | logger.info("上传文件,文件上传目录:{}" + dirPath); 53 | if (!dir.exists()) { 54 | dir.mkdirs(); 55 | } 56 | Runtime.getRuntime().exec("chmod -R 777 " + dir); 57 | String filename = multipartFile.getOriginalFilename();// 获取上传的文件的名称 58 | String prefix = filename.substring(filename.lastIndexOf(".") + 1);//获取后缀 59 | String filePath = dirPath + "/" + StringUtil.createUUID() + "." + prefix; 60 | logger.info("上传文件,开始创建目标文件,文件完整路径:{}"+filePath); 61 | File file = new File(ResourceUtil.dataDir() + "/" + filePath); 62 | if (!file.exists()) { 63 | file.createNewFile(); 64 | } 65 | logger.info("上传文件,文件完整路径:{}"+file.getAbsolutePath()); 66 | // ImageUtil.transPictureTojpg(multipartFile, file); 67 | Runtime.getRuntime().exec("chmod -R 777 " + file); 68 | multipartFile.transferTo(file); 69 | return filePath; 70 | } 71 | } 72 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/HtmlToText.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils; 2 | 3 | import javax.swing.text.html.HTMLEditorKit; 4 | import javax.swing.text.html.parser.ParserDelegator; 5 | import java.io.*; 6 | /** 7 | * 将富文本转换为文本 8 | * @author taoxy 2019/1/9 9 | */ 10 | public class HtmlToText extends HTMLEditorKit.ParserCallback { 11 | private static HtmlToText html2Text = new HtmlToText(); 12 | 13 | StringBuffer stringBuffer; 14 | 15 | private HtmlToText() { 16 | } 17 | 18 | public void parse(String str) throws IOException { 19 | 20 | InputStream iin = new ByteArrayInputStream(str.getBytes()); 21 | Reader in = new InputStreamReader(iin); 22 | stringBuffer = new StringBuffer(); 23 | ParserDelegator delegator = new ParserDelegator(); 24 | // the third parameter is TRUE to ignore charset directive 25 | delegator.parse(in, this, Boolean.TRUE); 26 | iin.close(); 27 | in.close(); 28 | } 29 | 30 | public void handleText(char[] text, int pos) { 31 | stringBuffer.append(text); 32 | } 33 | 34 | public String getText() { 35 | return stringBuffer.toString(); 36 | } 37 | 38 | public static String getContent(String str) { 39 | try { 40 | html2Text.parse(str); 41 | } catch (IOException e) { 42 | // TODO Auto-generated catch block 43 | e.printStackTrace(); 44 | } 45 | return html2Text.getText(); 46 | } 47 | } -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/ImageUtil.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils; 2 | 3 | 4 | import org.apache.log4j.Logger; 5 | import org.springframework.web.multipart.MultipartFile; 6 | 7 | import javax.imageio.ImageIO; 8 | import java.awt.*; 9 | import java.awt.image.BufferedImage; 10 | import java.io.File; 11 | import java.io.IOException; 12 | 13 | import static com.dfs.utils.FileUtil.deleteTmpfile; 14 | 15 | /** 16 | * @author taoxy 2019/1/3 17 | */ 18 | public class ImageUtil { 19 | 20 | private static final Logger logger = Logger.getLogger(FileUploadUtil.class); 21 | 22 | 23 | public static void transPictureTojpg(MultipartFile imageFile, File file) throws IOException { 24 | File tmpFile = null; 25 | try { 26 | if (imageFile.getName().contains(".jpg") || imageFile.getName().contains(".JPG")) { 27 | imageFile.transferTo(file); 28 | //将png图片转格式为jpg 29 | } else { 30 | tmpFile = File.createTempFile("tmp", ".png"); 31 | logger.info("创建格式转换临时文件完成,文件完整路径:{}" + tmpFile.getAbsolutePath()); 32 | imageFile.transferTo(tmpFile); 33 | BufferedImage bufferedImage = ImageIO.read(tmpFile); 34 | BufferedImage newBufferedImage = new BufferedImage(bufferedImage.getWidth(), bufferedImage.getHeight(), BufferedImage.TYPE_INT_RGB); 35 | newBufferedImage.createGraphics().drawImage(bufferedImage, 0, 0, Color.WHITE, null); 36 | ImageIO.write(newBufferedImage, "jpg", file); 37 | } 38 | } catch (Exception e) { 39 | 40 | } finally { 41 | deleteTmpfile(tmpFile); 42 | } 43 | 44 | } 45 | } 46 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/JsonUtils.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils; 2 | 3 | 4 | import com.google.gson.*; 5 | import com.google.gson.reflect.TypeToken; 6 | 7 | import java.lang.reflect.Type; 8 | import java.util.*; 9 | 10 | /** 11 | * @author taoxy 2019/1/3 12 | */ 13 | public class JsonUtils { 14 | 15 | 16 | /** 17 | * java对象转字符串 18 | * @return 19 | */ 20 | public static String toJsonWithGson(Object obj) { 21 | Gson gson = new Gson(); 22 | return gson.toJson(obj); 23 | } 24 | 25 | /** 26 | * json字符串转java对象 27 | * @param json 28 | * @param typeOfT 29 | * @return 30 | */ 31 | public static Object toObjectFromString(String json, Type typeOfT) { 32 | Gson gson = new Gson(); 33 | Object obj = gson.fromJson(json, typeOfT); 34 | return obj; 35 | } 36 | 37 | /** 38 | * java复杂类型对象转字符串 39 | * @param obj 40 | * @param type 41 | * @return 42 | */ 43 | public static String toJsonWithGson(Object obj, Type type) { 44 | Gson gson = new Gson(); 45 | return gson.toJson(obj, type); 46 | } 47 | 48 | /** 49 | * 非泛型List json 返回 50 | * @param list 51 | * @return 52 | */ 53 | @SuppressWarnings("rawtypes") 54 | public static String getSimpleListJson(List list) { 55 | Gson gson = new GsonBuilder().setDateFormat("yyyy-MM-dd HH:mm:ss") 56 | .create(); 57 | String listToJson = gson.toJson(list); 58 | return listToJson; 59 | } 60 | 61 | /** 62 | * 非泛型 Map json 返回 63 | * @param map 64 | * @return 65 | */ 66 | public static String getSimpleMapJson(Map map) { 67 | Gson gson = new GsonBuilder().setDateFormat("yyyy-MM-dd HH:mm:ss") 68 | .create(); 69 | String listToJson = gson.toJson(map); 70 | return listToJson; 71 | } 72 | 73 | /** 74 | * 泛型约束List 转换 75 | * @param list 76 | * @return 77 | */ 78 | public static String getGenericList(List list) { 79 | Type type = new TypeToken>() { 80 | }.getType(); 81 | Gson gson = new GsonBuilder().setDateFormat("yyyy-MM-dd HH:mm:ss") 82 | .create(); 83 | return gson.toJson(list, type); 84 | } 85 | 86 | 87 | /** 88 | * Ajax 请求结果反馈(主要针对添加、删除、更新) 89 | * @param result 处理结果 90 | * @param reson 处理状态 91 | * @return 92 | */ 93 | public static String operatorStatue(boolean result, String reson) { 94 | Map resultMap = new HashMap(); 95 | resultMap.put("result", result); 96 | resultMap.put("reson", reson); 97 | return JsonUtils.getSimpleMapJson(resultMap); 98 | } 99 | 100 | /** 101 | * Ajax 请求结果反馈(主要针对修改对象)带有反馈对象 102 | * @param result 处理结果 103 | * @param reson 处理状态 104 | * @return 105 | */ 106 | public static String operatorStatueWithObj(Object object, boolean result, String reson) { 107 | Map resultMap = new HashMap(); 108 | resultMap.put("obj", object); 109 | resultMap.put("result", result); 110 | resultMap.put("reson", reson); 111 | return JsonUtils.getSimpleMapJson(resultMap); 112 | } 113 | 114 | /** 115 | * 对象转Json 116 | * 117 | * @return 118 | */ 119 | public static String getJAVABeanJSON(Object o) { 120 | Gson gson = new GsonBuilder().setDateFormat("yyyy-MM-dd HH:mm:ss") 121 | .create(); 122 | 123 | String ObjtToJson = gson.toJson(o); 124 | return ObjtToJson; 125 | } 126 | 127 | /** 128 | * Json 转map 结构 129 | * 130 | * @param data 131 | * @return 132 | */ 133 | public static Map jsonToMap(String data) { 134 | GsonBuilder gb = new GsonBuilder(); 135 | Gson g = gb.create(); 136 | Map map = g.fromJson(data, 137 | new TypeToken>() { 138 | }.getType()); 139 | return map; 140 | } 141 | 142 | @SuppressWarnings("unused") 143 | private static class UtilDateSerializer implements JsonSerializer, 144 | JsonDeserializer { 145 | 146 | public JsonElement serialize(Date date, Type type, 147 | JsonSerializationContext context) { 148 | return new JsonPrimitive(date.getTime()); 149 | } 150 | 151 | public Date deserialize(JsonElement element, Type type, 152 | JsonDeserializationContext context) throws JsonParseException { 153 | return new Date(element.getAsJsonPrimitive().getAsLong()); 154 | } 155 | 156 | } 157 | 158 | @SuppressWarnings("unused") 159 | private static class UtilCalendarSerializer implements 160 | JsonSerializer, JsonDeserializer { 161 | public JsonElement serialize(Calendar cal, Type type, 162 | JsonSerializationContext context) { 163 | return new JsonPrimitive(Long.valueOf(cal.getTimeInMillis())); 164 | } 165 | 166 | public Calendar deserialize(JsonElement element, Type type, 167 | JsonDeserializationContext context) throws JsonParseException { 168 | Calendar cal = Calendar.getInstance(); 169 | cal.setTimeInMillis(element.getAsJsonPrimitive().getAsLong()); 170 | return cal; 171 | } 172 | } 173 | 174 | /** 175 | * java对象转字符串 176 | * @param 泛型占位符 177 | * @param obj T 178 | * @return String 179 | */ 180 | public static String toJson(T obj) { 181 | Gson gson = new GsonBuilder().setDateFormat("yyyy-MM-dd HH:mm:ss").enableComplexMapKeySerialization().create(); 182 | return gson.toJson(obj); 183 | } 184 | 185 | 186 | /** 187 | * java对象转字符串 188 | * @param obj 被转对象 189 | * @param dateFormatter 自定义日期格式 190 | * @return 191 | */ 192 | public static String toJson(T obj, String dateFormatter) { 193 | Gson gson = new GsonBuilder().setDateFormat(dateFormatter).enableComplexMapKeySerialization().create(); 194 | return gson.toJson(obj); 195 | } 196 | 197 | /** 198 | * @param 泛型占位符 199 | * @param json String 字符串 200 | * @param type Type 201 | * @return T 转换后的结果对象 202 | */ 203 | @SuppressWarnings("unchecked") 204 | public static T fromJson(String json, Type type) { 205 | Gson gson = new GsonBuilder().setDateFormat("yyyy-MM-dd HH:mm:ss").create(); 206 | Object obj = gson.fromJson(json, type); 207 | return (T) obj; 208 | } 209 | 210 | /** 211 | * json字符串转java对象 212 | * 213 | * @param json json 数据串 214 | * @param type Gson type 类型 215 | * @param dateFormat 日期格式 216 | * @return T 217 | */ 218 | @SuppressWarnings("unchecked") 219 | public static T fromJson(String json, Type type, String dateFormat) { 220 | Gson gson = new GsonBuilder().setDateFormat(dateFormat).create(); 221 | Object obj = gson.fromJson(json, type); 222 | return (T) obj; 223 | } 224 | 225 | /** 226 | * json 转 map 227 | * 228 | * @param json json 数据串 229 | * @return Map 230 | */ 231 | public static Map json2Map(String json) { 232 | GsonBuilder gb = new GsonBuilder(); 233 | Gson g = gb.create(); 234 | Map map = g.fromJson(json, new TypeToken>() { 235 | }.getType()); 236 | return map; 237 | } 238 | 239 | /** 240 | * 解析JSON为原始JsonElement 241 | * 242 | * @param json json串 243 | * @return JsonElement 244 | */ 245 | public static JsonElement fromJson(String json) { 246 | return new JsonParser().parse(json); 247 | } 248 | 249 | 250 | /** 251 | * map转换为json,并让=不转义 252 | * 253 | * @param tempMap 254 | * @return 255 | */ 256 | public static String map2Json(Map tempMap) { 257 | Gson gson = new GsonBuilder().disableHtmlEscaping().create(); 258 | return gson.toJson(tempMap); 259 | } 260 | 261 | public static String getJsonStringParam(String userInfo, String param) { 262 | JsonParser parser = new JsonParser(); 263 | JsonObject jsonObject = (JsonObject) parser.parse(userInfo); 264 | if (jsonObject.get(param) == null) { 265 | return null; 266 | } else { 267 | try { 268 | String s = jsonObject.get(param).getAsString(); 269 | if (StringUtil.isEmpty(s)) { 270 | return null; 271 | } 272 | return jsonObject.get(param).getAsString(); 273 | } catch (Exception e) { 274 | String s = jsonObject.get(param).toString(); 275 | if (StringUtil.isEmpty(s)) { 276 | return null; 277 | } 278 | return jsonObject.get(param).toString(); 279 | } 280 | } 281 | } 282 | 283 | public static Integer getJsonIntParam(String userInfo, String param) { 284 | JsonParser parser = new JsonParser(); 285 | JsonObject jsonObject = (JsonObject) parser.parse(userInfo); 286 | if (jsonObject.get(param) == null){ 287 | return -1; 288 | }else { 289 | try{ 290 | Integer s = jsonObject.get(param).getAsInt(); 291 | if (s==null){ 292 | return -1; 293 | } 294 | return s; 295 | }catch (Exception e){ 296 | return -1; 297 | } 298 | } 299 | } 300 | 301 | public static List> json2ListMap(String s) { 302 | Gson gson = new Gson(); 303 | List> resultList = gson.fromJson(s, new TypeToken>>() { 304 | }.getType()); 305 | return resultList; 306 | } 307 | 308 | public static List> json2ListList(String s) { 309 | try { 310 | Gson gson = new Gson(); 311 | List> result = gson.fromJson(s, new TypeToken>>() { 312 | }.getType()); 313 | return result; 314 | } catch (Exception e) { 315 | e.printStackTrace(); 316 | return null; 317 | } 318 | 319 | } 320 | 321 | public static List json2List(String s) { 322 | try { 323 | Gson gson = new Gson(); 324 | List resultList = gson.fromJson(s, new TypeToken>() { 325 | }.getType()); 326 | return resultList; 327 | } catch (Exception e) { 328 | e.printStackTrace(); 329 | return null; 330 | } 331 | 332 | } 333 | public static List getJsonListParam(String userInfo, String param) { 334 | JsonParser parser = new JsonParser(); 335 | JsonObject jsonObject = (JsonObject) parser.parse(userInfo); 336 | if (jsonObject.get(param) == null){ 337 | return null; 338 | }else { 339 | try{ 340 | Gson gson = new Gson(); 341 | List resultList = gson.fromJson(jsonObject.get(param), new TypeToken>() { 342 | }.getType()); 343 | return resultList; 344 | }catch (Exception e){ 345 | return null; 346 | } 347 | } 348 | } 349 | } 350 | 351 | 352 | 353 | 354 | 355 | 356 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/Md5.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils; 2 | 3 | import java.security.MessageDigest; 4 | import java.security.NoSuchAlgorithmException; 5 | 6 | /** 7 | * @author taoxy 2019/1/3 8 | */ 9 | public class Md5 { 10 | 11 | /* 12 | * MD5 算法 13 | */ 14 | 15 | // 全局数组 16 | private final static String[] strDigits = { "0", "1", "2", "3", "4", "5", 17 | "6", "7", "8", "9", "a", "b", "c", "d", "e", "f" }; 18 | 19 | public Md5() { 20 | } 21 | 22 | // 返回形式为数字跟字符串 23 | private static String byteToArrayString(byte bByte) { 24 | int iRet = bByte; 25 | // System.out.println("iRet="+iRet); 26 | if (iRet < 0) { 27 | iRet += 256; 28 | } 29 | int iD1 = iRet / 16; 30 | int iD2 = iRet % 16; 31 | return strDigits[iD1] + strDigits[iD2]; 32 | } 33 | 34 | // 返回形式只为数字 35 | private static String byteToNum(byte bByte) { 36 | int iRet = bByte; 37 | System.out.println("iRet1=" + iRet); 38 | if (iRet < 0) { 39 | iRet += 256; 40 | } 41 | return String.valueOf(iRet); 42 | } 43 | 44 | // 转换字节数组为16进制字串 45 | private static String byteToString(byte[] bByte) { 46 | StringBuffer sBuffer = new StringBuffer(); 47 | for (int i = 0; i < bByte.length; i++) { 48 | sBuffer.append(byteToArrayString(bByte[i])); 49 | } 50 | return sBuffer.toString(); 51 | } 52 | 53 | public static String GetMD5Code(String strObj) { 54 | String resultString = null; 55 | try { 56 | resultString = new String(strObj); 57 | MessageDigest md = MessageDigest.getInstance("MD5"); 58 | // md.digest() 该函数返回值为存放哈希值结果的byte数组 59 | resultString = byteToString(md.digest(strObj.getBytes())); 60 | } catch (NoSuchAlgorithmException ex) { 61 | ex.printStackTrace(); 62 | } 63 | return resultString; 64 | } 65 | } 66 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/MessageUtils.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils; 2 | 3 | import com.aliyuncs.DefaultAcsClient; 4 | import com.aliyuncs.IAcsClient; 5 | import com.aliyuncs.dysmsapi.model.v20170525.SendSmsRequest; 6 | import com.aliyuncs.dysmsapi.model.v20170525.SendSmsResponse; 7 | import com.aliyuncs.exceptions.ClientException; 8 | import com.aliyuncs.http.MethodType; 9 | import com.aliyuncs.profile.DefaultProfile; 10 | import com.aliyuncs.profile.IClientProfile; 11 | import com.dfs.model.AliyunMessageConfig; 12 | 13 | /** 14 | * @author taoxy 2019/3/13 15 | */ 16 | public class MessageUtils { 17 | 18 | public static Boolean internalTextMessage(String mobile, String singnName, String templateName, String templateParam) throws ClientException { 19 | System.setProperty(AliyunMessageConfig.defaultConnectTimeout, AliyunMessageConfig.time); 20 | System.setProperty(AliyunMessageConfig.defaultReadTimeout, AliyunMessageConfig.time); 21 | IClientProfile profile = DefaultProfile.getProfile("cn-hangzhou", AliyunMessageConfig.accessKeyId, 22 | AliyunMessageConfig.accessKeySecret); 23 | DefaultProfile.addEndpoint("cn-hangzhou", "cn-hangzhou", AliyunMessageConfig.product, AliyunMessageConfig.domain); 24 | IAcsClient acsClient = new DefaultAcsClient(profile); 25 | SendSmsRequest request = new SendSmsRequest(); 26 | request.setMethod(MethodType.POST); 27 | request.setPhoneNumbers(mobile); 28 | request.setSignName(singnName); 29 | request.setTemplateCode(templateName); 30 | request.setTemplateParam(templateParam); 31 | SendSmsResponse sendSmsResponse = acsClient.getAcsResponse(request); 32 | return (sendSmsResponse.getCode() != null && sendSmsResponse.getCode().equals("OK")); 33 | } 34 | } 35 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/PayUtil.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils; 2 | 3 | import org.apache.commons.codec.digest.DigestUtils; 4 | 5 | import java.io.*; 6 | import java.net.HttpURLConnection; 7 | import java.net.URL; 8 | import java.util.*; 9 | 10 | import org.jdom.Document; 11 | import org.jdom.Element; 12 | import org.jdom.input.SAXBuilder; 13 | 14 | /** 15 | * @author taoxy 2019/1/9 16 | */ 17 | public class PayUtil { 18 | /** 19 | * 签名字符串 20 | * 21 | * @param text 需要签名的字符串 22 | * @param key 密钥 23 | * @param input_charset 编码格式 24 | * @return 签名结果 25 | */ 26 | public static String sign(String text, String key, String input_charset) { 27 | text = text + "&key=" + key; 28 | return DigestUtils.md5Hex(getContentBytes(text, input_charset)); 29 | } 30 | 31 | /** 32 | * 签名字符串 33 | * 34 | * @param text 需要签名的字符串 35 | * @param sign 签名结果 36 | * @param key 密钥 37 | * @param input_charset 编码格式 38 | * @return 签名结果 39 | */ 40 | public static boolean verify(String text, String sign, String key, String input_charset) { 41 | text = text + "&key=" + key; 42 | String mysign = DigestUtils.md5Hex(getContentBytes(text, input_charset)).toUpperCase(); 43 | System.out.println("==========mysign=" + mysign + "=============="); 44 | System.out.println("==========sign=" + sign + "=============="); 45 | if (mysign.equals(sign)) { 46 | return true; 47 | } else { 48 | return false; 49 | } 50 | } 51 | 52 | 53 | /** 54 | * @param content 55 | * @param charset 56 | * @return 57 | * @throws java.security.SignatureException 58 | * @throws UnsupportedEncodingException 59 | */ 60 | public static byte[] getContentBytes(String content, String charset) { 61 | if (charset == null || "".equals(charset)) { 62 | return content.getBytes(); 63 | } 64 | try { 65 | return content.getBytes(charset); 66 | } catch (UnsupportedEncodingException e) { 67 | throw new RuntimeException("MD5签名过程中出现错误,指定的编码集不对,您目前指定的编码集是:" + charset); 68 | } 69 | } 70 | 71 | private static boolean isValidChar(char ch) { 72 | if ((ch >= '0' && ch <= '9') || (ch >= 'A' && ch <= 'Z') || (ch >= 'a' && ch <= 'z')) 73 | return true; 74 | if ((ch >= 0x4e00 && ch <= 0x7fff) || (ch >= 0x8000 && ch <= 0x952f)) 75 | return true;// 简体中文汉字编码 76 | return false; 77 | } 78 | 79 | /** 80 | * 除去数组中的空值和签名参数 81 | * 82 | * @param sArray 签名参数组 83 | * @return 去掉空值与签名参数后的新签名参数组 84 | */ 85 | public static Map paraFilter(Map sArray) { 86 | Map result = new HashMap(); 87 | if (sArray == null || sArray.size() <= 0) { 88 | return result; 89 | } 90 | for (String key : sArray.keySet()) { 91 | String value = sArray.get(key); 92 | if (value == null || value.equals("") || key.equalsIgnoreCase("sign")) { 93 | continue; 94 | } 95 | result.put(key, value); 96 | } 97 | return result; 98 | } 99 | 100 | /** 101 | * 把数组所有元素排序,并按照“参数=参数值”的模式用“&”字符拼接成字符串 102 | * 103 | * @param params 需要排序并参与字符拼接的参数组 104 | * @return 拼接后字符串 105 | */ 106 | public static String createLinkString(Map params) { 107 | List keys = new ArrayList<>(params.keySet()); 108 | Collections.sort(keys); 109 | String prestr = ""; 110 | for (int i = 0; i < keys.size(); i++) { 111 | String key = keys.get(i); 112 | String value = params.get(key); 113 | if (i == keys.size() - 1) {// 拼接时,不包括最后一个&字符 114 | prestr = prestr + key + "=" + value; 115 | } else { 116 | prestr = prestr + key + "=" + value + "&"; 117 | } 118 | } 119 | return prestr; 120 | } 121 | 122 | /** 123 | * @param requestUrl 请求地址 124 | * @param requestMethod 请求方法 125 | * @param outputStr 参数 126 | */ 127 | public static String httpRequest(String requestUrl, String requestMethod, String outputStr) { 128 | // 创建SSLContext 129 | StringBuffer buffer = null; 130 | try { 131 | URL url = new URL(requestUrl); 132 | HttpURLConnection conn = (HttpURLConnection) url.openConnection(); 133 | conn.setRequestMethod(requestMethod); 134 | conn.setDoOutput(true); 135 | conn.setDoInput(true); 136 | conn.connect(); 137 | //往服务器端写内容 138 | if (null != outputStr) { 139 | OutputStream os = conn.getOutputStream(); 140 | os.write(outputStr.getBytes("utf-8")); 141 | os.close(); 142 | } 143 | // 读取服务器端返回的内容 144 | InputStream is = conn.getInputStream(); 145 | InputStreamReader isr = new InputStreamReader(is, "utf-8"); 146 | BufferedReader br = new BufferedReader(isr); 147 | buffer = new StringBuffer(); 148 | String line = null; 149 | while ((line = br.readLine()) != null) { 150 | buffer.append(line); 151 | } 152 | br.close(); 153 | } catch (Exception e) { 154 | e.printStackTrace(); 155 | } 156 | return buffer.toString(); 157 | } 158 | 159 | public static String urlEncodeUTF8(String source) { 160 | String result = source; 161 | try { 162 | result = java.net.URLEncoder.encode(source, "UTF-8"); 163 | } catch (UnsupportedEncodingException e) { 164 | // TODO Auto-generated catch block 165 | e.printStackTrace(); 166 | } 167 | return result; 168 | } 169 | 170 | /** 171 | * 解析xml,返回第一级元素键值对。如果第一级元素有子节点,则此节点的值是子节点的xml数据。 172 | * 173 | * @param strxml 174 | * @return 175 | * @throws org.jdom2.JDOMException 176 | * @throws IOException 177 | */ 178 | public static Map doXMLParse(String strxml) throws Exception { 179 | if (null == strxml || "".equals(strxml)) { 180 | return null; 181 | } 182 | 183 | Map m = new HashMap(); 184 | InputStream in = String2Inputstream(strxml); 185 | SAXBuilder builder = new SAXBuilder(); 186 | Document doc = builder.build(in); 187 | Element root = doc.getRootElement(); 188 | List list = root.getChildren(); 189 | Iterator it = list.iterator(); 190 | while (it.hasNext()) { 191 | Element e = (Element) it.next(); 192 | String k = e.getName(); 193 | String v = ""; 194 | List children = e.getChildren(); 195 | if (children.isEmpty()) { 196 | v = e.getTextNormalize(); 197 | } else { 198 | v = getChildrenText(children); 199 | } 200 | 201 | m.put(k, v); 202 | } 203 | 204 | //关闭流 205 | in.close(); 206 | 207 | return m; 208 | } 209 | 210 | /** 211 | * 获取子结点的xml 212 | * 213 | * @param children 214 | * @return String 215 | */ 216 | public static String getChildrenText(List children) { 217 | StringBuffer sb = new StringBuffer(); 218 | if (!children.isEmpty()) { 219 | Iterator it = children.iterator(); 220 | while (it.hasNext()) { 221 | Element e = (Element) it.next(); 222 | String name = e.getName(); 223 | String value = e.getTextNormalize(); 224 | List list = e.getChildren(); 225 | sb.append("<" + name + ">"); 226 | if (!list.isEmpty()) { 227 | sb.append(getChildrenText(list)); 228 | } 229 | sb.append(value); 230 | sb.append(""); 231 | } 232 | } 233 | 234 | return sb.toString(); 235 | } 236 | 237 | public static InputStream String2Inputstream(String str) { 238 | return new ByteArrayInputStream(str.getBytes()); 239 | } 240 | 241 | 242 | 243 | } -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/RequestBodyUtils.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils; 2 | 3 | import java.io.IOException; 4 | import java.io.Reader; 5 | import java.io.StringWriter; 6 | import java.io.Writer; 7 | 8 | /** 9 | * @author taoxy 2019/01/15 10 | * 这是duboo里面的一段源码 11 | */ 12 | public class RequestBodyUtils { 13 | 14 | private static final int BUFFER_SIZE = 1024 * 8; 15 | 16 | /** 17 | * read string. 18 | * 19 | * @param reader Reader instance. 20 | * @return String. 21 | * @throws IOException 22 | */ 23 | public static String read(Reader reader) throws IOException { 24 | StringWriter writer = new StringWriter(); 25 | try { 26 | write(reader, writer); 27 | return writer.getBuffer().toString(); 28 | } finally { 29 | writer.close(); 30 | } 31 | } 32 | 33 | /** 34 | * write. 35 | * 36 | * @param reader Reader. 37 | * @param writer Writer. 38 | * @return count. 39 | * @throws IOException 40 | */ 41 | public static long write(Reader reader, Writer writer) throws IOException { 42 | return write(reader, writer, BUFFER_SIZE); 43 | } 44 | 45 | /** 46 | * write. 47 | * 48 | * @param reader Reader. 49 | * @param writer Writer. 50 | * @param bufferSize buffer size. 51 | * @return count. 52 | * @throws IOException 53 | */ 54 | public static long write(Reader reader, Writer writer, int bufferSize) throws IOException { 55 | int read; 56 | long total = 0; 57 | char[] buf = new char[BUFFER_SIZE]; 58 | while ((read = reader.read(buf)) != -1) { 59 | writer.write(buf, 0, read); 60 | total += read; 61 | } 62 | return total; 63 | } 64 | 65 | } -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/ResourceUtil.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils; 2 | 3 | 4 | import java.util.ResourceBundle; 5 | 6 | /** 7 | * @author taoxy 2019/1/9 8 | */ 9 | public class ResourceUtil { 10 | private static ResourceBundle bundle = ResourceBundle.getBundle("sysConfig"); 11 | 12 | public static String algorithmServer() { 13 | return bundle.getString("algorithmServer"); 14 | } 15 | 16 | public static String pictureInsert() { 17 | return bundle.getString("pictureInsert"); 18 | } 19 | 20 | public static String dataDir() { 21 | return bundle.getString("dataDir"); 22 | } 23 | 24 | public static String imageServer() { 25 | return bundle.getString("imageServer"); 26 | } 27 | 28 | public static String wikiDir() { 29 | return bundle.getString("wikiDir"); 30 | } 31 | 32 | public static String originDir() { 33 | return bundle.getString("originDir"); 34 | } 35 | 36 | public static String avaterInsert() { 37 | return bundle.getString("avaterInsert"); 38 | } 39 | 40 | public static String tmpDir() { 41 | return bundle.getString("tmpDir"); 42 | } 43 | 44 | public static String bossServer() { 45 | return bundle.getString("bossServer"); 46 | } 47 | 48 | public static String wikiImage() { 49 | return bundle.getString("wikiImage"); 50 | } 51 | 52 | public static String wikiVideo() { 53 | return bundle.getString("wikiVideo"); 54 | } 55 | 56 | public static String citrusDaily() { 57 | return bundle.getString("citrusDaily"); 58 | } 59 | 60 | public static String detection() { 61 | return bundle.getString("detection"); 62 | } 63 | 64 | public static String chat() { 65 | return bundle.getString("chat"); 66 | } 67 | 68 | public static String advertImageDir() { 69 | return bundle.getString("advertImageDir"); 70 | } 71 | 72 | public static String specialistImageDir() { 73 | return bundle.getString("specialistImageDir"); 74 | } 75 | } 76 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/ResponseUtil.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils; 2 | 3 | import com.dfs.model.ApiCodeEnum; 4 | import com.dfs.response.Response; 5 | /** 6 | * @author taoxy 2019/1/9 7 | */ 8 | public class ResponseUtil { 9 | 10 | public static String getResponse(Object content, ApiCodeEnum code) { 11 | Response outputParam = new Response(); 12 | outputParam.setContent(content); 13 | outputParam.setStatus(code.getCode()); 14 | outputParam.setMsg(code.getMsg()); 15 | return JsonUtils.toJsonWithGson(outputParam); 16 | } 17 | 18 | public static String getResponse(ApiCodeEnum code) { 19 | Response outputParam = new Response(); 20 | outputParam.setContent(new Object()); 21 | outputParam.setStatus(code.getCode()); 22 | outputParam.setMsg(code.getMsg()); 23 | return JsonUtils.toJsonWithGson(outputParam); 24 | } 25 | 26 | public static String getResponse(String code, String msg, Object content) { 27 | Response outputParam = new Response(); 28 | outputParam.setContent(content); 29 | outputParam.setStatus(code); 30 | outputParam.setMsg(msg); 31 | return JsonUtils.toJsonWithGson(outputParam); 32 | } 33 | 34 | public static String getResponse(String code, String msg) { 35 | Response outputParam = new Response(); 36 | outputParam.setContent(new Object()); 37 | outputParam.setStatus(code); 38 | outputParam.setMsg(msg); 39 | return JsonUtils.toJsonWithGson(outputParam); 40 | } 41 | 42 | } 43 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/RunPyUtil.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils; 2 | 3 | import java.io.BufferedReader; 4 | import java.io.InputStreamReader; 5 | 6 | 7 | /** 8 | * @author taoxy 2019/1/3 9 | */ 10 | public class RunPyUtil { 11 | 12 | public static String runCmd(String cmd) throws Exception { 13 | BufferedReader br = null; 14 | try { 15 | Process p = Runtime.getRuntime().exec(cmd); 16 | br = new BufferedReader(new InputStreamReader(p.getInputStream())); 17 | String line = null; 18 | StringBuffer sb = new StringBuffer(); 19 | while ((line = br.readLine()) != null) { 20 | sb.append(line + "\n"); 21 | } 22 | return sb.toString(); 23 | } finally { 24 | if (br != null) { 25 | try { 26 | br.close(); 27 | } catch (Exception e) { 28 | e.printStackTrace(); 29 | } 30 | } 31 | } 32 | } 33 | } -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/SerializeUtil.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils; 2 | 3 | import java.io.ByteArrayInputStream; 4 | import java.io.ByteArrayOutputStream; 5 | import java.io.ObjectInputStream; 6 | import java.io.ObjectOutputStream; 7 | 8 | public class SerializeUtil { 9 | public static byte[] serialize(Object object) { 10 | ObjectOutputStream oos = null; 11 | ByteArrayOutputStream baos = null; 12 | try { 13 | //序列化 14 | baos = new ByteArrayOutputStream(); 15 | oos = new ObjectOutputStream(baos); 16 | oos.writeObject(object); 17 | byte[] bytes = baos.toByteArray(); 18 | return bytes; 19 | } catch (Exception e) { 20 | } 21 | return null; 22 | } 23 | 24 | public static Object unserialize(byte[] bytes) { 25 | ByteArrayInputStream bais = null; 26 | try { 27 | //反序列化 28 | bais = new ByteArrayInputStream(bytes); 29 | ObjectInputStream ois = new ObjectInputStream(bais); 30 | return ois.readObject(); 31 | } catch (Exception e) { 32 | } 33 | return null; 34 | } 35 | } -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/StringUtil.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils; 2 | 3 | import java.util.UUID; 4 | 5 | 6 | /** 7 | * @author taoxy 2019/1/3 8 | */ 9 | public class StringUtil { 10 | /** 11 | * @param str 12 | * @return 13 | * @description 给定字符串是否为空或空串 14 | * @author taoxy 15 | * @created 2018年12月4日 下午5:15:46 16 | */ 17 | public static boolean isNotEmpty(String str) { 18 | if (str != null && str.length() != 0) { 19 | return true; 20 | } 21 | return false; 22 | } 23 | 24 | /** 25 | * @param str 26 | * @return 27 | * @description 给定字符串是否为空或空串 28 | * @author taoxy 29 | * @created 2018年12月4日 下午5:15:46 30 | */ 31 | public static boolean isEmpty(String str) { 32 | if (str != null && str.length() != 0) { 33 | return false; 34 | } 35 | return true; 36 | } 37 | 38 | public static StringBuffer getWikiContentInString(String contentList) { 39 | String[] contents = contentList.split("

"); 40 | StringBuffer contentbuffer = new StringBuffer(); 41 | for (int i = 1; i < contents.length ; i++) { 42 | contents[i] = contents[i].trim(); 43 | String[] part = contents[i].split("
"); 44 | for (String string2 : part) { 45 | StringBuffer stringBuffer = new StringBuffer(); 46 | string2 = string2.replace("[", ""); 47 | string2 = string2.replace("]", ""); 48 | stringBuffer.append(string2); 49 | contentbuffer.append(stringBuffer); 50 | } 51 | } 52 | return contentbuffer; 53 | } 54 | 55 | public static String createUUID() { 56 | return UUID.randomUUID().toString(); 57 | } 58 | 59 | } 60 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/WebContextUtil.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils; 2 | 3 | import javax.servlet.http.HttpServletRequest; 4 | 5 | import org.springframework.web.context.request.RequestContextHolder; 6 | import org.springframework.web.context.request.ServletRequestAttributes; 7 | 8 | 9 | /** 10 | * @author taoxy 2019/1/3 11 | */ 12 | public class WebContextUtil { 13 | public static HttpServletRequest getRequest() { 14 | HttpServletRequest request = ((ServletRequestAttributes) RequestContextHolder.getRequestAttributes()).getRequest(); 15 | return request; 16 | } 17 | } 18 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/ZipUtils.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils; 2 | 3 | import org.apache.log4j.Logger; 4 | 5 | import java.io.File; 6 | import java.io.FileInputStream; 7 | import java.io.FileNotFoundException; 8 | import java.io.FileOutputStream; 9 | import java.io.IOException; 10 | import java.io.InputStream; 11 | import java.util.Enumeration; 12 | import java.util.List; 13 | import java.util.zip.ZipEntry; 14 | import java.util.zip.ZipException; 15 | import java.util.zip.ZipFile; 16 | import java.util.zip.ZipOutputStream; 17 | 18 | 19 | /** 20 | * @author taoxy 2019/1/3 21 | */ 22 | public class ZipUtils { 23 | 24 | private static final Logger log = Logger.getLogger(ZipUtils.class); 25 | 26 | private static final int BUFFER = 1024 * 4; 27 | 28 | private ZipUtils() { 29 | } 30 | 31 | /** 32 | * APDPlat中的重要打包机制 33 | * 将jar文件中的某个文件夹里面的内容复制到某个文件夹 34 | * 35 | * @param jar 包含静态资源的jar包 36 | * @param subDir jar中包含待复制静态资源的文件夹名称 37 | * @param loc 静态资源复制到的目标文件夹 38 | * @param force 目标静态资源存在的时候是否强制覆盖 39 | */ 40 | public static void unZip(String jar, String subDir, String loc, boolean force) { 41 | try { 42 | File base = new File(loc); 43 | if (!base.exists()) { 44 | base.mkdirs(); 45 | } 46 | 47 | ZipFile zip = new ZipFile(new File(jar)); 48 | Enumeration entrys = zip.entries(); 49 | while (entrys.hasMoreElements()) { 50 | ZipEntry entry = entrys.nextElement(); 51 | String name = entry.getName(); 52 | if (!name.startsWith(subDir)) { 53 | continue; 54 | } 55 | // 去掉subDir 56 | name = name.replace(subDir, "").trim(); 57 | if (name.length() < 2) { 58 | log.debug(name + " 长度 < 2"); 59 | continue; 60 | } 61 | if (entry.isDirectory()) { 62 | File dir = new File(base, name); 63 | if (!dir.exists()) { 64 | dir.mkdirs(); 65 | log.debug("创建目录"); 66 | } else { 67 | log.debug("目录已经存在"); 68 | } 69 | log.debug(name + " 是目录"); 70 | } else { 71 | File file = new File(base, name); 72 | if (file.exists() && force) { 73 | file.delete(); 74 | } 75 | if (!file.exists()) { 76 | InputStream in = zip.getInputStream(entry); 77 | FileUtil.copy(in, file); 78 | log.debug("创建文件"); 79 | } else { 80 | log.debug("文件已经存在"); 81 | } 82 | log.debug(name + " 不是目录"); 83 | } 84 | } 85 | } catch (ZipException ex) { 86 | log.error("文件解压失败", ex); 87 | } catch (IOException ex) { 88 | log.error("文件操作失败", ex); 89 | } 90 | } 91 | 92 | /** 93 | * 创建ZIP文件 94 | * 95 | * @param zipPath 生成的zip文件存在路径(包括文件名) 96 | */ 97 | public static boolean createZip(List sourcePaths, String zipPath) { 98 | FileOutputStream fos = null; 99 | ZipOutputStream zos = null; 100 | try { 101 | fos = new FileOutputStream(zipPath); 102 | zos = new ZipOutputStream(fos); 103 | for (String sourcePath : sourcePaths) { 104 | writeZip(new File(sourcePath), "", zos); 105 | } 106 | } catch (FileNotFoundException e) { 107 | log.error("创建ZIP文件失败", e); 108 | return false; 109 | } finally { 110 | try { 111 | if (zos != null) { 112 | zos.close(); 113 | } 114 | } catch (IOException e) { 115 | log.error("创建ZIP文件失败", e); 116 | return false; 117 | } 118 | 119 | } 120 | return true; 121 | } 122 | 123 | /** 124 | * 创建ZIP文件 125 | * 126 | * @param sourcePath 文件或文件夹路径 127 | * @param zipPath 生成的zip文件存在路径(包括文件名) 128 | */ 129 | public static void createZip(String sourcePath, String zipPath) { 130 | FileOutputStream fos = null; 131 | ZipOutputStream zos = null; 132 | try { 133 | fos = new FileOutputStream(zipPath); 134 | zos = new ZipOutputStream(fos); 135 | writeZip(new File(sourcePath), "", zos); 136 | } catch (FileNotFoundException e) { 137 | log.error("创建ZIP文件失败", e); 138 | } finally { 139 | try { 140 | if (zos != null) { 141 | zos.close(); 142 | } 143 | } catch (IOException e) { 144 | log.error("创建ZIP文件失败", e); 145 | } 146 | 147 | } 148 | } 149 | 150 | /** 151 | * 写入ZIP文件 152 | * 153 | * @param file 154 | * @param parentPath 155 | * @param zos 156 | */ 157 | private static void writeZip(File file, String parentPath, ZipOutputStream zos) { 158 | if (file.exists()) { 159 | if (file.isDirectory()) {// 处理文件夹 160 | parentPath += file.getName() + File.separator; 161 | File[] files = file.listFiles(); 162 | for (File f : files) { 163 | writeZip(f, parentPath, zos); 164 | } 165 | } else { 166 | FileInputStream fis = null; 167 | try { 168 | fis = new FileInputStream(file); 169 | ZipEntry ze = new ZipEntry(parentPath + file.getName()); 170 | zos.putNextEntry(ze); 171 | byte[] buffer = new byte[BUFFER]; 172 | int len; 173 | while ((len = fis.read(buffer)) != -1) { 174 | zos.write(buffer, 0, len); 175 | zos.flush(); 176 | } 177 | 178 | } catch (FileNotFoundException e) { 179 | log.error("创建ZIP文件失败", e); 180 | } catch (IOException e) { 181 | log.error("创建ZIP文件失败", e); 182 | } finally { 183 | try { 184 | if (fis != null) { 185 | fis.close(); 186 | } 187 | } catch (IOException e) { 188 | log.error("创建ZIP文件失败", e); 189 | } 190 | } 191 | } 192 | } 193 | } 194 | 195 | } 196 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/pay/wechat/AESUtil.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils.pay.wechat; 2 | 3 | 4 | 5 | import java.security.Security; 6 | 7 | import javax.crypto.Cipher; 8 | import javax.crypto.spec.SecretKeySpec; 9 | 10 | import org.bouncycastle.jce.provider.BouncyCastleProvider; 11 | 12 | import com.dfs.utils.Md5; 13 | 14 | 15 | public class AESUtil 16 | { 17 | 18 | /** 19 | * 密钥算法 20 | */ 21 | private static final String ALGORITHM = "AES"; 22 | 23 | /** 24 | * 加解密算法/工作模式/填充方式 25 | */ 26 | private static final String ALGORITHM_MODE_PADDING = "AES/ECB/PKCS7Padding"; 27 | /** 28 | * 生成key 29 | */ 30 | static 31 | { 32 | Security.addProvider(new BouncyCastleProvider()); 33 | } 34 | 35 | /** 36 | * AES加密 37 | * 38 | * @param data 39 | * @return 40 | * @throws Exception 41 | */ 42 | public static String encryptData(String data, String key) 43 | throws Exception 44 | { 45 | // 创建密码器 46 | Cipher cipher = Cipher.getInstance(ALGORITHM_MODE_PADDING); 47 | // 初始化 48 | SecretKeySpec secretKey = new SecretKeySpec( 49 | Md5.GetMD5Code(key).toLowerCase().getBytes(), ALGORITHM); 50 | cipher.init(Cipher.ENCRYPT_MODE, secretKey); 51 | return Base64Util.encode(cipher.doFinal(data.getBytes())); 52 | } 53 | 54 | /** 55 | * AES解密 56 | * 57 | * @param base64Data 58 | * @return 59 | * @throws Exception 60 | */ 61 | public static String decryptData(String base64Data,String key) 62 | throws Exception 63 | { 64 | // 创建密码器 65 | Cipher cipher = Cipher.getInstance(ALGORITHM_MODE_PADDING); 66 | // 初始化 67 | SecretKeySpec secretKey = new SecretKeySpec( 68 | Md5.GetMD5Code(key).toLowerCase().getBytes(), ALGORITHM); 69 | cipher.init(Cipher.DECRYPT_MODE, secretKey); 70 | return new String(cipher.doFinal(Base64Util.decode(base64Data))); 71 | } 72 | 73 | public static void main(String[] args) 74 | throws Exception 75 | { 76 | // String A 为测试字符串,是微信返回过来的退款通知字符串 77 | String A = "oSWxqqMF5lk2EF+gdrdt5wPrOru854za5XjHq5cUXs74zF9+jlxGOo7DHQIuntolVF3kQAruoMoNK5lLRsCulgG2hAT+6sNen8f/f3drMxfsTFOj3aBTKkIHs2p3AVJA4fXpGRCpejq3JJplSQnnSwFljzcxvqe7rU3y/H0KpFyBuYUSEf+msbkHEnHnIHQi4p9JDlLPWoKHramM7R65Qd13GdUU41scNybWCkwl+q/cY2Nv6KUt490JXTbTEgZNE6ArJKGg9woRMUdJEimTnv2OSY16yjo8dlIiozEoHcoQsvSFuMA5DHfHmtk5gbn8y6FVLHbt8XmmOIkfl/CVCXGQ+fGJmazxmqpTLBnAxXogFX2c2h8ZFqrWHW0wWZNSqpRX8HnMBw4V5hUMCiN9ASP3AzkpbtxdkDaeJYagVFgpB7oXxNUlQMy7pCqWCqbhoeLlZtzACx3qNqf57cQLn06T8wrYddf3f78oIYceVWMBses6wcJW2uTUdci4hYOQn5G+iVGLRzMuI8xwQSeBtdrWBor842tEsg4/wgFRxiEgjN+Jl+pCbwULjzt870OwC/UKD9mM3bhyay1jxeKNfkqgks0TH9eZXT1mR6IBfIUipgk9nTrGLFQwt4AAAf7/KoW7A3d1eYGY1vo/QkinixiZsxOJhzw95X6wiiARPa8oe0180lCuhLtIrNRlxyVMbbwA8GQVuCCE6w+/yKIF+el+Gcf7Gm2ljQzV7PEwiomW/DsBqUb5mwGfI52NLRa70kJ8vgaXeMN1xhwWYLzg02muvGGwS2P4kgGO0Sg0L5ycpN7Vp421+HnAPdcW6y/pQi03BKAR6fZT5JQYAIoNN4K8K6ZbgfZiuG32q0q4bwVWrg4jBlyPmj8JwHtbikbAgoJ9sUwWYi7P+Btk1ZHCPLW90p+1mIL8eVpneOaon3mSW0R4JDiIJK8oYLD/1n4NTKRTg9c6OMdSHnK8BUnodw=="; 78 | String B = AESUtil.decryptData(A,"1471da051c9b43cb9763b39647a33ba4"); 79 | System.out.println(B); 80 | } 81 | 82 | } -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/pay/wechat/MessageUtil.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils.pay.wechat; 2 | 3 | 4 | import java.io.IOException; 5 | import java.io.Writer; 6 | import java.util.HashMap; 7 | import java.util.List; 8 | 9 | import javax.servlet.http.HttpServletRequest; 10 | 11 | import org.dom4j.Document; 12 | import org.dom4j.Element; 13 | import org.dom4j.io.SAXReader; 14 | 15 | import com.thoughtworks.xstream.XStream; 16 | import com.thoughtworks.xstream.core.util.QuickWriter; 17 | import com.thoughtworks.xstream.io.HierarchicalStreamWriter; 18 | import com.thoughtworks.xstream.io.xml.PrettyPrintWriter; 19 | import com.thoughtworks.xstream.io.xml.XppDriver; 20 | public class MessageUtil { 21 | public static HashMap parseXML(HttpServletRequest request) throws Exception, IOException{ 22 | HashMap map=new HashMap(); 23 | // 通过IO获得Document 24 | SAXReader reader = new SAXReader(); 25 | Document doc = reader.read(request.getInputStream()); 26 | //得到xml的根节点 27 | Element root=doc.getRootElement(); 28 | recursiveParseXML(root,map); 29 | return map; 30 | } 31 | private static void recursiveParseXML(Element root,HashMap map){ 32 | //得到根节点的子节点列表 33 | List elementList=root.elements(); 34 | //判断有没有子元素列表 35 | if(elementList.size()==0){ 36 | map.put(root.getName(), root.getTextTrim()); 37 | } 38 | else{ 39 | //遍历 40 | for(Element e:elementList){ 41 | recursiveParseXML(e,map); 42 | } 43 | } 44 | } 45 | private static XStream xstream = new XStream(new XppDriver() { 46 | public HierarchicalStreamWriter createWriter(Writer out) { 47 | return new PrettyPrintWriter(out) { 48 | // 对所有xml节点都增加CDATA标记 49 | boolean cdata = true; 50 | public void startNode(String name, Class clazz) { 51 | super.startNode(name, clazz); 52 | } 53 | protected void writeText(QuickWriter writer, String text) { 54 | if (cdata) { 55 | /* writer.write(" writer.write(text); 56 | writer.write("]]>"); */ 57 | writer.write(text); 58 | /* writer.write("]]>"); */ 59 | } else { 60 | writer.write(text); 61 | } 62 | } 63 | }; 64 | } 65 | }); 66 | 67 | public static String messageToRefundXML(RefundPo refundPo){ 68 | xstream.alias("xml",RefundPo.class); 69 | return xstream.toXML(refundPo); 70 | } 71 | public static String messageToXML(PaymentPo paymentPo){ 72 | xstream.alias("xml",PaymentPo.class); 73 | return xstream.toXML(paymentPo); 74 | } 75 | 76 | public static String messageToQueryXML(QueryPo queryPo){ 77 | xstream.alias("xml",RefundPo.class); 78 | return xstream.toXML(queryPo); 79 | } 80 | 81 | public static String messageToTransferXML(TransferPo transferPo) 82 | { 83 | xstream.alias("xml",TransferPo.class); 84 | return xstream.toXML(transferPo); 85 | } 86 | } 87 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/pay/wechat/P12Request.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils.pay.wechat; 2 | 3 | 4 | import java.io.File; 5 | import java.io.FileInputStream; 6 | import java.io.IOException; 7 | import java.net.SocketTimeoutException; 8 | import java.security.KeyManagementException; 9 | import java.security.KeyStore; 10 | import java.security.KeyStoreException; 11 | import java.security.NoSuchAlgorithmException; 12 | import java.security.UnrecoverableKeyException; 13 | import java.security.cert.CertificateException; 14 | 15 | import javax.net.ssl.SSLContext; 16 | 17 | import org.apache.http.HttpEntity; 18 | import org.apache.http.HttpResponse; 19 | import org.apache.http.client.config.RequestConfig; 20 | import org.apache.http.client.methods.HttpPost; 21 | import org.apache.http.conn.ConnectTimeoutException; 22 | import org.apache.http.conn.ConnectionPoolTimeoutException; 23 | import org.apache.http.conn.ssl.SSLConnectionSocketFactory; 24 | import org.apache.http.conn.ssl.SSLContexts; 25 | import org.apache.http.entity.StringEntity; 26 | import org.apache.http.impl.client.CloseableHttpClient; 27 | import org.apache.http.impl.client.HttpClients; 28 | import org.apache.http.util.EntityUtils; 29 | 30 | public class P12Request { 31 | 32 | // 连接超时时间,默认10秒 33 | private int socketTimeout = 10000; 34 | 35 | // 传输超时时间,默认30秒 36 | private int connectTimeout = 30000; 37 | 38 | // 请求器的配置 39 | private static RequestConfig requestConfig; 40 | 41 | // HTTP请求器 42 | private static CloseableHttpClient httpClient; 43 | 44 | 45 | 46 | public static void main(String[] args) { 47 | 48 | 49 | } 50 | 51 | /** 52 | * 加载证书 53 | * 54 | * @param path 55 | * @throws IOException 56 | * @throws KeyStoreException 57 | * @throws UnrecoverableKeyException 58 | * @throws NoSuchAlgorithmException 59 | * @throws KeyManagementException 60 | */ 61 | private static void initCert(String path,String merchantNo) throws IOException, 62 | KeyStoreException, UnrecoverableKeyException, 63 | NoSuchAlgorithmException, KeyManagementException { 64 | // 拼接证书的路径 65 | KeyStore keyStore = KeyStore.getInstance("PKCS12"); 66 | 67 | // 加载本地的证书进行https加密传输 68 | FileInputStream instream = new FileInputStream(new File(path)); 69 | try { 70 | keyStore.load(instream, merchantNo.toCharArray()); // 加载证书密码,默认为商户ID 71 | } catch (CertificateException e) { 72 | e.printStackTrace(); 73 | } catch (NoSuchAlgorithmException e) { 74 | e.printStackTrace(); 75 | } finally { 76 | instream.close(); 77 | } 78 | 79 | // Trust own CA and all self-signed certs 80 | SSLContext sslcontext = SSLContexts.custom() 81 | .loadKeyMaterial(keyStore, merchantNo.toCharArray()) // 加载证书密码,默认为商户ID 82 | .build(); 83 | // Allow TLSv1 protocol only 84 | SSLConnectionSocketFactory sslsf = new SSLConnectionSocketFactory( 85 | sslcontext, new String[] { "TLSv1" }, null, 86 | SSLConnectionSocketFactory.BROWSER_COMPATIBLE_HOSTNAME_VERIFIER); 87 | 88 | httpClient = HttpClients.custom() 89 | .setSSLSocketFactory(sslsf).build(); 90 | 91 | // 根据默认超时限制初始化requestConfig 92 | requestConfig = RequestConfig.custom() 93 | .setSocketTimeout(10000).setConnectTimeout(30000).build(); 94 | 95 | } 96 | 97 | /** 98 | * 通过Https往API post xml数据 99 | * 100 | * @param url 101 | * API地址 102 | * @param xmlObj 103 | * 要提交的XML数据对象 104 | * @param path 105 | * 当前目录,用于加载证书 106 | * @return 107 | * @throws IOException 108 | * @throws KeyStoreException 109 | * @throws UnrecoverableKeyException 110 | * @throws NoSuchAlgorithmException 111 | * @throws KeyManagementException 112 | */ 113 | public static String httpsRequest(String url, String xmlObj, String merchantNo,String path) 114 | throws IOException, KeyStoreException, UnrecoverableKeyException, 115 | NoSuchAlgorithmException, KeyManagementException { 116 | // 加载证书 117 | initCert(path,merchantNo); 118 | 119 | String result = null; 120 | 121 | HttpPost httpPost = new HttpPost(url); 122 | 123 | // 得指明使用UTF-8编码,否则到API服务器XML的中文不能被成功识别 124 | StringEntity postEntity = new StringEntity(xmlObj, "UTF-8"); 125 | httpPost.addHeader("Content-Type", "text/xml"); 126 | httpPost.setEntity(postEntity); 127 | 128 | // 设置请求器的配置 129 | httpPost.setConfig(requestConfig); 130 | 131 | try { 132 | HttpResponse response = httpClient.execute(httpPost); 133 | 134 | HttpEntity entity = response.getEntity(); 135 | 136 | result = EntityUtils.toString(entity, "UTF-8"); 137 | 138 | } catch (ConnectionPoolTimeoutException e) { 139 | e.printStackTrace(); 140 | } catch (ConnectTimeoutException e) { 141 | e.printStackTrace(); 142 | } catch (SocketTimeoutException e) { 143 | e.printStackTrace(); 144 | } catch (Exception e) { 145 | e.printStackTrace(); 146 | } finally { 147 | httpPost.abort(); 148 | } 149 | 150 | return result; 151 | } 152 | } 153 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/pay/wechat/PayUtil.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils.pay.wechat; 2 | 3 | 4 | import org.apache.commons.codec.digest.DigestUtils; 5 | import org.apache.log4j.Logger; 6 | import org.dom4j.Document; 7 | import org.dom4j.Element; 8 | import org.dom4j.io.SAXReader; 9 | 10 | import java.io.*; 11 | import java.net.HttpURLConnection; 12 | import java.net.URL; 13 | import java.security.SignatureException; 14 | import java.util.*; 15 | 16 | 17 | /** 18 | * @author 19 | * @version 创建时间:2017年1月17日 下午7:46:29 类说明 20 | */ 21 | public class PayUtil { 22 | 23 | public static final Logger log = Logger.getLogger(PayUtil.class); 24 | /* 25 | * 商户支付url 26 | */ 27 | public static String trans_url = "https://api.mch.weixin.qq.com/mmpaymkttransfers/promotion/transfers"; 28 | /** 29 | * 签名字符串 30 | * @param text需要签名的字符串 31 | * @param key 密钥 32 | * @param input_charset编码格式 33 | * @return 签名结果 34 | */ 35 | public static String sign(String text/*, String key*/, String input_charset) { 36 | /*text = text + key; */ 37 | return DigestUtils.md5Hex(getContentBytes(text, input_charset)); 38 | } 39 | /** 40 | * 签名字符串 41 | * @param text需要签名的字符串 42 | * @param sign 签名结果 43 | * @param key密钥 44 | * @param input_charset 编码格式 45 | * @return 签名结果 46 | */ 47 | public static boolean verify(String text, String sign, String key, String input_charset) { 48 | text = text + key; 49 | String mysign = DigestUtils.md5Hex(getContentBytes(text, input_charset)); 50 | if (mysign.equals(sign)) { 51 | return true; 52 | } else { 53 | return false; 54 | } 55 | } 56 | /** 57 | * @param content 58 | * @param charset 59 | * @return 60 | * @throws SignatureException 61 | * @throws UnsupportedEncodingException 62 | */ 63 | public static byte[] getContentBytes(String content, String charset) { 64 | if (charset == null || "".equals(charset)) { 65 | return content.getBytes(); 66 | } 67 | try { 68 | return content.getBytes(charset); 69 | } catch (UnsupportedEncodingException e) { 70 | throw new RuntimeException("MD5签名过程中出现错误,指定的编码集不对,您目前指定的编码集是:" + charset); 71 | } 72 | } 73 | /** 74 | * 生成6位或10位随机数 param codeLength(多少位) 75 | * @return 76 | */ 77 | public static String createCode(int codeLength) { 78 | String code = ""; 79 | for (int i = 0; i < codeLength; i++) { 80 | code += (int) (Math.random() * 9); 81 | } 82 | return code; 83 | } 84 | private static boolean isValidChar(char ch) { 85 | if ((ch >= '0' && ch <= '9') || (ch >= 'A' && ch <= 'Z') || (ch >= 'a' && ch <= 'z')) 86 | return true; 87 | if ((ch >= 0x4e00 && ch <= 0x7fff) || (ch >= 0x8000 && ch <= 0x952f)) 88 | return true;// 简体中文汉字编码 89 | return false; 90 | } 91 | /** 92 | * 除去数组中的空值和签名参数 93 | * @param sArray 签名参数组 94 | * @return 去掉空值与签名参数后的新签名参数组 95 | */ 96 | public static Map paraFilter(Map sArray) { 97 | Map result = new HashMap(); 98 | if (sArray == null || sArray.size() <= 0) { 99 | return result; 100 | } 101 | for (String key : sArray.keySet()) { 102 | Object value = (Object) sArray.get(key); 103 | if (value == null || value.equals("") || key.equalsIgnoreCase("sign") 104 | || key.equalsIgnoreCase("sign_type")) { 105 | continue; 106 | } 107 | result.put(key, value); 108 | } 109 | return result; 110 | } 111 | /** 112 | * 把数组所有元素排序,并按照“参数=参数值”的模式用“&”字符拼接成字符串 113 | * @param params 需要排序并参与字符拼接的参数组 114 | * @return 拼接后字符串 115 | */ 116 | public static String createLinkString(Map params) { 117 | List keys = new ArrayList(params.keySet()); 118 | Collections.sort(keys); 119 | String prestr = ""; 120 | for (int i = 0; i < keys.size(); i++) { 121 | String key = keys.get(i); 122 | Object value = (Object) params.get(key); 123 | if (i == keys.size() - 1) {// 拼接时,不包括最后一个&字符 124 | prestr = prestr + key + "=" + value; 125 | } else { 126 | prestr = prestr + key + "=" + value + "&"; 127 | } 128 | } 129 | return prestr; 130 | } 131 | /** 132 | * 133 | * @param requestUrl请求地址 134 | * @param requestMethod请求方法 135 | * @param outputStr参数 136 | */ 137 | public static String httpRequest(String requestUrl,String requestMethod,String outputStr){ 138 | // 创建SSLContext 139 | StringBuffer buffer=null; 140 | try{ 141 | URL url = new URL(requestUrl); 142 | HttpURLConnection conn = (HttpURLConnection) url.openConnection(); 143 | conn.setRequestMethod(requestMethod); 144 | conn.setDoOutput(true); 145 | conn.setDoInput(true); 146 | conn.connect(); 147 | //往服务器端写内容 148 | if(null !=outputStr){ 149 | OutputStream os=conn.getOutputStream(); 150 | os.write(outputStr.getBytes("utf-8")); 151 | os.close(); 152 | } 153 | // 读取服务器端返回的内容 154 | InputStream is = conn.getInputStream(); 155 | InputStreamReader isr = new InputStreamReader(is, "utf-8"); 156 | BufferedReader br = new BufferedReader(isr); 157 | buffer = new StringBuffer(); 158 | String line = null; 159 | while ((line = br.readLine()) != null) { 160 | buffer.append(line); 161 | } 162 | }catch(Exception e){ 163 | e.printStackTrace(); 164 | } 165 | return buffer.toString(); 166 | } 167 | public static String urlEncodeUTF8(String source){ 168 | String result=source; 169 | try { 170 | result=java.net.URLEncoder.encode(source, "UTF-8"); 171 | } catch (UnsupportedEncodingException e) { 172 | // TODO Auto-generated catch block 173 | e.printStackTrace(); 174 | } 175 | return result; 176 | } 177 | 178 | public static Map parseXmlToMap(String xml) { 179 | InputStream in = new ByteArrayInputStream(xml.getBytes()); 180 | // 读取输入流 181 | SAXReader reader = new SAXReader(); 182 | Document document = null; 183 | Map map = new HashMap(); 184 | try 185 | { 186 | // XXE漏洞修复 187 | reader.setFeature("http://apache.org/xml/features/disallow-doctype-decl", true); 188 | reader.setFeature("http://xml.org/sax/features/external-general-entities", false); 189 | reader.setFeature("http://xml.org/sax/features/external-parameter-entities", false); 190 | reader.setEncoding("GB2312"); 191 | document = reader.read(in); 192 | 193 | // 得到xml根元素 194 | Element root = document.getRootElement(); 195 | // 得到根元素的所有子节点 196 | List elementList = root.elements(); 197 | for (Element element : elementList) 198 | { 199 | map.put(element.getName(), element.getText()); 200 | } 201 | } 202 | catch (Exception e) 203 | { 204 | e.printStackTrace(); 205 | } 206 | return map; 207 | } 208 | 209 | public static Map parseXmlToMap(InputStream in) { 210 | // 读取输入流 211 | SAXReader reader = new SAXReader(); 212 | Document document = null; 213 | try 214 | { 215 | // XXE漏洞修复 216 | reader.setFeature("http://apache.org/xml/features/disallow-doctype-decl", true); 217 | reader.setFeature("http://xml.org/sax/features/external-general-entities", false); 218 | reader.setFeature("http://xml.org/sax/features/external-parameter-entities", false); 219 | document = reader.read(in); 220 | } 221 | catch (Exception e) 222 | { 223 | e.printStackTrace(); 224 | } 225 | System.out.println(document.getStringValue()); 226 | 227 | // 得到xml根元素 228 | Element root = document.getRootElement(); 229 | // 得到根元素的所有子节点 230 | List elementList = root.elements(); 231 | Map map = new HashMap(); 232 | for (Element element : elementList) 233 | { 234 | map.put(element.getName(), element.getText()); 235 | } 236 | return map; 237 | } 238 | 239 | } 240 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/pay/wechat/PaymentPo.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils.pay.wechat; 2 | 3 | 4 | public class PaymentPo { 5 | private String appid;//小程序ID 6 | private String mch_id;//商户号 7 | private String device_info;//设备号 8 | private String nonce_str;//随机字符串 9 | private String sign;//签名 10 | private String body;//商品描述 11 | private String detail;//商品详情 12 | private String attach;//附加数据 13 | private String out_trade_no;//商户订单号 14 | private String fee_type;//货币类型 15 | private String spbill_create_ip;//终端IP 16 | private String time_start;//交易起始时间 17 | private String time_expire;//交易结束时间 18 | private String goods_tag;//商品标记 19 | private int total_fee;//总金额 20 | private String notify_url;//通知地址 21 | private String trade_type;//交易类型 22 | private String limit_pay;//指定支付方式 23 | private String openid;//用户标识 24 | private String transactionId;//微信订单号 25 | private String scene_info;//H5支付场景信息 26 | 27 | public String getTransactionId() { 28 | return transactionId; 29 | } 30 | public void setTransactionId(String transactionId) { 31 | this.transactionId = transactionId; 32 | } 33 | public String getAppid() { 34 | return appid; 35 | } 36 | public void setAppid(String appid) { 37 | this.appid = appid; 38 | } 39 | public String getMch_id() { 40 | return mch_id; 41 | } 42 | public void setMch_id(String mch_id) { 43 | this.mch_id = mch_id; 44 | } 45 | public String getDevice_info() { 46 | return device_info; 47 | } 48 | public void setDevice_info(String device_info) { 49 | this.device_info = device_info; 50 | } 51 | public String getNonce_str() { 52 | return nonce_str; 53 | } 54 | public void setNonce_str(String nonce_str) { 55 | this.nonce_str = nonce_str; 56 | } 57 | public String getSign() { 58 | return sign; 59 | } 60 | public void setSign(String sign) { 61 | this.sign = sign; 62 | } 63 | public String getBody() { 64 | return body; 65 | } 66 | public void setBody(String body) { 67 | this.body = body; 68 | } 69 | public String getDetail() { 70 | return detail; 71 | } 72 | public void setDetail(String detail) { 73 | this.detail = detail; 74 | } 75 | public String getAttach() { 76 | return attach; 77 | } 78 | public void setAttach(String attach) { 79 | this.attach = attach; 80 | } 81 | public String getOut_trade_no() { 82 | return out_trade_no; 83 | } 84 | public void setOut_trade_no(String out_trade_no) { 85 | this.out_trade_no = out_trade_no; 86 | } 87 | public String getFee_type() { 88 | return fee_type; 89 | } 90 | public void setFee_type(String fee_type) { 91 | this.fee_type = fee_type; 92 | } 93 | public String getSpbill_create_ip() { 94 | return spbill_create_ip; 95 | } 96 | public void setSpbill_create_ip(String spbill_create_ip) { 97 | this.spbill_create_ip = spbill_create_ip; 98 | } 99 | public String getTime_start() { 100 | return time_start; 101 | } 102 | public void setTime_start(String time_start) { 103 | this.time_start = time_start; 104 | } 105 | public String getTime_expire() { 106 | return time_expire; 107 | } 108 | public void setTime_expire(String time_expire) { 109 | this.time_expire = time_expire; 110 | } 111 | public String getGoods_tag() { 112 | return goods_tag; 113 | } 114 | public void setGoods_tag(String goods_tag) { 115 | this.goods_tag = goods_tag; 116 | } 117 | public int getTotal_fee() { 118 | return total_fee; 119 | } 120 | public void setTotal_fee(int total_fee) { 121 | this.total_fee = total_fee; 122 | } 123 | public String getNotify_url() { 124 | return notify_url; 125 | } 126 | public void setNotify_url(String notify_url) { 127 | this.notify_url = notify_url; 128 | } 129 | public String getTrade_type() { 130 | return trade_type; 131 | } 132 | public void setTrade_type(String trade_type) { 133 | this.trade_type = trade_type; 134 | } 135 | public String getLimit_pay() { 136 | return limit_pay; 137 | } 138 | public void setLimit_pay(String limit_pay) { 139 | this.limit_pay = limit_pay; 140 | } 141 | public String getOpenid() { 142 | return openid; 143 | } 144 | public void setOpenid(String openid) { 145 | this.openid = openid; 146 | } 147 | public String getScene_info() { 148 | return scene_info; 149 | } 150 | public void setScene_info(String scene_info) { 151 | this.scene_info = scene_info; 152 | } 153 | 154 | } 155 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/pay/wechat/QueryPo.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils.pay.wechat; 2 | 3 | 4 | public class QueryPo { 5 | private String appid; 6 | private String mch_id; 7 | private String nonce_str; 8 | private String sign; 9 | private String out_trade_no; 10 | public String getAppid() 11 | { 12 | return appid; 13 | } 14 | public void setAppid(String appid) 15 | { 16 | this.appid = appid; 17 | } 18 | public String getMch_id() 19 | { 20 | return mch_id; 21 | } 22 | public void setMch_id(String mch_id) 23 | { 24 | this.mch_id = mch_id; 25 | } 26 | public String getNonce_str() 27 | { 28 | return nonce_str; 29 | } 30 | public void setNonce_str(String nonce_str) 31 | { 32 | this.nonce_str = nonce_str; 33 | } 34 | public String getSign() 35 | { 36 | return sign; 37 | } 38 | public void setSign(String sign) 39 | { 40 | this.sign = sign; 41 | } 42 | public String getOut_trade_no() 43 | { 44 | return out_trade_no; 45 | } 46 | public void setOut_trade_no(String out_trade_no) 47 | { 48 | this.out_trade_no = out_trade_no; 49 | } 50 | 51 | } 52 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/pay/wechat/RefundPo.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils.pay.wechat; 2 | 3 | 4 | public class RefundPo { 5 | private String appid; 6 | private String mch_id; 7 | private String nonce_str; 8 | private String sign; 9 | private String sign_type; 10 | private String transaction_id; 11 | private String out_trade_no; 12 | private String out_refund_no; 13 | private Integer total_fee; 14 | private Integer refund_fee; 15 | private String refund_fee_type; 16 | private String refund_desc; 17 | private String refund_account; 18 | private String notify_url; 19 | public String getAppid() { 20 | return appid; 21 | } 22 | public void setAppid(String appid) { 23 | this.appid = appid; 24 | } 25 | public String getMch_id() { 26 | return mch_id; 27 | } 28 | public void setMch_id(String mch_id) { 29 | this.mch_id = mch_id; 30 | } 31 | public String getNonce_str() { 32 | return nonce_str; 33 | } 34 | public void setNonce_str(String nonce_str) { 35 | this.nonce_str = nonce_str; 36 | } 37 | public String getSign() { 38 | return sign; 39 | } 40 | public void setSign(String sign) { 41 | this.sign = sign; 42 | } 43 | public String getSign_type() { 44 | return sign_type; 45 | } 46 | public void setSign_type(String sign_type) { 47 | this.sign_type = sign_type; 48 | } 49 | public String getTransaction_id() { 50 | return transaction_id; 51 | } 52 | public void setTransaction_id(String transaction_id) { 53 | this.transaction_id = transaction_id; 54 | } 55 | public String getOut_trade_no() { 56 | return out_trade_no; 57 | } 58 | public void setOut_trade_no(String out_trade_no) { 59 | this.out_trade_no = out_trade_no; 60 | } 61 | public String getOut_refund_no() { 62 | return out_refund_no; 63 | } 64 | public void setOut_refund_no(String out_refund_no) { 65 | this.out_refund_no = out_refund_no; 66 | } 67 | public Integer getTotal_fee() { 68 | return total_fee; 69 | } 70 | public void setTotal_fee(Integer total_fee) { 71 | this.total_fee = total_fee; 72 | } 73 | public Integer getRefund_fee() { 74 | return refund_fee; 75 | } 76 | public void setRefund_fee(Integer refund_fee) { 77 | this.refund_fee = refund_fee; 78 | } 79 | public String getRefund_fee_type() { 80 | return refund_fee_type; 81 | } 82 | public void setRefund_fee_type(String refund_fee_type) { 83 | this.refund_fee_type = refund_fee_type; 84 | } 85 | public String getRefund_desc() { 86 | return refund_desc; 87 | } 88 | public void setRefund_desc(String refund_desc) { 89 | this.refund_desc = refund_desc; 90 | } 91 | public String getRefund_account() { 92 | return refund_account; 93 | } 94 | public void setRefund_account(String refund_account) { 95 | this.refund_account = refund_account; 96 | } 97 | public String getNotify_url() { 98 | return notify_url; 99 | } 100 | public void setNotify_url(String notify_url) { 101 | this.notify_url = notify_url; 102 | } 103 | 104 | } 105 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/pay/wechat/TransferPo.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils.pay.wechat; 2 | 3 | 4 | /** 5 | * 6 | * 商户号向个人付款po 7 | * @see TransferPo 8 | * @date 2018年9月7日 9 | * @author bodong.liu@ttxn.com 10 | */ 11 | public class TransferPo 12 | { 13 | /** 商户账号appid*/ 14 | public String mch_appid; 15 | /** 微信支付商户号*/ 16 | public String mchid; 17 | /** 随机串*/ 18 | public String nonce_str; 19 | /** 签名*/ 20 | public String sign; 21 | /** 商户订单号*/ 22 | public String partner_trade_no; 23 | /** 用户id*/ 24 | public String openid; 25 | /** 是否校验用户姓名 NO_CHECK:不校验真实姓名 FORCE_CHECK:强校验真实姓名*/ 26 | public String check_name; 27 | /** 金额 单位:分*/ 28 | public Integer amount; 29 | /** 企业付款描述信息*/ 30 | public String desc; 31 | /** ip地址*/ 32 | public String spbill_create_ip; 33 | public String getMchAppid() { 34 | return mch_appid; 35 | } 36 | public void setMchAppid(String mch_appid) { 37 | this.mch_appid = mch_appid; 38 | } 39 | public String getMchid() { 40 | return mchid; 41 | } 42 | public void setMchid(String mchid) { 43 | this.mchid = mchid; 44 | } 45 | public String getNonceStr() { 46 | return nonce_str; 47 | } 48 | public void setNonceStr(String nonce_str) { 49 | this.nonce_str = nonce_str; 50 | } 51 | public String getSign() { 52 | return sign; 53 | } 54 | public void setSign(String sign) { 55 | this.sign = sign; 56 | } 57 | public String getPartnerTradeNo() { 58 | return partner_trade_no; 59 | } 60 | public void setPartnerTradeNo(String partner_trade_no) { 61 | this.partner_trade_no = partner_trade_no; 62 | } 63 | public String getOpenid() { 64 | return openid; 65 | } 66 | public void setOpenid(String openid) { 67 | this.openid = openid; 68 | } 69 | public String getCheckName() { 70 | return check_name; 71 | } 72 | public void setCheckName(String check_name) { 73 | this.check_name = check_name; 74 | } 75 | public Integer getAmount() { 76 | return amount; 77 | } 78 | public void setAmount(Integer amount) { 79 | this.amount = amount; 80 | } 81 | public String getDesc() { 82 | return desc; 83 | } 84 | public void setDesc(String desc) { 85 | this.desc = desc; 86 | } 87 | public String getSpbillCreateIp() { 88 | return spbill_create_ip; 89 | } 90 | public void setSpbillCreateIp(String spbill_create_ip) { 91 | this.spbill_create_ip = spbill_create_ip; 92 | } 93 | @Override 94 | public String toString() 95 | { 96 | return "TransferPo [mch_appid=" + mch_appid + ", mchid=" + mchid + ", nonce_str=" 97 | + nonce_str + ", sign=" + sign + ", partner_trade_no=" + partner_trade_no + ", openid=" 98 | + openid + ", check_name=" + check_name + ", amount=" + amount + ", desc=" + desc 99 | + ", spbill_create_ip=" + spbill_create_ip + "]"; 100 | } 101 | } 102 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/utils/pay/wechat/UUIDHexGenerator.java: -------------------------------------------------------------------------------- 1 | package com.dfs.utils.pay.wechat; 2 | 3 | 4 | import java.util.Random; 5 | 6 | import javax.servlet.http.HttpServletRequest; 7 | 8 | import org.apache.commons.lang.StringUtils; 9 | 10 | /** 11 | * @author 12 | * @version 创建时间:2017年1月17日 下午7:45:06 类说明 13 | */ 14 | public class UUIDHexGenerator { 15 | private static String sep = ""; 16 | /* private static final int IP; */ 17 | private static short counter = (short) 0; 18 | /* private static final int JVM = (int) (System.currentTimeMillis() >>>; */ 19 | private static UUIDHexGenerator uuidgen = new UUIDHexGenerator(); 20 | 21 | /* 22 | * static { int ipadd; try { ipadd = 23 | * toInt(InetAddress.getLocalHost().getAddress()); } catch (Exception e) { 24 | * ipadd = 0; } IP = ipadd; } 25 | */ 26 | public static UUIDHexGenerator getInstance() { 27 | return uuidgen; 28 | } 29 | 30 | /**/ 31 | protected static String format(int intval) { 32 | String formatted = Integer.toHexString(intval); 33 | StringBuffer buf = new StringBuffer("00000000"); 34 | buf.replace(8 - formatted.length(), 8, formatted); 35 | return buf.toString(); 36 | } 37 | 38 | protected static String format(short shortval) { 39 | String formatted = Integer.toHexString(shortval); 40 | StringBuffer buf = new StringBuffer("0000"); 41 | buf.replace(4 - formatted.length(), 4, formatted); 42 | return buf.toString(); 43 | } 44 | 45 | /* 46 | * protected static int getJVM() { return JVM; } 47 | */ 48 | protected synchronized static short getCount() { 49 | if (counter < 0) { 50 | counter = 0; 51 | } 52 | return counter++; 53 | } 54 | 55 | /* 56 | * protected static int getIP() { return IP; } 57 | */ 58 | protected static short getHiTime() { 59 | return (short) (System.currentTimeMillis() >>> 32); 60 | } 61 | 62 | protected static int getLoTime() { 63 | return (int) System.currentTimeMillis(); 64 | } 65 | 66 | //生成随机字符串 67 | public static String getNonce_str() { 68 | String base = "ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789"; 69 | Random random = new Random(); 70 | StringBuilder sb = new StringBuilder(); 71 | for (int i = 0; i < 15; i++) { 72 | int number = random.nextInt(base.length()); 73 | sb.append(base.charAt(number)); 74 | } 75 | return sb.toString(); 76 | } 77 | /** 78 | * @param args 79 | */ 80 | public static void main(String[] args) { 81 | String id = ""; 82 | UUIDHexGenerator uuid = UUIDHexGenerator.getInstance(); 83 | /* 84 | * for (int i = 0; i < 100; i++) { id = uuid.generate(); } 85 | */ 86 | id = uuid.getNonce_str(); 87 | System.out.println(id); 88 | } 89 | 90 | public static String getIp(HttpServletRequest request) { 91 | String ip = request.getHeader("X-Forwarded-For"); 92 | if (StringUtils.isNotEmpty(ip) && !"unKnown".equalsIgnoreCase(ip)) { 93 | // 多次反向代理后会有多个ip值,第一个ip才是真实ip 94 | int index = ip.indexOf(","); 95 | if (index != -1) { 96 | return ip.substring(0, index); 97 | } else { 98 | return ip; 99 | } 100 | } 101 | ip = request.getHeader("X-Real-IP"); 102 | if (StringUtils.isNotEmpty(ip) && !"unKnown".equalsIgnoreCase(ip)) { 103 | return ip; 104 | } 105 | return request.getRemoteAddr(); 106 | } 107 | } -------------------------------------------------------------------------------- /src/main/java/com/dfs/websocket/CacheConstant.java: -------------------------------------------------------------------------------- 1 | package com.dfs.websocket; 2 | 3 | /** 4 | * 緩存常量名稱 5 | * Created by taoxy1988 on 2019/3/10 6 | */ 7 | public class CacheConstant { 8 | 9 | private CacheConstant(){} 10 | 11 | /** 12 | * websocket用戶accountId 13 | */ 14 | public static final String WEBSOCKET_ACCOUNT = "websocket_account"; 15 | 16 | } 17 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/websocket/Constants.java: -------------------------------------------------------------------------------- 1 | package com.dfs.websocket; 2 | 3 | public class Constants { 4 | 5 | 6 | private Constants(){} 7 | 8 | /** 9 | * SessionId 10 | */ 11 | public static final String SESSIONID = "sessionid"; 12 | 13 | /** 14 | * Session對象Key, 用戶id 15 | */ 16 | public static final String SKEY_ACCOUNT_ID = "accountId"; 17 | 18 | 19 | 20 | } 21 | 22 | -------------------------------------------------------------------------------- /src/main/java/com/dfs/websocket/HttpSessionIdHandshakeInterceptor.java: -------------------------------------------------------------------------------- 1 | package com.dfs.websocket; 2 | import org.springframework.http.server.ServerHttpRequest; 3 | import org.springframework.http.server.ServerHttpResponse; 4 | import org.springframework.http.server.ServletServerHttpRequest; 5 | import org.springframework.stereotype.Component; 6 | import org.springframework.web.socket.WebSocketHandler; 7 | import org.springframework.web.socket.server.support.HttpSessionHandshakeInterceptor; 8 | 9 | import javax.servlet.http.HttpSession; 10 | import java.util.Map; 11 | 12 | /** 13 | * websocket握手(handshake)接口 14 | * Created by taoxy1988 on 2019/3/10 15 | */ 16 | @Component 17 | public class HttpSessionIdHandshakeInterceptor extends HttpSessionHandshakeInterceptor { 18 | 19 | 20 | @Override 21 | public boolean beforeHandshake(ServerHttpRequest request, 22 | ServerHttpResponse response, WebSocketHandler wsHandler, 23 | Map attributes) throws Exception { 24 | //解決The extension [x-webkit-deflate-frame] is not supported問題 25 | if(request.getHeaders().containsKey("Sec-WebSocket-Extensions")) { 26 | request.getHeaders().set("Sec-WebSocket-Extensions", "permessage-deflate"); 27 | } 28 | //檢查session的值是否存在 29 | if (request instanceof ServletServerHttpRequest) { 30 | ServletServerHttpRequest servletRequest = (ServletServerHttpRequest) request; 31 | HttpSession session = servletRequest.getServletRequest().getSession(false); 32 | String accountId = (String) session.getAttribute(Constants.SKEY_ACCOUNT_ID); 33 | //把session和accountId存放起來 34 | attributes.put(Constants.SESSIONID, session.getId()); 35 | attributes.put(Constants.SKEY_ACCOUNT_ID, accountId); 36 | } 37 | return super.beforeHandshake(request, response, wsHandler, attributes); 38 | } 39 | 40 | 41 | @Override 42 | public void afterHandshake(ServerHttpRequest request, 43 | ServerHttpResponse response, WebSocketHandler wsHandler, 44 | Exception ex) { 45 | super.afterHandshake(request, response, wsHandler, ex); 46 | } 47 | 48 | 49 | } -------------------------------------------------------------------------------- /src/main/java/com/dfs/websocket/MsgWeixin.java: -------------------------------------------------------------------------------- 1 | package com.dfs.websocket; 2 | 3 | import java.util.Date; 4 | 5 | public class MsgWeixin { 6 | 7 | 8 | private Date createtime; 9 | private String schoolId; 10 | private String wxMsgId; 11 | private String toUserId; 12 | private String appId; 13 | private String content; 14 | private String fromUserId; 15 | private String status; 16 | private String chatId; 17 | private String msgType; 18 | 19 | public Date getCreatetime() { 20 | return createtime; 21 | } 22 | 23 | public void setCreatetime(Date createtime) { 24 | this.createtime = createtime; 25 | } 26 | 27 | public String getSchoolId() { 28 | return schoolId; 29 | } 30 | 31 | public void setSchoolId(String schoolId) { 32 | this.schoolId = schoolId; 33 | } 34 | 35 | public String getWxMsgId() { 36 | return wxMsgId; 37 | } 38 | 39 | public void setWxMsgId(String wxMsgId) { 40 | this.wxMsgId = wxMsgId; 41 | } 42 | 43 | public String getToUserId() { 44 | return toUserId; 45 | } 46 | 47 | public void setToUserId(String toUserId) { 48 | this.toUserId = toUserId; 49 | } 50 | 51 | public String getAppId() { 52 | return appId; 53 | } 54 | 55 | public void setAppId(String appId) { 56 | this.appId = appId; 57 | } 58 | 59 | public String getContent() { 60 | return content; 61 | } 62 | 63 | public void setContent(String content) { 64 | this.content = content; 65 | } 66 | 67 | public String getFromUserId() { 68 | return fromUserId; 69 | } 70 | 71 | public void setFromUserId(String fromUserId) { 72 | this.fromUserId = fromUserId; 73 | } 74 | 75 | public String getStatus() { 76 | return status; 77 | } 78 | 79 | public void setStatus(String status) { 80 | this.status = status; 81 | } 82 | 83 | public String getChatId() { 84 | return chatId; 85 | } 86 | 87 | public void setChatId(String chatId) { 88 | this.chatId = chatId; 89 | } 90 | 91 | public String getMsgType() { 92 | return msgType; 93 | } 94 | 95 | public void setMsgType(String msgType) { 96 | this.msgType = msgType; 97 | } 98 | 99 | } -------------------------------------------------------------------------------- /src/main/java/com/dfs/websocket/PresenceChannelInterceptor.java: -------------------------------------------------------------------------------- 1 | package com.dfs.websocket; 2 | 3 | import com.dfs.utils.RedisSingletonUtil; 4 | import org.slf4j.Logger; 5 | import org.slf4j.LoggerFactory; 6 | import org.springframework.messaging.Message; 7 | import org.springframework.messaging.MessageChannel; 8 | import org.springframework.messaging.simp.stomp.StompHeaderAccessor; 9 | import org.springframework.messaging.support.ChannelInterceptorAdapter; 10 | import org.springframework.stereotype.Component; 11 | 12 | /** 13 | * stomp連接處理類 14 | * Created by taoxy1988 on 2019/3/10 15 | */ 16 | @Component 17 | public class PresenceChannelInterceptor extends ChannelInterceptorAdapter { 18 | 19 | private static final Logger logger = LoggerFactory.getLogger(PresenceChannelInterceptor.class); 20 | private static final RedisSingletonUtil redisUtil = new RedisSingletonUtil(); 21 | 22 | @Override 23 | public void postSend(Message message, MessageChannel channel, boolean sent) { 24 | StompHeaderAccessor sha = StompHeaderAccessor.wrap(message); 25 | // ignore non-STOMP messages like heartbeat messages 26 | if (sha.getCommand() == null) { 27 | return; 28 | } 29 | //這裏的sessionId和accountId對應HttpSessionIdHandshakeInterceptor攔截器的存放key 30 | String sessionId = sha.getSessionAttributes().get(Constants.SESSIONID).toString(); 31 | String accountId = sha.getSessionAttributes().get(Constants.SKEY_ACCOUNT_ID).toString(); 32 | //判斷客戶端的連接狀態 33 | switch (sha.getCommand()) { 34 | case CONNECT: 35 | connect(sessionId, accountId); 36 | break; 37 | case CONNECTED: 38 | break; 39 | case DISCONNECT: 40 | disconnect(sessionId, accountId, sha); 41 | break; 42 | default: 43 | break; 44 | } 45 | } 46 | 47 | //連接成功 48 | private void connect(String sessionId, String accountId) { 49 | logger.debug(" STOMP Connect [sessionId: " + sessionId + "]"); 50 | //存放至ehcache 51 | String cacheName = CacheConstant.WEBSOCKET_ACCOUNT; 52 | //若在多個瀏覽器登錄,直接覆蓋保存 53 | redisUtil.setString(cacheName + accountId, sessionId); 54 | } 55 | 56 | //斷開連接 57 | private void disconnect(String sessionId, String accountId, StompHeaderAccessor sha) { 58 | logger.debug("STOMP Disconnect [sessionId: " + sessionId + "]"); 59 | sha.getSessionAttributes().remove(Constants.SESSIONID); 60 | sha.getSessionAttributes().remove(Constants.SKEY_ACCOUNT_ID); 61 | //ehcache移除 62 | String cacheName = CacheConstant.WEBSOCKET_ACCOUNT; 63 | if (redisUtil.get(cacheName + accountId) != null) { 64 | redisUtil.remove(cacheName + accountId); 65 | } 66 | 67 | } 68 | 69 | } -------------------------------------------------------------------------------- /src/main/java/com/dfs/websocket/StompSubscribeEventListener.java: -------------------------------------------------------------------------------- 1 | package com.dfs.websocket; 2 | 3 | import org.slf4j.Logger; 4 | import org.slf4j.LoggerFactory; 5 | import org.springframework.context.ApplicationListener; 6 | import org.springframework.messaging.simp.stomp.StompHeaderAccessor; 7 | import org.springframework.stereotype.Component; 8 | import org.springframework.web.socket.messaging.SessionSubscribeEvent; 9 | 10 | /** 11 | * 監聽訂閱地址的用戶 12 | * Created by taoxy1988 on 2019/3/10 13 | */ 14 | @Component 15 | public class StompSubscribeEventListener implements ApplicationListener { 16 | 17 | private static final Logger logger = LoggerFactory.getLogger(StompSubscribeEventListener.class); 18 | 19 | @Override 20 | public void onApplicationEvent(SessionSubscribeEvent sessionSubscribeEvent) { 21 | StompHeaderAccessor headerAccessor = StompHeaderAccessor.wrap(sessionSubscribeEvent.getMessage()); 22 | //這裏的sessionId對應HttpSessionIdHandshakeInterceptor攔截器的存放key 23 | // String sessionId = headerAccessor.getSessionAttributes().get(Constants.SESSIONID).toString(); 24 | logger.info("stomp Subscribe : "+headerAccessor.getMessageHeaders() ); 25 | } 26 | } -------------------------------------------------------------------------------- /src/main/java/com/dfs/websocket/WebSocketConfig.java: -------------------------------------------------------------------------------- 1 | package com.dfs.websocket; 2 | import org.springframework.context.annotation.Bean; 3 | import org.springframework.context.annotation.Configuration; 4 | import org.springframework.messaging.simp.config.ChannelRegistration; 5 | import org.springframework.messaging.simp.config.MessageBrokerRegistry; 6 | import org.springframework.web.socket.config.annotation.*; 7 | 8 | /** 9 | * web socket配置 10 | * Created by taoxy1988 on 2019/3/10 11 | */ 12 | @Configuration 13 | //開啓對websocket的支持,使用stomp協議傳輸代理消息, 14 | // 這時控制器使用@MessageMapping和@RequestMaping一樣 15 | @EnableWebSocketMessageBroker 16 | public class WebSocketConfig extends AbstractWebSocketMessageBrokerConfigurer { 17 | 18 | 19 | /** 20 | * 服務器要監聽的端口,message會從這裏進來,要對這裏加一個Handler 21 | * 這樣在網頁中就可以通過websocket連接上服務了 22 | */ 23 | @Override 24 | public void registerStompEndpoints(StompEndpointRegistry stompEndpointRegistry) { 25 | //註冊stomp的節點,映射到指定的url,並指定使用sockjs協議 26 | stompEndpointRegistry.addEndpoint("/contactChatSocket").withSockJS().setInterceptors(httpSessionIdHandshakeInterceptor()); ; 27 | } 28 | 29 | //配置消息代理 30 | @Override 31 | public void configureMessageBroker(MessageBrokerRegistry registry) { 32 | // queue、topic、user代理 33 | registry.enableSimpleBroker("/queue", "/topic","/user"); 34 | registry.setUserDestinationPrefix("/user/"); 35 | } 36 | 37 | /** 38 | * 消息傳輸參數配置 39 | */ 40 | @Override 41 | public void configureWebSocketTransport(WebSocketTransportRegistration registry) { 42 | registry.setMessageSizeLimit(8192) //設置消息字節數大小 43 | .setSendBufferSizeLimit(8192)//設置消息緩存大小 44 | .setSendTimeLimit(10000); //設置消息發送時間限制毫秒 45 | } 46 | 47 | 48 | /** 49 | * 輸入通道參數設置 50 | */ 51 | @Override 52 | public void configureClientInboundChannel(ChannelRegistration registration) { 53 | registration.taskExecutor().corePoolSize(4) //設置消息輸入通道的線程池線程數 54 | .maxPoolSize(8)//最大線程數 55 | .keepAliveSeconds(60);//線程活動時間 56 | registration.setInterceptors(presenceChannelInterceptor()); 57 | } 58 | 59 | /** 60 | * 輸出通道參數設置 61 | */ 62 | @Override 63 | public void configureClientOutboundChannel(ChannelRegistration registration) { 64 | registration.taskExecutor().corePoolSize(4).maxPoolSize(8); 65 | registration.setInterceptors(presenceChannelInterceptor()); 66 | } 67 | 68 | @Bean 69 | public HttpSessionIdHandshakeInterceptor httpSessionIdHandshakeInterceptor() { 70 | return new HttpSessionIdHandshakeInterceptor(); 71 | } 72 | 73 | @Bean 74 | public PresenceChannelInterceptor presenceChannelInterceptor() { 75 | return new PresenceChannelInterceptor(); 76 | } 77 | 78 | 79 | } -------------------------------------------------------------------------------- /src/main/resources/applicationContext.xml: -------------------------------------------------------------------------------- 1 | 2 | 19 | 20 | 22 | 23 | 24 | 25 | 26 | 27 | 29 | 30 | 31 | 32 | 33 | 35 | 36 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | classpath:src/main/resources/environment/${env}.properties 48 | classpath:sysConfig.properties 49 | 50 | 51 | 52 | 53 | 54 | 56 | 57 | 58 | 59 | 60 | 61 | 62 | 63 | 64 | 65 | 66 | 67 | 68 | 69 | 70 | 71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | 83 | 84 | 85 | 86 | 87 | 88 | 89 | 90 | 91 | 92 | 93 | 94 | 95 | 96 | 97 | -------------------------------------------------------------------------------- /src/main/resources/com/dfs/SenseAgroAdminMapper.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | and ${criterion.condition} 27 | 28 | 29 | and ${criterion.condition} #{criterion.value} 30 | 31 | 32 | and ${criterion.condition} #{criterion.value} and #{criterion.secondValue} 33 | 34 | 35 | and ${criterion.condition} 36 | 38 | #{listItem} 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | and ${criterion.condition} 57 | 58 | 59 | and ${criterion.condition} #{criterion.value} 60 | 61 | 62 | and ${criterion.condition} #{criterion.value} and #{criterion.secondValue} 63 | 64 | 65 | and ${criterion.condition} 66 | 68 | #{listItem} 69 | 70 | 71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | id, member_name, member_password, register_time, update_time, is_banned 80 | 81 | 95 | 101 | 102 | delete from sense_agro_admin 103 | where id = #{id,jdbcType=INTEGER} 104 | 105 | 106 | delete from sense_agro_admin 107 | 108 | 109 | 110 | 111 | 112 | insert into sense_agro_admin (id, member_name, member_password, 113 | register_time, update_time, is_banned 114 | ) 115 | values (#{id,jdbcType=INTEGER}, #{memberName,jdbcType=VARCHAR}, #{memberPassword,jdbcType=VARCHAR}, 116 | #{registerTime,jdbcType=INTEGER}, #{updateTime,jdbcType=INTEGER}, #{isBanned,jdbcType=INTEGER} 117 | ) 118 | 119 | 120 | insert into sense_agro_admin 121 | 122 | 123 | id, 124 | 125 | 126 | member_name, 127 | 128 | 129 | member_password, 130 | 131 | 132 | register_time, 133 | 134 | 135 | update_time, 136 | 137 | 138 | is_banned, 139 | 140 | 141 | 142 | 143 | #{id,jdbcType=INTEGER}, 144 | 145 | 146 | #{memberName,jdbcType=VARCHAR}, 147 | 148 | 149 | #{memberPassword,jdbcType=VARCHAR}, 150 | 151 | 152 | #{registerTime,jdbcType=INTEGER}, 153 | 154 | 155 | #{updateTime,jdbcType=INTEGER}, 156 | 157 | 158 | #{isBanned,jdbcType=INTEGER}, 159 | 160 | 161 | 162 | 168 | 169 | update sense_agro_admin 170 | 171 | 172 | member_name = #{memberName,jdbcType=VARCHAR}, 173 | 174 | 175 | member_password = #{memberPassword,jdbcType=VARCHAR}, 176 | 177 | 178 | register_time = #{registerTime,jdbcType=INTEGER}, 179 | 180 | 181 | update_time = #{updateTime,jdbcType=INTEGER}, 182 | 183 | 184 | is_banned = #{isBanned,jdbcType=INTEGER}, 185 | 186 | 187 | where id = #{id,jdbcType=INTEGER} 188 | 189 | 190 | update sense_agro_admin 191 | set member_name = #{memberName,jdbcType=VARCHAR}, 192 | member_password = #{memberPassword,jdbcType=VARCHAR}, 193 | register_time = #{registerTime,jdbcType=INTEGER}, 194 | update_time = #{updateTime,jdbcType=INTEGER}, 195 | is_banned = #{isBanned,jdbcType=INTEGER} 196 | where id = #{id,jdbcType=INTEGER} 197 | 198 | -------------------------------------------------------------------------------- /src/main/resources/com/dfs/SenseAgroUserMapper.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | id, specialist_id, add_time, valid_time, sessionId 13 | 14 | 22 | 28 | 29 | delete from sense_agro_user 30 | where id = #{id,jdbcType=INTEGER} 31 | 32 | 33 | insert into sense_agro_user (id, specialist_id, add_time, 34 | valid_time, sessionId) 35 | values (#{id,jdbcType=INTEGER}, #{specialistId,jdbcType=INTEGER}, #{addTime,jdbcType=INTEGER}, 36 | #{validTime,jdbcType=INTEGER}, #{sessionid,jdbcType=VARCHAR}) 37 | 38 | 39 | insert into sense_agro_user 40 | 41 | 42 | id, 43 | 44 | 45 | specialist_id, 46 | 47 | 48 | add_time, 49 | 50 | 51 | valid_time, 52 | 53 | 54 | sessionId, 55 | 56 | 57 | 58 | 59 | #{id,jdbcType=INTEGER}, 60 | 61 | 62 | #{specialistId,jdbcType=INTEGER}, 63 | 64 | 65 | #{addTime,jdbcType=INTEGER}, 66 | 67 | 68 | #{validTime,jdbcType=INTEGER}, 69 | 70 | 71 | #{sessionid,jdbcType=VARCHAR}, 72 | 73 | 74 | 75 | 76 | update sense_agro_user 77 | 78 | 79 | specialist_id = #{specialistId,jdbcType=INTEGER}, 80 | 81 | 82 | add_time = #{addTime,jdbcType=INTEGER}, 83 | 84 | 85 | valid_time = #{validTime,jdbcType=INTEGER}, 86 | 87 | 88 | sessionId = #{sessionid,jdbcType=VARCHAR}, 89 | 90 | 91 | where id = #{id,jdbcType=INTEGER} 92 | 93 | 94 | update sense_agro_user 95 | set specialist_id = #{specialistId,jdbcType=INTEGER}, 96 | add_time = #{addTime,jdbcType=INTEGER}, 97 | valid_time = #{validTime,jdbcType=INTEGER}, 98 | sessionId = #{sessionid,jdbcType=VARCHAR} 99 | where id = #{id,jdbcType=INTEGER} 100 | 101 | -------------------------------------------------------------------------------- /src/main/resources/mybatis-config.xml: -------------------------------------------------------------------------------- 1 | 2 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | -------------------------------------------------------------------------------- /src/main/resources/springmvc.xml: -------------------------------------------------------------------------------- 1 | 2 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | application/json;charset=utf-8 35 | text/html;charset=utf-8 36 | 37 | application/x-www-form-urlencoded;charset=utf-8 38 | multipart/form-data;charset=utf-8 39 | application/x-www-form-urlencoded 40 | text/plain;charset=utf-8 41 | 42 | 43 | 44 | 45 | 46 | 47 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 57 | 58 | 59 | /WEB-INF/ 60 | 61 | 62 | 63 | .html 64 | 65 | 66 | 67 | 68 | 69 | 77 | -------------------------------------------------------------------------------- /src/main/webapp/WEB-INF/web.xml: -------------------------------------------------------------------------------- 1 | 4 | 5 | 6 | 7 | 8 | 9 | org.springframework.web.context.request.RequestContextListener 10 | 11 | 12 | 13 | 14 | org.springframework.web.context.ContextLoaderListener 15 | 16 | 17 | 18 | contextConfigLocation 19 | classpath:applicationContext.xml 20 | 21 | 22 | 23 | spring.profiles.active 24 | dev 25 | 26 | 27 | spring.profiles.default 28 | dev 29 | 30 | 31 | spring.liveBeansView.mbeanDomain 32 | dev 33 | 34 | 35 | 36 | SpringMVC 37 | org.springframework.web.servlet.DispatcherServlet 38 | 39 | contextConfigLocation 40 | classpath:springmvc.xml 41 | 42 | 1 43 | 44 | 45 | 209715200 46 | 524288000 47 | 0 48 | 49 | 50 | 51 | SpringMVC 52 | / 53 | 54 | 55 | 56 | 57 | CharacterEncodingFilter 58 | org.springframework.web.filter.CharacterEncodingFilter 59 | 60 | encoding 61 | utf-8 62 | 63 | 64 | forceEncoding 65 | true 66 | 67 | 68 | 69 | CharacterEncodingFilter 70 | /* 71 | 72 | 73 | index.html 74 | 75 | 76 | 77 | corsFilter 78 | com.dfs.filter.CorsFilter 79 | 80 | allowOrigin 81 | http://localhost:8080,http://www.taoxy.online 82 | 83 | 84 | allowMethods 85 | GET,POST,PUT,DELETE,OPTIONS 86 | 87 | 88 | allowCredentials 89 | true 90 | 91 | 92 | allowHeaders 93 | DNT,X-Mx-ReqToken,Keep-Alive,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Authorization,Token 94 | 95 | 96 | exposeHeaders 97 | DNT,X-Mx-ReqToken,Keep-Alive,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Authorization,Token 98 | 99 | 100 | 101 | corsFilter 102 | /* 103 | 104 | 105 | -------------------------------------------------------------------------------- /src/main/webapp/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 |