微信小程序-进阶知识

2020/7/11 微信小程序
// 小程序通信与网页通信的区别
1. 小程序中的渲染层中会有多个 webview,逻辑层只有一个 JsCore 用来执行 js 代码
    所有的 webview 都共用这个逻辑层,WXS 是每个 webview 中独有的 JsCore
    所以它比逻辑层中的 JsCore 快的原因是他不需要经过微信 Native 中转
2. 浏览器中的渲染层和逻辑层都是在同一个线程里面,互斥的,而不同 tab 之间都是不同的线程
    所以他们之间没办法进行通信,小程序中 webview 共用的逻辑层是同一个线程,所以它可以进行通信
3. 在网页中想实现不同 tab 之间的通信
    1. 同域
        1. localStorage 简单易用,推荐
        2. SharedWorker 调试不方便,不兼容 IE11
        3. Broadcast Channel
    2. 跨域
        1. WebSocket 需要服务端,成本较高
        2. iframe + localStorage
        3. 可以监听页面显示去执行对应的逻辑,addEventListener(visibilityChange, fn)
4. 网页和 iframe  之间的通信
    1. 使用 postMessage
----------------------------------------------------------------------------------------------
// 登录微信公众平台后,概念理解,包括小程序
1. 公众号设置下功能设置:
    业务域名: h5网页所对应的域名,如果不设置在有输入框时微信会提示“防欺诈盗号,请勿支付或输入QQ密码”
    js接口安全域名: 要想使用微信JS-SDK,包括有分享、支付等功能,如果不设置则无法使用
    网页授权域名: 从别的App或网页跳转到微信进行授权登录,确认登录后再返回App或网页,如果不设置则无法实现微信授权
2. 人员设置: 设置绑定运营者,用于管理素材、文章等公众号服务
3. 开发者工具设置: 设置绑定开发者,如果不绑定则无法进行扫码进行开发联调测试
4. 网页授权access_token: 用于获取用户的身份信息,只在网页授权时使用
5. 普通access_token: 用于调用非网页授权的所有接口
6. 在获取access_token时需要配置访问IP白名单,否则获取不到
7. unionID: 开发者到微信开发平台把公众号、移动应用、小程序进行关联,用户进入其中一个程序就会生成unionID,且不管进入哪一个unionID是相同的,有用户个人信息
8. openID: 用户进入公众号、移动应用、小程序都会生成一个openID,且每个openID都是不一样的即使是同一个用户
9. 公众号的微信认证每年300
10. 小程序版本管理即从开发工具中上传的代码,需要微信审核后才可进行发布
11. 小程序成员管理可以添加开发成员和体验成员
12. 小程序的开发设置中的服务器域名的request合法域名,就是项目域名,不配置则无法调用后端接口
13. 小程序的开发设置中的业务域名是要从小程序中通过web-view打开H5页面则需要配置业务域名
14. 在公众号中的小程序管理中可以关联小程序,可以把之前通过邮箱注册的小程序进行关联,也可以通过快速注册并认证小程序实现快速注册和关联,会直接复用公众号的资料
15. 小程序只能分享给朋友,不能分享第三方应用 // 把图片放在朋友圈实现分享
16. 微信组件有版本,和微信App版本有关系,需在开发时去查看当前微信App版本是否能使用
17. 微信API有版本,和微信App版本有关系,需在开发时使用wx.canIUse()方法进行判断是否能使用
18. 可以把全局的变量挂载到App.js中的App中,当做window使用
19. 小程序的AppSecret即小程序秘钥只能重置且无法查看
20. 微信公众号网页需要配置域名不能用 ip
21. 微信小程序和微信公众号的业务域名需要放文件校验授权才能配置成功
22. webview 中的跳转链接需要配置业务域名
----------------------------------------------------------------------------------------------
// 微信H5两种授权流程
1. 静默授权: 对于前端用户来说是无感知的
    // 第一次是跳转,需要带上appid和redirect_uri地址和scope为snsapi_base
    // 当跳转成功后会到微信会回跳到redirect_uri地址并在url中返回code,没有确认登录界面
    获取code
    // 第二次是请求,需要带上appid和secret即公众号秘钥和返回的code
    // 当请求成功后会返回openid和access_token和过期时间等信息
    获取openid // 静默授权到此完成授权流程,只获取openid,无需再通过openid和access_token去拉去用户信息授权
