为什么不使用SQL语句,而使用ORM框架管理数据库?首先,在python程序中嵌入原生SQL语句,不方便维护,ORM框架使用面向对象思想,使用较方便;第二,如果更换底层数据库引擎,ORM框架不需要修改代码。ORM框架也有其弊端,如有一定的性能损耗,且高级查询编写复杂,有一定的学习成本。

1、配置数据库链接

Flask-SQLAlchemy 中,数据库使用 URL 指定。一般开发环境使用SQLite,生产环境使用MySQL,使用MySQL时,还需要再安装相应的依赖包。

几种最流行的数据库引擎使用的 URL 格式:

数据库引擎 URL
MySQL mysql://username:password@hostname/database
SQLite(Linux,macOS) sqlite:////absolute/path/to/database
SQLite(Windows) sqlite:///c:/absolute/path/to/database

配置数据库:

app.config['SQLALCHEMY_DATABASE_URI'] ='sqlite:///' + os.path.join(basedir, 'data.sqlite')
app.config['SQLALCHEMY_TRACK_MODIFICATIONS'] = False
db = SQLAlchemy(app) # SQLALCHEMY_TRACK_MODIFICATIONS 参数决定是否追踪对象的修改,SQLAlchemy建议配置此变量,不然会有警告。

2、定义模型

模型这个术语表示应用使用的持久化实体。在ORM中,模型一般是一个表示数据表的类,类的实例对应一条记录,类中的属性对应于数据库表中的列。

所以模型定义,类似原生SQL的CREATE TABLE语句:

class Role(db.Model):
# 定义表名
__tablename__ = 'roles' # 定义字段
id = db.Column(db.Integer, primary_key=True)
name = db.Column(db.String(64), unique=True) def __repr__(self):
return '<Role %r>' % self.name

常用列类型与列选项:https://www.cnblogs.com/adamans/articles/9815040.html

3、关系

关系型数据库的表和表之间需要建立“一对多”,“多对一”和“一对一”的关系,这样才能够按照应用程序的逻辑来组织和存储数据。在关系型数据库中,关系是通过主键和外键来维护,其中外键既可以通过数据库来约束,也可以不设置约束,仅依靠应用程序的逻辑来保证,这里讨论使用数据库来约束的情况。

3.1 一对多

例如角色和用户是一对多关系,一个用户只对用一个角色,而一个角色可以对应多个用户:

class Role(db.Model):
# ...
users = db.relationship('User', backref='role') class User(db.Model):
# ...
role_id = db.Column(db.Integer, db.ForeignKey('roles.id'))

添加到 User 模型中的 role_id 列被定义为外键,就是这个外键建立起了关系。传给 db.ForeignKey() 的参数 'roles.id' 表明,这列的值是 roles 表中相应行的 id值。

添加到 Role 模型中的 users 属性代表这个关系的面向对象视角,对于一个 Role 类的实例,其 users 属性将返回与角色相关联的用户组成的列表。db.relationship() 的第一个参数表明这个关系的另一端是哪个模型,backref 参数向 User 模型中添加一个 role 属性,从而定义反向关系。通过 User 实例的这个属性可以获取对应的 Role 模型对象,而不用再通过 role_id 外键获取。

3.2 一对一

一对一关系可以用前面介绍的一对多关系表示,但调用 db.relationship() 时要把 uselist 属性设为 False,把“多”变成“一”。

3.3 多对一

多对一关系从“多”这一侧看,就是一对多关系,对调两个表即可。

3.4 多对多

上述关系至少都有一侧是单个实体,所以记录之间的联系通过外键实现,让外键指向那个实体。但是,可能两侧都是“多”的关系,如有学生表和课程表,学生可能选多个课程,课程也可能被多个学生选。这种时候一般使用第三张表(即关联表)来表示关系:

