您的位置:首页 > 移动开发 > 微信开发

微信公众号开发之天气应用

2015-11-12 22:03 711 查看
20151228更新:百度API对天气信息的返回结果做了改变,指数信息需要重新解析,原有的代码公众号调用时已经无法正常显示指数信息。

20151230更新:28号是百度API升级造成的短暂故障,现已恢复正常,代码不需要更改。

本天气应用,通过发送城市名或位置获取天气信息,利用百度SDK

百度Key申请:http://lbsyun.baidu.com/apiconsole/key

通过上一个链接申请到AK和SK,也可以只申请AK不申请SK,申请了SK的需要计算SN

接口的形式如:http://api.map.baidu.com/telematics/v3/weather?location=北京&output=json&ak=yourkey

申请了SK的接口形式如:http://api.map.baidu.com/telematics/v3/weather?location=北京&output=json&ak=yourkey&sn=yoursn

接口说明:http://developer.baidu.com/map/carapi-7.htm

SN生成算法:http://developer.baidu.com/map/lbs-appendix.htm#.appendix1

其中location=后面接城市名或经纬度,但是跟微信获取到的顺序刚好相反,location=($object->Location_Y,$object->Location_X)

Weather类文件Weather.php

<?php

class Weather
{
var $ak = 'AK';
var $sk = 'SK';
var $url = 'http://api.map.baidu.com/telematics/v3/weather?location=%s&output=%s&ak=%s&sn=%s';
var $uri = '/telematics/v3/weather';

//计算sn
function caculateAKSN($ak, $sk, $url, $querystring_arrays, $method = 'GET')
{
if ($method === 'POST'){
ksort($querystring_arrays);
}
$querystring = http_build_query($querystring_arrays);
return md5(urlencode($url.'?'.$querystring.$sk));
}

//$location可填地名或经纬度,$output可填json或xml
//locationToWeatherResult('长沙');
//locationToWeatherResult('121.67397,38.793570');
public function locationToWeatherResult($location,$output='json'){
//当前为GBK编码时需要转换
//$location = iconv('GB2312','UTF-8',$location);

//构造请求串数组
$querystring_arrays = array (
'location' => $location,
'output' => $output,
'ak' => $this->ak
);

//调用sn计算函数,默认get请求
$sn = $this->caculateAKSN($this->ak, $this->sk, $this->uri, $querystring_arrays);
$target = sprintf($this->url, urlencode($location), $output, $this->ak, $sn);

$content = file_get_contents($target);
return $content;
}
}
?>


微信主页php页面

<?php
define("TOKEN", "token");

$wechatObj = new wechatCallbackapiTest();
if (!isset($_GET['echostr'])) {
$wechatObj->responseMsg();
}else{
$wechatObj->valid();
}

class wechatCallbackapiTest
{
//验证签名
public function valid()
{
$echoStr = $_GET["echostr"];
$signature = $_GET["signature"];
$timestamp = $_GET["timestamp"];
$nonce = $_GET["nonce"];
$token = TOKEN;
$tmpArr = array($token, $timestamp, $nonce);
sort($tmpArr);
$tmpStr = implode($tmpArr);
$tmpStr = sha1($tmpStr);
if($tmpStr == $signature){
echo $echoStr;
exit;
}
}

public function responseMsg()
{
$postStr = $GLOBALS["HTTP_RAW_POST_DATA"];
if (!empty($postStr)){
$this->logger("R ".$postStr);
$postObj = simplexml_load_string($postStr, 'SimpleXMLElement', LIBXML_NOCDATA);
$RX_TYPE = trim($postObj->MsgType);

$result = "";
switch ($RX_TYPE)
{
case "event":
$result = $this->receiveEvent($postObj);
break;
case "text":
$result = $this->receiveText($postObj);
break;
case "location":
$result = $this->receiveLocation($postObj);
break;
}
$this->logger("T ".$result);
echo $result;
}else {
echo "";
exit;
}
}

private function receiveEvent($object)
{
switch ($object->Event)
{
case "subscribe":
$content =  "感谢您关注【微微微时代】"."\n"."微信号:vvvtimes"."\n"."微信原始ID:gh_f420fbb7e319"."\n";
break;
}
$result = $this->transmitText($object, $content);
return $result;
}

private function receiveText($object)
{
$keyword = trim($object->Content);
require_once './Weather.php';
$weather = new Weather();
$output = $weather->locationToWeatherResult($keyword);
$content = json_decode($output, true);

$result = $this->transmitNews($object, $content);
return $result;
}

private function receiveLocation($object)
{
$location_xpoint = $object->Location_X;
$location_ypoint = $object->Location_Y;
$keyword = $location_ypoint.",".$location_xpoint;
require_once './Weather.php';
$weather = new Weather();
$output = $weather->locationToWeatherResult($keyword);
$content = json_decode($output, true);

$result = $this->transmitNews($object, $content);
return $result;
}

private function transmitText($object, $content)
{
if (!isset($content) || empty($content)){
return "";
}
$textTpl = "<xml>
<ToUserName><![CDATA[%s]]></ToUserName>
<FromUserName><![CDATA[%s]]></FromUserName>
<CreateTime>%s</CreateTime>
<MsgType><![CDATA[text]]></MsgType>
<Content><![CDATA[%s]]></Content>
</xml>";
$result = sprintf($textTpl, $object->FromUserName, $object->ToUserName, time(), $content);
return $result;
}

private function transmitNews($object, $weatherContent)
{
$city = $weatherContent['results'][0]['currentCity'];
$index_data = $weatherContent['results'][0]['index'];//指数
$weather_data = $weatherContent['results'][0]['weather_data'];
$pm25= $weatherContent['results'][0]['pm25'];

if($weatherContent['error']!=0){
return "";
}
$itemTpl = "<item>
<Title><![CDATA[%s]]></Title>
<Description><![CDATA[%s]]></Description>
<PicUrl><![CDATA[%s]]></PicUrl>
<Url><![CDATA[%s]]></Url>
</item>";
$item_str='';
//标题1条,指数6条,天气4条,微信最大是10条图文,所以抽2条指数显示
$title=$city.'天气预报 '."PM2.5:".$pm25;
$description='';
$picUrl= '';
$url='';
$item_str = sprintf($itemTpl, $title, $description, $picUrl, $url);
$newIndex_data= Array($index_data[0],$index_data[3]);
foreach ($newIndex_data as $item){
$title = $item['tipt'].":".$item['des'];
$description='';
$picUrl= '';
$url='';
$item_str .= sprintf($itemTpl, $title, $description, $picUrl, $url);
}
foreach ($weather_data as $item){
$title = $item['date'].$item['weather'].$item['temperature'];
$description='';
$picUrl= $item['dayPictureUrl'];
$url='';
$item_str .= sprintf($itemTpl, $title, $description, $picUrl, $url);
}
$newsTpl = "<xml>
<ToUserName><![CDATA[%s]]></ToUserName>
<FromUserName><![CDATA[%s]]></FromUserName>
<CreateTime>%s</CreateTime>
<MsgType><![CDATA[news]]></MsgType>
<Content><![CDATA[]]></Content>
<ArticleCount>%s</ArticleCount>
<Articles>
$item_str</Articles>
</xml>";

$result = sprintf($newsTpl, $object->FromUserName, $object->ToUserName, time(), count($newIndex_data)+count($weather_data)+1);
return $result;
}

private function logger($log_content)
{

}
}
?>


使用时,替换掉百度的AK,SK,替换掉微信的TOKEN即可

效果如下



内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: