初始化和配置

ORM(Object Relational Mapper) 对象关系映射。指将面对对象得方法映射到数据库中的关系对象中。
Flask-SQLAlchemy是一个Flask扩展,能够支持多种数据库后台,我们可以不需要关心SQL的处理细节,操作数据库,一个基本关系对应一个类,而一个实体对应类的实例对象,通过调用方法操作数据库。Flask-SQLAlchemy有很完善的文档。

Flask-SQLAlchemy是通过URL指定数据库的连接信息的。
初始化的两种方法如下(以连接Mysql数据库为例):

from flask_sqlalchemy import SQLAlchemy
from flask import FLask
app = Flask(__name__)
app.config['SQLALCHEMY_DATABASE_URI'] = \
"mysql://root:12345@localhost/test"
db = SQLAlchemy(app)

或者

from flask_sqlalchemy import SQLAlchemy
from flask import FLask
db = SQLAlchemy() def create_app():
app = Flask(__name__)
db.init_app(app)
return app

两者的区别在于:第一种不需要启动flask的app_context;但是第二种方法则需要,因为可能会创建多个Flask应用,但是我的理解是一般地开发时,Flask实例是延迟创建的,因为在运行时难以修改配置信息,这种方法符合这种情况。
Flask-SQLAlchemy的则需要在Flask.config中声明。更多详细信息需要查配置。例如配置信息中指出SQLAlchemy是可以绑定多个数据库引擎。再例如:在新浪SAE云平台开发个人博客时遇到gone away这种问题就需要添加SQLALCHEMY_POOL_RECYCLE信息,新浪开发者文档中有说明。


SQLALchemy处理 对象->关系

SQLAlchemy是如何处理对象到关系的?实例来自于数据库系统概论内容。

简单实例

创建学生students表

class Student(db.Model):
__tablename__ = 'students' #指定表名
sno = db.Column(db.String(10), primary_key=True)
sname = db.Column(db.String(10))
sage = db.Column(db.Integer)

API文档说明创建对象需要继承db.Model类关联数据表项,db.Model类继承Query类提供有数据查询方法;__tablename__指定数据库的表名,在Flask-SQLAlchemy中是可省的。Column指定表字段。

SQLAlchemy支持字段类型有:

类型名 python类型 说明
Integer int 普通整数,32位
Float float 浮点数
String str 变长字符串
Text str 变长字符串,对较长字符串做了优化
Boolean bool 布尔值
PickleType 任何python对象 自动使用Pickle序列化

来源于Simple ExampleFlask Web开发有更详细的内容。
其余的参数指定属性的配置选项,常用的配置选项如下:

选项名 说明
primarykey 如果设为True,表示主键
unique 如果设为True,这列不重复
index 如果设为True,创建索引,提升查询效率
nullable 如果设为True,允许空值
default 为这列定义默认值

如使用default默认time属性如下:

time = db.Column(db.Date, default=datetime.utcnow)

说明default可以接受lambda表达式。

一对多

按创建单张表的方法,创建学院Deptment表

class Deptment(db.Model):
__tablename__ = 'deptments'
dno = db.Column(db.Integer, primary_key=True)
dname = Sname = db.Column(db.String(10),index=True)

学院和学生是一对多的关系。Flask-SQLAlchemy是通过db.relationship()解决一对多的关系。在Dept中添加属性,代码如下:

class Deptment(db.Model):
...
students = db.relationship('Student', backref='dept') class Student(db.Model):
...
dept_no = db.Column(db.Integer, db.ForeignKey('deptments.dno'))

表的外键由db.ForeignKey指定,传入的参数是表的字段。db.relations它声明的属性不作为表字段,第一个参数是关联类的名字,backref是一个反向身份的代理,相当于在Student类中添加了dept的属性。例如,有Deptment实例dept和Student实例stu。dept.students.count()将会返回学院学生人数;stu.dept.first()将会返回学生的学院信息的Deptment类实例。一般来讲db.relationship()会放在这一边。

