设为首页 收藏本站
查看: 1795|回复: 0

[经验分享] 微信公众平台开发(免费云BAE+高效优雅的Python+网站开放的API)

[复制链接]

尚未签到

发表于 2015-4-20 11:01:55 | 显示全部楼层 |阅读模式
  虽然校园App是个我认为的绝对的好主意,但最近有个也不错的营销+开发的模式出现:微信平台+固定域名服务器。
  微信公众平台的运行模式不外两个:
  一、机器人模式或称转发模式,将说话内容转发到服务器上完成,拿服务器的回复再一次转发,就完成一次问答谈话。
  二、人控模式,一个自然人登陆公众平台上,能直接接触到所有关注者,与之交互,这一定也是最累的。
  
  微信公众平台若是服务号,用来做微网站,省去了登录认证过程。但说白了就是微信定制版的微网站。这我一学期后才搞懂,如果早些弄懂就不会做那么多无用功。
  
  微信公众平台须有正面头像+身份证的照片来实名认证,非常严格。顺便一说,微信公众平台官方说法是偏支持大企而非个人。
  服务器(准确的说只是一个引擎)有新浪云SAE,百度云BAE,阿里云AAE。
  SAE最早,但使用云豆消费,注册只送500个。到现在,BAE允许创建10个应用而不用实名认证,SAE是需实名认证的。还有BAE比SAE强的就是支持git,虽然两者都支持svn,非常合时,刚好我学习git中,我果断选择BAE。云上建的每个应用可有20个版本,但任一个版都可以并且唯一上线。AAE(阿里云)一直不支持python,很让人失望。
  第一阶段:入门——轻轻走过飘过。
  下面是用数天时间借鉴前人成果Kingson的《一个用Python和Bottle实现基于微信公众平台API和SAE查询豆瓣电影的简单应用》开发的。
  这个例子非常适合在用Python的开发人员。经过一番狠狠的折腾,我还弄懂了其它问题:云的概念、OAuth、token、微信API调用,网站API调用、python等,百度谷歌都会有答案。
  还有很多像微信API通信认证(话说竞然用xml而不用json通信,不过这是取舍问题,无可厚非),python web框架,git对接云服务器……用了我许多时间。过程曲折复杂,看起来只是转移一下云平台,但实名认证,开发者域名的认证等浪费了我很多时间,因为没经验,很多各种问题都撞上了,尤其是我这种粗心大意,心眼碗粗的人,整个过程实在不算顺利,但我相信别人都会比我顺利,因为我连最低级的错都犯了。不多说,贴上关键代码代码。
  下载地址:http://pan.baidu.com/s/1d1g3l
  



  1 #! /usr/bin/env python
  2 # coding=utf-8
  3 __author__ = 'jszhou'
  4 from bottle import *
  5 import hashlib
  6 import xml.etree.ElementTree as ET
  7 import urllib2
  8 # import requests
  9 import json
