博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
小程序商城笔记
阅读量:2240 次
发布时间:2019-05-09

本文共 16891 字,大约阅读时间需要 56 分钟。

1、三端分离:

服务端:主要是查询数据库,获取数据;

客户端:向服务端发送请求,完成自身逻辑;

CMS:向服务端发送请求,实现发货与发送微信信息。(CMS就是公司内部用户用的,主要功能是添加、修改商品这一类功能)

2、基于token管理权限:登录和有些用户有权限看什么,有些用户没有权限看什么。

3、

ORM模型(面向对象的模型),简单理解为:数据库中的一张表就是一个对象。关联模型就是多张表有关联,比如写sql语句的时候,多表关联

4、单元测试的作用:当业务代码复杂的时候,有可能会出现这种情况,刚修改一个地方的Bug,结果其他地方出问题了。要解决这种情况,就应该用单元测试

5、在GitHub上下载think-php

   下载think-5.0.7 这个里面找到(相当于一个demo)

   下载ThinkPHP核心代码   framework-5.0.7

 

下载以后,把这俩个解压,把think-5.0.7解压,改名为项目名字,比如zerg,放在XAMPP下的htodcs文件夹下;把framework-5.0.7解压,改名为thinkphp放到zerg文件夹下,结构为:

 6、下载XAMPP  

这个表示PHP的版本

点击这块,选择相应的php版本

7、微信里的登录、微信支付(预订单、库存量检测与回调通知处理(这是重点)、微信模板信息(非常重要,这是微信小程序唯一可以告诉用户的消息机制,模板信息是被动的,只有用户在小程序里触发了某些选项后,才有权利向用户发送这些消息,不能主动、随意地向用户推送消息))

8、Token令牌的存储:(1)、用后端语言自带的方法;(2)、写到一个配置文件里;(3)、存储到数据库里

9、

Web产品矩阵:

用一个技术把上面的这些产品都凝合起来,以实现更好的复用性,让整个架构变得合理和流畅。现在做web产品要有公共服务的概念。要有一个公共的api向这些产品提供共有的数据和服务

10、能写出代码和写出易维护的代码不是一回事

前端绝不等于做界面和特效,前端与服务器在编程思维上的差异越来越小了

前端已经变得和服务器一样需要处理大量的业务逻辑

11、第三方组件应该合理选择:

(1)、第三方组件封装的层次不一样,有时候引入第三方组件会引发代码bug

(2)、很多功能我们用不上,要浪费很多时间去学习第三方组件,并不比我们自己实现功能消耗的时间短

(3)、第三方组件的一些功能与我们自己所要求的功能有冲突,要花很多时间去处理

(4)、第三方组件会侵入我们自己的代码

(5)、用第三方组件,不利于提高自己的逻辑能力和开发能力

(6)、有一些复杂的功能,比如访问数据库,自己写不出来,或者写出来的效用不好,就可以使用第三方组件库

(7)、有的第三方组件库没有侵入自己的代码,只是作为一个类库来使用,这样的第三方组件库可以使用

12、

vendor:第三方的插件就安装到这里

thinpphp:tp5的核心代码,用来支持框架的运行

runtime:运行文件、日志文件就放在runtime里

public:外部站点的目录,这里面的文件,可以被直接访问到

extend:之前已经写好的第三方类库,放入这个里面的类库,命名空间是可以被框架自动注册的

application:核心代码

13、tp5自带的web服务器:配置PHP环境变量,把D:\xampp\php(php.exe)添加到PATH里面,cmd进入public文件夹,运行php -S localhost:8080 router.php

在浏览器中输入localhost:8080

这个只是本地测试用,最好还是用xampp

 14。URL路径格式

说明:蓝色的:域名

index.php 入口文件,PHP默认的

绿色index:模块名(项目中会有多个模块)

紫色index:controller名

棕色Index:controller下面的文件

对比下面的结构

 15、创建class的时候,如何自动匹配命名空间

config.php里定义的命名空间,默认为app,可以修改

