zoukankan      html  css  js  c++  java
  • 微信公众号开发之上传图文消息素材(十二)

    群发消息太重要了,公众号管理员需要定期通过公众号群发一些消息,用户通过推送的消息可以定期了解公众号的最新信息。

    群发图文消息的过程如下:

    1. 首先,预先将图文消息中需要用到的图片,使用上传图文消息内图片接口,上传成功并获得图片 URL;
    2. 上传图文消息素材,需要用到图片时,请使用上一步获取的图片 URL;
    3. 使用对用户标签的群发,或对 OpenID 列表的群发,将图文消息群发出去,群发时微信会进行原创校验,并返回群发操作结果;
    4. 在上述过程中,如果需要,还可以预览图文消息、查询群发状态,或删除已群发的消息等。

    群发图片、文本等其他消息类型的过程如下:

    1. 如果是群发文本消息,则直接根据下面的接口说明进行群发即可;
    2. 如果是群发图片、视频等消息,则需要预先通过素材管理接口准备好 mediaID。

    这一篇具体内容特别多,更多开发细节和注意事项请参考微信公众号开发文档【群发接口和原创校验】仔细阅读其他部分!!!

    目录【这是微信开发文档提供的目录,我们只演示部分重要的模块!!!】

    1 上传图文消息内的图片获取URL【订阅号与服务号认证后均可用】

    2 上传图文消息素材【订阅号与服务号认证后均可用】

    3 根据标签进行群发【订阅号与服务号认证后均可用】

    4 根据OpenID列表群发【订阅号不可用,服务号认证后可用】

    5 删除群发【订阅号与服务号认证后均可用】

    6 预览接口【订阅号与服务号认证后均可用】

    7 查询群发消息发送状态【订阅号与服务号认证后均可用】

    8 事件推送群发结果

    9 使用 clientmsgid 参数,避免重复推送

    10 控制群发速度

    一、上传图文消息内的图片获取URL【订阅号与服务号认证后均可用】

    请注意,本接口所上传的图片不占用公众号的素材库中图片数量的5000个的限制。图片仅支持jpg/png格式,大小必须在1MB以下。

    接口调用请求说明

    http请求方式: POST https://api.weixin.qq.com/cgi-bin/media/uploadimg?access_token=ACCESS_TOKEN 调用示例(使用curl命令,用FORM表单方式上传一个图片): curl -F media=@test.jpg "https://api.weixin.qq.com/cgi-bin/media/uploadimg?access_token=ACCESS_TOKEN"

    /**
         上传图文消息内的图片获取URL
         */
        public String uploadimg(String filePath) {
    
            String accessToken = accessTokenUtil.getAccessToken();
            if (accessToken != null) {
                String url = URIConstant.UPLOAD_IMG_URL.replace("ACCESS_TOKEN", accessToken);
                log.info("UPLOAD_IMG_URL:{}",url);
    
                //设置请求体,注意是LinkedMultiValueMap
                MultiValueMap<String, Object> data = new LinkedMultiValueMap<>();
    
                //设置上传文件
                FileSystemResource fileSystemResource = new FileSystemResource(filePath);
                data.add("media", fileSystemResource);
    
                //上传文件,设置请求头
                HttpHeaders httpHeaders = new HttpHeaders();
                httpHeaders.setContentType(MediaType.MULTIPART_FORM_DATA);
                httpHeaders.setContentLength(fileSystemResource.getFile().length());
    
                HttpEntity<MultiValueMap<String, Object>> requestEntity = new HttpEntity<MultiValueMap<String, Object>>(data,
                        httpHeaders);
                try{
                    //这里RestTemplate请求返回的字符串直接转换成JSONObject会报异常,后续深入找一下原因
    //                ResponseEntity<JSONObject> resultEntity = restTemplate.exchange(url,
    //                        HttpMethod.POST, requestEntity, JSONObject.class);
                    String resultJSON = restTemplate.postForObject(url, requestEntity, String.class);
                    log.info("上传返回的信息是:{}",resultJSON);
                    return resultJSON;
                }catch (Exception e){
                    log.error(e.getMessage());
                }
            }
            return null;
    
        }

    @ApiOperation(value = "上传图文消息内的图片获取URL")
    @RequestMapping(value = "/uploadImg", method = RequestMethod.POST)
    public Object uploadImg(String filePath) {
    
        String result = newsUtil.uploadimg(filePath);
        log.info("resut:{}",JSONObject.parseObject(result).toJSONString());
        return result;
    }

    我们在swagger中测试这个上传图文素材图片接口,填写一个正确的图片路径

    结果如下

    二、上传图文消息素材【订阅号与服务号认证后均可用】

    接口调用请求说明

    http请求方式: POST https://api.weixin.qq.com/cgi-bin/media/uploadnews?access_token=ACCESS_TOKEN

    POST数据说明

    POST数据示例如下:

    {
       "articles": [	 
            {
                "thumb_media_id":"qI6_Ze_6PtV7svjolgs-rN6stStuHIjs9_DidOHaj0Q-mwvBelOXCFZiq2OsIU-p",
                "author":"xxx",		
                "title":"Happy Day",		 
                "content_source_url":"www.qq.com",		
                "content":"content",		 
                "digest":"digest",
                "show_cover_pic":1,
                "need_open_comment":1,
                "only_fans_can_comment":1
            },	 
            {
                "thumb_media_id":"qI6_Ze_6PtV7svjolgs-rN6stStuHIjs9_DidOHaj0Q-mwvBelOXCFZiq2OsIU-p",
                "author":"xxx",		
                "title":"Happy Day",		 
                "content_source_url":"www.qq.com",		
                "content":"content",		 
                "digest":"digest",
                "show_cover_pic":0,
                "need_open_comment":1,
                "only_fans_can_comment":1
            }
       ]
    }

     限于文章篇幅有限,字段详细说明请自行参照开发文档

    package com.xu.wemall.pojo.news;
    
    import io.swagger.annotations.ApiModel;
    import io.swagger.annotations.ApiModelProperty;
    import lombok.AllArgsConstructor;
    import lombok.Data;
    import lombok.NoArgsConstructor;
    
    @Data
    @NoArgsConstructor
    @AllArgsConstructor
    @ApiModel(value = "新闻消息发送对象")
    public class News {
    
        @ApiModelProperty(value = "标题")
        private String title;
    
        @ApiModelProperty(value = "图文消息的封面图片素材id(必须是永久 media_ID)")
        private String thumb_media_id;
    
        @ApiModelProperty(value = "作者")
        private String author;
    
        @ApiModelProperty(value = "图文消息的摘要,仅有单图文消息才有摘要,多图文此处为空")
        private String digest;
    
        @ApiModelProperty(value = "是否显示封面,0为false,即不显示,1为true,即显示")
        private Integer show_cover_pic;
    
        @ApiModelProperty(value = "图文消息的具体内容,支持HTML标签,必须少于2万字符,小于1M,且此处会去除JS")
        private String content;
    
        @ApiModelProperty(value = "图文消息的原文地址,即点击“阅读原文”后的URL")
        private String content_source_url;
    
        @ApiModelProperty(value = "是否打开评论,0不打开,1打开")
        private Integer need_open_comment;
    
        @ApiModelProperty(value = "是否粉丝才可评论,0所有人可评论,1粉丝才可评论")
        private Integer only_fans_can_comment;
    
    }
    

    package com.xu.wemall.pojo.news;
    
    import lombok.AllArgsConstructor;
    import lombok.Data;
    import lombok.EqualsAndHashCode;
    import lombok.NoArgsConstructor;
    
    import java.util.List;
    
    @Data
    @AllArgsConstructor
    @NoArgsConstructor
    @EqualsAndHashCode(callSuper = false)
    public class Articles {
    
        List<News> articles;
    
    }
    

     这里重点要说一下thumb_media_id这个参数,他是一个上传永久图片素材type是thumb获得的media_id,,接口地址是

    https://api.weixin.qq.com/cgi-bin/material/add_material?access_token=ACCESS_TOKEN&type=TYPE

    package com.xu.wemall.components.weixin;
    
    import com.alibaba.fastjson.JSONObject;
    import com.xu.wemall.commons.constants.URIConstant;
    import com.xu.wemall.pojo.news.Articles;
    import com.xu.wemall.pojo.news.News;
    import lombok.extern.slf4j.Slf4j;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.core.io.FileSystemResource;
    import org.springframework.http.HttpEntity;
    import org.springframework.http.HttpHeaders;
    import org.springframework.http.MediaType;
    import org.springframework.stereotype.Component;
    import org.springframework.util.LinkedMultiValueMap;
    import org.springframework.util.MultiValueMap;
    import org.springframework.web.client.RestTemplate;
    
    import java.util.ArrayList;
    import java.util.List;
    
    /**
     * 功能:图文素材工具类
     */
    @Slf4j
    @Component
    public class NewsUtil {
    
        @Autowired
        private RestTemplate restTemplate;
    
        @Autowired
        private AccessTokenUtil accessTokenUtil;
    
        private Articles createArticles(){
    
            Articles articles = new Articles();
    
            List<News> dataList = new ArrayList<>();
            News  news1 = new News();
            news1.setTitle("标题");
            news1.setThumb_media_id("J49eq_VE823b_wZH3Op4DFkLa4Lm4jkTSxX_VbiBWhY");
            news1.setAuthor("作者");
            news1.setDigest("图文消息的摘要,仅有单图文消息才有摘要,多图文此处为空。如果本字段为没有填写,则默认抓取正文前64个字。");
            news1.setShow_cover_pic(1);//显示封面
            news1.setContent("图文消息的具体内容,支持HTML标签,必须少于2万字符,小于1M,且此处会去除JS,涉及图片url必须来源 "上传图文消息内的图片获取URL"接口获取。外部图片url将被过滤。");
            news1.setContent_source_url("https://www.baidu.com/");  //图文消息的原文地址,即点击“阅读原文”后的URL
            news1.setNeed_open_comment(1);   //Uint32  是否打开评论,0不打开,1打开
            news1.setOnly_fans_can_comment(1);    //Uint32 是否粉丝才可评论,0所有人可评论,1粉丝才可评论
    
    
            News  news2 = new News();
            news2.setTitle("标题");
            news2.setThumb_media_id("J49eq_VE823b_wZH3Op4DOvK45tuhPJfr3n1_h1w1h8");
            news2.setAuthor("作者");
            news2.setDigest("图文消息的摘要,仅有单图文消息才有摘要,多图文此处为空。如果本字段为没有填写,则默认抓取正文前64个字。");
            news2.setShow_cover_pic(1);//显示封面
            news2.setContent("图文消息的具体内容,支持HTML标签,必须少于2万字符,小于1M,且此处会去除JS,涉及图片url必须来源 "上传图文消息内的图片获取URL"接口获取。外部图片url将被过滤。");
            news2.setContent_source_url("https://www.baidu.com/");  //图文消息的原文地址,即点击“阅读原文”后的URL
            news2.setNeed_open_comment(1);   //Uint32  是否打开评论,0不打开,1打开
            news2.setOnly_fans_can_comment(1);    //Uint32 是否粉丝才可评论,0所有人可评论,1粉丝才可评论
            dataList.add(news1);
            dataList.add(news2);
    
            articles.setArticles(dataList);
            return articles;
    
        }
        /**
         *新增永久图文素材
         */
        public String addNews() {
    
            Articles articles = this.createArticles();
            String accessToken = accessTokenUtil.getAccessToken();
            if (accessToken != null) {
                log.info("URL{}", URIConstant.ADD_NEWS_URL);
                String url = URIConstant.ADD_NEWS_URL.replace("ACCESS_TOKEN", accessToken);
                log.info("ADD_NEWS_URL:{}", url);
    
                //将菜单对象转换成JSON字符串
                String jsonNews = JSONObject.toJSONString(articles);
                log.info("JSONNEWS:{}",jsonNews);
    
                //发起POST请求创建菜单
                String jsonObject = restTemplate.postForObject(url, jsonNews,String.class);
    
                return jsonObject;
            }
            return null;
        }
    
        /**
         *上传图文消息素材
         */
        public String uploadNews() {
    
            Articles articles = this.createArticles();
            String accessToken = accessTokenUtil.getAccessToken();
            if (accessToken != null) {
                log.info("URL{}", URIConstant.UPLOAD_NEWS_URL);
                String url = URIConstant.UPLOAD_NEWS_URL.replace("ACCESS_TOKEN", accessToken);
                log.info("UPLOAD_NEWS_URL:{}", url);
    
                //将菜单对象转换成JSON字符串
                String jsonNews = JSONObject.toJSONString(articles);
                log.info("JSONNEWS:{}",jsonNews);
    
                //发起POST请求创建菜单
                String jsonObject = restTemplate.postForObject(url, jsonNews,String.class);
    
                return jsonObject;
            }
            return null;
        }
    
        /**
         上传图文消息内的图片获取URL
         */
        public String uploadimg(String filePath) {
    
            String accessToken = accessTokenUtil.getAccessToken();
            if (accessToken != null) {
                String url = URIConstant.UPLOAD_IMG_URL.replace("ACCESS_TOKEN", accessToken);
                log.info("UPLOAD_IMG_URL:{}",url);
    
                //设置请求体,注意是LinkedMultiValueMap
                MultiValueMap<String, Object> data = new LinkedMultiValueMap<>();
    
                //设置上传文件
                FileSystemResource fileSystemResource = new FileSystemResource(filePath);
                data.add("media", fileSystemResource);
    
                //上传文件,设置请求头
                HttpHeaders httpHeaders = new HttpHeaders();
                httpHeaders.setContentType(MediaType.MULTIPART_FORM_DATA);
                httpHeaders.setContentLength(fileSystemResource.getFile().length());
    
                HttpEntity<MultiValueMap<String, Object>> requestEntity = new HttpEntity<MultiValueMap<String, Object>>(data,
                        httpHeaders);
                try{
                    //这里RestTemplate请求返回的字符串直接转换成JSONObject会报异常,后续深入找一下原因
    //                ResponseEntity<JSONObject> resultEntity = restTemplate.exchange(url,
    //                        HttpMethod.POST, requestEntity, JSONObject.class);
                    String resultJSON = restTemplate.postForObject(url, requestEntity, String.class);
                    log.info("上传返回的信息是:{}",resultJSON);
                    return resultJSON;
                }catch (Exception e){
                    log.error(e.getMessage());
                }
            }
            return null;
    
        }
    
    }
    
    

    我们在Controller中添加我们的方法 

    package com.xu.wemall.controller.weixin;
    
    import com.alibaba.fastjson.JSONObject;
    import com.xu.wemall.components.weixin.NewsUtil;
    import io.swagger.annotations.Api;
    import io.swagger.annotations.ApiOperation;
    import lombok.extern.slf4j.Slf4j;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.web.bind.annotation.RequestMapping;
    import org.springframework.web.bind.annotation.RequestMethod;
    import org.springframework.web.bind.annotation.RestController;
    
    /**
     * 类名称: NewsController
     * 类描述: 图文素材接口
     */
    @Slf4j
    @RestController
    @Api(tags = "图文素材接口")
    @RequestMapping(value = "/news")
    public class NewsController {
    
        @Autowired
        private NewsUtil newsUtil;
    
        @ApiOperation(value = "上传图文素材")
        @RequestMapping(value = "/addNews", method = RequestMethod.POST)
        public Object addNews() throws Exception{
    
            String result = newsUtil.addNews();
            //log.info("resut:{}",JSONObject.parseObject(result).toJSONString());
            return result;
        }
    
        @ApiOperation(value = "上传图文消息素材")
        @RequestMapping(value = "/uploadNews", method = RequestMethod.POST)
        public Object uploadNews() throws Exception{
    
            String result = newsUtil.uploadNews();
            //log.info("resut:{}",JSONObject.parseObject(result).toJSONString());
            return result;
        }
    
        @ApiOperation(value = "上传图文消息内的图片获取URL")
        @RequestMapping(value = "/uploadImg", method = RequestMethod.POST)
        public Object uploadImg(String filePath) {
    
            String result = newsUtil.uploadimg(filePath);
            log.info("resut:{}",JSONObject.parseObject(result).toJSONString());
            return result;
        }
    
    
    
    }
    

    打开swagger,测试一下我们的controller方法,我们先上传几个type=thumb的永久素材

    获得media_id后设置到我们的

    最后上传图文消息素材

    如果需要在群发图文中插入小程序,则在调用上传图文消息素材接口时,需在content字段中添加小程序跳转链接,有三种样式的可供选择,具体请仔细参考开发文档【群发接口和原创校验

    今天的内容先到这里,我们下回再见!

    如果您觉得此文有帮助,可以小小打赏一下,持续更新更有动力哟!

  • 相关阅读:
    WPF 进度条
    WPF CPU使用率线性表
    Android annotation
    git 操作
    git 合并指定目录到master
    远程连接mysql报错,ERROR 1045 (28000): Access denied for user 'ODBC'@'localhost' (using password: NO)解决方案
    centos7 安装python2.7.14 并与原版本共存
    pycahrm 断点调试
    ImportError: No module named Crypto.Cipher 报错解决方法
    python操作 rabbitMQ
  • 原文地址:https://www.cnblogs.com/xulijun137/p/12222127.html
Copyright © 2011-2022 走看看