简单的通过xmlrpc支持离线编辑的代码。初学python,希望各位python高手指点。
code.py主要是webpy的内容。
# -*- coding: utf-8 -*- import web import webxml render = web.template.render('templates/') urls = ( '/', 'index', '/RPC2', 'webxml.rpc' ) class index: def GET(self): db = web.database(dbn='postgres', user='postgres', pw='dianxin', db='blog_db') posts = db.select('post') return render.index(posts) webxml.init() if __name__ == "__main__": app = web.application(urls, globals()) app.run()
templates/index.html 一个简单的模板
$def with (posts) <html> <head> <meta http-equiv="Content-Type" content="text/html; charset=UTF-8" /> <title>博客</title> </head> <body> $for post in posts: <div> <h2>$post.post_title</h2> $:post.post_content </div> </body> </html>
webxml.py主要使用xmlrpc库的使用
# -*- coding: utf-8 -*- import web from metaWeblog import Api from SimpleXMLRPCServer import SimpleXMLRPCDispatcher dispatcher = SimpleXMLRPCDispatcher(allow_none=False, encoding="UTF-8") def init(): global dispatcher dispatcher.register_introspection_functions() dispatcher.register_function(Api().getUsersBlogs, 'blogger.getUsersBlogs') dispatcher.register_function(Api().getCategories, 'metaWeblog.getCategories') dispatcher.register_function(Api().getRecentPosts, 'metaWeblog.getRecentPosts') dispatcher.register_function(Api().getPost, 'metaWeblog.getPost') dispatcher.register_function(Api().newPost, 'metaWeblog.newPost') dispatcher.register_function(Api().newMediaObject, 'metaWeblog.newMediaObject') dispatcher.register_function(Api().editPost, 'metaWeblog.editPost') dispatcher.register_function(Api().deletePost, 'metaWeblog.deletePost') class rpc: def GET(self): print "Method GET is not alowed for XMLRPC requests" def POST(self): global dispatcher response = dispatcher._marshaled_dispatch(web.webapi.data()) return response
metaWeblog.py实现了metaWeblog的规范
# -*- coding: utf-8 -*- import psycopg2 import os import xmlrpclib class Api: def getUsersBlogs(self, appkey, username, password): self.__isUser(username, password) struct = {} struct['blogid'] = '2' struct['url'] = '' struct['blogName'] = 'webpyblog' tmp = [] tmp.append(struct) return tmp def getPost(self, postid, username, password): self.__isUser(username, password) conn = psycopg2.connect("dbname=blog_db user=postgres password=dianxin") cur = conn.cursor() cur.execute("select post_title, post_content from post where post_id = %d", postid) post = cur.fetchone() conn.commit() cur.close() conn.close() struct = {} struct['postid'] = postid struct['title'] = post.post_title #struct['link'] = 'localhost/post/' + postid struct['description'] = post.post_content return struct def getRecentPosts(self, blogid, username, password, numberOfPosts=5): self.__isUser(username, password) conn = psycopg2.connect("dbname=blog_db user=postgres password=dianxin") cur = conn.cursor() cur.execute("select * from post") posts = cur.fetchall() conn.commit() cur.close() conn.close() tmp = [] for post in posts: print(post) struct = {} struct['postid'] = post.post_id struct['title'] = post.post_title #struct['link'] = 'localhost/post/1' struct['description'] = post.post_content tmp.append(struct) print(tmp) return tmp def newPost(self, blogid, username, password, struct, publish): self.__isUser(username, password) title = struct['title'] description = struct['description'] categories = struct['categories'] conn = psycopg2.connect("dbname=blog_db user=postgres password=dianxin") cur = conn.cursor() cur.execute("INSERT INTO post (post_title, post_content) VALUES (%s, %s) returning post_id", (title, description)) id = cur.fetchone() conn.commit() cur.close() conn.close() return id[0] def editPost(self, postid, username, password, struct, publish): self.__isUser(username, password) title = struct['title'] description = struct['description'] categories = struct['categories'] conn = psycopg2.connect("dbname=blog_db user=postgres password=dianxin") cur = conn.cursor() cur.execute("update post set post_title = %s, post_content = %s where post_id = %s", (title, description, postid)) conn.commit() cur.close() conn.close() return True def getCategories(self, blogid, username, password): self.__isUser(username, password) struct = {} struct['categoryId'] = 1 struct['categoryName'] = 'Python' struct['htmlUrl'] = 'localhost/categroy/1' struct['rssUrl'] = 'localhost/categroy/1' tmp = [] tmp.append(struct) return tmp def newMediaObject(self, blogid, username, password, data): self.__isUser(username, password) name = data['name'] type = data['type'] bits = data['bits'] (basename, filename) = os.path.split(name) img_path = os.path.join('images', filename) if not os.path.exists('images'): os.makedirs('images') if not os.path.isfile(img_path): file_i = open(img_path, 'wb') file_i.write(bits.data) file_i .close() struct = {} struct['url'] = '/' + (img_path) print(struct['url']) return struct def deletePost(self, appkey, postid, username, password, publish): self.__isUser(username, password) conn = psycopg2.connect("dbname=blog_db user=postgres password=dianxin") cur = conn.cursor() cur.execute("delete from post where post_id = %s", postid) conn.commit() cur.close() conn.close() return True def __isUser(self, username, password): if not (username == 'leo' and password == 'dianxin'): raise xmlrpclib.Fault(401, '用户名或密码错误!')