2. 用户信息授权: 对于前端用户来说只是点击了一个确认登录按钮
    // 第一次是跳转,需要带上appid和redirect_uri地址和scope为snsapi_userinfo
    // 当跳转成功后会到微信确认登录界面,点击确认登录后会回跳到redirect_uri地址并在url中返回code
    用户点击确认登录,会返回code // 获取code
    // 第二次是请求,需要带上appid和secret即公众号秘钥和返回的code
    // 当请求成功后会返回openid和access_token和refresh_token和过期时间等信息
    通过code换取网页授权access_token // 获取openid和access_token
    // 由于access_token拥有较短的有效期,当access_token超时后,可以使用refresh_token进行刷新
    // refresh_token有效期为30天,当refresh_token失效之后,需要用户重新授权
    // 第三次是请求,带上appid和refresh_token即可拿到新的access_token
    // 如果不需要直接执行第四次请求
    刷新access_token // 如果需要
    // 第四次是请求,需要带上openid和access_token
    // 当请求成功后会返回用户信息完成授权流程
    获取用户信息
----------------------------------------------------------------------------------------------
// 微信H5授权前后端流程
1. 前端:
    判断是否授过权,可使用后端写在localStorage或cookit中的token或openId作为条件
    在获取后端的接口getUserInfo时就可以进行判断有没有上述的条件,如果没有就会去授权,如果有授权就能拿到用户信息
    直接通过window.location.href方式跳转到后端指定的地址,带上重定向地址即首页和其他业务需求参数
    不通过ajax接口方式传递的参数的原因是微信用户信息授权需要跳转至微信页面再去请求微信接口,所以无法通过ajax返回
    全部都是通过后端进行跳转,在授权成功后再由后端重定向到一开始前端传递过来的地址即首页完成授权
2. 后端:
    参考上面微信H5两种授权流程
    在获取access_token时需要配置访问的IP白名单
    且由于公众号的secret和获取到的access_token安全级别都非常高,必须只保存在服务器,不允许传给客户端
    后续刷新access_token、通过access_token获取用户信息等步骤,也必须从服务器发起
----------------------------------------------------------------------------------------------
// 通过使用微信JS-SDK,网页开发者可借助微信高效地使用拍照、选图、语音、位置等手机系统的能力
// 同时可以直接使用微信分享、扫一扫、卡券、支付等微信特有的能力,为微信用户提供更优质的网页体验
// 微信JS-SDK调用流程
1. 在公众号中绑定域名,即接口安全域名,如果不配置就无法调用
2. 引入js文件,即微信JS-SDK,可通过下载官方文件内容也可引入官方文件也可使用npm包 // 官方: http://res.wx.qq.com/open/js/jweixin-1.6.0.js
3. 通过config接口注入权限验证配置 // 需要后端进行授权后才能拿到的配置
    wx.config({
    // 开启调试模式,调用的所有api的返回值会在客户端alert出来,若要查看传入的参数,
    // 可以在pc端打开,参数信息会通过log打出,仅在pc端时才会打印。
      debug: true,
      appId: '', // 必填,公众号的唯一标识
      timestamp: , // 必填,生成签名的时间戳
      nonceStr: '', // 必填,生成签名的随机串
      signature: '',// 必填,签名
      jsApiList: [] // 必填,需要使用的JS接口列表
    })
4. 通过ready接口处理成功验证 // 在config中的jaApiList中的才能使用
    wx.ready(function(){
    // config信息验证后会执行ready方法,所有接口调用都必须在config接口获得结果之后,
    // config是一个客户端的异步操作,所以如果需要在页面加载时就调用相关接口,
    // 则须把相关接口放在ready函数中调用来确保正确执行。对于用户触发时才调用的接口,
    // 则可以直接调用,不需要放在ready函数中。
    })
5. 通过error接口处理失败验证
    wx.error(function(res){
    // config信息验证失败会执行error函数,如签名过期导致验证失败,
    // 具体错误信息可以打开config的debug模式查看,也可以在返回的res参数中查看,
    // 对于SPA可以在这里更新签名。
    })
----------------------------------------------------------------------------------------------
// 在使用微信JS-SDK前需要准备的config的签名
1. 签名算法需要有一个随机数、一个时间戳、一个url、一个ticket // ticket由微信返回,其他由自己定义
2. ticket需要有普通的access_token,直接通过微信接口获取,需要普通的access_token,就能返回ticket
3. 普通的access_token直接通过微信接口获取,需要appid和secret即公众号秘钥,就能返回access_token // 需要配置访问IP白名单
4. 对得到的签名参数按照字段名的ASCII码从小到大排序(字典序)后,使用URL键值对的格式(即key1=value1&key2=value2…)
5. 再对转换后的格式进行sha1加密即能得到config中的signature
6. 注意:
    签名用的noncestr和timestamp必须与wx.config中的nonceStr和timestamp相同
    签名用的url必须是调用JS接口页面的完整URL
    出于安全考虑,开发者必须在服务器端实现签名的逻辑
