十七、python操作SQLAlchemy(二)
发布日期:2021-10-31 07:31:27 浏览次数:18 分类:技术文章

本文共 6814 字,大约阅读时间需要 22 分钟。

SQLAlchemy

SQLAlchemy本身无法操作数据库,其必须通过pymysql等第三方插件。上图中Dialect用于和数据API进行交流,根据配置文件的不同调用不同的数据库API,从而实现对数据库的操作。

# mysqldbmysql+mysqldb://
:
@
[:
]/
# pymysqlmysql+pymysql://
:
@
/
[?
]# mysql-connectormysql+mysqlconnector://
:
@
[:
]/
# cx_oracle oracle+cx_oracle://user:pass@host:port/dbname[?key=value&key=value...]

对比

ORM思想的核心是隐藏了数据访问细节,提供了通用的数据库交互。并且完全不用考虑SQL语句,从而快速开发。

使用SQL创建表

CREATE TABLE student(  id int not null auto_increment,  name varchar(100),  age int,  address varchar(100),  PRIMARY KEY(id))

上述是一个简单的创建单表的语句。

使用SQLAlchemy

  • 方法1
from sqlalchemy import create_engine, Column, String, Integer, MetaDatafrom sqlalchemy.ext.declarative import declarative_baseengine = create_engine("mysql+pymysql://root:123456@localhost/test", encoding='UTF-8', echo=True)Base = declarative_base()    #生成orm基类class Student(Base):    __tablename__ = 'student'    #指定表名    id = Column(Integer, primary_key=True)    name = Column(String(100))    age = Column(Integer)    address = Column(String(100))Base.metadata.create_all(engine)    #创建表结构- 方法2
from sqlalchemy import Table, MetaData, Column, Integer, String, create_enginefrom sqlalchemy.orm import mapperengine = create_engine("mysql+pymysql://root:123456@localhost/test", encoding='UTF-8', echo=True)metadata = MetaData()student = Table('student', metadata,             Column('id', Integer, primary_key=True),             Column('name', String(100)),             Column('age', Integer),             Column('address', String(100))             )class Student(object):    def __init__(self, name, age, address):        self.name = name        self.age = age        self.address = addressmapper(Student, student)    #此处有问题,待解决

说明

echo=True 显示每条执行的SQL语句,可以关闭。
create_engine()返回一个Engine的实例,并且表示通过数据库语法处理细节的核心接口,这种情况下数据库语法将被解释成python的类方法。
上面简单示例对比了下使用SQL直接创建表和使用ORM框架建表的区别,下面开始介绍SQLAlchemy的使用。

安装

通过pip install SQLAlchemy安装,访问mysql使用pymysql,安装方法pip install pumysql。可以参照python访问mysql。

插入

from sqlalchemy import create_engine, Column, String, Integer, MetaDatafrom sqlalchemy.ext.declarative import declarative_basefrom sqlalchemy.orm import sessionmakerengine = create_engine("mysql+pymysql://root:123456@localhost/test", encoding='UTF-8', echo=True)DBsession = sessionmaker(bind=engine) #创建与数据库的会话session class ,注意,这里返回给session的是个class,不是实例session = DBsession()    #生成session实例Base = declarative_base()class Student(Base):    __tablename__ = 'student'    id = Column(Integer, primary_key=True)    name = Column(String(100))    age = Column(Integer)    address = Column(String(100))student1 = Student(id=1001, name='Alice', age=25, address="anhui")student2 = Student(id=1002, name='Bob', age=69, address="beijing")student3 = Student(id=1003, name='Cerry', age=14, address="jiangsu")session.add_all([student1, student2, student3])session.commit()session.close()

查询

查询是通过Session的query()方法创建一个查询对象,这个函数的参数可以是任何类或者类的描述的集合。

查询出来的数据是一个对象,直接通过对象的属性调用。

from sqlalchemy import create_enginefrom sqlalchemy.orm import sessionmakerfrom db.orm2 import Studentengine = create_engine('mysql+pymysql://root:123456@localhost/test')DBsession = sessionmaker(bind=engine)session = DBsession()a = session.query(Student)print(a)for i in a:    print(i.id, i.name, i.age, i.address)输出结果SELECT student.id AS student_id, student.name AS student_name, student.age AS student_age, student.address AS student_address FROM student1001 Alice 25 anhui1002 Bob 69 beijing1003 Cerry 14 jiangsu