class c(db.Model):
id = db.Column(db.Integer, primary_key=True)
name = db.Column(db.String)
classes = db.relationship('Class',
secondary=registrations,
backref=db.backref('students', lazy='dynamic'),
lazy='dynamic') class Class(db.Model):
id = db.Column(db.Integer, primary_key=True)
name = db.Column(db.String) registrations = db.Table('registrations',
db.Column('student_id', db.Integer, db.ForeignKey('students.id')),
db.Column('class_id', db.Integer, db.ForeignKey('classes.id'))
)

多对多关系仍使用定义一对多关系的 db.relationship()方法定义,但在多对多关系中,必须把 secondary 参数设为关联表。多对多关系可以在任何一个类中定义,backref参数会处理好关系的另一侧。关联表就是一个简单的表,不是模型,SQLAlchemy 会自动接管这个表。

Studentclasses 关系使用列表语义,这样处理多对多关系特别简单:

# 查看Student实例所选课程、Class实例被选情况
>>> s.classes.all()
>>> c.students.all() # 增加课程
>>> s.classes.append(c)
>>> db.session.add(s)
>>> db.session.commit() # 取消选课
>>> s.classes.remove(c)
>>> db.session.add(c)
>>> db.session.commit()

关联表使用db.Table类定义

指定了lazy='dynamic' 参数,所以关系两侧返回的查询都可接受额外的过滤器

3.5 自引用

多对多有种特殊情况,即关系中的两侧都在同一个表中,这种关系称为自引用关系。如用户表之间的关注关系,

4、数据库操作

对数据库的改动通过数据库会话管理,在 Flask-SQLAlchemy 中,数据库会话由 db.session 表示。调用 db.session.commit()提交事务,db.session.rollback() 回滚事务。

创建表、删除表

db.create_all()
db.drop_all()

CREATE

admin_role = Role(name='Admin')
db.session.add(admin_role)
db.session.add_all([admin_role, mod_role])
db.session.commit()

UPDATE

admin_role.name = 'Administrator'
db.session.add(admin_role)
db.session.commit()

DELETE

db.session.delete(mod_role)
db.session.commit()

READ

<模型类>.query.<过滤方法>.<查询方法>

User.query.all()
User.query.filter_by(role=user_role).all()
Role.query.filter_by(name='User').first()
# 查看查询API...

5、文档

sqlalchemy中文文档:https://www.osgeo.cn/sqlalchemy/

sqlalchemy英文文档:https://docs.sqlalchemy.org/

flask-sqlalchemy文档:http://www.pythondoc.com/flask-sqlalchemy/index.html

Flask:数据库管理的更多相关文章

  1. python+mysql+flask创建一个微博应用(持续更新)

    微博应用的结构: 用户管理,包括登录管理,会话,用户角色,个人档案及用户头像. 数据库管理,包括数据库迁移处理. Web表单支持,包括字段检验和用于防止垃圾邮件的验证码功能. 大数据的分页功能. 全文 ...

  2. 狗书无敌,天下第一(flask基础)

    为什么选择使用flask? 和其他框架相比, Flask 之所以能脱颖而出,原因在于它让开发者做主,使其能对程序具有全面的创意控制. 在 Flask 中,你可以自主选择程序的组件,如果找不到合适的,还 ...

  3. flask 面试题

    1,什么是Flask,有什么优点?概念解释Flask是一个Web框架,就是提供一个工具,库和技术来允许你构建一个Web应用程序.这个Web应用程序可以是一些Web页面,博客,wiki,基于Web的日里 ...

  4. [Python]Python入坑小项目推荐- Flask example minitwit

    知乎上看到的Python练手项目推荐,链接见:https://www.zhihu.com/question/29372574,不知道是我自己懒得看还是理解力不行,这些项目真的是...太大了呀~~~~ ...

  5. Flask关于请求表单的粗浅应用及理解+简单SQL语句温习

    1.请求表单 请求表单的知识点是flask数据请求中很小的一部分,首先要了解一下GET和POST请求:http://www.w3school.com.cn/tags/html_ref_httpmeth ...

  6. Python的Flask框架与数据库连接的教程

     命令行方式运行Python脚本 在这个章节中,我们将写一些简单的数据库管理脚本.在此之前让我们来复习一下如何通过命令行方式执行Python脚本. 如果Linux 或者OS X的操作系统,需要有执行脚 ...

  7. django和flask的区别

    转载至https://blog.csdn.net/tulan_xiaoxin/article/details/79132214 (1)Flask Flask确实很“轻”,不愧是Micro Framew ...

  8. pthon web框架flask(一)

    pthon web框架优劣: 知乎上有一个讨论Python 有哪些好的 Web 框架?,从这个讨论中最后我选择了flask,原因是: Django,流行但是笨重,还麻烦,人生苦短,肯定不选 web.p ...

  9. 详说Flask、Django、Pyramid三大主流 Web 框架

    前言 目前随着 Python 在大数据.云计算.人工智能方面的热度,Python Web 应该也会被更多企业了解使用. Python Web 框架千万种,没必要都去了解和学习,身边总有人说高手都用 F ...

