Web2py初探
- Web2py框架简单介绍
我们从Design网页中可以看到,Web2py应用程序中设计所需要的所有内容:
Models:描述数据结构的,主要是数据库
Controllers:描述控制流的,网页的解析、跳转等
Views:描述网页的,网页设计部分主要由此完成
Languages
Static files:图像、CCS、JSP等文件放在这里
- Web2py之Hello world!
修改controller中的default.py
def index():
return dict(message="Hello from MyApp")
在这里说明一下,return的变量到哪里去了?事实上,return到view里面去了。在view里面,default\index.html是可以看到这个变量的“人”,不过index.html并不是传统意义上的html,在这里我叫它为模板。Index里面可以看到刚才return的变量message,利用内嵌python执行块{{}},就可以成功的将message这个变量利用起来。事实上我认为Web2py把这个index“模板”拿出来重新生成新的 index.html,然后返回到客户端浏览器。
<html>
<head></head>
<body>
<h1>{{=message}}</h1>
</body>
</html>
测试结果:
- 你不用管Cookie,Web2py帮你完成这个事情,你只需要关注session,一般情况下,你的电脑连接到Wweb2py的时候,它会帮你保存你以前的登录状态。Session可以保存你想保存的当前连接的信息,比如购物筐里面的货物。。。
def index():
if not session.counter: session.counter=1
else: session.counter+=1
return dict(message="Hello from MyApp",counter=session.counter)
- 表单 FORM, INPUT, TEXTAREA, and SELECT/OPTION 同时作用在controller和view的函数。
def first():
form=FORM(INPUT(_name='visitor_name',requires=IS_NOT_EMPTY()),
INPUT(_type='submit'))
if form.accepts(request.vars,session):
session.visitor_name=form.vars.visitor_name
redirect(URL(r=request,f='second'))
return dict(form=form)
在例子中,FORM有两个INPUT标签,在INPUT标签定义时,一下划线为开头的变量为其参数。
{{extend 'layout.html'}}
What is your name?
{{=form}}
- 创建图像博客
在model中新建文件db.py,添加如下代码:
db=SQLDB("sqlite://storage.db")
//新建一个数据库全局变量对象
db.define_table('image',
SQLField('title'),
SQLField('file','upload'))
//定义一个新表,define_table是db的一个函数,第一个参数为表的名称,其他的为表项。’upload’类型是web2py一个特殊的类型,它用来存储上产文件的名称。
db.define_table('comment',
SQLField('image_id',db.image),
SQLField('author'),
SQLField('email'),
SQLField('body','text'))
//定义comment表,其中image_id是reference类型的,指向数据库db.image
db.image.title.requires=[IS_NOT_EMPTY(),IS_NOT_IN_DB(db,db.image.title)]
//定义约束条件
db.comment.image_id.requires=IS_IN_DB(db,db.image.id,'%(title)s')
db.comment.author.requires=IS_NOT_EMPTY()
db.comment.email.requires=IS_EMAIL()
db.comment.body.requires=IS_NOT_EMPTY()
值得注意的是,每次执行这段代码的时候,如果这个表不存在,则在数据库中新建此表,如果这个表存在,但与此表不太一样,则进行移植,如果此表存在,且和定义一模一样,则不作任何操作。这种方式叫做转移,如果想要禁止移植,则在define_table的最后一个参数传入migrate=False即可。
Default.py文件
def index():
images=db().select(db.image.ALL,orderby=db.image.title)
return dict(images=images)
default/index.html文件
{{extend 'layout.html'}}
<h1>Current Images</h1>
<ul>
{{for image in images:}}
{{=LI(A(image.title,_href=URL(r=request,f="show",args=[image.id])))}}
{{pass}}
</ul>
Default.py文件
def show():
image=db(db.image.id==request.args[0]).select()[0]
form=SQLFORM(db.comment,fields=['author','email','body'])
form.vars.image_id=image.id
if form.accepts(request.vars,session):
response.flash='your comment is posted'
comments=db(db.comment.image_id==image.id).select()
return dict(image=image,comments=comments,form=form)
def download():
import os
path=os.path.join(request.folder,'uploads',request.args[0])
return response.stream(path)
default/show.html文件
{{extend 'layout.html'}}
<h1>Image: {{=image.title}}</h1>
<center>
<img width="200px"
src="{{=URL(r=request,f='download',args=[image.file])}}"/>
</center>
{{if len(comments):}}
<h2>Comments</h2><br /><p>
{{for comment in comments:}}
<p>{{=comment.author}} says <i>{{=comment.body}}</i></p>
{{pass}}</p>
{{else:}}
<h2>No comments posted yet</h2>
{{pass}}
<h2>Post a comment</h2>
{{=form}}