flask框架(其六)(与数据库的交互)

SQLALchemy 实际上是对数据库的抽象,让开发者不用直接和 SQL 语句打交道,而是通过 Python 对象来操作数据库,在舍弃一些性能开销的同时,换来的是开发效率的较大提升

安装 flask-sqlalchemy(尽量安装在虚拟环境之中)

pip install flask-sqlalchemy
pip install flask-mysqldb

以实例来说明flask-sqlalchemy 的使用!

from flask import Flask, render_template
# 1----导入flask_sqlalchemy
from flask_sqlalchemy import SQLAlchemy

app = Flask(__name__)
# 2----配置数据库的链接
app.config['SQLALCHEMY_DATABASE_URI'] = 'mysql://root:x@localhost/test'
# 动态追踪修改,如果开启相当与debug模式,加大内存开销!
app.config['SQLALCHEMY_TRACK_MODIFICATIONS'] = False
#查询时会显示原始SQL语句
app.config['SQLALCHEMY_ECHO'] = True

# 3----实例化SQAlchemy对象,和程序实例进行关联
db = SQLAlchemy(app)

# 4----定义模型类:实现一对多的模型,角色(一)(管理员和普通用户)和用户(多)
# 需要继承自db.Model
class Role(db.Model):
    # 定义表名,不定义那么就会是类的名称!
    __tablename__ = 'roles'
    # 定义主键、角色名、定义关系引用
    id = db.Column(db.Integer, primary_key=True)
    name = db.Column(db.String(64), unique=True)
    '''
    第一个参数为多方的类名、第二个参数为反向引用
    backref用于在关系另一端的类中快捷地创建一个指向当前类对象的属性,
    lazy='select'表示全部加载,lazy='dynamic'表示查询多少加载多少
    '''
    us = db.relationship('User', backref='role',lazy='select')
    # repr返回的查询数据的可读字符串
    def __repr__(self):
        return 'role:%s' % self.name

class User(db.Model):
    # 定义表名
    __tablename__ = 'users'
    # 定义主键、角色名、定义关系引用,你可以不使用id 使用new_id
    id = db.Column('new_id',db.Integer, primary_key=True)
    name = db.Column(db.String(64), unique=True)
    pswd = db.Column(db.String(32))
    email = db.Column(db.String(64), unique=True)
    # 定义外键,必须设置,才能够将两者联系起来
    role_id = db.Column(db.Integer, db.ForeignKey('roles.id'))
    # repr返回的查询数据的可读字符串
    def __repr__(self):
        return 'user:%s' % self.name

@app.route('/')
def hello_world():
    return render_template('login.html')

if __name__ == '__main__':
    #更新现有数据库表的粗暴方式是先删除旧表再重新创建
    # 删除表,由于数据的即时更新,数据容易出错
    db.drop_all()
    # 创建表
    db.create_all()
    # 通过模型类添加数据
    ro1 = Role(name='admin')
    ro2 = Role(name='user')
    # session是数据库会话对象,保存了对数据的操作,add_all表示添加多条数据,add()添加1条
    #现在这些对象只存在于Python 中,还未写入数据库,只是加到了会话之中
    db.session.add_all([ro1, ro2])
    # commit执行后,数据才会写入到数据库中
    db.session.commit()
    #创建表相当于创建对象!
    us1 = User(name='wang', email='wang@163.com', pswd='123456', role_id=ro1.id)
    us2 = User(name='zhang', email='zhang@189.com', pswd='201512', role_id=ro2.id)
    us3 = User(name='chen', email='chen@126.com', pswd='987654', role_id=ro2.id)
    us4 = User(name='zhou', email='zhou@163.com', pswd='456789', role_id=ro1.id)
    db.session.add_all([us1, us2, us3, us4])
    db.session.commit()
    app.run(debug=True)

数据库操作详解:

''' 
    Role.query 返回是一个对象,以下所有的函数是链式调用的,也就是说可以追加到一起,返回最终的结果!first()与all()会停止链式调用
    Role.query.all() 返回的是Role.query的所有的模型对象结果
    Role.query.filter_by(role=user_role).all() 先对Role.query执行精确查询,再显示所有的查询
    只需要使用类名就可以查询,创建对象的过程就是插入数据的过程。使用命令行查询,删除即可
    all() 返回的是列表! frist() 第一个数据,并且是字符串的形式!
    Role.query.all()  查询Role 类的所有的数据
    Role.query.get(1) 查询第一个数据!是通过主键来查询的!
    Role.query.get(3) 查询第三个数据!必须要有参数
    Role.query.filter(Role.name!='admin').first() 过滤查询!查询条件为name!='admin'
    Role.query.filter_by(name='admin').first()
    Role.query.filter(User.name.startswith('w')).first()  模糊查询!
    Role.query.filter(User.name.endswith('w')).first()
    from sqlalchemy import not_,and_,or_
    User.query.filter(not_(User.name=='chen')).all() 与或非的使用!
    两张表相互联系:
        role = Role.query.get(1)
        role.us   #查询与admin 关联的都有的用户
        user = User.query.get(1)
        user.role  #查询与 user 关联的所有的职位
    更新数据需要提交:
        User.query.filter(User.name=='zhang').updata({'name':'xi'})
        db.session.commit()
    删除数据:
        user = User.query.first()
        db.session.delete(user)
        db.session.commit()

    db.Column('user_name',db.Boolean) 第二个参数指定字段是什么类型!
    如果数据库支持boolean那么就会将 db.Column 作为 True 或者False,如果不支持,那么就会转换为0或者1

'''

 

1,在 Flask-SQLAlchemy 中,查询操作是通过 query 对象操作数据。filter 是过滤器,all或者first是执行器
2,最基本的查询是返回表中所有数据,可以通过过滤器进行更精确的数据库查询。
3,会话用 db.session 表示。在准备把数据写入数据库前,要先将数据添加到会话中然后调用 commit() 方法提交会话

posted @ 2018-05-21 10:03  十七楼的羊  阅读(234)  评论(0编辑  收藏  举报