package abc.controller; import com.alibaba.fastjson.JSONObject; import lombok.extern.slf4j.Slf4j; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.data.redis.core.RedisTemplate; import org.springframework.data.redis.core.StringRedisTemplate; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RestController; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import java.io.OutputStream; import java.util.ArrayList; import java.util.List; import java.util.Map; import java.util.concurrent.TimeUnit; @RestController @RequestMapping("/weixin") @Slf4j public class WxGZHMsgController { public static final String token = "aadffxxxxxxxx"; public static String access_token=""; private StringRedisTemplate stringRedisTemplate; private RedisTemplate redisTemplate; public static final String wxc_="plzwxc_"; @Autowired public WxGZHMsgController(StringRedisTemplate stringRedisTemplate,RedisTemplate redisTemplate) { this.stringRedisTemplate = stringRedisTemplate; this.redisTemplate = redisTemplate; init(); } private void init() { try { String url = "https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid=aadffxxxxxxxx&secret=000xxxxxxsdfsdfsf"; String ret = HttpUtil.doGet(url); /* {"access_token":"ACCESS_TOKEN","expires_in":7200} */ JSONObject json = JSONObject.parseObject(ret); access_token = json.getString("access_token"); log.info("get access_token="+access_token); } catch (Exception e) { e.printStackTrace(); } } private String getTicket(String userId) { String url = "https://api.weixin.qq.com/cgi-bin/qrcode/create?access_token=" + access_token; String postStr = "{\"expire_seconds\": 604800, \"action_name\": \"QR_STR_SCENE\", \"action_info\": {\"scene\": {\"scene_str\": \""+wxc_ + userId + "\"}}}"; String ret = HttpUtil.doPost(url, postStr); /* {"ticket":"gQH47joAAAAAAAAAASxodHRwOi8vd2VpeGluLnFxLmNvbS9xL2taZ2Z3TVRtNzJXV1Brb3ZhYmJJAAIEZ23sUwMEmm 3sUw==","expire_seconds":60,"url":"http://weixin.qq.com/q/kZgfwMTm72WWPkovabbI"} */ JSONObject json = JSONObject.parseObject(ret); String ticket = json.getString("ticket"); String key=wxc_ + userId; stringRedisTemplate.opsForValue().set(key, ticket, 604800, TimeUnit.SECONDS); return ticket; } /** * 获取用户微信公众号平台扫码传图地址 * https://mp.weixin.qq.com/cgi-bin/showqrcode?ticket=gQHI8DwAAAAAAAAAAS5odHRwOi8vd2VpeGluLnFxLmNvbS9xLzAyOTR5MDFVc0dhemUxUXZFZnh3MVMAAgQf26dgAwQAjScA */ @RequestMapping("/getUserWxcTicketUrl") public FormatResult getUserWxcTicketUrl(HttpServletRequest request) { String userId = UserContext.getUserId(request); if(userId==null) { return new FormatResult(999,"登录超时或未登录"); } String key =wxc_+userId; String ticket = stringRedisTemplate.opsForValue().get(key); if(ticket==null||ticket.length()>256) { try { ticket = getTicket(userId); } catch (Exception e) { init(); ticket = getTicket(userId); } } log.info(userId+")getUserWxcTicketUrl ticket="+ticket); /* https://mp.weixin.qq.com/cgi-bin/showqrcode?ticket=gQGy8DwAAAAAAAAAAS5odHRwOi8vd2VpeGluLnFxLmNvbS9xLzAyLWpMTzFyc0dhemUxVTdLazF3MXMAAgQHIa1gAwQAjScA */ return new FormatResult("https://mp.weixin.qq.com/cgi-bin/showqrcode?ticket="+ticket); } public static final String wxcPicList_="wxcPicList_"; private boolean checkEchostr(String echostr,HttpServletRequest request, HttpServletResponse resp) { if(echostr!=null) { /* 参数 描述 signature 微信加密签名,signature结合了开发者填写的token参数和请求中的timestamp参数、nonce参数。 timestamp 时间戳 nonce 随机数 */ String signature=request.getParameter("signature"); String timestamp=request.getParameter("timestamp"); String nonce=request.getParameter("nonce"); log.info("echostr="+echostr); log.info("nonce="+nonce); log.info("timestamp="+timestamp); log.info("token="+token); log.info("signature="+signature); String source=timestamp+nonce+token; String sha1= CTools.getSha1(source); log.info("mySha1="+sha1); log.info("is Equal?="+sha1.equalsIgnoreCase(signature)); try { resp.getWriter().println(echostr); resp.getWriter().close(); request.getInputStream().close(); return sha1.equalsIgnoreCase(signature); } catch (Exception e) { } } return false; } @RequestMapping(value = "/receiveMsg") public void receiveMsg(HttpServletRequest request, HttpServletResponse resp) { String echostr=request.getParameter("echostr"); if(checkEchostr(echostr,request,resp)) { return; } StringBuilder sb= new StringBuilder(); byte[] buffer=new byte[512]; int n =-1; try { while ((n = request.getInputStream().read(buffer)) > 0) { sb.append(new String(buffer, 0, n)); } String xml=sb.toString(); log.info(xml); Map map =CTools.xmlToMap(xml); String FromUserName=(String)map.get("FromUserName"); String EventKey=(String)map.get("EventKey"); String PicUrl=(String)map.get("PicUrl"); if(PicUrl!=null&&PicUrl.startsWith("http")) { String userId=stringRedisTemplate.opsForValue().get(FromUserName); if(userId!=null) { String pic=PicUrl; String key=wxcPicList_+userId; List aList=(List)redisTemplate.opsForValue().get(key); if(aList == null) { aList = new ArrayList(); } aList.add(PicUrl); redisTemplate.opsForValue().set(key,aList,300,TimeUnit.SECONDS); log.info("key:"+key+";value="+aList); } } else if(EventKey!=null&&EventKey.contains(wxc_)) { int i=EventKey.indexOf(wxc_); String userId=EventKey.substring(i+wxc_.length()); stringRedisTemplate.opsForValue().set(FromUserName,userId,24*60*60,TimeUnit.SECONDS); String key=wxcPicList_+userId; redisTemplate.delete(key); try { OutputStream out=resp.getOutputStream(); out.write(getRetXml(FromUserName).getBytes("utf-8")); out.close(); request.getInputStream().close(); return; }catch (Exception e) { } } // } catch (Exception e) { e.printStackTrace(); } try { resp.getWriter().println("SUCCESS"); resp.getWriter().close(); request.getInputStream().close(); }catch (Exception e) { } } public String getRetXml(String toUser) { StringBuilder sb=new StringBuilder(); sb.append("\n<?xml version=\"1.0\" encoding=\"UTF-8\" ?>\n<xml>\n<ToUserName><![CDATA[").append(toUser).append("]]></ToUserName>\n<FromUserName><![CDATA[gh_5de2c93ceef9]]></FromUserName><CreateTime>"); sb.append(System.currentTimeMillis()/1000); sb.append("</CreateTime>\n<MsgType><![CDATA[text]]></MsgType>\n<Content><![CDATA[HI,您已开启微信传图模式,点击左下的小键盘图标,发送你需要上传的图片吧。]]></Content>\n</xml>\n\n"); return sb.toString(); } }
public static String doPost(String httpUrl, String param) { HttpURLConnection connection = null; InputStream is = null; OutputStream os = null; BufferedReader br = null; String result = null; try { URL url = new URL(httpUrl); // 通过远程url连接对象打开连接 connection = (HttpURLConnection) url.openConnection(); // 设置连接请求方式 connection.setRequestMethod("POST"); // 设置连接主机服务器超时时间:15000毫秒 connection.setConnectTimeout(15000); // 设置读取主机服务器返回数据超时时间:60000毫秒 connection.setReadTimeout(60000); // 默认值为:false,当向远程服务器传送数据/写数据时,需要设置为true connection.setDoOutput(true); // 默认值为:true,当前向远程服务读取数据时,设置为true,该参数可有可无 connection.setDoInput(true); // 设置传入参数的格式:请求参数应该是 name1=value1&name2=value2 的形式。 connection.setRequestProperty("Content-Type", "application/json"); // 设置鉴权信息:Authorization: Bearer da3efcbf-0845-4fe3-8aba-ee040be542c0 //connection.setRequestProperty("Authorization", "Bearer da3efcbf-0845-4fe3-8aba-ee040be542c0"); // 通过连接对象获取一个输出流 os = connection.getOutputStream(); // 通过输出流对象将参数写出去/传输出去,它是通过字节数组写出的 os.write(param.getBytes()); // 通过连接对象获取一个输入流,向远程读取 if (connection.getResponseCode() == 200) { is = connection.getInputStream(); // 对输入流对象进行包装:charset根据工作项目组的要求来设置 br = new BufferedReader(new InputStreamReader(is, "UTF-8")); StringBuffer sbf = new StringBuffer(); String temp = null; // 循环遍历一行一行读取数据 while ((temp = br.readLine()) != null) { sbf.append(temp); sbf.append("\r\n"); } result = sbf.toString(); } } catch (MalformedURLException e) { e.printStackTrace(); } catch (IOException e) { e.printStackTrace(); } finally { // 关闭资源 if (null != br) { try { br.close(); } catch (IOException e) { e.printStackTrace(); } } if (null != os) { try { os.close(); } catch (IOException e) { e.printStackTrace(); } } if (null != is) { try { is.close(); } catch (IOException e) { e.printStackTrace(); } } // 断开与远程地址url的连接 connection.disconnect(); } return result; }
public static String getSha1(String str) { if (null == str || 0 == str.length()) { return null; } char[] hexDigits = { '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'a', 'b', 'c', 'd', 'e', 'f'}; try { MessageDigest mdTemp = MessageDigest.getInstance("SHA1"); mdTemp.update(str.getBytes("UTF-8")); byte[] md = mdTemp.digest(); int j = md.length; char[] buf = new char[j * 2]; int k = 0; for (int i = 0; i < j; i++) { byte byte0 = md[i]; buf[k++] = hexDigits[byte0 >>> 4 & 0xf]; buf[k++] = hexDigits[byte0 & 0xf]; } return new String(buf); } catch (NoSuchAlgorithmException e) { e.printStackTrace(); } catch (UnsupportedEncodingException e) { e.printStackTrace(); } return ""; } /** * XML格式字符串转换为Map * * @param strXML XML字符串 * @return XML数据转换后的Map * @throws Exception */ public static Map<String, String> xmlToMap(String strXML) throws Exception { try { Map<String, String> data = new HashMap<String, String>(); DocumentBuilder documentBuilder = newDocumentBuilder(); InputStream stream = new ByteArrayInputStream(strXML.getBytes("UTF-8")); org.w3c.dom.Document doc = documentBuilder.parse(stream); doc.getDocumentElement().normalize(); NodeList nodeList = doc.getDocumentElement().getChildNodes(); for (int idx = 0; idx < nodeList.getLength(); ++idx) { Node node = nodeList.item(idx); if (node.getNodeType() == Node.ELEMENT_NODE) { org.w3c.dom.Element element = (org.w3c.dom.Element) node; data.put(element.getNodeName(), element.getTextContent()); } } try { stream.close(); } catch (Exception ex) { // do nothing } return data; } catch (Exception ex) { log.error(strXML+" can't trans to Map error:"+ex.getMessage(),ex); throw ex; } } public static DocumentBuilder newDocumentBuilder() throws ParserConfigurationException { DocumentBuilderFactory documentBuilderFactory = DocumentBuilderFactory.newInstance(); documentBuilderFactory.setFeature("http://apache.org/xml/features/disallow-doctype-decl", true); documentBuilderFactory.setFeature("http://xml.org/sax/features/external-general-entities", false); documentBuilderFactory.setFeature("http://xml.org/sax/features/external-parameter-entities", false); documentBuilderFactory.setFeature("http://apache.org/xml/features/nonvalidating/load-external-dtd", false); documentBuilderFactory.setFeature(XMLConstants.FEATURE_SECURE_PROCESSING, true); documentBuilderFactory.setXIncludeAware(false); documentBuilderFactory.setExpandEntityReferences(false); return documentBuilderFactory.newDocumentBuilder(); } public static Document newDocument() throws ParserConfigurationException { return newDocumentBuilder().newDocument(); }
全部评论