----------------------------------------------------------------------------------------------
// 接口调用说明
1. 所有接口通过wx对象(也可使用jWeixin对象)来调用,参数是一个对象,除了每个接口本身需要传的参数之外,还有以下通用参数:
    success:接口调用成功时执行的回调函数。
    fail:接口调用失败时执行的回调函数。
    complete:接口调用完成时执行的回调函数,无论成功或失败都会执行。
    cancel:用户点击取消时的回调函数,仅部分有用户取消操作的api才会用到。
    trigger: 监听Menu中的按钮点击时触发的方法,该方法仅支持Menu中的相关接口。
2. 不要尝试在trigger中使用ajax异步请求修改本次分享的内容,因为客户端分享操作是一个同步操作,这时候使用ajax的回包会还没有返回。
3. 以上几个函数都带有一个参数,类型为对象,其中除了每个接口本身返回的数据之外,还有一个通用属性errMsg,其值格式如下:
    调用成功时:"xxx:ok" ,其中xxx为调用的接口名
    用户取消时:"xxx:cancel",其中xxx为调用的接口名
    调用失败时:其值为具体错误信息
----------------------------------------------------------------------------------------------
// 接口调用示例
1. wx.ready(function () {   // 在完成config注入后要先调用ready再调用接口
     wx.updateAppMessageShareData({ // 分享
        desc: '', // 分享描述
        link: '', // 分享链接,该链接域名或路径必须与当前页面对应的公众号JS安全域名一致
        imgUrl: '', // 分享图标
        success: function () {
        // 设置成功
        }
     })
   })
