java编写微信小程序订阅消息提醒推送踩坑记录(2024-03-25热乎出炉)

按图索骥,如果有问题 欢迎在下方评论 看到我就会马上为您解答
开发者需要按照如下步骤完成:

填写服务器配置
验证服务器地址的有效性
第一步:填写服务器配置
登录小程序后台后,在「开发」-「开发管理」-「消息推送」中,管理员扫码启用消息服务,填写服务器地址(URL)、令牌(Token) 和 消息加密密钥(EncodingAESKey)等信息。
URL必须得服务器上有的接口地址 而且 如果没有会提示系统错误
TOken 有了接口没有进行token验证 就会告诉你Token效验失败
数据格式推荐JSON格式
在这里插入图片描述
第二步 验证接口
例如 /wxMessage 需将此请求允许匿名访问名单中
URL接口配置如 https://www.baidu.com/prod-api/wxMessage
在你提交配置的时候 wx会给你发get请求来验证地址

    @GetMapping("/wxMessage")
    public String wxMessage(HttpServletRequest request) throws Exception {
        String msgSignature = request.getParameter("signature");
        String msgTimestamp = request.getParameter("timestamp");
        String msgNonce = request.getParameter("nonce");
        String echostr = request.getParameter("echostr");
        if (WXPublicUtils.verifyUrl(msgSignature, msgTimestamp, msgNonce)) {
            return echostr;
        }
        return null;
    }

WXPublicUtils.verifyUrl 工具类


import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.security.MessageDigest;
import java.util.Arrays;

public class WXPublicUtils {

    private static final Logger logger = LoggerFactory.getLogger(WXPublicUtils.class);

    public static boolean verifyUrl(String msgSignature, String timeStamp, String nonce)
            throws Exception {
        String signature = getSHA1("配置的toekn密码", timeStamp, nonce);
        if (!signature.equals(msgSignature)) {
            throw new Exception("token验证失败");
        }
        return true;
    }


    public static String getSHA1(String token, String timestamp, String nonce) throws Exception {
        try {
            String[] array = new String[]{token, timestamp, nonce};
            StringBuffer sb = new StringBuffer();
            // 字符串排序
            Arrays.sort(array);
            for (int i = 0; i < 3; i++) {
                sb.append(array[i]);
            }
            String str = sb.toString();
            // SHA1签名生成
            MessageDigest md = MessageDigest.getInstance("SHA-1");
            md.update(str.getBytes());
            byte[] digest = md.digest();

            StringBuffer hexstr = new StringBuffer();
            String shaHex = "";
            for (int i = 0; i < digest.length; i++) {
                shaHex = Integer.toHexString(digest[i] & 0xFF);
                if (shaHex.length() < 2) {
                    hexstr.append(0);
                }
                hexstr.append(shaHex);
            }
            return hexstr.toString();
        } catch (Exception e) {
            e.printStackTrace();
            throw new Exception("token验证失败");
        }
    }
}

ok 由于是公网环境 配置完 部署至服务器 跑起来就可以保存成功了

接下来去订阅消息处增加模板 自行选择模板内容 记住模板id与模板参数名称

在这里插入图片描述
在这里插入图片描述

我这里是引用了两个模板 参数不一 自己进行区分

import lombok.Data;
import java.util.Map;
@Data
public class WxMssVo {
    private String touser;//用户openid
    private String template_id;//模版id
    private String page = "pages/index/index";//默认跳到小程序首页
    private Map<String, TemplateDataVo> data;//推送文字
}
import lombok.Data;
@Data
public class TemplateDataVo {

    private String value;
    public TemplateDataVo(String value){
        this.value=value;
    }

封装数据至微信客户端

import com.alibaba.fastjson2.JSON;
import com.alibaba.fastjson2.JSONObject;
import com.ruoyi.finance.domain.TemplateDataVo;
import com.ruoyi.finance.domain.WxMssVo;
import org.springframework.http.HttpEntity;
import org.springframework.http.HttpHeaders;
import org.springframework.http.MediaType;
import org.springframework.http.ResponseEntity;
import org.springframework.http.converter.StringHttpMessageConverter;
import org.springframework.web.client.RestTemplate;
import java.nio.charset.StandardCharsets;
import java.util.HashMap;
import java.util.Map;



public class WxUtil {
    private static RestTemplate restTemplate = new RestTemplate();