随机推荐

  1. B - 规律题2

    10 123456 1:f(y)=1+2+3+4+5+6=21 2:f(y)=3 3        3 b进制,<b; 10 123 1+2+3=6;是3的倍数 1234 =(999)*1+99 ...

  2. Codeforces Round #626 (Div. 2) E. Instant Noodles(二分图,最大公因数)

    题意: 给你一个二分图,求左侧端点的所有可能子集中的点相连的右侧端点的权值的和的最大公因数. 题解: 若所有右侧端点均不在同一左侧子集中,则求所有权值的最大公因数即可 . 否则,将在相同左侧子集中的右 ...

  3. CodeForces 893C (并查集板子题)

    刷题刷到自闭,写个博客放松一下 题意:n个人,m对朋友,每寻找一个人传播消息需要花费相应的价钱,朋友之间传播消息不需要花钱,问最小的花费 把是朋友的归到一起,求朋友中花钱最少的,将所有最少的加起来. ...

  4. HDU2732 Leapin' Lizards 最大流

    题目 题意: t组输入,然后地图有n行m列,且n,m<=20.有一个最大跳跃距离d.后面输入一个n行的地图,每一个位置有一个值,代表这个位置的柱子可以经过多少个猴子.之后再输入一个地图'L'代表 ...

  5. 智能社讲解js基础

    一,Javascript的组成ECMAScript:翻译,核心,解释器,DOM:文档对象模型,Document Object Model 操作HTML的能力,document对象BOM:浏览器对象模型 ...

  6. H.264视频压缩标准

    H.264 这部分一直在讲,但是却没有系统的来说.接下来要详细. 参看:H.264视频压缩标准 一.简介 H.264是最新的视频压缩标准,它也称为MPEG-4 Part 10或AVC(高级视频编码). ...

  7. AbstractQueuedSynchronizer的使用和juc里的相关类的解析

    对AQS进行解析后,先来实现两个简单的基于AQS的类,然后再解析juc里基于AQS构造的类. 1.基于AQS的类的示例 首先先看这个类,这个类是<Java并发编程实战>的一个示例,AQS源 ...

  8. java变量、数据类型、运算符

    关键字.保留字.标识符 关键字 Java关键字是对Java编译器有特殊含义的字符串,是编译器和程序员的一个约定,程序员利用关键字来告诉编译器其声明的变量类型.类.方法特性等信息 保留字 goto.co ...

  9. bash variables plus operator All In One

    bash variables plus operator All In One Errors missing pass params #!/usr/bin/env bash # echo emoji ...

  10. TypeScript Developer Roadmap

    TypeScript Developer Roadmap https://github.com/xgqfrms/TypeScript-Developer-Roadmap https://typescr ...