使用PhpStrom配置,setting-->Directories ,选中application,点击Sources,,然后点击右下角的,设置为app

 

实战经验:php中,模块的范围大,中小型的项目,单一模块就够了,不要一个功能一个模块

16、虚拟域名的配置

现在启动项目,如果要访问

Url为:http://localhost/zerg/public/index.php/sample/test/hello

效果为:

 

这样的话太长了

现在起个虚拟域名:z.cn

点击xampp里的

找到D:\xampp\apache\conf\extra下的httpd-vhosts.conf文件,在最下面加入如下代码:

1 
2 DocumentRoot "D:\xampp\htdocs\zerg\public"3 ServerName z.cn4

在C:\Windows\System32\drivers\etc下找到hosts文件,最下面加入如下代码:

1 127.0.0.1 z.cn

重新启动Apache

输入url:http://z.cn/sample/test/hello

显示效果为:

 

 

PhpStrom 断点调试:

在项目的public下面创建一个文件infor.php

输入phpinfo();

在浏览器打开 localhost/zerg(项目名)/public/infor.php(我配置了虚拟域名,所以打开的Url 是:http://z.cn/infor.php) 

在打开的页面里搜索Xdebug,如果有就说明安装成功了,如果没有,就说明没有安装

 

安装一个Xdebug  网站是:

 

在刚才Infor的页面,查找源代码,然后复制,粘贴到下面的框里

 

 这样就会出现与本地使用的php相匹配的Xdebug,不过7以下的不行

链接:https://pan.baidu.com/s/1O3tdu0rz0hA_bBC2YY3xhA

提取码:zhwo

 这个里面有

下载好文件后,

 

 找到这个路径D:\xampp\php\ext,把刚才的文件放进去

点击

打开php.ini,把下面的代码复制到最下面

[Xdebug]zend_extension = D:\xampp\php\ext\php_xdebug-2.2.5-5.6-vc11.dll (这个路径根据你自己的来)xdebug.remote_enable=1xdebug.remote_handler=dbgpxdebug.remote_mode=reqxdebug.remote_host=localhostxdebug.remote_port=9000xdebug.idekey="PHPSTORM"

重启

 

刷新infor页面,查找Xdebug,如果有,说明安装成功

 

现在开始配置调试

点击

 

配置服务器

点击下面的启动调试

把这个复制到postman的接口后面,请求的时候,就可以开启调试

 17、Postman   后端接口调试工具

 18、ThinkPHP5中支持三种路由:

(1)、默认的,PATH_INFO:

1 //配置式路由 2 return [ 3     '__pattern__' => [ 4         'name' => '\w+', 5     ], 6     '[hello]'     => [ 7         ':id'   => ['index/hello', ['method' => 'get'], ['id' => '\d+']], 8         ':name' => ['index/hello', ['method' => 'post']], 9     ],10 11 ];

(2)、强制路由(最标准的,项目中推荐用这种)

开启强制路由:在application/config.php中,,值改为true

 

 

1 //动态路由2 use think\Route;3 4 Route::rule('hello', 'sample/Test/hello');

 

标准路由的俩种写法:

1 //(1)、第一种写法2 Route::rule('hello', 'sample/Test/hello', 'GET', ['https'=>true]);3 Route::rule('hello', 'sample/Test/hello', 'GET|POST', ['https'=>true]);4 //(2)、第二种写法5 Route::get('hello', 'sample/Test/hello');6 Route::post();7 Route::any();

 

 (3)、混合模式

就是上面俩种都可以用

 

19、路由参数

20、验证器  

21、REST之前的重要协议是SOAP,重,使用XML描述数据

REST是用JSON描述数据

XML和JSON都是通用的,与语言无关,可以在不同的语言之间交换数据

REST的出现,更多的是给我提供了一种轻量级的思维方式,前端可以通过javascript直接访问后台

 22、REST是一种思想,RESTFuL API 是基于REST的API的设计理论

无状态:假如发生了俩个http请求,这俩个Http请求之间是没有先后顺序的,也没有直接的关系,第二个请求是不需要依赖第一个请求的。

             比如我们在访问数据库的时候,是要链接和打开数据库的,只有这个成功了,才能去做一些对数据库的操作,删除和增加,完成后要记得把这个链接close掉,这就不是无状态的,必须有个前置操作。

             RESTFUL 请求就没有这些

备注:传统开发中的GET、POST和RESTFUL中的GET、POST,用法没有区别,但是意义上区别很大

在传统开发中,选择GET、POST的依据是:如果传输的数据简单,不需要保密,就用GET,否则就用POST

在RESTFUL中,选择GET还是POST,是看对资源是做什么操作,如果是获取资源,就用GET,如果是创建资源,就用POST

404:找不到页面

400:请求参数错误

401:没有权限访问

403:当前的资源被禁止。有权限访问,但是因为某些原因,资源被禁止

例子:有俩个用户请求数据,A用户请求的时候传递的是B用户的ID,这时候就应该返回403

500:服务器的未知错误,(1)、确实不知道哪里错了,无法返回具体的错误提示,所以就返回500;(2)、知道哪里错误了,但是这是我服务器的原因,与你客户端无关,不想让客户端知道服务器出了什么问题,返回500

豆瓣的简单,GitHub的标准  

完全按照标准REST不容易,尤其是在内部开发中,比如查询,参数不同,如果做成给一个接口,要各种判断,代码会非常复杂

23、什么时候用全局异常:(1)、每级要处理上级的异常,很繁琐,也有可能没有捕获,(2)、有些异常没有预料到,没有捕获。需要一个全局异常,做出统一的处理

此外很多框架中已经有了全局异常,比如thinkphp5,这时候就需要我们重写这个错误

 

 23、thinkphp里的数据库三种操作方法:

(1)、原生SQL   

1 Db::query('select * from banner_item where banner_id=?',[$id]);

24、详细:

项目运行中发现一个问题,当url错误的时候,会报错:httpException不是Exception,经过调试发现,httpException继承的是\RuntimeException,不是Exception的子类

25、连接数据库的原理

如果是直接用sql连接数据库,那就是用Collection连接

如果用的是Query查询,就是先用Builder(生成器)编译成SQL,再传给Collertion

在TP5中,不是直接访问数据库,是通过一个中间层来操作数据库,就是dal,好处:(1)、简化sql代码的编写;(2)、不需要关心具体的实现,只要同意使用中间层提供的db类,就可以访问不同的数据库

db的原理:它是一个工厂模式,使用的时候,db根据不同的配置文件,来调用不同的驱动,这个驱动才是真正决定Collection是什么类型的

 27、开启SQL日志记录

index.php是入口文件,每一个url请求过来,都会经过这个文件,所以可以在这个文件进行配置

28、

ORM  Object Relational Mapping 对象关系映射   设计表的时候,要当成对象来设计,操作的时候,不是在操作表,而是在操作一个个对象

在tp5中,模型不只是一张表,更是一个业务逻辑,当业务逻辑简单时,模型可以是一张表,但是复杂时,是多张表的联合

29、Db是一个数据库访问层,model是建立在Db访问层上的更加抽象的一个处理业务逻辑的模型层

30、thinkPhp5里类和模型的区别,类是一个抽象的,模型是具体的(类似于java里的对象)

thinkPhp5调用模型的方法有俩种:静态调用(推荐)和实例对象调用。这个和Java里面不一样,Java都是new 一个实例对象后,调用里面的方法

为什么不推荐用实例对象调用呢?

逻辑上的问题:实例化对象后,模型对象对应数据库里的一条数据,一条数据get一个id,这个说不过去

面向对象中,类和对象的区别,model里面,一个类对应的是数据库的一张表,而一个new出来的对象,对应的是表里的一条数据

31、查询数据的时候,隐藏某些字段   

32、tp5里公开的配置项文件是extra,在这个文件添加文件(这个里面可以自定义一些配置,下面的这个表示返回的图片路径前面加上http://z.cn/image)

调用的时候

config('setting.img_prefix')

 33、在TP5里面,如果出现router前面类似的,就需要开启完整路由匹配

 

在config.php里面

改为true

33、8.16数据库字段冗余的合理利用(合理的)

在设计数据库的时候,可以适当的冗余,举个例子:product表关联的image表,我们要获取img的url,就需要查询imgage表,如果product表数量很多的话,速度会变慢,有一种优化的方法,把url存在product里面,这样只要查询image表就可以,不用再查询image表了

39、8-19 

如果想在某个方法里隐藏某个字段,可以使用TP5框架里的collection,它可以把数据转换成一个对象,这样就可以使用里面的方法hidden来进行隐藏字段

1 $collection = collection($products);2 $products = $collection->hidden(['summary']);

在thinkphp5中,直接修改database里的

// 数据集返回类型 'resultset_type'  => 'collection' 这样就可以让返回的数据为collection对象 TP5中,判断对象为空,可以使用isEmpty()方法

40. 9-1  token

验证token:(1)、验证这个token在数据库里;(2)、这个token没有过期;(3)、如果token在数据库里,而且没有过期,还要验证这个token所在的分组有权限调用这个接口

 41、9-2微信身份体系设计

 

在小程序中,我们是基于微信体系做的,所以登录的时候不需要输入账号和密码

小程序把code码发送给getToken接口,getToken接口接收到code码以后,会向微信服务器发送一个请求,把code码传递到微信服务器,微信服务器接收到code码以后,会返还openid(用户身份的标识)和session_key

session_key的作用:在微信体系中,可以直接访问微信服务器拿到一个加密信息,要想解密这个信息,就需要session_key

加密信息里面包含一个UnionID(也是用户的标识)

UnionID和openid的区别:

   openid是一个用户针对一个小程序,它有一个openid,一个用户在不同的小程序中,openid是不同的

   UnionID在不同的小程序下是相同的,只要是同一个账号注册的小程序、公众号、服务号,都是相同的

从微信服务器获取到openid后,把它存储到服务器中,生成token,然后返回给小程序端

我们可以把token保存到缓存中,因为我们有可能会遇到这种情况,打开一个页面,就需要请求一次服务器,获取token,验证token是否有效,如果把token保存到缓存中,就可以在缓存中获取token进行验证,减少服务器压力

备注:缓存的维护不容易,选取技术的时候,要慎重,既要考虑到优点,还要考虑到缺点

 

 42、 9-11 闭包函数构建查询器 

 要求:关联俩张表查询数据,根据imgs表里的order字段进行排序,经过演变后,使用了下面的写法(多看)

model/Product.php

1 public static function getProductDetail($id) 2     { 3         $product = self::with([ 4             'imgs' => function($query){ 5                 $query->with(['imgUrl']) 6                     // order('order', 'asc') 第一个order是排序,第二个order是数据库里的字段 7                 ->order('order', 'asc'); 8             } 9         ])10             ->with(['properties'])11             ->find($id);12         return $product;13     }

 43、9-12 通过令牌获取用户标识

令牌Token是用户访问受保护的接口的必须参数

为什么不直接传递UID,而是通过令牌获取UID?

uid是自增长生成的,容易被别人猜到

 

使用令牌获取UID的好处是:在post提交的时候,如果提交的是俩个用户,令牌是A用户的,UID是B用户的,这样修改的地址就是B用户的,容易出错

44、9-15 参数过滤

Controller/Address.php

1  // 根据规则取字段是很有必要的,防止恶意更新非客户端字段2         $data = $validate->getDataByRule(input('post.'));
getDataByRule 这个方法是用来过滤客户端传回的参数的,uid我们是用token获取的,但是为了怕客户端传过来uid,覆盖token获取的uid,所以我们要过滤参数

 45、10-1 Scope权限作用域

用来判断用户的权限,可以先创建一个配置文件,在里面配置好几种权限,然后代码里用到什么就调用

47、前置方法

就是请求接口时,先执行这个方法

48、小程序下单支付流程

 小程序调用下单API,检查库存,如果有库存,就下单成功;下单成功后,调用支付API,我们自己的服务器调用微信服务器,生成预订单,返回支付参数,然后把支付参数传给小程序,小程序拿到支付参数后,就调用相应的接口,请求微信,进行支付,弹出支付窗口。支付成功或失败后,一方面返回给小程序提示信息,另一方面返回给我们的服务器信息(异步的,会在一定时间内多次推送)

49、10-10 订单快照

订单快照 保存的信息是当时下单时候的信息,地址和商品价格、数量,一般都是通过商品ID查询获取商品信息,这样不好,因为商品的名称和价格有可能改变,这样获取的数据和当时下单的时候的数据不一样,解决办法是下单的时候,就把订单里的商品信息都保存在订单order表里

50、TP5自动写入时间戳

在表里面,经常有create_time,update_time,delete_time这些属性,如果我们不想在保存数据的时候手动加入,可以在对应的mode里面写入如下代码,当保存数据的时候,自动加入当前时间

1 protected $autoWriteTimestamp = true;   //自动返回当前时间戳

什么时候TP5会给create_time自动加入时间,当检测到新加一条数据的时候

同样,如果做的是删除操作的时候,会自动给delete_time自动加入时间

这里特别说明下delete_time这个,现在我们很多时候删除数据,并不是真实的删除,而是假删除,只要delete_time有值,就表示这条数据被删除了

记住:要使用TP5自动写入时间戳,必须用模型的方式,如果用原生SQL,是不行的

如何自定义TO5里的create_time,update_time,delete_time这些名称

 

 51、TP5中使用事务

遇到下面的问题

我们执行一个方法的时候,在俩个表里保存相关的数据,如果只保存了前面的数据,后面的没有保存成功,这样会出问题,这里用到的数据库中的事务

在TP5中。要解决这个问题,就需要下面的代码

Db::startTrans();   Db::commit();
1 Db::startTrans(); 2         try{ 3             $orderNo = $this->makeOrderNo(); 4             $order = new \app\api\model\Order(); 5             $order->user_id = $this->uid; 6             $order->order_no = $orderNo; 7             $order->total_price = $snap['orderPrice']; 8             $order->total_count = $snap['totalCount']; 9             $order->snap_img = $snap['snapImg'];10             $order->snap_name = $snap['snapName'];11             $order->snap_address = $snap['snapAddress'];12             $order->snap_items = json_encode($snap['pStatus']);13 14             $order->save();15 16             $orderID = $order->id;17             $create_time = $order->create_time;18 19             foreach ($this->oProducts as &$p){20                 $p['order_id'] = $orderID;21             }22             $orderProduct = new OrderProduct();23             $orderProduct->saveAll($this->oProducts);24             Db::commit();25             return [26                 'order_no' => $orderNo,27                 'order_id' => $orderID,28                 'create_time' => $create_time29             ];30         }catch (Exception $ex){31             Db::rollback();32             throw $ex;33         }

 52、微信支付SDK

分为俩端的,客户端和服务端

客户端:在百度搜索微信支付开发者文档

 

 

服务端:在百度搜索微信支付开发者文档

 53、 10-21

下载PHP版的SDK,解压,在extend下创建个文件夹,把lib里的复制到里面

 54、在TP5中,引入extend里的文件

 

 55、  10-18

 

生成一个微信服务器需要的订单,不是我们真正的订单,用预订单,是为了从微信服务器返回支付参数

 

56、小程序业务流程

 57、微信支付  签名  10-26

签名的作用:为了保证传送的数据不被修改(当然,这是相对的,不能保证一定不被修改)

 

举例说明签名的作用:服务端有三个参数:A。B、C,现在用这个三个参数和APPKey四个参数一起,使用MD5,做成Sign签名,然后传送给客户端,客户端又传送到微信服务端,

微信服务端用同样的规则把传过来的参数和APPKey生成Sign签名,进行验证,俩个签名是不是一样,如果一样,就说明传送过来的参数正确

58、10-29  支付回调通知处理

1 // 微信支付回调处理 2     public function receiveNotify(){ 3        //通知频率为15/15/30/180/1800/1800/1800/3600,单位:秒 4  5         //1.检查库存量,有可能超卖 6         //2.更新这个订单的status状态 7         //3.减库存 8         //如果成功处理,返回微信成功处理信息,否则返回未成功处理信息 9 10         //微信返回的数据特点:post,xml格式,不会携带参数11         // 使用SDK的好处 可以处理XML格式12     }

微信支付成以后,会调用一个接口,返回处理的信息,这个接口需要我们自己定义receiveNotify()

备注:这个接口必须是post请求,返回的格式是xml,而且不会再里面携带参数(类似url?xx=xx这种)

我们用了SDK,可以很容易的处理XML数据  

要覆盖WxPay.Notify.php里的NotifyProcess方法

59、10-30 支付回调通知

$data的说明  

确定是否成功,要看下面这个字段

 60、把本地服务转换成外网,可以使用类似ngrok,不过这种工具,一般不安全

61、使用了代理以后,secure.php里pay_back_url要重新配置,具体看 10-23

 62、10-34 可以断点调试微信支付的回调吗?

正常情况,微信支付后,会自己调用我们提供的接口,这时我们是无法断点调试接口信息的

有一个方法:新创建一个方法,微信服务器调用的方法里面调这个方法,在这个方法里面断点调试微信服务器返回的信息

63、10-37

要把返回的数据里的某个字段进行json格式化处理,可以在Model里定义读取器

 

微信端

64、11-3 

微信小程序在真机上运行时要提前配置域名

进入小程序后台管理界面 

 

 只是请求的话只需要配置 request合法域名

 

65、11-4  异步回调和箭头函数

66、11-6

1 // if(params.sCallBack){2         //   params.sCallBack(res);3         // }4         // 这俩种写法是一样的  推荐用下面的,微信的demo中就这样写的5         params.sCallBack && params.sCallBack(res.data);

 67、小程序模板template的一些注意

父文件:

1 
2
3 4
5

模板文件:

1 

 (1)、父文件要引入模板文件的路径

 (2)、父文件里的is和模板文件里的name一致

 (3)、模板文件里不进行js操作,需要的数据是由父文件里传过来的,使用 data={}

  (4)、模板文件的样式,在父文件的样式里引入

1 @import "../tpls/products/products-tpl.wxss";

 67、底部的配置

1 "tabBar": { 2     "list": [ 3       { 4         "pagePath": "pages/home/home", 5         "text": "首页", 6         "iconPath": "imgs/toolbar/home.png", 7         "selectedIconPath": "imgs/toolbar/home@selected.png" 8       }, 9       {10         "pagePath": "pages/category/category",11         "iconPath": "imgs/toolbar/category.png",12         "selectedIconPath": "imgs/toolbar/category@selected.png",13         "text": "分类"14       },15       {16         "pagePath": "pages/cart/cart",17         "iconPath": "imgs/toolbar/cart.png",18         "selectedIconPath": "imgs/toolbar/cart@selected.png",19         "text": "购物车"20       },21       {22         "pagePath": "pages/my/my",23         "iconPath": "imgs/toolbar/my.png",24         "selectedIconPath": "imgs/toolbar/my@selected.png",25         "text": "我的"26       }27     ],28     "borderStyle": "white", // 边框的颜色29     "selectedColor": "#AB956D", //选中以后文字的颜色30     "color": "#989898", // 未选中文字的颜色31     "backgroundColor": "#F5F5F5" // 背景颜色32   }

 68、调试技巧

引入template的时候,不显示:在template里面随便打一行字,如果显示,就说么是数据的问题,如果不显示,就说明模板没有引入,这时候就要检查俩个地方:

  (1)、在父组件里,有没有用inport引入模板文件

  (2)、父组件传入的数据key和模板里的是否一致

   

 

 

在微信开发工具里,AppData里可以查看当前页面里的数据

 

69、11-16 动态设置导航栏标题

wx.setNavigationBarTitle(Object object)

注意:1、要在onReady里面调用,在onLoad里调用的时候,有可能会失效  2、全局设置导航栏标题的的地方必须为空,否则有可能先显示全局设置的,然后显示动态设置的,会闪一下

 

70、11-18 Picker组件

1 
2
3
4
数量
5
{
{productCount}}
6
7
8

 

picker对flex的支出不是很好,所以为了让picker里面的值都在中间,可以在他们外面包裹一个view,view源码里用的是flex布局

71、11-23 微信小程序数据从服务器端到前端的流程

 

页面初始化时,JS层调用API,从服务器端获取数据,然后进行数据绑定,在wxml显示数据。

前端有时候会进行操作,通过标签的自定义属性(data-)把参数传递到js层,js层用event获取,然后把参数通过API传递到服务器端,服务器端响应后把心得数据

再传递到J层,然后进行新的数据绑定

 

在小程序中,数据绑定是最重要的部分,类似的有angular,js和vue.js

 72、编译设置

每次我们改变代码的时候,都会跳转到第一页,可以这样设置

这样就会跳转到指定页面

 

73、12-4

1  for (let i = 0; i < len; i++) {2       //避免 0.05 + 0.01 = 0.060 000 000 000 000 005 的问题,乘以 100 *1003       if (data[i].selectStatus) {4         account +=5           data[i].counts * multiple * Number(data[i].price) * multiple;6         selectedCounts += data[i].counts;7         selectedTypeCounts++;8       }9     }

注意这种写法,在Js里,小数相乘会出现特别的结果,可以先乘以10的幂数,把值变成整数再相乘,最后对结果进行处理

74、12-5 购物车页面开发

不需要在页面显示,可以是用block,类似于大括号。

wx:if和wx:else不一定非要俩个相似的标签

75、跳转到tab栏下面的页面,必须使用switchTab

76、13-4 客户端令牌管理机制

程序初始化的时候,先从缓存(Storage)中读取令牌,检测令牌,如果令牌失效或者不存在,则请求token,把获取到的令牌保存到缓存(token)中

model(泛指所有向后端发送请求的文件)中请求后端API的时候,携带令牌去请求

如果在初始化的时候有令牌,在请求API的时候却没有,返回401,那就重新请求令牌,然后携带令牌去请求API

75、13-17 获取用户信息

1 wx.login({ 2       success: function () { 3  4         wx.getUserInfo({ 5  6           success: function (res) { 7             typeof cb == "function" && cb(res.userInfo); 8           }, 9 10           fail: function (res) {11             typeof cb == "function" && cb({12               avatarUrl: '../../imgs/icon/user@default.png',13               nickName: '零食小贩'14             });15           }16 17         });18       },19 20     })

备注:wx.login获取code,进而获取poenid,是不需要授权的

          wx.getUserInfo是需要授权的 

76、13-17 获取用户信息

在小程序里面,最好不要在页面中间自定义Loding组件,体验效果不好;如果特别需要,可以在顶部定义一个

77、wx.getUserInfo  获取用户信息

调用这个接口前,会让用户授权,如果是同意,可成功获取用户信息;如果是不同意,那将进入fail回调,而且不会再出现授权页面

78、13-20

合并俩个数组

1 this.data.orderArr.push.apply(this.data.orderArr, data);

79、13-20

onReachBottom 是Page的事件,页面滚动到最底部的时候触发
scroll-view组件也有这种效果,不过如果需要js控制好,那么推荐用onReachBottom

80、微信模板信息   14章的总结

微信模板信息链接:

看使用说明:

步骤一:获取模板 ID

有两个方法可以获取模板 ID:

  1. 通过模板消息管理接口获取模板 ID(详见 )
  2. 在微信公众平台手动配置获取模板 ID

登录 https://mp.weixin.qq.com 获取模板,如果没有合适的模板,可以申请添加新模板,审核通过后可使用,详见 

 

要想使用模板信息,需要先在https://mp.weixin.qq.com 这个里面选择需要的模板

点击添加按钮进行添加

添加完以后,记住 模板ID,请求模板信息接口的时候,要用这个ID(对应的参数是template_id)

 

步骤二:页面的  组件,属性 report-submit 为 true 时,可以声明为需要发送模板消息,此时点击按钮提交表单可以获取 formId,用于发送模板消息。或者当用户完成 ,可以获取 prepay_id 用于发送模板消息。

  有俩种发送模板信息的情况,一种是使用form组件,一种是支付完成后发送

  现在讨论支付完成这种情况,注意prepay_id ,这也是参数之一,对应的参数是form_id

 

步骤三:调用接口下发模板消息(详见  )

  通过上面俩个步骤,获取了template_id和form_id,再加上其他参数,就可以请求接口了

 

现在我们来看,分析发送模板信息接口

   参数分析

       string access_token  小程序全局唯一后台接口调用凭据 

         具体信息,查看

       string touser   接收者(用户)的 openid

       string template_id  所需下发的模板消息的id   上面已经说了

       string page   点击模板卡片后的跳转页面,仅限本小程序内的页面。支持带参数,(示例index?foo=bar)。该字段不填则模板无跳转。

       string form_id  表单提交场景下,为 submit 事件带上的 ;支付场景下,为本次支付的 

       string data  模板内容,不填则下发空模板

       string emphasis_keyword   模板需要放大的关键词,不填则默认无放大

      

      请求数据实例

      

1 { 2   "touser": "OPENID", 3   "template_id": "TEMPLATE_ID", 4   "page": "index", 5   "form_id": "FORMID", 6   "data": { 7       "keyword1": { 8           "value": "339208499" 9       },10       "keyword2": {11           "value": "2015年01月05日 12:30"12       },13       "keyword3": {14           "value": "腾讯微信总部"15       } ,16       "keyword4": {17           "value": "广州市海珠区新港中路397号"18       }19   },20   "emphasis_keyword": "keyword1.DATA"21 }

 

  81、15-2  另一种思路处理库存量的问题

      之前是先创建订单,在支付以后在数据库里扣除数量;

       新的思路是在创建订单后,就暂时扣除数量,支付以后,就正式扣除数量,如果在一段时间就没有支付,就恢复数量

       难点是:如何控制,没有支付就恢复数量,可以使用定时器(不是很好),队列(类似于redis)

转载于:https://www.cnblogs.com/zhaobao1830/p/9348416.html

你可能感兴趣的文章
Dubbo分布式服务框架入门(附工程)
查看>>
两年Java开发工作经验面试总结
查看>>
作为Java面试官--谈谈一年来的面试总结
查看>>
两年Java程序员面试经
查看>>
面试心得与总结---BAT、网易、蘑菇街
查看>>
如何面试有2年java工作经验的应聘人员
查看>>
Java实现简单的递归操作
查看>>
面试Java程序员需具备的11个技能
查看>>
HashMap 和 HashTable 到底哪不同 ?
查看>>
Java实现简单的递归操作
查看>>
Struts2工作原理和执行流程图
查看>>
在线预览Word,Excel~
查看>>
hibernate延迟加载(get和load的区别)
查看>>
关于文件拷贝效率问题
查看>>
MyBatis分页插件PageHelper的使用
查看>>
【MyBatis学习01】宏观上把握MyBatis框架
查看>>
【MyBatis学习02】走进MyBatis的世界
查看>>
【MyBatis学习03】原始dao开发方法及其弊端
查看>>
【MyBatis学习04】mapper代理方法开发dao
查看>>
【MyBatis学习05】SqlMapConfig.xml文件中的配置总结
查看>>