flask05 Flask Model

版权声明:转载请注明出处 https://blog.csdn.net/qq_42806416/article/details/83794786

Flask Model

使用ORM的原因:

随着项目越来越大 使用原生sql就会出现如下问题

  1. SQL语句重复使用率不高 越复杂的sql语句就越长 会出现很多类似的SQL语句 并且不易读
  2. 很多SQL语句都是在业务逻辑中拼接出来的 如果数据库需要更改 就要修改这些逻辑 就会漏掉对某些SQL语句的更改
  3. 容易忽略WEB安全问题(SQL注入)

好处:

  1. 易用性 可以有效的减少SQL语句的重复性 使语句看起来更加直观
  2. 设计灵活 用简单的语句就可以实现复杂的查询
  3. 可移植性 支持多个数据库的链接 只要更改链接方式 其它都不用

一、flask-sqlalchemy

安装:

pip3 install flask-sqlalchemy

(1) 创建数据库

create database if not exists 库名 character set utf8;

(2) 安装pymysql

pip3 install pymysql

(3) 配置数据库的链接地址

mysql

app.config[‘SQLALCHEMY_DATABASE_URI’] = ‘mysql+pymysql://username:password@host:port/database’

sqlite

app.config[‘SQLALCHEMY_DATABASE_URI’] = ‘sqlite:///数据库的路径/数据库名称.sqlite’

二、字段类型 约束条件

字段类型

类型名 说明
Integer 整形
SmallInteger 小整形
BigInteger 长整形
Float 浮点形
String varchar
Text 长文本 text
Boolean tinyint
Date 日期 datetime.date
Time 时间 datetime.time
DateTime 日期和时间 datetime.datetime

可选约束条件

选项 说明
primary_key 主键
unique 唯一索引
index 常规索引
nullable 是否为空 默认为True
default 默认值

三、创建模型

创建User模型表

from exts import db
#创建User模型
class User(db.Model):
    __tablename__ = 'user' #起表名
    id = db.Column(db.Integer,primary_key=True) #主键
    username = db.Column(db.String(12),index=True)
    password_hash = db.Column(db.String(128),default='123456')
    age = db.Column(db.Integer,default=18)
    sex = db.Column(db.Boolean,default=True)
    email = db.Column(db.String(60),default='[email protected]')
    icon = db.Column(db.String(70),default='default.jpg')
    confirm = db.Column(db.Boolean,default=False) #激活状态 默认不激活

    def __str__(self):
        return self.username

四、创建表 简单的增删改查

(1) 创建表

@app.route('/create_table/')
def create_table():
    db.create_all()
    return 'create_table'

(2) 删除表

@app.route('/drop_table/')
def drop_table():
    db.drop_all()
    return 'drop_table'

(3) 添加一条数据 add

@app.route('/insert_one/')
def insert_one():
    try:
        u = User(username='张三',password_hash='zhangsan123456',age=20,sex=False,email='[email protected]',confirm=True)
        db.session.add(u)
        db.session.commit() #提交 默认开启了事物
    except:
        db.session.rollback() #回滚
    return 'insert_one'

(4) 添加多条数据 add_all

#添加多条数据
@app.route('/insert_many/')
def insert_many():
    try:
        u1 = User(username='李四')
        u2 = User(username='王五')
        db.session.add_all([u1,u2])
        db.session.commit() #提交 默认开启了事物
    except:
        db.session.rollback() #回滚
    return 'insert_many'

(5) 查询一条数据 get

@app.route('/select_one/')
def select_one():
    u = User.query.get(1)
    print(u.username)
    print(u.age)
    print(u.sex)
    return 'select_one'

(6) 修改一条数据 add

#修改数据
@app.route('/update/')
def update():
    u = User.query.get(1)
    u.username = '赵六'
    u.age = 30
    u.sex = True
    db.session.add(u)
    db.session.commit()
    return 'update'

(7) 删除一条数据 delete

#删除数据
@app.route('/delete/')
def delete():
    u = User.query.get(1)
    db.session.delete(u)
    db.session.commit()
    return 'delete'

五、更改保存的方式

(1) 更改配置参数

app.config[‘SQLALCHEMY_COMMIT_ON_TEARDOWN’] = True

(2) 自定义表单基类

models.py

from exts import db
class ModelBase:
    # 添加一条数据
    def save(self):
        try:
            db.session.add(self)
            db.session.commit()  # 提交 默认开启了事物
        except:
            db.session.rollback()  # 回滚

    # 添加多条数据
    @staticmethod
    def saveAll(*args):
        try:
            db.session.add_all(args)
            db.session.commit()  # 提交 默认开启了事物
        except:
            db.session.rollback()  # 回滚

    # 删除一条数据
    def delete(self):
        try:
            db.session.delete(self)
            db.session.commit()  # 提交 默认开启了事物
        except:
            db.session.rollback()  # 回滚

#创建User模型
class User(ModelBase,db.Model):
    ...