多对多

多对多的关系可以分解成一对多关系,例如:学生选课,学生与课程之间的关系:

sc = db.Table('sc',
db.Column('sno', db.String(10), db.ForeignKey('students.sno'))
db.Column('cno',db.String(10), db.ForeignKey('courses.cno'))
) Class Course(db.Model):
__tablename__ = 'courses'
cno = db.Column(db.String(10), primary_key=True)
cname = db.Column(db.String(10), index=True)
students = db.relationship('Student',
secondary=sc,
backref=db.backref('course',lazy='dynamic'),
lazy='dynamic'
)

sc表由db.Table声明,我们不需要关心这张表,因为这张表将会由SQLAlchemy接管,它唯一的作用是作为students表和courses表关联表,所以必须在db.relationship()中指出sencondary关联表参数。lazy是指查询时的惰性求值的方式,这里有详细的参数说明,而db.backref是声明反向身份代理,其中的lazy参数是指明反向查询的惰性求值方式,SQLAlchemy鼓励这种方式声明多对多的关系。

但是如果关联表中有自定义的字段,如sc表中添加成绩字段则需要更改表声明方式,将sc更改为继承db.Model的对象并设置sc:courses = 1:n 和sc:student = 1:n的关系。


SQLALchemy处理 关系->对象

Flask-SQLAlchemy查询中有详细的说明。创建关系后该如何查询到对象?

SQLAlchemy有查询过滤器如下:

过滤器 说明
filter() 把过滤器添加到原查询,返回新查询
filter_by() 把等值过滤器添加到原查询,返回新查询
limit() 使用指定值限制原查询返回的结果数量,返回新查询
offset() 偏移原查询返回的结果,返回新查询
order_by() 排序返回结果,返回新查询
groupby() 原查询分组,返回新查询

这些过滤器返回的结果都是一个新查询,我的理解是这些查询其实是生成的SQL语句,lazy的惰性求值方式也体现在查询上,而这些语句不能生成需要查询的对象,需要调用其他的方法生成对象。

SQL查询执行函数:

方法 说明
all() 以列表形式返回结果
first() 返回第一个结果,如果没有返回None
first_or_404() 返回第一个结果,如果没有抛出404异常
get() 返回主键对应记录,没有则返回None
get_or_404() 返回主键对应记录,如果没有抛出404异常
count() 返回查询结果数量
paginate() 返回paginate对象,此对象用于分页

