java版微信公众号开发(五)模版消息
模板消息仅用于公众号向用户发送重要的服务通知,只能用于符合其要求的服务场景中,如信用卡刷卡通知,商品购买成功通知等。不支持广告等营销类消息以及其它所有可能对用户造成骚扰的消息。记录好模版ID以及参数的名称。废话不多说,直接上干货。
·
模板消息仅用于公众号向用户发送重要的服务通知,只能用于符合其要求的服务场景中,如信用卡刷卡通知,商品购买成功通知等。不支持广告等营销类消息以及其它所有可能对用户造成骚扰的消息。
废话不多说,直接上干货
以测试号为例,正式号需要公众号认证之后再模版库中添加,测试号可直接新增:
最终实现结果:
记录好模版ID以及参数的名称。以下是代码实现:
/** 处理流程审批下发的业务服务层方法实现
*/
@Override
public void flowTemPlateMessageService(Param param) {
logger.info("【消息模块】流程审批模版发送:===>【{}】", param);
//备份,token过期需要递归处理
FlowTemplateMessageParam param2 = param;
//下面的token换成自己的token获取逻辑
String url = String.format("https://api.weixin.qq.com/cgi-bin/message/template/send?access_token=%s",
token);
//1.获取审批流程的json模版
String data = MessageUtil.getFlowMessageJson();
ObjectMapper objectMapper = new ObjectMapper();
FlowTemplate template = null;
try {
template = objectMapper.readValue(data, FlowTemplate.class);
} catch (JsonProcessingException e) {
logger.warn("【消息模块】流程审批服务层异常:===>【objectMapper】【{}】", e.toString());
String message = "数据格式错误";
logger.warn(message);
throw new ServiceException(ServiceCode.ERROR_SERVICE, message);
}
//2.将参数设置到json模版中
FlowTemplate.Data dataObject = new FlowTemplate.Data();
//2.1审批编号
String character_string166 = param.getInstanceId();
if(character_string166.length()>=32){
character_string166 = character_string166.substring(0,16)+"...";
}
FlowTemplate.Keyword character_string16 = new FlowTemplate.Keyword();
character_string16.setValue(character_string166);
dataObject.setCharacter_string16(character_string16);
//2.2审批类型
//判断是否超过20个字符
String thing99 = param.getName();
if(thing99.length()>=18){
thing99 = thing99.substring(0,15)+"...";
}
FlowTemplate.Keyword thing9 = new FlowTemplate.Keyword();
thing9.setValue(thing99);
dataObject.setThing9(thing9);
//2.3流程名称
String thing77 = param.getTheme();
if(thing77.length()>=18){
thing77 = thing77.substring(0,15)+"...";
}
FlowTemplate.Keyword thing7 = new FlowTemplate.Keyword();
thing7.setValue(thing77);
dataObject.setThing7(thing7);
//2.4申请人
String thing88 = param.getPersonnel();
if(thing88.length()>=18){
thing88 = thing88.substring(0,15)+"...";
}
FlowTemplate.Keyword thing8 = new FlowTemplate.Keyword();
thing8.setValue(thing88);
dataObject.setThing8(thing8);
//2.5申请时间
FlowTemplate.Keyword time12 = new FlowTemplate.Keyword();
time12.setValue(param.getTime());
dataObject.setTime12(time12);
template.setData(dataObject);
//3.获取接收者的openId
String openId = param.getOpenid();
//4.将后续所需要用的参数放入到Url中
template.setTouser(param.getOpenid());
//flowTemplateId模版消息ID,可采用多种方式获取
template.setTemplateId(flowTemplateId);
template.setUrl("http://www.baidu.com");//不配置url模版消息不可跳转
// 将对象转换为 JSON 字符串
logger.info("【消息模块】流程审批模版消息附带的URL:===>【{}】", template.getUrl());
String jsonString = null;
try {
jsonString = objectMapper.writeValueAsString(template);
} catch (JsonProcessingException e) {
logger.warn("【消息模块】流程审批服务层异常:===>【jsonString->objectMapper】【{}】", e.toString());
String message = "数据格式错误";
logger.warn(message);
throw new ServiceException(ServiceCode.ERROR_SERVICE, message);
}
//5.发送请求
logger.info("【消息模块】调用微信发送消息模版参数json数据:===> 【{}】",jsonString);
String result= HttpUtil.doPost(url, jsonString);
logger.info("【消息模块】调用微信发送消息模版返回结果:===> 【{}】",result);
String message = "";
try {
//6.记录发送的消息
JSONObject jsonObject = new JSONObject(result);
int code = jsonObject.getInt("errcode");
if(code == 43004){
//需要接收者关注
message = "需要接收者关注";
logger.warn("【消息模块】流程审批模版发送失败:===>【{}】
【{}】",param2,message);
throw new ServiceException(ServiceCode.ERROR_SERVICE ,message);
}else if(code == 42007 ){
//用户修改微信密码,需要重新授权
message = "用户公众号授权信息过期,请确认用户关注情况";
logger.warn("【消息模块】流程审批模版发送失败:===>【{}】【{}】",param2,message);
throw new ServiceException(ServiceCode.ERROR_SERVICE, message);
}else if(code == 50005){
//用户未关注公众号
message = "用户未关注公众号,请确认客户关注情况";
logger.warn("【消息模块】流程审批模版发送失败:===>【{}】【{}】",param2,message);
throw new ServiceException(ServiceCode.ERROR_SERVICE, message);
}else if(code == 40014 || code ==40001 || code ==42001){
logger.info("【消息模块】微信access_token过期或无效,需要重新获取token并发送模版消息");
//重新获取token,递归处理
flowTemPlateMessageService(param2);
}
else if(code == 43101 ){
logger.info("【消息模块】客户拒收该消息");
message = "客户拒收该消息推送,请确认客户微信公众号设置:公众号主页===>右上三个点===>设置===>通知消息管理";
throw new ServiceException(ServiceCode.ERROR_SERVICE ,message);
}
}catch (Exception e){
logger.error("未知错误:",e);
}
}
以下是三个工具类:
MessageUtil、FlowTemplate、HttpUtil
MessageUtil
import com.alibaba.fastjson.JSONObject;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
/***
* 微信模版json样式工具类
**/
public class MessageUtil {
/**
* 流程审批模版的json样式
* @return
*/
public static String getFlowMessageJson(){
return "{\n" +
" \"touser\":\"OPENID\",\n" +
" \"template_id\":\"ngqIpbwh8tQlEpBO27izEYtY\",\n" +
" \"url\":\"http://weixin.qq.com/download\", \n" +
" \"data\":{\n" +
" \"character_string16\":{\n" +
" \"value\":\"流程编号\"\n" +
" },\n" +
" \"thing9\": {\n" +
" \"value\":\"审批类型\"\n" +
" },\n" +
" \"thing7\": {\n" +
" \"value\":\"流程名称\"\n" +
" },\n" +
" \"thing8\": {\n" +
" \"value\":\"申请人\"\n" +
" },\n" +
" \"time12\": {\n" +
" \"value\":\"申请日期\"\n" +
" }\n" +
" }\n" +
" }";
}
}
FlowTemplate
/**
* 流程审批的消息模版对象实体类
*/
public class FlowTemplate implements Serializable {
private String touser;
@JsonProperty("template_id")
private String templateId;
private String url;
private Data data;
public static class Data {
private Keyword character_string16;
private Keyword thing9;
private Keyword thing7;
private Keyword thing8;
private Keyword time12;
// 创建对应的 getter 和 setter 方法
}
public static class Keyword {
private String value;
// 创建对应的 getter 和 setter 方法
}
// 创建对应的 getter 和 setter 方法
}
HttpUtil
/**
* 发送http请求的工具类
*/
public class HttpUtil {
/**
* post方式的http请求
* @param httpUrl 请求地址
* @param param 请求参数
* @return 返回结果
*/
public static String doPost(String httpUrl, String param) {
HttpURLConnection connection = null;
InputStream inputStream = null;
OutputStream outputStream = null;
BufferedReader bufferedReader = 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);
// 设置传入参数的格式:请求参数应该是 name1=value1&name2=value2 的形式。
connection.setRequestProperty("Content-Type", "application/x-www-form-urlencoded");
// 通过连接对象获取一个输出流
outputStream = connection.getOutputStream();
// 通过输出流对象将参数写出去/传输出去,它是通过字节数组写出的
outputStream.write(param.getBytes());
// 通过连接对象获取一个输入流,向远程读取
if (connection.getResponseCode() == 200) {
inputStream = connection.getInputStream();
// 对输入流对象进行包装:charset根据工作项目组的要求来设置
bufferedReader = new BufferedReader(new InputStreamReader(inputStream, StandardCharsets.UTF_8));
StringBuilder sbf = new StringBuilder();
String temp;
// 循环遍历一行一行读取数据
while ((temp = bufferedReader.readLine()) != null) {
sbf.append(temp);
sbf.append(System.getProperty("line.separator"));
}
result = sbf.toString();
}
} catch (IOException e) {
e.printStackTrace();
} finally {
// 关闭资源
if (null != bufferedReader) {
try {
bufferedReader.close();
} catch (IOException e) {
e.printStackTrace();
}
}
if (null != outputStream) {
try {
outputStream.close();
} catch (IOException e) {
e.printStackTrace();
}
}
if (null != inputStream) {
try {
inputStream.close();
} catch (IOException e) {
e.printStackTrace();
}
}
if (connection != null) {
connection.disconnect();
}
}
return result;
}
}
更多推荐
已为社区贡献4条内容
所有评论(0)