10
11 app = Bottle()
12
13 """
14 Change Log:
15 03-04--03-08 完成微信API+Python自动回复代码雏形,可以通过电影ID查询电影信息,以Text形式返回给用户电影
16 Title和电影summary
17 # 03-11 完成通过电影名称查询并返回图文格式的数据
18 # 03-13 1.增加给新关注的用户自动返回“欢迎关注豆瓣电影,输入电影名称即可快速查询电影讯息哦!”信息的功能
19         2.完善注释信息
20  
21 关于本地调试问题:
22 微信没有提供本地调试功能,给用户造成不小的麻烦。
23 打开Bottle的Debug功能,在本地运行自己的代码(启动Server),使用Chrome或Firefox上的Advanced Rest Client插件来模拟微信服务器向自己的应用发送请求,
24 这样就可以看到详细的报错信息,方便开发者定位修复问题,其相当于,自己的应用是SAE,而Advanced Rest Client模拟的是新微信客户端和微信服务器。
25 也有同学自己写脚本,模拟微信服务器发送数据,这也是同样的道理。
26  
27 遗留问题:
28 1.从豆瓣拿到的海报图片都是竖向的,而微信中显示的是横向的,所以在微信看图片就被裁了一节,不过还好能看,
29   如何能完整显示海报图片,有待进一步research;
30 2.现在的通过电影名称返回的结果,实际上是拿的豆瓣返回的第一条数据,这样就有可能不准确,如何精确匹配用户的
31   查询条件,也还需要进一步研究。
32 """
33  
34 @app.get("/")
35 def checkSignature():
36     """
37     这里是用来做接口验证的,从微信Server请求的URL中拿到“signature”,“timestamp”,"nonce"和“echostr”,
38     然后再将token, timestamp, nonce三个排序并进行Sha1计算,并将计算结果和拿到的signature进行比较,
39     如果相等,就说明验证通过。
40     话说微信的这个验证做的很渣,因为只要把echostr返回去,就能通过验证,这也就造成我看到一个Blog中,
41     验证那儿只返回了一个echostr,而纳闷了半天。
42     附微信Server请求的Url示例:http://yoursaeappid.sinaapp.com//?signature=730e3111ed7303fef52513c8733b431a0f933c7c
43 &echostr=5853059253416844429&timestamp=1362713741&nonce=1362771581
44     """
45     token = ""  # 你在微信公众平台上设置的TOKEN
46     signature = request.GET.get('signature', None)  # 拼写不对害死人那,把signature写成singnature,直接导致怎么也认证不成功
47     timestamp = request.GET.get('timestamp', None)
48     nonce = request.GET.get('nonce', None)
49     echostr = request.GET.get('echostr', None)
50     tmpList = [token, timestamp, nonce]
51     tmpList.sort()
52     tmpstr = "%s%s%s" % tuple(tmpList)
53     hashstr = hashlib.sha1(tmpstr).hexdigest()
54     if hashstr == signature:
55         return echostr
56     else:
57         return "wws:indentify error"
58  
59 def parse_msg():
60     """
61     这里是用来解析微信Server Post过来的XML数据的,取出各字段对应的值,以备后面的代码调用,也可用lxml等模块。
62     """
63     recvmsg = request.body.read()  # 严重卡壳的地方,最后还是在Stack OverFlow上找到了答案
64     root = ET.fromstring(recvmsg)
65     msg = {}
66     for child in root:
67         msg[child.tag] = child.text
68     return msg
69  
70 def query_movie_info():
71     """
72     这里使用豆瓣的电影search API,通过关键字查询电影信息,这里的关键点是,一是关键字取XML中的Content值,
73     二是如果Content中存在汉字,就需要先转码,才能进行请求
74     """
75     movieurlbase = "http://api.douban.com/v2/movie/search"
76     DOUBAN_APIKEY = ""  # 这里需要填写你自己在豆瓣上申请的应用的APIKEY
77     movieinfo = parse_msg()
78     searchkeys = urllib2.quote(movieinfo["Content"].encode("utf-8"))  # 如果Content中存在汉字,就需要先转码,才能进行请求
79     url = '%s?q=%s&apikey=%s' % (movieurlbase, searchkeys, DOUBAN_APIKEY)
80     # return "{'url': %s}" % url
81     # url = '%s%s?apikey=%s' % (movieurlbase, id["Content"], DOUBAN_APIKEY)
82     # resp = requests.get(url=url, headers=header)
83     resp = urllib2.urlopen(url)
84     movie = json.loads(resp.read())
85     # return "{'movie': %s}" % movie
86     # info = movie["subjects"][0]["title"] + movie["subjects"][0]["alt"]
87     # info = movie['title'] + ': ' + ''.join(movie['summary'])
88     return movie
89     # return info
90  
91 def query_movie_details():
92     """
93     这里使用豆瓣的电影subject API,通过在query_movie_info()中拿到的电影ID,来获取电影的summary。
94     """
95     movieurlbase = "http://api.douban.com/v2/movie/subject/"
96     DOUBAN_APIKEY = ""  # 这里需要填写你自己在豆瓣上申请的应用的APIKEY
97     id = query_movie_info()
98     url = '%s%s?apikey=%s' % (movieurlbase, id["subjects"][0]["id"], DOUBAN_APIKEY)
99     resp = urllib2.urlopen(url)
100     description = json.loads(resp.read())
101     description = ''.join(description['summary'])
102     return description
103  
104 @app.post("/")
105 def response_msg():
106     """
107     这里是响应微信Server的请求,并返回数据的主函数,判断Content内容,如果是“Hello2BizUser”,就
108     表明是一个新注册用户,调用纯文本格式返回,如果是其他的内容就组织数据以图文格式返回。
109  
110     基本思路:
111     # 拿到Post过来的数据
112     # 分析数据(拿到FromUserName、ToUserName、CreateTime、MsgType和content)
113     # 构造回复信息(将你组织好的content返回给用户)
114     """
115     #拿到并解析数据
116     msg = parse_msg()
117     #设置返回数据模板
118     #纯文本格式
119     textTpl = """
120              
121              
122              %s
123              
124              
125              0
126              """
127     #图文格式
128     pictextTpl = """
129                 
130                 
131                 %s
132                 
133                 1
134                 
135                 
136                 
137                 
138                 
139                 
140                 
141                 
142                 1
143                  """
144     #判断Content内容,如果等于"Hello2BizUser",表明是一个新关注用户,如果不是,就返回电影标题,电影简介
145     #和电影海报组成的图文信息
146     if msg["Content"] == "Hello2BizUser":
147         echostr = textTpl % (
148             msg['FromUserName'], msg['ToUserName'], str(int(time.time())), msg['MsgType'],
149             u"欢迎关注豆瓣电影,输入电影名称即可快速查询电影讯息哦!")
150         return echostr
151     else:
152         Content = query_movie_info()
153         description = query_movie_details()
154         echostr = pictextTpl % (msg['FromUserName'], msg['ToUserName'], str(int(time.time())),
155                                 Content["subjects"][0]["title"], description,
156                                 Content["subjects"][0]["images"]["large"], Content["subjects"][0]["alt"])
157         return echostr
158  
159 if __name__ == "__main__":
160     # Interactive mode
161     debug(True)
162     run(app,host='127.0.0.1', port=8080, reloader=True)
163 else:
164     # Mod WSGI launch
165 #    import sae
166 #    debug(True)
167 #    os.chdir(os.path.dirname(__file__))
168 #    app = default_app()
169 #    application = sae.create_wsgi_app(app)
170
171 #################################################
172     #os.chdir(os.path.dirname(__file__))#Forbidden to access
173     from bae.core.wsgi import WSGIApplication
174     application = WSGIApplication(app)
  
  注:代码中用json.dumps会更好。 后注:此注不对。
  
  深入阶段,将http://www.iyunv.com/mchina/tag/%E5%BE%AE%E4%BF%A1%E5%85%AC%E4%BC%97/里的功能用python实现之。
  ……
  本代码需要与bottle.py一并上传到服务器空间。
  
  微信开发调试小工具下载:http://www.iyunv.com/linkbiz/archive/2013/05/16/3080306.html
  附上一些特别信息:
  本人微信公众号pythonwoodpub,              开发项目澳洲红酒微信服务号,
   DSC0000.jpg DSC0001.jpg

