投票应用

综合表单,模板,视图,数据库等知识,创建一个投票应用。

创建模型类

# coding=utf-8
""" 电影投票应用 """

from datetime import datetime,timedelta
from flask import Flask,render_template,request,session,redirect,url_for
from flask_sqlalchemy import SQLAlchemy
from flask_migrate import Migrate, MigrateCommand
from flask_script import Shell,Manager
from flask_wtf import FlaskForm
from wtforms import StringField,SubmitField
from wtforms.validators import DataRequired
import time

app = Flask(__name__)
app.config["DEBUG"] = True
app.config["SECRET_KEY"] ='SDAGSDGASDGASDGASDGDSAGDSA'
# 将flask对象交给扩展命令行工具管理
manager = Manager(app)
# 连接数据库
app.config['SQLALCHEMY_DATABASE_URI'] = 'mysql://root:mysql@192.168.20.73:3306/flask_py'
# 自动提交数据库中的改动
app.config['SQLALCHEMY_COMMIT_ON_TEARDOWN'] = True
# 追踪对象
app.config['SQLALCHEMY_TRACK_MODIFICATIONS'] = True

# 创建数据库对象
db = SQLAlchemy(app)

# 第一个参数是Flask的实例,第二个参数是 Sqlalchemy数据库实例
Migrate(app, db)
# manager  是Flask-Script的实例,这条语句在flask-Script中添加一个db命令
manager.add_command('db', MigrateCommand)



class Form(FlaskForm):
    content = StringField(label='留言板',validators=[DataRequired()])
    submit = SubmitField(label='提交')


class Movie(db.Model):
    """ 创建电影模型类"""

    # id
    id = db.Column(db.Integer, primary_key=True)
    # 电影名称
    name = db.Column(db.String(40), unique=True)
    # 演员
    cast = db.Column(db.String(100))
    # 票数
    votes = db.Column(db.Integer, default=0)

class Message(db.Model):
    __tablename__ = 'message'
    id = db.Column(db.Integer,primary_key=True)
    content = db.Column(db.String(300))
    time = db.Column(db.DateTime, default=datetime.now, nullable=False)



if __name__ == '__main__':
    manager.run()

构造数据:

直接在数据库中插入:

insert into movie values(0,'前任3:再见前任','主演:韩庚 姚星彤 郑 恺 丽坤 李相烨',0);
insert into movie values(0,'霸王别姬','主演:张国荣 张丰毅 巩俐 英达 葛优',0);
insert into movie values(0,'芳华','黄轩领衔主演,苗苗、钟楚曦联合主演',0);
insert into movie values(0,'追龙','主演:甄子丹 刘德华 胡然 徐冬冬 伍允龙',0);
insert into movie values(0,'一代宗师','主演:梁朝伟 章子怡 张震宋 慧乔 赵本山',0);


视图函数:

@app.route('/', methods=['GET', 'POST'])
def index():
    # 创建一个表单对象
    form = Form()
    # 将所有电影查询出来
    movie = Movie.query.all()
    # 将所有的留言按照id降序查询出来
    message = Message.query.order_by(db.desc(Message.id))
    # 每次都查询下session看是否有投票过,用来判断是否显示投票结果
    is_vote = session.get('is_vote')
    context = {
        'form': form,
        'movie': movie,
        'message': message,
        'is_vote': is_vote
    }
    if form.validate_on_submit():
        """验证通过"""
        content = form.content.data
        msg = Message(content=content)
        db.session.add(msg)
        db.session.commit()
    return render_template('index.html', **context)


@app.route('/votes/<int:id>')
def voted(id):
    """ 投票计数"""
    # 第一次请求没有session或者session保存的时间戳下于当前时间则票数加1
    is_vote = session.get('is_vote')
    if not (is_vote and float(is_vote) > time.time()):
        # 将对应电影查询出来
        m = Movie.query.get(id)
        m.votes += 1
        db.session.add(m)
        db.session.commit()
        # Flask 中session 是保存在cookie中,默认是关闭浏览器就超时,这里设置session的超时时间
        session.permanent = True
        app.permanent_session_lifetime = timedelta(seconds=60*60*24)

        # 保存一个session 一天之后的时间戳
        session['is_vote'] = time.time() + 60*60*24
    # 投票成功,重定向回 index视图
    return redirect(url_for('index'))


模板:

    <!DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>投票</title>
    </head>
    <body>

        {% for m in  movie  %}
            <dt>{{ m.name }}:</dt>
                <dd>{{ m.cast }}</dd>
                <a href="{{ url_for('voted',id=m.id) }}">点击投票</a> <br><br>
        {% endfor %}

    <hr>
    <span>投票结果:</span>

        {% if is_vote %}
        {% for m in movie %}
            <p>{{ m.name }} 得票 : <span>{{ m.votes }}</span></p>
        {% endfor %}
        {% else %}
            <span>需要投票之后才能查看结果</span>
        {% endif %}

    <hr>
    <form action="/" method="post">

    {{ form.csrf_token }}
    {{ form.content.label }}
    {{ form.content }}
    {{ form.submit }}
    </form>
    <dt>留言:</dt>
    {% for msg in message %}
        <dt>网友{{ msg.time }} 留言:</dt>
            <dd>{{ msg.content }}</dd>
        <br>
    {% endfor %}

    </body>
    </html>
Iyoyo电子书 一本集作者多年开发经验的python电子书 all right reserved,powered by Gitbook文件修订时间: 2022年 11:15:49