2. wx.ready(function () {   // 在完成config注入后要先调用ready再调用接口
      wx.chooseImage({ // 选择图片
        count: 1, // 默认9
        sizeType: ['original', 'compressed'], // 可以指定是原图还是压缩图,默认二者都有
        sourceType: ['album', 'camera'], // 可以指定来源是相册还是相机,默认二者都有
        success: function (res) {
        var localIds = res.localIds; // 返回选定照片的本地ID列表,localId可以作为img标签的src属性显示图片
        }
      })
    }
----------------------------------------------------------------------------------------------
// H5和小程序开发的区别
1. 运行不同:
    H5运行在浏览器中,小程序运行JSCode
2. 服务器不同:
    H5通过nginx等服务器访问,小程序依托微信App
3. Api不同:
    H5DOM/BOM,小程序没有DOM/BOM
----------------------------------------------------------------------------------------------
// 微信小程序授权流程,先登录再授权,两步操作分开
1. 前端通过wx.login()方法获取code
2. 把code通过接口传给后端
3. 后端通过微信code2Session()方法获取openid、unionid、session_key即会话秘钥,需要带上appid和secret和code
4. 如果要获取用户敏感信息如手机号等需要session_key进行解密,其他的基本信息和H5一样不需要解密 // 敏感信息是加密的
5. 前端通过wx.getUserInfo获取用户信息再通过接口把信息传给后端完成授权
    获取用户信息(明文、加密),需要用户授权 // 微信自带授权弹框
    有wichCredentials参数,如果为true,必须要求用户已登录否则拿不到信息
    为false,不需要登录,但拿不到加密信息,如果授权被拒绝则不会再显示触发授权
    如果要重新触发则需调用wx.openSetting()
6. wx.login // 不需要授权,静默登录,登录状态有时效性,多久失效由微信服务器决定
7. wx.openSetting() // 用户全部的授权记录,让用户重新授权
8. 在新版的小程序中要想让用户授权必须使用button让用户点击引导授权
   通过wx.getSetting()判断用户是否授权,如果用户已经授权,可以调用getUserInfo获取用户信息,没授权则获取不到
9. 在使用授权button时<button open-type="getUserInfo" bind:getUserInfo="方法名"> // 通过方法名的event拿到用户信息
10. 内置组件<open-data>这个可以获取用户信息,只在wxml中有用
----------------------------------------------------------------------------------------------
// 微信小程序分享
1. 通过button的open-type开发能力share即可实现按钮分享
2. 通过配置page生命周期的onShareAppMessage()方法配置标题、图片等
3. 如果不配置则无法实现点击右上角三个点进行分享、分享的弹框的标题、图片是系统截取的
----------------------------------------------------------------------------------------------
// 订阅号微信认证特权
1. 自定义菜单 // 可设置跳转外部链接, 设置纯文本消息
2. 可使用部分开发接口
3. 可以申请广告主功能
4. 可以申请卡券功能
5. 可以申请多客服功能
6. 公众号头像及详细资料会显示加V标识
----------------------------------------------------------------------------------------------
// 服务号微信认证特权
1. 全部高级开发接口
2. 可以申请开通微信支付功能
3. 可以申请开通微信小店
4. 可以申请广告主功能
5. 可以申请卡券功能
6. 可以申请多客服功能
7. 公众号头像及详细资料会显示加V标识
----------------------------------------------------------------------------------------------
// 微信支付认证
1. 在公众号微信支付选择接入微信认证去注册商户号, 完成接入
2. 在商户平台注册一个商户号, 在商户平台填写appid实现关联公众号或小程序或App, 完成接入
3. H5在完成接入后需要在商户平台配置支付授权目录, 目录是支付页面的上一级的路由, 小程序不需要
    : webchenjie.cn/a/b , b是支付页面, 则授权目录是 webchnjie.cn/a
4. 在商户平台的账户中心的API安全中设置密钥
----------------------------------------------------------------------------------------------
// 小程序支付流程
1. 前端:
        wx.requestPayment() // 微信API发起微信支付
        需要的参数:
            timeStamp // 时间戳
            nonceStr // 随机字符串
            package // 后端调用微信统一下单接口返回的prepay_id的参数值, 格式是prepay_id='值'
            signType // 签名算法
            paySign // 签名, 此签名需要后端的prepay_id等数据拼接加密生成签名
            success // 成功回调, requestPayment: ok 支付成功 / requestPayment: fail cancel 支付取消
            fail // 失败回调
            complete // 不管成功失败都会执行的回调
2. 后端:
        调用微信统一下单接口 // https://api.mch.winxin.qq.com/pay/unifiedorder
        调用的流程:
            通过参数生成签名包括商户中心的app密钥
            组装XML格式
            获取prepay_id
        需要的参数:
            参数有很多都需要拼接成xml格式进行调用
            有一个notify_url参数是通知地址即回调地址, 微信会把支付结果通知到此参数的url中去, 需要响应接收存入数据库完成支付操作
        返回的结果:
            返回的数据是XML格式, 需要通过插件转成json格式 // xml2js
            当报错时:
                return_code // 返回状态码 有SUCCESS/FAIL 报错返回FAIL
                return_msg // 返回信息 签名失败
            当成功时:
                return_code // 返回状态码 有SUCCESS/FAIL 成功返回SUCCESS
                result_code // 业务结果 有SUCCESS/FAIL 成功返回SUCCESS
                其他返回值...
            当return_code和result_code都是SUCCESS时就会返回prepay_id // 前端需要的参数
----------------------------------------------------------------------------------------------
1. web-view组件内嵌普通H5只支持识别小程序码
2. web-view组件内嵌公众号文章只支持识别小程序码和公众号二维码
3. 二维码/小程序码图片不支持长按识别。仅在wx.previewImage中支持长按识别
----------------------------------------------------------------------------------------------
// H5支付流程
1. 前端:
        wx.chooseWXPay() // 微信JS-SDK发起微信支付
        需要的参数:
            timeStamp // 时间戳
            nonceStr // 随机字符串
            package // 后端调用微信统一下单接口返回的prepay_id的参数值, 格式是prepay_id='值'
            signType // 签名算法
            paySign // 签名, 此签名需要后端的prepay_id等数据拼接加密生成签名
            success // 成功回调, chooseWXPay: ok 支付成功 / chooseWXPay: fail 支付取消
            cancel // 取消回调
            fail // 失败回调
            complete // 不管成功失败都会执行的回调
2. 后端:
        调用微信统一下单接口 // https://api.mch.winxin.qq.com/pay/unifiedorder
        调用的流程:
            通过参数生成签名包括商户中心的app密钥
            组装XML格式
            获取prepay_id
        需要的参数:
            参数有很多都需要拼接成xml格式进行调用
            有一个notify_url参数是通知地址即回调地址, 微信会把支付结果通知到此参数的url中去, 需要响应接收存入数据库完成支付操作
        返回的结果:
            返回的数据是XML格式, 需要通过插件转成json格式 // xml2js
            当报错时:
                return_code // 返回状态码 有SUCCESS/FAIL 报错返回FAIL
                return_msg // 返回信息 签名失败
            当成功时:
                return_code // 返回状态码 有SUCCESS/FAIL 成功返回SUCCESS
                result_code // 业务结果 有SUCCESS/FAIL 成功返回SUCCESS
                其他返回值...
            当return_code和result_code都是SUCCESS时就会返回prepay_id // 前端需要的参数
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
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
Last Updated: 2024/7/31 12:57:25
    飘向北方
    那吾克热-NW,尤长靖