运维网声明 1、欢迎大家加入本站运维交流群:群②:261659950 群⑤:202807635 群⑦870801961 群⑧679858003
2、本站所有主题由该帖子作者发表,该帖子作者与运维网享有帖子相关版权
3、所有作品的著作权均归原作者享有,请您和我们一样尊重他人的著作权等合法权益。如果您对作品感到满意,请购买正版
4、禁止制作、复制、发布和传播具有反动、淫秽、色情、暴力、凶杀等内容的信息,一经发现立即删除。若您因此触犯法律,一切后果自负,我们对此不承担任何责任
5、所有资源均系网友上传或者通过网络收集,我们仅提供一个展示、介绍、观摩学习的平台,我们不对其内容的准确性、可靠性、正当性、安全性、合法性等负责,亦不承担任何法律责任
6、所有作品仅供您个人学习、研究或欣赏,不得用于商业或者其他用途,否则,一切后果均由您自己承担,我们对此不承担任何法律责任
7、如涉及侵犯版权等问题,请您及时通知我们,我们将立即采取措施予以解决
8、联系人Email:admin@iyunv.com 网址:www.yunweiku.com

所有资源均系网友上传或者通过网络收集,我们仅提供一个展示、介绍、观摩学习的平台,我们不对其承担任何法律责任,如涉及侵犯版权等问题,请您及时通知我们,我们将立即处理,联系人Email:kefu@iyunv.com,QQ:1061981298 本贴地址:https://www.yunweiku.com/thread-58734-1-1.html 上篇帖子: 【转】Python @classmethod @staticmethod 下篇帖子: python 使用pymssql连接sql server数据库
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

扫码加入运维网微信交流群X

扫码加入运维网微信交流群

扫描二维码加入运维网微信交流群,最新一手资源尽在官方微信交流群!快快加入我们吧...

扫描微信二维码查看详情

客服E-mail:kefu@iyunv.com 客服QQ:1061981298


QQ群⑦:运维网交流群⑦ QQ群⑧:运维网交流群⑧ k8s群:运维网kubernetes交流群


提醒:禁止发布任何违反国家法律、法规的言论与图片等内容;本站内容均来自个人观点与网络等信息,非本站认同之观点.


本站大部分资源是网友从网上搜集分享而来,其版权均归原作者及其网站所有,我们尊重他人的合法权益,如有内容侵犯您的合法权益,请及时与我们联系进行核实删除!



合作伙伴: 青云cloud

快速回复 返回顶部 返回列表