session.query(Student)结果为查询的SQL语句,若出现查询结果错误可以通过查看SQL确认。

filter()和filter_by()

过滤条件。==、!=、like等过滤操作都可以在filter函数中使用。

from sqlalchemy import create_enginefrom sqlalchemy.orm import sessionmakerfrom db.orm2 import Studentengine = create_engine('mysql+pymysql://root:123456@localhost/test')DBsession = sessionmaker(bind=engine)session = DBsession()a = session.query(Student).filter(Student.id == 1001)b = session.query(Student).filter_by(id=1001)for x in a:    print(x.id, x.name, x.age, x.address)for i in b:    print(i.id, i.name, i.age, i.address)输出结果1001 Alice 25 anhui1001 Alice 25 anhui

filter()和filter_by()区别

filter可以像写sql的where条件那样写>、<等条件,但引用列名时,需要通过类名.属性名的方式。

filter_by可以使用python的正常参数传递方法传递条件,指定列名时,不需要额外指定类名,参数名对应类中的属性名,不能使用>、<等条件。
当使用filter的时候条件之间是使用==,filter_by使用的是=。
filter不支持组合查询,只能连续调用filter变相实现。filter_by的参数是**kwargs,直接支持组合查询。

filters = {
'id':1002, 'name':'Bob'}b = session.query(Student).filter_by(**filters)for i in b: print(i.id, i.name, i.age, i.address)输出结果1002 Bob 69 beijing
  • all()返回一个列表,可以通过遍历列表获取每个对象。
a = session.query(Student).filter(Student.id > 1001).all()print(a)for x in a:    print(x.id, x.name, x.age, x.address)输出结果[
,
]1002 Bob 69 beijing1003 Cerry 14 jiangsu
  • one() 返回且仅返回一个查询结果。当结果数量不足或者多于一个时会报错。
a = session.query(Student).filter(Student.id == 1001).one()print(a)print(a.id, a.name, a.age, a.address)输出结果
1001 Alice 25 anhui
  • first()返回至多一个结果,而且以单项形式,而不是只有一个元素的tuple形式返回。
a = session.query(Student).filter(Student.id > 1001).first()print(a)print(a.id, a.name, a.age, a.address)输出结果
1002 Bob 69 beijing
  • 说明
MetaData类主要用于保存表结构,连接字符串等数据,是一个多表共享的对象。metadata = MetaData(engine)绑定一个数据源的metadata。metadata.create_all(engine) 创建表,该操作会先判断表是否存在,若存在则不创建。Table类构造函数为Table.__init__(self, name, metadata,*args, **kwargs)name 表名metadata 共享的元数据args中Column是列定义下面是可变参数`*kwargs`定义schema 此表的结构名称,默认Noneautoload 自动从现有表中读入表结构,默认Falseautoload_with 从其他engine读取结构,默认Noneinclude_columns 如果autoload设置为True,则此项数组中的列明将被引用,没有写的列明将被忽略,None表示所有都列明都引用,默认Nonemustexist 如果为True,表示这个表必须在其他的python应用中定义,必须是metadata的一部分,默认Falseuseexisting 如果为True,表示这个表必须被其他应用定义过,将忽略结构定义,默认Falseowner 表所有者,用于Orcal,默认Nonequote 设置为True,如果表明是SQL关键字,将强制转义,默认Falsequote_schema 设置为True,如果列明是SQL关键字,将强制转义,默认Falsemysql_engine mysql专用,可以设置’InnoDB’或’MyISAM’Column类构造函数为Column.__init__(self, name, type_, *args, **kwargs)name 列名type_ 类型,更多类型sqlalchemy.types下面是*args参数定义Constraint(约束)ForeignKey(外键)ColumnDefault(默认)Sequenceobjects(序列)定义key 列名的别名,默认None下面是**kwargs参数定义primary_key 如果为True,则是主键nullable 是否可为Null,默认是Truedefault 默认值,默认是Noneindex 是否是索引,默认是Trueunique 是否唯一键,默认是Falseonupdate 指定一个更新时候的值,这个操作是定义在SQLAlchemy中,不是在数据库里的,当更新一条数据时设置,大部分用于updateTime这类字段autoincrement 设置为整型自动增长,只有没有默认值,并且是Integer类型,默认是Truequote 如果列明是关键字,则强制转义,默认False创建会话Session的主要目的是建立与数据库的会话,它维护你加载和关联的所有数据库对象。它是数据库查询(Query)的一个入口。在SQLAlchemy中,数据库的查询操作是通过Query对象来实现的,而Session提供了创建Query对象的接口。Query对象返回的结果是一组同一映射(Identity Map)对象组成的集合。事实上,集合中的一个对象,对应于数据库表中的一行(即一条记录)。所谓同一映射,是指每个对象有一个唯一的ID。如果两个对象(的引用)ID相同,则认为它们对应的是相同的对象。要完成数据库查询,就需要建立与数据库的连接。这就需要用到Engine对象。一个Engine可能是关联一个Session对象,也可能关联一个数据库表。当然Session最重要的功能还是实现原子操作。

