微信公众号工具类
package com.xxx.service.attendance.provider.utils;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.xxx.service.attendance.provider.persistence.entity.CheckLog;
import com.xxxx.standard.service.spring.redis.tool.RedisUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Component;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;
import javax.annotation.PostConstruct;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.transform.OutputKeys;
import javax.xml.transform.Transformer;
import javax.xml.transform.TransformerFactory;
import javax.xml.transform.dom.DOMSource;
import javax.xml.transform.stream.StreamResult;
import java.io.ByteArrayInputStream;
import java.io.InputStream;
import java.io.StringWriter;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.text.SimpleDateFormat;
import java.util.Arrays;
import java.util.HashMap;
import java.util.Map;
@Component
public class WxUtils {
private static Logger logger = LoggerFactory.getLogger(WxUtils.class);
public static final String WX_TOKEN_KEY = "WX_TOKEN_KEY";
public static final String WX_MESSAGE_PREFIX = "WX_MESSAGE_PREFIX:%s";
@Value("${wx.miniprogram.appId}")
private String miniProgramAppId;
@Value("${wx.miniprogram.path}")
private String miniProgramPath;
@Value("${wx.official.account.template}")
private String officialAccountTemplateId;
public static String WX_CHECK_NOTIC_TEMPLATEID = null;
public static String WX_CHECK_NOTIC_MINIPROGRAM_APP_ID = null;
public static String WX_CHECK_NOTIC_MINIPROGRAM_PATH = null;
public static final SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
public static final SimpleDateFormat sdf1 = new SimpleDateFormat("HH:mm:ss");
@PostConstruct
public void init(){
WX_CHECK_NOTIC_TEMPLATEID = this.officialAccountTemplateId;
WX_CHECK_NOTIC_MINIPROGRAM_APP_ID = this.miniProgramAppId;
WX_CHECK_NOTIC_MINIPROGRAM_PATH = this.miniProgramPath;
}
public static String getToken(String appId,String secret){
String token = RedisUtils.get(WX_TOKEN_KEY);
if(token == null){
String str = HttpUtils.get("https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid="+appId+"&secret="+secret);
JSONObject jsonObject = JSON.parseObject(str);
token = jsonObject.get("access_token") == null?null:(String)jsonObject.get("access_token");
Integer expiresIn = jsonObject.get("expires_in") == null?null:(Integer)jsonObject.get("expires_in");
if(token != null){
RedisUtils.set(WX_TOKEN_KEY,token,(expiresIn-100)*1000);
}
}
return token;
}
public static JSONObject getUserInfo(String accessToken,String openId){
String str = HttpUtils.get("https://api.weixin.qq.com/cgi-bin/user/info?access_token="+accessToken+"&openid="+openId+"&lang=zh_CN");
return JSON.parseObject(str);
}
public static Map<String, String> xmlToMap(String strXml) throws Exception {
Map<String, String> data = new HashMap<String, String>();
DocumentBuilderFactory documentBuilderFactory = DocumentBuilderFactory.newInstance();
DocumentBuilder documentBuilder= documentBuilderFactory.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) {
ex.printStackTrace();
}
return data;
}
public static String mapToXml(Map<String, String> data) throws Exception {
DocumentBuilderFactory documentBuilderFactory = DocumentBuilderFactory.newInstance();
DocumentBuilder documentBuilder= documentBuilderFactory.newDocumentBuilder();
org.w3c.dom.Document document = documentBuilder.newDocument();
org.w3c.dom.Element root = document.createElement("xml");
document.appendChild(root);
for (String key: data.keySet()) {
String value = data.get(key);
if (value == null) {
value = "";
}
value = value.trim();
org.w3c.dom.Element filed = document.createElement(key);
filed.appendChild(document.createTextNode(value));
root.appendChild(filed);
}
TransformerFactory tf = TransformerFactory.newInstance();
Transformer transformer = tf.newTransformer();
DOMSource source = new DOMSource(document);
transformer.setOutputProperty(OutputKeys.ENCODING, "UTF-8");
transformer.setOutputProperty(OutputKeys.INDENT, "yes");
StringWriter writer = new StringWriter();
StreamResult result = new StreamResult(writer);
transformer.transform(source, result);
String output = writer.getBuffer().toString();
try {
writer.close();
}
catch (Exception ex) {
ex.printStackTrace();
}
return output;
}
public static boolean checkSignature(String signature, String timestamp, String nonce,String token) {
String[] arr = new String[] { token, timestamp, nonce };
Arrays.sort(arr);
StringBuilder content = new StringBuilder();
for (int i = 0; i < arr.length; i++) {
content.append(arr[i]);
}
MessageDigest md = null;
String tmpStr = null;
try {
md = MessageDigest.getInstance("SHA-1");
byte[] digest = md.digest(content.toString().getBytes());
tmpStr = byteToStr(digest);
} catch (NoSuchAlgorithmException e) {
e.printStackTrace();
}
content = null;
return tmpStr != null ? tmpStr.equals(signature.toUpperCase()) : false;
}
private static String byteToStr(byte[] byteArray) {
String strDigest = "";
for (int i = 0; i < byteArray.length; i++) {
strDigest += byteToHexStr(byteArray[i]);
}
return strDigest;
}
private static String byteToHexStr(byte mByte) {
char[] Digit = { '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F' };
char[] tempArr = new char[2];
tempArr[0] = Digit[(mByte >>> 4) & 0X0F];
tempArr[1] = Digit[mByte & 0X0F];
String s = new String(tempArr);
return s;
}
public static boolean customSend(String token,Map map){
String url = "https://api.weixin.qq.com/cgi-bin/message/custom/send?access_token="+token;
String param = JSON.toJSONString(map);
String str = HttpUtils.postJson(url,param);
JSONObject jsonObject = JSON.parseObject(str);
int errcode = jsonObject.get("errcode") == null?-1:(int)jsonObject.get("errcode");
if(errcode != 0){
System.err.println("param:"+param+" \nresult:"+str);
}
return errcode == 0;
}
public static boolean sendLogNotic(String accessToken, String openId, CheckLog checkLog){
Map map = new HashMap<>();
map.put("touser",openId);
map.put("template_id",WX_CHECK_NOTIC_TEMPLATEID);
map.put("topcolor","#FF0000");
Map miniprogram = new HashMap<>();
miniprogram.put("appid",WX_CHECK_NOTIC_MINIPROGRAM_APP_ID);
miniprogram.put("pagepath",WX_CHECK_NOTIC_MINIPROGRAM_PATH);
map.put("miniprogram",miniprogram);
Map data = new HashMap<>();
Map first = new HashMap<>();
first.put("value","您好,"+checkLog.getStudentName()+"在学校考勤了");
first.put("color","#173177");
data.put("first",first);
Map keyword1 = new HashMap<>();
keyword1.put("value",checkLog.getStudentName());
keyword1.put("color","#173177");
data.put("keyword1",keyword1);
Map keyword2 = new HashMap<>();
keyword2.put("value",sdf.format(checkLog.getDayTime())+" "+sdf1.format(checkLog.getHourTime()));
keyword2.put("color","#173177");
data.put("keyword2",keyword2);
Map remark = new HashMap<>();
remark.put("value","点击查看详情");
remark.put("color","#173177");
data.put("remark",remark);
map.put("data",data);
String url = "https://api.weixin.qq.com/cgi-bin/message/template/send?access_token="+accessToken;
String paramStr = JSON.toJSONString(map);
String str = HttpUtils.postJson(url,paramStr);
JSONObject result = JSON.parseObject(str);
if(result.get("errcode") != null && (Integer)result.get("errcode") == 0){
return true;
}
logger.error("sendLogNotic-url:{}",url);
logger.error("sendLogNotic-paramStr:{}",paramStr);
logger.error("sendLogNotic-str:{}",str);
return false;
}
}