功能需求
公司新开的公众号需要将公司平台现在的所有精品文章都导入,手动导入会有很多的工作量,所以采用自动化同步文章的方式来达到效果
开发说明
微信open api提供了新增永久素材的接口,本次功能是基于这个接口进行数据同步的
使用到的接口
- 获取永久素材列表接口:material/batchget_material
- 新增永久素材接口:material/add_news
- 新增媒体文件接口:material/add_material
- 图文类型
- 单图文(要求有默认的封面,需要提前上传到微信公众号后台)
环境要求
php版本:5.5以下(因为下面代码中的上传媒体文件必须要求在此环境,否则会调用微信接口失败)
开发流程
1、从公司平台获取所有的文章列表
2、遍历文章列表,查看文章是否有图片附件,若有进行第三步,否则进行第四步
3、检测所有的附件,取出第一个图片附件,并调用新增媒体文件接口上传图片获得返回后的media_id
4、调用素材列表接口获取默认的封面图片,并从中得到的数据中获取media_id
5、根据返回获取到的media_id开始调用上传图文接口上传素材
6、记录返回信息
接口设计
获取微信素材列表接口
此接口是用于获取默认的图片media_id同步平台数据接口
此接口是用户同步我们自己的文章数据到微信功能实现
接口常量
1
2
3
4
5
6
7
8
9
10
|
private $app_id = 'wx189ae9fa8816b131' ;
private $app_secret = '36f5f430c591acbae3505fe877733283' ;
const API_URL_PREFIX = 'https://api.weixin.qq.com/cgi-bin' ;
const MEDIA_FOREVER_UPLOAD_URL = '/material/add_material?' ;
const MEDIA_FOREVER_NEWS_UPLOAD_URL = '/material/add_news?' ;
const MEDIA_FOREVER_NEWS_UPDATE_URL = '/material/update_news?' ;
const MEDIA_FOREVER_GET_URL = '/material/get_material?' ;
const MEDIA_FOREVER_DEL_URL = '/material/del_material?' ;
const MEDIA_FOREVER_COUNT_URL = '/material/get_materialcount?' ;
const MEDIA_FOREVER_BATCHGET_URL = '/material/batchget_material?' ;
|
获取微信素材列表接口
action接口方法
说明:该方法为此接口的入口方法
调用方式:http://${domain}/weixin/get_articles/
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
|
/**
* 获取图片素材接口
*/
public function get_articles_action(){
$token = $this ->get_access_token();
$list = $this ->getForeverList( $token , 'image' ,0,20);
echo json_encode( $list );
}
get_access_token方法
private function get_access_token() {
$access_token = AWS_APP::cache()->get( 'access_token' );
if (! $access_token ){
error_log ( 'get access_token from weixin ' );
$appId = $this ->app_id;
$appSecret = $this ->app_secret;
$url = "https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid=$appId&secret=$appSecret" ;
$res = json_decode( $this -> httpGet( $url ));
$access_token = $res -> access_token;
AWS_APP::cache()->set( 'access_token' , $access_token ,time()+3600);
} else {
error_log ( 'get access_token from cache ' );
}
error_log ( 'access_token is :' . $access_token );
return $access_token ;
}
|
调用微信素材接口方法
说明:该方法为调用微信获取永久素材列表接口方法
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
|
/**
* 获取永久素材列表
* @param $token
* @param $type 类型有image,vedio和audio
* @param $offset 起始位置,0表示从第一个
* @param $count 个数,区间为0~20
*/
public function getForeverList( $token , $type , $offset , $count ){
$data = array (
'type' => $type ,
'offset' => $offset ,
'count' => $count ,
);
$result = $this ->http_post(
self::API_URL_PREFIX.self::MEDIA_FOREVER_BATCHGET_URL. 'access_token=' . $token ,
self::json_encode( $data )
);
error_log ( 'forever list is :' . $result );
if ( $result )
{
$json = json_decode( $result ,true);
if (isset( $json [ 'errcode' ])) {
$this ->errCode = $json [ 'errcode' ];
$this ->errMsg = $json [ 'errmsg' ];
return false;
}
return $json ;
}
return false;
}
|
同步文章到微信接口
action方法
说明:该方法为此接口的入口方法
调用方式:http://${domain}/weixin/upload_article/
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
|
/**
* 同步问答的文章到订阅号上接口
*/
public function index_action(){
$article_list = $this ->model( 'article' )->get_articles_list(null, 1, 18, 'add_time DESC' );
$access_token = $this ->get_access_token();
$base_url = 'http://wenda.qiezilife.com/article/' ;
foreach ( $article_list as $key => $article ){
if ( $article [ 'has_attach' ]){
$attaches = $this ->model( 'publish' )->get_attach( 'article' , $article [ 'id' ], 'max' );
foreach ( $attaches as $i => $a ){
//过滤获取第一张图片
if ( $a [ 'is_image' ]){
$attache = $a ;
break ;
}
}
$img = $attache [ 'path' ];
$size = filesize ( $img );
echo $img . ',size is :' . $size ;
echo '<br/>' ;
$file_info = array (
'filename' => $img ,
'content-type' => 'image/jpg' , //文件类型
'filelength' => $size
);
$upload_img_result = $this ->upload_meterial( $file_info , $access_token );
$media_id = $upload_img_result ;
error_log ( 'media_id is ===============>' . $media_id );
} else {
$media_id = '1PoTp0SqruwWu_HX0HR_jUp4STX5HSpYkibb1Ca8ZQA' ;
}
$articles = array ();
//上传图片成功了就开始上传图文
$upload_article_data = array (
'title' => $article [ 'title' ],
'thumb_media_id' => $media_id ,
'author' => '茄子营养师' ,
'digest' => '茄子生活,你的品质生活指南' ,
'show_cover_pic' => 1,
'content' => $article [ 'message' ],
'content_source_url' => $base_url . $article [ 'id' ]
);
$articles [] = $upload_article_data ;
$data = array (
'articles' => $articles
);
$result = $this ->uploadForeverArticles( $access_token , $data );
echo self::json_encode( $result );
error_log ( 'upload_article result is : ' .json_encode( $result ));
error_log ( '============================upload end============================' );
}
}
|
uploadForeverArticles方法
说明:该方法为调用微信上传永久素材接口方法
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
|
/**
* 上传永久图文素材(认证后的订阅号可用)
* 新增的永久素材也可以在公众平台官网素材管理模块中看到
* @param array $data 消息结构{"articles":[{...}]}
* @return boolean|array
*/
public function uploadForeverArticles( $access_token , $data ){
error_log ( 'post data is=======> ' .self::json_encode( $data ));
$url = self::API_URL_PREFIX.self::MEDIA_FOREVER_NEWS_UPLOAD_URL. 'access_token=' . $access_token ;
$result = HTTP::request( $url , 'POST' , self::json_encode( $data ));
error_log ( 'weixin return result is =====>' . $result );
if ( $result )
{
$json = json_decode( $result ,true);
if (! $json || ! empty ( $json [ 'errcode' ])) {
$this ->errCode = $json [ 'errcode' ];
$this ->errMsg = $json [ 'errmsg' ];
return false;
}
return $json ;
}
return false;
}
|
upload_meterial方法
说明:该方法为调用微信上传永久素材接口方法
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
|
/**
* 请注意该方法必须保证php的版本在5.6以下,否则会爆40015错误
*/
function upload_meterial( $file_info , $access_token ){
$url = "https://api.weixin.qq.com/cgi-bin/material/add_material?access_token={$access_token}&type=image" ;
$ch1 = curl_init ();
$timeout = 5;
$real_path = "{$file_info['filename']}" ;
//$real_path=str_replace("/", "\\", $real_path);
$data = array ( "media" => "@{$real_path}" , 'form-data' => $file_info );
curl_setopt ( $ch1 , CURLOPT_URL, $url );
curl_setopt ( $ch1 , CURLOPT_POST, 1 );
curl_setopt ( $ch1 , CURLOPT_RETURNTRANSFER, 1 );
curl_setopt ( $ch1 , CURLOPT_CONNECTTIMEOUT, $timeout );
curl_setopt ( $ch1 , CURLOPT_SSL_VERIFYPEER, FALSE );
curl_setopt ( $ch1 , CURLOPT_SSL_VERIFYHOST, false );
curl_setopt ( $ch1 , CURLOPT_POSTFIELDS, $data );
$result = curl_exec ( $ch1 );
echo '<br/>' ;
echo 'reulst is ==========>' . $result ;
curl_close ( $ch1 );
if (curl_errno()==0){
$result =json_decode( $result ,true);
//var_dump($result);
return $result [ 'media_id' ];
} else {
return false;
}
}
|
http_post方法
说明:该方法为调http post请求方法
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
|
/**
* POST 请求
* @param string $url
* @param array $param
* @param boolean $post_file 是否文件上传
* @return string content
*/
private function http_post( $url , $param , $post_file =false){
$oCurl = curl_init();
if ( stripos ( $url , "https://" )!==FALSE){
curl_setopt( $oCurl , CURLOPT_SSL_VERIFYPEER, FALSE);
curl_setopt( $oCurl , CURLOPT_SSL_VERIFYHOST, false);
curl_setopt( $oCurl , CURLOPT_SSLVERSION, 1); //CURL_SSLVERSION_TLSv1
}
if ( is_string ( $param ) || $post_file ) {
$strPOST = $param ;
} else {
$aPOST = array ();
foreach ( $param as $key => $val ){
$aPOST [] = $key . "=" .urlencode( $val );
}
$strPOST = join( "&" , $aPOST );
}
curl_setopt( $oCurl , CURLOPT_URL, $url );
curl_setopt( $oCurl , CURLOPT_RETURNTRANSFER, 1 );
curl_setopt( $oCurl , CURLOPT_POST,true);
curl_setopt( $oCurl , CURLOPT_POSTFIELDS, $strPOST );
$sContent = curl_exec( $oCurl );
$aStatus = curl_getinfo( $oCurl );
curl_close( $oCurl );
if ( intval ( $aStatus [ "http_code" ])==200){
return $sContent ;
} else {
return false;
}
}
|
遇到的问题
在开发的过程中,在调用微信上传媒体文件时候始终得到的返回数据为
1
|
{"errcode":41005,"errmsg":"media data missing hint: [3fSt_0048e297]"}
|
原因:php版本的问题,我本机的版本5.6,而带有@识别的php方法必须是5.5以下才能识别,5.5以上的版本将这个特性去除了。
解决方法:更换php的版本到5.5或者5.5以下,不更换php的版本的方法暂时没有找到
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持服务器之家。
原文链接:https://segmentfault.com/a/1190000005631406