使用

#添加一条数据
@view.route('/insert_one/')
def insert_one():
    u = User()
    u.username = '张聚全'
    u.save()
    return 'insert_one'

import random
#添加多条数据
@view.route('/insert_many/')
def insert_many():
    lastname = ['张','王','赵','钱','孙','李','周','吴','郑']
    firstname = ['文','超','峰','兴','尧','秀','良','程','天','玉']
    name1 = lastname[random.randrange(len(lastname))]+firstname[random.randrange(len(firstname))]+firstname[random.randrange(len(firstname))]
    name2 = lastname[random.randrange(len(lastname))]+firstname[random.randrange(len(firstname))]+firstname[random.randrange(len(firstname))]
    u1 = User(username=name1,sex=random.randint(0,1),age=random.randint(0,100))
    u2 = User(username=name2,sex=random.randint(0,1),age=random.randint(0,100))
    User.saveAll(u1,u2)
    return 'insert_many'

#修改数据
@view.route('/update/')
def update():
    u = User.query.get(2)
    u.username = '王老七'
    u.age = 28
    u.sex = False
    u.save()
    return 'update'

#删除数据
@view.route('/delete/')
def delete():
    u = User.query.get(2)
    u.delete()
    return 'delete'

六、查询集

分类:

  1. 原始查询集

    没有经过条件筛选的查询称之为原始查询集

  2. 数据查询集

    通过过滤器的方法称之为数据查询集

过滤器特点:

链式调用

(1) all() 以列表形式返回所有对象

类名.query.all()

@view.route('/filter/')
def filter():
    data = User.query.all()
    print(data)
    return render_template('show.html',data=data)

(2) filter() 过滤查询默认所有

运算符的值

  1. >
  2. <
  3. >=
  4. <=
  5. ==
  6. !=

类名.query.filter([条件])

data = User.query.filter(User.sex==True,User.age<20) #查询性别为True and 年龄小于20
data = User.query.filter()#查询所有

(3) filter_by() 只支持单条件查询 默认查询所有

类名.query.filter_by(**kwargs)

data = User.query.filter_by()
data = User.query.filter_by(sex=True)
data = User.query.filter_by(sex=True,age=18)

(4) offset(num) 偏移值的num条

data = User.query.offset(5)

(5) limit(num) 取出num条数据

data = User.query.limit(5)

(6) offset limit

data = User.query.offset(5).limit(5)

(7) order_by 排序

排序

  1. 默认升序
  2. -降序

实例

data = User.query.order_by(User.age)
data = User.query.order_by(-User.age)

(8) first() 取出第一个对象

data = User.query.order_by(-User.age).first()
data = User.query.first()

(9) get(id值) 根据id查询数据返回对象 不存在 返回None

data = User.query.get(1)

(10) contains() 包含关系(模糊查询)

data = User.query.filter(User.username.contains('张'))

(11) like 模糊查询

data = User.query.filter(User.username.like('%张%'))
data = User.query.filter(User.username.like('张%'))
data = User.query.filter(User.username.like('%张'))
data = User.query.filter(User.username.like('%超'))

(12) startswith endswith 以…开头 以…结尾

data = User.query.filter(User.username.startswith('王'))
data = User.query.filter(User.username.endswith('文'))

(13) 比较运算符

  1. __gt__
  2. __ge__
  3. __lt__
  4. __le__
data = User.query.filter(User.age.__gt__(30))

(14) in 和 not … in …

data = User.query.filter(User.age.in_([10,20,30,40,18,91]))
data = User.query.filter(User.age.notin_([10,20,30,40,18,91]))

(15) null 和 not null

data = User.query.filter(User.username.is_(None))
data = User.query.filter(User.username==None)
data = User.query.filter(User.username!=None)
data = User.query.filter(User.username.isnot(None))

(16) and_

导入:

from sqlalchemy import and_

data = User.query.filter(and_(User.sex==True,User.age==18))
data = User.query.filter(User.sex==True,User.age==18)
data = User.query.filter(User.sex==True).filter(User.age==18)

(17) or_

导入:

from sqlalchemy import or_

data = User.query.filter(or_(User.sex==True,User.age==18))

(18) not_

导入:

from sqlalchemy import not_

data = User.query.filter(not_(User.sex == True))

(19) count 统计

data = User.query.filter().count()

(20) concat 连接

data = User.query.order_by(-Posts.path.concat(Posts.id))

七、迁移

安装

pip3 install flask-script

pip3 install flask-migrate

使用

from flask_script import Manager
from flask_migrate import Migrate,MigrateCommand

manager = Manager(app,db)
migrate = Migrate(app)

manager.add_command('db',MigrateCommand)

运行

  1. 初始化

    python3 manage.py db init

  2. 创建迁移

    python3 manage.py db migrate

  3. 执行迁移

    python3 manage.py db upgrade

猜你喜欢

转载自blog.csdn.net/qq_42806416/article/details/83794786