ORM通过session与数据库建立连接进行通信,如下所示

from sqlalchemy.orm import sessionmakerDBSession = sessionmaker(bind=engine)session = DBSession()

通过sessionmake方法创建一个Session工厂,然后在调用工厂的方法来实例化一个Session对象。

要了解更多关于SQLAlchemy内容可以点击SQLAlchemy Documentation查看官方介绍。

转载地址:https://blog.csdn.net/weixin_39934221/article/details/80320025 如侵犯您的版权,请留言回复原文章的地址,我们会给您删除此文章,给您带来不便请您谅解!

上一篇:十八、python中使用SQLAlchemy(三)
下一篇:十六、python操作SQLAlchemy(一)

发表评论

最新留言

表示我来过!
[***.240.166.169]2024年03月12日 23时26分37秒

关于作者

    喝酒易醉,品茶养心,人生如梦,品茶悟道,何以解忧?唯有杜康!
-- 愿君每日到此一游!

推荐文章

w3wp ash oracle,[20200409]使用ash_wait_chains注意的一个细节.txt 2019-04-21
c语言程序设计教程谭浩强张基温,C语言程序设计教程(第2版) 2019-04-21
idea xml文件引入类提示_IDEA中导入多module的Maven项目后子项目不正常的情况 2019-04-21
太赫兹芯片是什么原理_什么是太赫兹技术?艾舒朗太赫兹理疗鞋——脑梗后遗症+便秘+久站腿疼腿肿案例... 2019-04-21
exfat默认配置大小_mac开发配置技巧 2019-04-21
三星k3梅林没有软件中心_10万出头买顶配,1.4T合资家轿起亚K3换新,还带换挡拨片... 2019-04-21
k8s边缘节点_边缘计算容器及K8S应用的三种场景及部署选项 2019-04-21
诸葛io的技术架构图_基于泳道技术生成“无数”个测试环境 2019-04-21
互相引用 spring_# 技术笔记:spring、springBoot源码解析 2019-04-21
华为发布岳云鹏手机_鸿蒙2.0正式发布:明年华为手机全面升级 2019-04-21
ifpc挖filecoin_Filecoin挖矿分析全套 不容错过的干货 2019-04-21
python扫雷 高级算法_Python玩转算法—扫雷 2019-04-21
牛客网python测试考试答案_牛客网SQL题库之考试分数 2019-04-21
git获取所有branch_使用jGit 通过gitUrl 获取Git的所有分支 2019-04-21
mysql like 数字结尾_重拾MySQL之正则表达式 2019-04-21
mysql where从句_《快速念咒——MySQL自学入门指南》:第1章第8节:模糊查询LIKE——一窝兔子(上)... 2019-04-21
mysql 重置密码_mysql忘记密码如何重置密码,以及修改root密码的三种方法 2019-04-21
python-docx tables后追加内容_Mac brew安装MySQL8.0.21后忘记密码(重置密码篇) 2019-04-21
python中两个时间相减结果转为小时_Python起步(二)基础数据类型1 2019-04-21
定义泛化。举个例子_网易考拉应用的dubbo泛化调用,是如何实现的? 2019-04-21