    final Boolean flag = false;

    private final static String appid = "xxx";
    private final static String appSecret = "xxx";

    public static String pushOneUser(String access_token, String openid, String type, String templateId, String[] keywords) {
        String  msg ="";
        try{
            String url = "https://api.weixin.qq.com/cgi-bin/message/subscribe/send" +
                    "?access_token=" + access_token;
            //拼接推送的模版
            WxMssVo wxMssVo = new WxMssVo();
            wxMssVo.setTouser(openid);//用户openid
            wxMssVo.setTemplate_id(templateId);//模版id
            Map<String, TemplateDataVo> m = new HashMap<>();

            if (type.equals("1")) {
                m.put("thing3", new TemplateDataVo(keywords[0]));
                m.put("amount4", new TemplateDataVo(keywords[1]));
                m.put("thing5", new TemplateDataVo(keywords[2]));
                wxMssVo.setData(m);
            } else if (type.equals("2")) {
                m.put("thing2", new TemplateDataVo(keywords[0]));
                m.put("thing3", new TemplateDataVo(keywords[1]));
                m.put("time4", new TemplateDataVo(keywords[2]));
                m.put("amount6", new TemplateDataVo(keywords[3]));
                m.put("thing5", new TemplateDataVo(keywords[4]));
                wxMssVo.setData(m);
            }
            if (restTemplate == null) {
                restTemplate = new RestTemplate();
            }
            System.out.println("小程序data信息={}"+ JSON.toJSONString(wxMssVo));
            HttpHeaders headers = new HttpHeaders();
            //设置编码  不设置转码 可能会出现 乱码问题
            MediaType types = MediaType.parseMediaType("application/json; charset=UTF-8");
            // 请勿轻易改变此提交方式,大部分的情况下,提交方式都是表单提交
            headers.setContentType(types);
            headers.add("Accept", MediaType.APPLICATION_JSON.toString());
            if (restTemplate == null) {
                restTemplate = new RestTemplate();
            }
            String string = JSONObject.toJSONString(wxMssVo);
            HttpEntity<String> requestEntity = new HttpEntity<String>(string, headers);
            ResponseEntity<String> responseEntity = restTemplate.postForEntity(url, requestEntity, String.class);
            System.out.println("小程序推送结果={}"+ responseEntity.getBody());
            msg = responseEntity.getBody();
        }catch (Exception e){
            e.printStackTrace();
        }
       return  msg;
    }
    public static String getAccess_token() {

        String url = "https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential" +
                "&appid=" + appid + "&secret=" + appSecret;
        if (restTemplate == null) {
            restTemplate = new RestTemplate();
        }
        restTemplate.getMessageConverters().set(1,new StringHttpMessageConverter(StandardCharsets.UTF_8));
        String json = restTemplate.getForObject(url, String.class);
        JSONObject myJson = JSONObject.parseObject(json);
        return myJson.get("access_token").toString();
    }

    public static void main(String[] args) {
        try {

            System.out.println(getAccess_token());
            String values[] = {"智能电表001", "30.56", "您的电费已不足,请及时充值!"};

            pushOneUser(getAccess_token()
                    , "xxx", "1", "xxx"
                    , values);
        } catch (Exception e) {
            e.printStackTrace();
        }

    }
}






由于咱们选择的JSON数据格式 发过去前要格式化下 JSON.toJSONString(实体类)

{"data":{"amount4":{"value":"30.56"},"thing3":{"value":"智能电表001"},"thing5":{"value":"您的电费已不足,请及时充值!"}},"page":"pages/index/index","template_id":"模板id","touser":"openid"}

如果出现用户拒绝的这一步说明你的json格式ok 咱们还需要前端写函数触发订阅窗 让用户订阅咱们的消息
在这里插入图片描述
如果用户订阅了 就能收到信息了
我这个是一开始没加MediaType的
在这里插入图片描述

  • 11
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

boJIke

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值