慕课网 python微电影项目 小知识点整理

项目视频下载地址

链接: https://pan.baidu.com/s/11ROsvoKukAUAiEnztvS55A 密码: qsj2

项目代码github地址

链接: https://github.com/cafeUncle/movie-mooc.git

mysql命令

mysql命令行下,\s命令可以查看简单信息

慕课网 python微电影项目 小知识点整理_第1张图片

pip操作

pip 下载时如果很慢,可以使用-i命令指定下载源 使用--trusted-host指定信任的主机
pip install -i http://pypi.douban.com/simple/ --trustrt-host pypi.douban.com virtualenv


pip description
freeze Output installed packages in requirements format.
list List installed packages.

pip安装包的方式中,有如下两种安装方式:

pip install flask
pip install -r requirements.txt
  • 文件requirement.txt里面内容的格式和pip freeze的格式完全一样。因此我们可以将pip freeze的内容输出至requirements.txt。其他机器可以根据导出的requirements.txt进行包安装。
pip freeze > requirements.txt # 输出本地包环境至文件
pip install -r requirements.txt # 根据文件进行包安装
  • pip freeze 为什么比 pip list 的包少几个呢?
    因为pip , wheel , setuptools 等包,是自带的而无法(un)install的。考虑到pip freeze的用途,所以这些包并没有显示。
    如果一定要用pip freeze来显示所有包,可以加上参数-all,即pip freeze -all

蓝图

flask blueprint

  1. 定义蓝图
    app/admin/__init__.py
    from flask import Blueprint
    admin = Blueprint('admin', name)
    import views
  2. 调用蓝图
    app/admin/views.py
    from . import admin
    @admin.route("/")
  3. 注册蓝图
    app/__init__.py
    from flask import admin as admin_blueprint
    app.register_blueprint(admin_blueprint, url_prefix="/admin")
    必须先调用蓝图设置好路由,然后再注册蓝图

前台布局搭建

  1. 静态文件引入: {{ url_for('static', filename='文件路径') }}
  2. 定义路由: {{ url_for('模块名.视图名',变量=参数) }}
    模块名.视图名对应view.py中的方法名,而不是html文件名,个人认为写"/login"这样的路径更方便,学到后面如果发现url_for的特别用法,再来更新
  3. 定义数据块: {% block 数据块名称 %} ... {% endblock %}
    一般定义在base页面中,类似freemarker中的macro,可以在子模板中引用同名block块。
  1. 一般首先定义一个base模板,在内容中允许定义多个block块,由子模板引用,子模板决定替换哪些block块,没有定义的块即不替换,直接使用父模板的block块 。
  1. 通过{{ block.super }},可以引用上级代码块并在其基础上进行一些修改
{% block name%}
    {{ block.super }}
    

... {% endblock %}

  1. 引用时首先要在子模板中{% extends "base.html" %}

extends只能写在子模板第一行,参数一般为字符串,也可为变量,可带路径或相对路径,以TEMPLATE_DIRS的模板目录为基准

  1. 其它
  1. {% include 'includes/nav.html' %}

可带路径或相对路径,以TEMPLATE_DIRS的模板目录为基准
也可以使用变量名 {% include template_name %},包含的变量都会统一处理,不区分是第几层模板
被包含在(include)的页面里面不能用{%block%},类似jsp的静态导入<%@ include file="fileurl" %>和动态导入的区别

  1. {% import 'ui/page_admin.html' as pg %}

引用后可以使用别名调用。
page_admin.html 内容如下,类似freemarker的macro

{% macro page(data, url) %}
{% if data %}

{% endif %}
{%- endmacro %}

调用时


  1. {% for x in range(1,5)%}{{x}}{% endfor %}
{% for msg in get_flashed_messages(category_filter=['ok']) %} # 过滤显示flashed信息

操作成功!

{{msg}}
{% endfor %} {% for msg in get_flashed_messages(category_filter=['err']) %}

操作失败!

{{msg}}
{% endfor %}
{{form.title}} {% for err in form.title.errors %} # 显示validators的错误信息
{{err}}
{% endfor %}

后台

  1. 编写wtforms.validators的ValidationError自定义验证器时,方法名后缀一定要和参数名相同,否则不会触发该验证


    慕课网 python微电影项目 小知识点整理_第2张图片

FlaskForm

from flask_wtf import FlaskForm

class RoleForm(FlaskForm):   # 继承FlaskForm类
    name = StringField(   # 表单类型 StringField, PasswordField, SubmitField, FileField, TextAreaField, SelectField, SelectMultipleField
        label="角色名称",   # {{form.label}}
        validators=[   # 验证器
            DataRequired("请输入角色名称")
        ],
        description="角色名称",
        render_kw={   # 元素属性
            "class": "form-control",
            "id": "input_name",
            "placeholder": "请输入角色名称!"
        }
    )
star = SelectField(
        label="星级",
        validators=[
            DataRequired("请选择星级!")
        ],
        description="星级",
        coerce=int,
        choices=[(1, "1星"), (2, "2星"), (3, "3星"), (4, "4星"), (5, "5星")],
        render_kw={
            "class": "form-control"
        }
    )
    auths = SelectMultipleField(
        label="权限列表",
        validators=[
            DataRequired("请选择权限")
        ],
        coerce=int,
        choices=[(v.id, v.name) for v in auth_list],
        description="权限列表",
        render_kw={
            "class": "form-control"
        }
    )
    submit = SubmitField(
        "编辑",
        render_kw={
            "class": "btn btn-primary"
        }
    )
    def validate_account(self, field):   # 自定义验证器,第一个参数必须是self,方法名称必须是validate_变量名,否则无法匹配生效
        account = field.data
        admin = Admin.query.filter_by(name=account).count()
        if admin == 0:
            raise ValidationError("账号不存在!")
    def __repr__(self):   #  打印方法
        return "" % self.name
  1. 登录验证装饰器
def admin_login_req(f):
    @wraps(f)
    def decorated_function(*args, **kwargs):
        if 'admin' not in session:
            return redirect(url_for('admin.login', next=request.url))
        return f(*args, **kwargs)

    return decorated_function

使用时将@admin_login_req注解写在方法上

  1. 权限控制装饰器
def admin_auth(f):
    @wraps(f)
    def decorated_function(*args, **kwargs):
        admin = Admin.query.join(
            Role
        ).filter(
            Admin.role_id == Role.id,
            Admin.id == session['admin_id']
        ).first()
        auths = admin.role.auths
        auths = list(map(lambda v: int(v), auths.split(',')))
        auth_list = Auth.query.all()
        urls = [v.url for v in auth_list for val in auths if val == v.id]
        rule = request.url_rule
        print(urls)
        print(rule)
        if str(rule) not in urls:
            abort(404)
        return f(*args, **kwargs)
    return decorated_function

使用时将@admin_auth注解写在方法上

慕课网 python微电影项目 小知识点整理_第3张图片
  1. 上下文应用处理器 封装全局变量,展现到模板中
@admin.context_processor
def tpl_extra():
    data = dict(
        online_time=datetime.datetime.now().strftime('%Y-%m-%d %H:%M:%S')
    )
    return data

使用时在模板中用{{online_time}}调用

  1. 获取当前日期并格式化,及生成uuid
  1. werkzeug库
    from werkzeug.security import generate_password_hash
    from werkzeug.security import check_password_hash
    def check_pwd(self, pwd): # 检查密码
    from werkzeug.security import check_password_hash
    return check_password_hash(self.pwd, pwd)

  2. Gists

Gist 作用
request.url_rule 获取请求url
request.remote_addr 获取请求地址
Auth.query.all() 查询数据
Admin.query.filter_by(name=data['account']).first() 查询数据
db.session.add(admin_log) 插入数据
db.session.delete(movie) 删除数据
db.session.commit() 提交数据
session.pop('admin', None) 删除session
Tag.query.filter_by(name=data['name']).count() 统计
page_data = Tag.query.order_by(Tag.add_time.desc()).paginate(page=page, per_page=10) 排序 分页
Tag.query.filter_by(id=id).first_or_404() 找不到则返回404
@admin.route('/tag/del//', methods=['GET']) 路径参数
flash('添加电影成功', 'ok') {% for msg in get_flashed_messages(category_filter=['ok']) %}
page_data = Movie.query.join(Tag).filter(Movie.tag_id == Tag.id).order_by(Movie.add_time.desc()).paginate(page=page, per_page=10) 多表关联,排序分页
Movie.query.filter_by(title=data['title']).count() 筛选查询
if form.validate_on_submit() 用自定义的验证器验证表单
json.dumps({"t": str(datetime.datetime.now()), 'action': 'getJson'}) 格式化为json
request.args.get("next") 获取转发链接
page_data = MovieCol.query.join(Movie).join(User).filter(Movie.id == MovieCol.movie_id,User.id == 1).filter_by(Movie.title == '战狼').order_by(Movie.add_time.desc()).paginate(page=1,per_page=10) N个表关联

你可能感兴趣的:(慕课网 python微电影项目 小知识点整理)