Weiphp微信公众平台自定义菜单等开发
发布时间:2017-07-18, 10:29:52 分类:PHP | 编辑 off 网址 | 辅助
图集1/9
正文 101字数 1,357,004阅读
涉及后期修改数据表weiphp 获取access_token失败,请确认AppId和Secret配置是否正确,然后再重试。
微信公众平台后台修改
开发》基本设置
公众号设置:获取填写公众号基本信息
填写相关域名
(支付宝)给作者钱财以资鼓励 (微信)→
激活Windows
转到"设置"以激活Windows。
有过 8 条评论 »
订阅号无获取用户信息权限
当 scope 为 snsapi_base的时候没有影响。但是scope为snsapi_userinfo 就会提示 scope参数错误或没有scope权限
官网文档说snsapi_base授权只能拿到openid的。而且我实践也发现,有时snsapi_base授权得到的access_token是拿不到用户信息的,
只有在关注的情况下snsapi_base才可以获取到用户信息,否则只能获取到openid
你猜想的没错,经过证明如果先使用snsapi_userinfo参数去调用接口,在使用snsapi_base调用接口,确实会取到其它的参数,而直接使用snsapi_base参数调用接口只能获取到openid。
微信公众号开发文档 关于网页授权回调域名的说明
非静默授权的 URL 样例: https://open.weixin.qq.com/connect/oauth2/authorize?appid=wx841a97238d9e17b2&redirect_uri=http://cps.dianping.com/weiXinRedirect&response_type=code&scope=snsapi_userinfo &state=type%3Dquan%2Curl%3Dhttp%3A%2F%2Fmm.dianping.com%2Fweixin%2Faccount%2Fhome 静默授权的 URL 样例: https://open.weixin.qq.com/connect/oauth2/authorize?appid=wx841a97238d9e17b2&redirect_uri=http://cps.dianping.com/weiXinRedirect&response_type=code&scope=snsapi_base &state=type%3Dquan%2Curl%3Dhttp%3A%2F%2Fmm.dianping.com%2Fweixin%2Faccount%2Fhome
getBy动态查询
ThinkPHP getBy动态查询是一个魔术方法,可以根据某个字段名称动态得到对应的一条数据记录。
根据用户名(username)查询对应的用户资料记录:
public function chekUser(){ header("Content-Type:text/html; charset=utf-8"); $Dao = M("User"); // 查询数据 $user = $Dao->getByUsername('Admin'); if($list){ echo '用户名存在'; }else{ echo '用户名不存在'; } }
方法中传入的参数是查询的字段对应的值,上面例子执行的 SQL 语句为:
SELECT * FROM user WHERE username = 'Admin' LIMIT 1
请注意,在getBy之后紧跟着的字段名称,首字母必须大写。对于如 user_name 这样的字段名称,以驼峰法自动识别下划线,即:
$user = $Dao->getByUserName('Admin');
实际使用中可以灵活根据查询的字段名来定义 getBy 放入,如:getByEmail、getByTitle、getById 等。
在编辑一条信息的时候,用getById()而没用find()或者select(),现阶段还不明白具体原因,并且,也没有搜到ThinkPHP里面有关于getById()的相关说明。
这样的用法,是在官方的实例里面看到的。
具体操作如下:
function index(){ $data = M(“User”); //实例化模型 $vo = $data->getById($_GET[‘id’]); //符合条件的ID if($vo){ $this->assign(‘vo’,$vo); $this->display(); }else{ $this->error(“编辑项不存在。”); } }
在模板里面,执行PHP代码是这样的:
<php> //PHP代码 $type = $vo[字段名]; </php>
就上面一段代码,解决了所有问题,而在模板里面,需要调用符合条件的某个字段的时候,只需在需要调用的地方这样写:
{$vo.字段名}
而对于统计字段(通常指的是数字类型)的更新,系统还提供了 setInc 和 setDec 方法:
$User = M( "User" ); // 实例化 User 对象 $User->setInc( 'score','id=5',3 ); // 用户的积分加 3 $User->setInc( 'score','id=5' ); // 用户的积分加 1 $User->setDec( 'score','id=5',5 ); // 用户的积分减 5 $User->setDec( 'score','id=5' ); // 用户的积分减 1
而tp3.0有了新的改动,这样写了,方便了不少:
必须配合连贯操作where一起使用
$User = M("User"); // 实例化User对象 $User->where('id=5')->setInc('score',3); // 用户的积分加3 $User->where('id=5')->setInc('score'); // 用户的积分加1 $User->where('id=5')->setDec('score',5); // 用户的积分减5 $User->where('id=5')->setDec('score'); // 用户的积分减1
UPDATE user SET score=score+3 WHERE uid = 2
mysql CONCAT()函数用于将多个字符串连接成一个字符串,是最重要的mysql函数之一,下面就将为您详细介绍mysql CONCAT()函数,供您参考 mysql CONCAT(str1,str2,…) 返回结果为连接参数产生的字符串。如有任何一个参数为NULL ,则返回值为 NULL。或许有一个或多个参数。 如果所有参数均为非二进制字符串,则结果为非二进制字符串。 如果自变量中含有任一二进制字符串,则结果为一个二进制字符串。一个数字参数被转化为与之相等的二进制字符串格式;若要避免这种情况,可使用显式类型 cast, 例如: SELECT CONCAT(CAST(int_col AS CHAR), char_col) mysql> SELECT CONCAT(’My’, ‘S’, ‘QL’); -> ‘MySQL’ mysql> SELECT CONCAT(’My’, NULL, ‘QL’); -> NULL mysql> SELECT CONCAT(14.3); -> ‘14.3′ mysql CONCAT_WS(separator,str1,str2,…) CONCAT_WS() 代表 CONCAT With Separator ,是CONCAT()的特殊形式。 第一个参数是其它参数的分隔符。分隔符的位置放在要连接的两个字符串之间。分隔符可以是一个字符串,也可以是其它参数。如果分隔符为 NULL,则结果为 NULL。函数会忽略任何分隔符参数后的 NULL 值。 mysql> SELECT CONCAT_WS(’,',’First name’,'Second name’,'Last Name’); -> ‘First name,Second name,Last Name’ mysql> SELECT CONCAT_WS(’,',’First name’,NULL,’Last Name’); -> ‘First name,Last Name’ mysql CONCAT_WS()不会忽略任何空字符串。 (然而会忽略所有的 NULL)。
检测浏览器的 User Agent 应该是非常简单的事情
微信在 Android 下的 User Agent
mozilla/5.0 (linux; u; android 4.1.2; zh-cn; mi-one plus build/jzo54k) applewebkit/534.30 (khtml, like gecko) version/4.0 mobile safari/534.30 micromessenger/5.0.1.352
微信在 iPhone 下的 User Agent
mozilla/5.0 (iphone; cpu iphone os 5_1_1 like mac os x) applewebkit/534.46 (khtml, like gecko) mobile/9b206 micromessenger/5.0
通过javascript判断
很容易看出来,微信的 User Agent 都有‘micromessenger’字符串标示,我们判断是否含有这些字符串就OK了
function isWeixinBrowser(){ var ua = navigator.userAgent.toLowerCase(); return (/micromessenger/.test(ua)) ? true : false ; }
通过 PHP 判断
function is_weixin(){ if ( strpos($_SERVER['HTTP_USER_AGENT'], 'MicroMessenger') !== false ) { return true; } return false; }
我知道的方法是 在浏览器 more tools->network conditions
User agent 把 select automatically 取消勾选
下面的输入框输入
MicroMessenger 微信 AlipayClient 支付宝
isWeixinBrowser
判断是否为微信内置浏览器
在微信公众账号开发中,一般会在微站点使用微信用户授权接口,但是我们的网站也需要在非微信环境中正常使用,这就需要判断当前的浏览器是微信内置的浏览器,那么如何判断呢?
判断微信浏览器浏览器中的User Agent,经过在 iPhone 上微信的浏览器的检测,它的 User Agent 是:
Mozilla/5.0 (iPhone; CPU iPhone OS 6_1_3 like Mac OS X) AppleWebKit/536.26 (KHTML, like Gecko) Mobile/10B329 MicroMessenger/5.0.1
所以通过识别“MicroMessenger”这个关键字来确定是否微信内置的浏览器。
使用JavaScript 判断
function isWeixinBrowser() { var agent = navigator.userAgent.toLowerCase(); if (agent.match(/MicroMessenger/i) == "micromessenger") { return true; } else { return false; } }
使用PHP判断
function is_weixin() { if (strpos($_SERVER['HTTP_USER_AGENT'], 'MicroMessenger') !== false) { return true; } return false; } function weixin_version() { preg_match('/.*?(MicroMessenger\/([0-9.]+))\s*/', $_SERVER['HTTP_USER_AGENT'], $matches); echo '你的微信版本号为:'.$matches[2]; }
PHP“Cannot use object of type stdClass as array”
php再调用json_decode从字符串对象生成json对象时,如果使用[]操作符取数据,会得到下面的错误
错误:
Cannot use object of type stdClass as array
产生原因:
$res = json_decode($res); $res['key']; //把 json_decode() 后的对象当作数组使用。
解决方法(2种):
1、使用 json_decode($d, true)。就是使json_decode 的第二个变量设置为 true。
2、json_decode($res) 返回的是一个对象, 不可以使用 $res['key'] 进行访问, 换成 $res->key 就可以了。
$res->key
参考手册:json_decode
Return Values:Returns an object or if the optional assoc parameter is TRUE, an associative array is instead returned.
php给对象动态增加属性
示例代码
<?php error_reporting(-1); ini_set('display_errors','on'); class A { public $a = 'hello'; public function add() { $this->b = 'world'; }- public static function p() { echo 'world',PHP_EOL; }- } $a = new A; $a->add(); $a->c = 'test'; $a->p(); var_dump($a);
输出
world object(A)#1 (3) { ["a"]=> string(5) "hello" ["b"]=> string(5) "world" ["c"]=> string(4) "test" }
补充:对象可以调用对象所属类的静态方法,如
$a->p();
php 静态方法 静态变量和继承
代码
<?php class A { public static $count = 1; public static function func() { echo __METHOD__,' count: ',self::$count,PHP_EOL; } } class B extends A { public static $count = 2; // public static function func() { // echo __METHOD__,' count: ',self::$count,PHP_EOL; // } } B::func(); A::func();
结果
A::func count: 1 A::func count: 1
说明
从示例来看,PHP是允许覆写静态变量的,覆写静态方法也可以(去掉注释)。只是在运行时,如果发现本类中没有的方法,就会去父类中找,但是父类中用了self,self的变量就在方法所在的类中直接取,而不会回溯到调用方法的类中去找。
微信登录失败
安全域名校验出错,错误码:10003
是微信支付 lib/WxPay.Config.php文件配置错误,修改正确即可
<?php /** * 配置账号信息 */ class WxPayConfig { //=======【基本信息设置】===================================== // /** * TODO: 修改这里配置为您自己申请的商户信息 * 微信公众号信息配置 * * APPID:绑定支付的APPID(必须配置,开户邮件中可查看) * * MCHID:商户号(必须配置,开户邮件中可查看) * * KEY:商户支付密钥,参考开户邮件设置(必须配置,登录商户平台自行设置) * 设置地址:https://pay.weixin.qq.com/index.php/account/api_cert * * APPSECRET:公众帐号secert(仅JSAPI支付的时候需要配置, 登录公众平台,进入开发者中心可设置), * 获取地址:https://mp.weixin.qq.com/advanced/advanced?action=dev&t=advanced/dev&token=2005451881&lang=zh_CN * @var string */ const APPID = '****************'; const MCHID = '****************'; const KEY = '****************'; const APPSECRET = '****************';
这个错误通过修改文件WxPay.Api.php 解决,具体如下:
第537行
curl_setopt($ch,CURLOPT_SSL_VERIFYPEER,TRUE);
curl_setopt($ch,CURLOPT_SSL_VERIFYHOST,2);//严格校验
to
curl_setopt($ch,CURLOPT_SSL_VERIFYPEER,FALSE); curl_setopt($ch,CURLOPT_SSL_VERIFYHOST,FALSE);//严格校验2
session_destroy() destroys all of the data associated with the current session. It does not unset any of the global variables associated with the session, or unset the session cookie. To use the session variables again, session_start() has to be called.
它会destroys all of the data associated with the current session,但是它既不注销变量,又不注销session cookie。那它做了什么?还有这个函数有什么用呢?
session_destroy() 销毁当前会话中的全部数据, 但是不会重置当前会话所关联的全局变量, 也不会重置会话 cookie。 如果需要再次使用会话变量, 必须重新调用 session_start() 函数。
为了彻底销毁会话,比如在用户退出登录的时候,必须同时重置会话 ID。 如果是通过 cookie 方式传送会话 ID 的,那么同时也需要 调用setcookie() 函数来 删除客户端的会话 cookie。
范例
<?php // 初始化会话。 // 如果要使用会话,别忘了现在就调用: session_start(); // 重置会话中的所有变量 $_SESSION = array(); // 如果要清理的更彻底,那么同时删除会话 cookie // 注意:这样不但销毁了会话中的数据,还同时销毁了会话本身 if (ini_get("session.use_cookies")) { $params = session_get_cookie_params(); setcookie(session_name(), '', time() - 42000, $params["path"], $params["domain"], $params["secure"], $params["httponly"] ); } // 最后,销毁会话 session_destroy(); ?>
终结 Session 如果您希望删除某些 session 数据,可以使用 unset() 或 session_destroy() 函数。 unset() 函数用于释放指定的 session 变量: <?php unset($_SESSION['views']); ?> 您也可以通过 session_destroy() 函数彻底终结 session: <?php session_destroy(); ?> 注释:session_destroy() 将重置 session,您将失去所有已存储的 session 数据。
1、 最多创建3个一级菜单,一级菜单名称名字不多于4个汉字或8个字母。
2、 每个一级菜单下的子菜单最多可创建5个,子菜单名称名字不多于8个汉字或16个字母。
温馨提示:编辑中的菜单不会马上被用户看到,发布成功后,会在24小时后在手机端同步显示,粉丝不会收到更新提示,若多次编辑,以最后一次保存为准。