小猪今天在使用Visual Studio 2017 Community的编写ASP.NET Core 2.0程序,新建控制器的时候使用vs提供的基础功能:
1. 在控制器文件夹右键“新建”=》“控制器”
2. 填入控制器名称之后确定
给自己定个小目标,例如先写个十年代码,然后考虑再写二十年!
小猪今天在使用Visual Studio 2017 Community的编写ASP.NET Core 2.0程序,新建控制器的时候使用vs提供的基础功能:
1. 在控制器文件夹右键“新建”=》“控制器”
2. 填入控制器名称之后确定
今天小猪在查看小程序的文档时发现现在微信支持将传统二维码的微信扫描事件跳转到小程序了。
具体文档为:https://mp.weixin.qq.com/debug/wxadoc/introduction/qrcode.html
大概意思就是很多二维码是在微信小程序出生之前就已经出生了,所以原二维码可能并没有做一些特殊的设置来让微信来进行处理。如果当时的二维码的内容是一个网页地址,那么现在开发者可以设置一些规则将使用“微信扫一扫”功能扫描该二维码时跳转到指定的小程序而不是之前的网页地址了。
惊喜不惊喜?意外不意外?
more >>今天得到消息小程序开放了分享到微信群的更多功能,正好小猪前一段时间因为特别的忙而把本系列文章给耽搁了一点,期间就在想下面怎么来写这一系列的blog。今天正好就以此来开始吧。
小猪目前用的最多的小程序的分享是在骑行了摩拜单车以后在结算页面有一个分享出去抢免费骑行天数。
其实在此之前公众号的分享已经做的挺成熟了,用户可以根据指引分享自己独特的链接出去,被分享者打开的链接是带着分享者的信息的。这样的页面可以根据程序逻辑来做很多事情,例如:为自己拉票,分享自己的经验等。
可是在用户点了公众号的分享链接之后程序是不会知道用户到底是从哪来的,是从聊天窗口还是朋友圈?是从群聊天还是个人聊天?
小程序先开放了这个接口
正如官方解释所说:
当用户在群聊中点击小程序的分享卡片,开发者可获取群 ID 和群名称,更好地针对群场景提供个性化服务。
再如官方文档中的说明:
通常开发者希望分享出去的小程序被二次打开的时候能够获取到一些信息,例如群聊名字或者是群的标识。现在通过调用 wx.showShareMenu 并且设置 withShareTicket 为 true ,当用户将小程序分享到任一群聊之后,可以获取到此次分享的 shareTicket
官方文档地址:https://mp.weixin.qq.com/debug/wxadoc/dev/api/share.html#onshareappmessage
在公众号的页面里,很久之前程序是可以通过调用接口来直接引导用户分享页面的。后来腾讯对此做了限制,只能通过页面的右上角的目录按钮来点击分享。
在小程序里同样有该限制,而且必须要在定义了Page
对象的onShareAppMessage
函数之后,右上角菜单才会显示对应的“分享”按钮。1
2
3
4
5
6
7
8
9
10
11
12onShareAppMessage: function \(\) {
return {
title: '这里是机智life小程序',
path: '/page/index/index?id=123',
success: function(res) {
console.log(res)
},
fail: function(res) {
console.log(res)
}
}
}
运行程序结果可看到:
使用如下代码,来定义在回调里是否带上shareTicket参数,
1 |
|
如下图,
可见ShareTickets是个数组,也就是可以将页面同时分享到多个群,每一个群对应一个shareTicket
。使用shareTicket
可通过wx.getShareInfo
接口获取本次的分享信息。
使用下列代码来获取群信息:
1 | onShareAppMessage: function \(\) { |
运行程序,分享到一个测试群(在使用了showShareMenu
接口之后,再次点击右上角的分享之后,《微信web开发者工具》为我们建立了几个随即名称的群列表供测试),可以看到运行结果:
从上图中可以看到额外的数据:iv
、roomTopic
、rawData
、signature
、encryptedData
其中,roomTopic字段就是分享的群的名称.
如果想获取该群的ID,那么可以通过之前小猪介绍的跟着小猪来做小程序开发吧——解密CryptedData 来解密encryptedData。
解密完之后可以看到openGId
和之前已经存在的roomTopic
。
大功告成。
在手机上运行查看下效果:
在上两篇文章中小猪介绍了模板消息的使用情况,期间因为小程序模板消息的限制,在非支付场景下想使用模板消息那么必须使用微信小程序的表单来获取formId,这样就强制限制了必须有用户进行交互的情况下才可以使用模板消息功能,防止了小程序的模板消息功能被滥用。
这一篇文章介绍下小程序的表单相关。
稍微熟悉HTML的读者肯定知道html 的表单,微信小程序基于html程序,但是限制了原html表单的使用,只封装了我们常用的组件和属性。这样即防止了html表单的复杂变化,也提供了常用的组件功能。
今天小猪简单介绍几个常用的表单组件。
官方文档地址:https://mp.weixin.qq.com/debug/wxadoc/dev/component/
表单,将组件内的用户输入的<switch/>
<input/>
<checkbox/>
<slider/>
<radio/>
<picker/>
提交。
表单组件用来提交表单,微信小程序允许我们为表单添加如下属性
属性名 | 类型 | 说明 |
---|---|---|
report-submit | Boolean | 是否返回 formId 用于发送模板消息 |
bindsubmit | EventHandle | 携带 form 中的数据触发 submit 事件,event.detail = {value : {‘name’: ‘value’} , formId: ‘’} |
bindreset | EventHandle | 表单重置时会触发 reset 事件 |
上述的bindsubmit
属性和bindreset
属性都可以绑定一个js的事件函数,然后在用户点击提交和重置按钮时触发:例如下面的表单和对应js代码:1
2
3
4
5
6
7
8
9
10
11
12//<form bindsubmit="formSubmit" bindreset="formReset">
//<button formType="submit">Submit</button>
//<button formType="reset">Reset</button>
//js
Page({
formSubmit: function(e) {
console.log('form发生了submit事件,携带数据为:', e.detail.value)
},
formReset: function\(\) {
console.log('form发生了reset事件')
}
})
目前小程序支持如下的标签:
|- 标签名- |-说明- |
|—|—|:
|button |按钮|
|form |表单|
|input |输入框|
|checkbox| 多项选择器|
|radio |单项选择器|
|picker |列表选择器|
|picker-view |内嵌列表选择器|
|slider |滚动选择器|
|switch |开关选择器|
|label |标签|
建议读者分别写上这些标签,然后提交数据比对下具体的属性值。
例如下面的表单
1 |
|
配合下列js代码:
1 |
|
到界面上简单做几个输入值,点击提交按钮,看看后台对应获取到的值大概为:
1 |
|
官方文档地址:
https://mp.weixin.qq.com/debug/wxadoc/dev/api/notice.html#使用说明
在上一篇结束时小猪本打算这一篇使用falsk来做后端存储formId然后走标准的小程序开发流程来实现模板消息的功能。
但是后来仔细想想,如果读者本身自是想做小程序开发,对后端开发并不感兴趣,或者后端框架也不一定是基于Python的Flask,那其实对是否使用flask来做后端是并不关心的。
所以小猪这一篇开始,能不用后端的就不用后端,因为小程序框架本身已经为我们封装了wx.request
接口来访问网络了。我们可以方便的使用这个接口来代替服务器来做请求。
这个设置是用来限制我们的小程序中使用wx.request
接口时可以调用哪些域名来进行访问,一般而言我们配置我们自己的域名。
因为本篇文章需要在小程序内部调用发送模板消息的接口,所以需要将https://api.weixin.qq.com/
加入到合法域名里。
然后到微信《微信web开发者工具》里面的项目tag里刷新配置信息,如果不刷新的话可能会出现下述情况:
获取access_token的方法小猪很久之前就有单独的文章介绍过。和小猪一起搞微信公众号开发—获取Access_token
不过这里我们使用的是wx.request
接口来请求,所以我们直接使用调试的方法:
1. 打开网址https://mp.weixin.qq.com/debug/,确认选择的调试接口为获取access_token
2. 属于我们的appid 和secret值。
3. 点击调试,获取数据,在下面的返回框里找到对应的access_token值,并取出,这个值在两个小时之内是有效的。
直接使用跟着小猪来做小程序开发吧——获取用户Openid的方法来获取openid。
在微信小程序后台的模板消息栏里添加合适的模板消息,并记录其对应的模板ID。
因为我们只是为了体验下小程序的模板消息,所以我们把上面获取的信息先临时的保存在小程序的全局环境里:1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16//app.js
App({
onLaunch: function \(\) {
//调用API从本地缓存中获取数据
var logs = wx.getStorageSync('logs') || []
logs.unshift(Date.now\(\))
wx.setStorageSync('logs', logs)
},
//…… 省略了其他代码
globalData:{
userInfo:null,
openid:'oWv370DkivlAs-LPrxKKvQ9KP98w',
appid:'wx8fa41e5f33e****',
access_token:'********'
}
})
然后在对应的表单页的逻辑代码里sform.js:
1 |
|
对应的页面代码sform.wxml:`
页面代码里为了方便调试我们加上了一些调试信息。
上述代码逻辑很简单,根据主要就是获取到formid之后组装调用模板消息的必要信息,然后调用微信模板消息API,调用成功之后将信息反馈到小程序界面。
代码编写完成之后,转到《微信web开发者工具》的项目tag,点击预览按钮,编译上传完成之后微信扫描二维码就可以体验。
点击提交表单时可看到我们的服务通知
窗口里有了消息推送:
接下来的几篇小猪将围绕模板消息推动的功能分别向读者介绍小程序的几个功能
今天要介绍的是获取formId
在回答这个问题之前先简单的介绍下微信的模板消息功能。
在一开始,模板消息这个权限可不是所有都公众号都有的,即使你已经交了300块完成了微信认证。只有一些比较牛逼的企业例如说各个银行,人家的需求是类似在每次有交易信息的时候通知用户,这样的功能简直不能太好,人家本来是通过短信通知的,现在通过微信就可以了,而且还不收费,走运营商的短信接口可是需要大概一毛一条的。
所以这个权限是只有走内部流程的。
大概是在13年底的时候微信向所有认证的服务号开放了申请接口。这下模板消息这个功能就彻底开放出来了,每一个公众号都可以发送自己的模板消息,用户会在该公众号的回话窗口看到模板消息。
可是小程序是没有单独的回话窗口的,要使用模板消息,那用户收到的模板消息会在哪呢?
答案是在微信的单独的一个“服务通知”回话框里。
可是如果每一个小程序都可以像公众号那样无限制的发送模板消息的话,那这个“服务通知”的会话框很快就会被占领。
所以必须有一定的限制小程序使用模板消息,微信目前的限制是在如下两种情况下小程序才能够正常的使用模板消息:
1. 在小程序内使用了微信支付接口,
2. 在小程序里用户点击了表单,而且该表单的report-submit属性值为true时。
在上述第二种情况下,小程序框架会给出一个formid,利用这个formId才能正常发送模板消息。
使用类似下面的代码,注意表单的report-submit属性。1
2
3
4
5
6
7
8
9
10
11
12
13
14
15// demo.wxml
<form bindsubmit="formSubmit" bindreset="formReset" report-submit = "true">
<view class="section section_gap">
<view class="section__title">checkbox</view>
<checkbox-group name="checkbox">
<label><checkbox value="checkbox1"/>checkbox1</label>
<label><checkbox value="checkbox2"/>checkbox2</label>
</checkbox-group>
</view>
<view class="btn-area">
<button formType="submit">Submit</button>
<button formType="reset">Reset</button>
</view>
</form>
然后在对应的js文件里加上:
1 |
|
单机提交按钮之后可以看到运行结果:
form发生了submit事件,携带数据为: the formId is a mock one
因为我们是在IDE中测试,所以得到的formId值为the formId is a mock one
。在真机中我们可以得到一个具体的值,利用该值结合其他参数我们就可以发送模板消息啦。
下一篇小猪将使用flask结合mysql数据库来做一个demo,把这个formId 存储起来供下次使用。
如果您在看此文章之前有过其他程序的开发经验,那一定会知道一般例如安卓或者苹果的原生APP都提供了本地的存储功能,甚至可以使用sqlite数据库来做存储。可是微信的小程序框架基于微信本身,其实际运行环境只是在浏览器里面,所以不会提供那么丰富的数据存储实力。但html5开始已经可以在浏览器里面存储数据,好在微信的小程序给这个功能封装好了,这样我们可以使用数据存储。
每个微信小程序都可以有自己的本地缓存,可以通过 wx.setStorage(wx.setStorageSync)、
wx.getStorage(wx.getStorageSync)、
wx.clearStorage(wx.clearStorageSync)
可以对本地缓存进行设置、获取和清理。本地缓存最大为10MB。
上面的set和get都有对应的Sync方法,带Sync的方法为同步方法、不带Sync的方法为异步方法。
设置缓存都需要设置一个key和对应的data值,我们在《微信web开发者工具》中的调试状态下可以点击调试窗口的Storage 栏来查看我们缓存在本地的数据。
缓存可以保存数组、数值、字符串、对象。
提供setStorage
和setStorageSync
两个接口,并且在使用设置存储方法时,如果小程序的存储值当中已经存在对应的key的值,那么会使用新的值替换原来的值。
1 | wx.setStorage({ |
因为该方法为同步接口,所以直接设置key和data:
1 | wx.setStorageSync('key', 'value') |
上面两个demo中我们都使用了字符串缓存,当然我们也可以缓存一个对象,例如:
1 |
|
异步接口,所以我们可以定义几个回调:
1 |
|
其中,我们可以看出来,微信小程序的很多异步接口的回调都会给出三个回调:success、fail、complete,在执行成功的时候回执行success、complete回调;在执行失败之后会分别执行fail、complete回调。
该接口为同步接口,所以只需传递对应的key值就可以了。如下列代码:
1 |
|
使用wx.getStorageInfo
接口
例如下列代码:
1 |
|
也可以使用同步接口wx.getStorageInfoSync
。
在上一篇文章中,小猪介绍了如何解密通过wx.getUserInfo
接口获取到的cryptedData数据。其中的session_key小猪是写在flask的缓存中,缓存的键是写死为:xcx_session_key
。在真实环境中我们不能够这样写,因为这样不同的用户获取到的session_key是相同的,所以我们需要给不同的用户附上不同的缓存key。把flask的缓存key返回给微信小程序,小程序中可以固定一个key值,data值保持flask后台给到的值。
说的比较绕,这里需要读者好好理解下。
在flask的代码的使用code获取session_key中,使用下列代码:
1 |
|
接下来,在wx.request
的回调中把flask中返回的r3session_key保存起来:
1 |
|
再接下来,在调用wx.getUserInfo时将返回的数据加上从微信小程序本地缓存中取到的r3session
丢给flask来处理,flask根据来的r3session
从本地服务器的flask缓存中取到微信的值解密cryptedData。这才是一个完整的过程。
小程序的getUserInfo代码:
1 |
|
对应的flask代码:
1 |
|
参考官方文档地址:https://mp.weixin.qq.com/debug/wxadoc/dev/api/data.html
经过几篇文章的介绍,如果您是按照小猪的代码一步一步做的话你应该已经了解小程序开发的大致过程,接下来的重点无非就是熟悉小程序提供给大家的接口,然后根据这些接口来完善我们的业务逻辑。
接下来的几篇文章小猪将向大家介绍一个实际的功能:在小程序中添加备忘录,在适时的时候小程序将提醒用户。
tag:
缺失模块。
1、请确保node版本大于6.2
2、在博客根目录(注意不是yilia根目录)执行以下命令:
npm i hexo-generator-json-content --save
3、在根目录_config.yml里添加配置:
jsonContent: meta: false pages: false posts: title: true date: true path: true text: false raw: false content: false slug: false updated: false comments: false link: false permalink: false excerpt: false categories: false tags: true