Flask-SQLAlchemy 学习总结的更多相关文章

  1. flask SQLAlchemy中一对多的关系实现

    SQLAlchemy是Python中比较优秀的orm框架,在SQLAlchemy中定义了多种数据库表的对应关系, 其中一对多是一种比较常见的关系.利用flask sqlalchemy实现一对多的关系如 ...

  2. 读Flask源代码学习Python--config原理

    读Flask源代码学习Python--config原理 个人学习笔记,水平有限.如果理解错误的地方,请大家指出来,谢谢!第一次写文章,发现好累--!. 起因   莫名其妙在第一份工作中使用了从来没有接 ...

  3. flask, SQLAlchemy, sqlite3 实现 RESTful API 的 todo list, 同时支持form操作

    flask, SQLAlchemy, sqlite3 实现 RESTful API, 同时支持form操作. 前端与后台的交互都采用json数据格式,原生javascript实现的ajax.其技术要点 ...

  4. SQLAlchemy 学习笔记(二):ORM

    照例先看层次图 一.声明映射关系 使用 ORM 时,我们首先需要定义要操作的表(通过 Table),然后再定义该表对应的 Python class,并声明两者之间的映射关系(通过 Mapper). 方 ...

  5. flask建表遇到的错误: flask,sqlalchemy.exc.OperationalError: (MySQLdb._exceptions.OperationalError) (1071, 'Specified key was too long; max key length is 767 bytes')

    error:flask,sqlalchemy.exc.OperationalError: (MySQLdb._exceptions.OperationalError) (1071, 'Specifie ...

  6. python flask框架学习(二)——第一个flask程序

    第一个flask程序 学习自:知了课堂Python Flask框架——全栈开发 1.用pycharm新建一个flask项目 2.运行程序 from flask import Flask # 创建一个F ...

  7. Flask – SQLAlchemy成员增加

    目录 简介 结构 展示 技术 运行 代码 创建数据库表单 views视图 home主页 添加成员addnew.html 展示页show_all 简介 结构 $ tree -I "__pyca ...

  8. flask中SQLAlchemy学习

    ------------------------------------2019-08-22 17:53:54更新------------------------------ SQLALchemy实在 ...

  9. Flask框架学习笔记(API接口管理平台 V1.0)

    今天博主终于完成了API接口管理平台,最后差的就是数据库的维护, 博主这里介绍下平台的设计原理,首先基于python,利用flask的web框架+bootstrap前端框架完成,先阶段完成了前台展示页 ...

  10. Flask+SQLAlchemy+alembic+Flask-RESTful使用

    前言 其实准备把这篇删掉,先写Flask-restful相关的,后来想想大体框架还是先写出来,这两天踩了很多坑,有的谷歌也没有答案.一直摸索也总算是开始了. 正文 SQLAlchemy/alembic ...

随机推荐

  1. Spring和SpringMVC的区别

    spring 是是一个开源框架,是为了解决企业应用程序开发,功能如下◆目的:解决企业应用开发的复杂性◆功能:使用基本的JavaBean代替EJB,并提供了更多的企业应用功能◆范围:任何Java应用简单 ...

  2. AMD规范:define和require的区别

    define和require在依赖处理和回调执行上都是一样的,不一样的地方是define的回调函数需要有return语句返回模块对象(注意是对象),这样define定义的模块才能被其他模块引用:req ...

  3. 邮件发送工具类 SendMail.java

    package com.util; import org.apache.commons.mail.EmailException; import org.apache.commons.mail.Simp ...

  4. Android SingleTask与SingleInstance的区别

    Android SingleTask与SingleInstance的区别 原文地址 现有2个项目,taskA.taskB.taskA负责调用taskB中指定的界面. taskB中有3个界面,a.b.c ...

  5. SQL中的CASE的用法

    CASE在SQL语句中,很有点类似java等高级编程语言中的switch这样子的多分枝语句,但是有点不同的是,case后面接的是when,另外,when的后续分枝有点类似if后面接else.这个是我的 ...

  6. WPF性能提高--MSDN学习摘要

    关于性能 一.    关于硬件加速 1.对于大多数图形硬件而言,大型图面是指达到 2048x2048 或 4096x4096 像素大小的图面. 二.    合理的布局 1.简单地说,布局是一个递归系统 ...

  7. javascript中的事件学习总结

    一.实例: 一段用js实现的固定边栏滚动特效代码(跨浏览器使用): 二.总结: 由于事件处理在不同浏览器之间存在差异(主要是要考虑ie8及以下浏览器的兼容性),所以在使用处理事件的方法之前,先要判断当 ...

  8. 轻量级开源内存数据库SQLite性能测试

    [IT168 专稿]SQLite是一款轻型的数据库,它占用资源非常的低,同时能够跟很多程序语言相结合,但是支持的SQL语句不会逊色于其他开源数据库.它的设计目标是嵌入式的,而且目前已经在很多嵌入式产品 ...

  9. 高性能MySQL --- 读书笔记(1) - 2016/8/2

    此书不但帮助MySQL初学者提高使用技巧,更为有经验的MySQL DBA指出了开发高性能MySQL应用的途径.全书包括14章,内容覆盖MySQL系统架构.设计应用技巧.SQL语句优化.服务器性能调优. ...

  10. html元素背景样式大小调整

    定义元素背景设置 background-size属性cover自适应填充背景,background-size: 100% 100%; background-size: 左右比例  上下比例: 再介绍几 ...