SQLAlchemy是Python编程语言下的一款ORM框架,该框架建立在数据库API之上,使用关系对象映射进行数据库操作,简言之便是:将对象转换成SQL,然后使用数据API执行SQL并获取执行结果。
SQLAchemy下载
pip3 install sqlalchemy
SQLAchemy使用
SQLAlchemy本身无法操作数据库,其必须以来pymsql等第三方插件,Dialect用于和数据API进行交流,根据配置文件的不同调用不同的数据库API,从而实现对数据库的操作,如:
MySQL-Python mysql+mysqldb://<user>:<password>@<host>[:<port>]/<dbname> pymysql mysql+pymysql://<username>:<password>@<host>/<dbname>[?<options>] MySQL-Connector mysql+mysqlconnector://<user>:<password>@<host>[:<port>]/<dbname> cx_Oracle oracle+cx_oracle://user:pass@host:port/dbname[?key=value&key=value...] 更多详见:http://docs.sqlalchemy.org/en/latest/dialects/index.html
1、用sqlalchemy建表
import sqlalchemy from sqlalchemy import create_engine from sqlalchemy.ext.declarative import declarative_base from sqlalchemy import Column, Integer, String # 连接方式 mysql+pymysql 用户名 root 密码 123456 主机 localhost 库 testdb encoding 字符集 engine = create_engine("mysql+pymysql://root:123456@localhost/testdb",encoding='utf-8', echo=True) Base = declarative_base() # 生成orm基类 class User(Base): __tablename__ = 'user' # 表名 id = Column(Integer, primary_key=True) name = Column(String(32)) password = Column(String(64)) Base.metadata.create_all(engine) # 创建表结构
如果数据库已经有了这个表了就不会创建了,也不会报错。
添加数据
先导入sessionmaker
from sqlalchemy.orm import sessionmaker
Session_class = sessionmaker(bind=engine) # 创建与数据库的会话session class ,注意,这里返回给session的是个class,不是实例 Session = Session_class() # 生成session实例 cursor user_obj1 = User(name="alex", password="alex3714") # 生成你要创建的数据对象
user_obj2 = User(name="jack", password="122") # 生成你要创建的数据对象 print(user_obj.name, user_obj.id) # 此时还没创建对象呢,不信你打印一下id发现还是None Session.add(user_obj1) # 把要创建的数据对象添加到这个session里, 一会统一创建
Session.add(user_obj2) # 把要创建的数据对象添加到这个session里, 一会统一创建 print(user_obj.name, user_obj.id) # 此时也依然还没创建 Session.commit() # 现此才统一提交,创建数据
数据查询
Session_class = sessionmaker(bind=engine) # 创建与数据库的会话session class ,注意,这里返回给session的是个class,不是实例 Session = Session_class() # 生成session实例 cursor data = Session.query(User).filter_by(name="alex").all() #filter_by 查出来的是一个列表 print(data)
data = Session.query(User).filter_by().all()
如果filter_by没有设置条件就把表中的数据都查出来了。
虽然是4条数据,但是完全看不懂,转换下数据显示格式。
在User类中添加一个方法:
class User(Base): __tablename__ = 'user' # 表名 id = Column(Integer, primary_key=True) name = Column(String(32)) password = Column(String(64)) def __repr__(self): #添加的方法 return "<%s name:%s>" % (self.id,self.name)
first() 取数据的第一条 , 没有last()方法
data = Session.query(User).filter_by().first()
filter_by和filter的小区别
某些条件下用filter_by:
data = Session.query(User).filter_by(id=2).all()
转成filter就要写成:
data = Session.query(User).filter(User.id==2).all()
还有就是filter_by不能直接写 > <这种条件 要用filter。
data = Session.query(User).filter(User.id>2).all()
多个条件
data = Session.query(User).filter(User.id>2).filter(User.id<5).all()
修改数据
还是通过面向对象的方式修改。
data = Session.query(User).filter(User.id>2).filter(User.id<5).first() print(data) data.name = 'Jack Liu' data.password = 'Shit happens' Session.commit()
原数据的name
回滚
原理和事务的回滚是一样的。
my_user = Session.query(User).filter_by(id=1).first() my_user.name = "Jack" fake_user = User(name='Rain', password='12345') Session.add(fake_user) print(Session.query(User).filter(User.name.in_(['Jack', 'rain'])).all()) # 这时看session里有你刚添加和修改的数据 Session.rollback() # 此时你rollback一下 print('after rollback') print(Session.query(User).filter(User.name.in_(['Jack', 'rain'])).all()) # 再查就发现刚才添加的数据没有了。
统计和分组
统计 count()
Session.query(User).filter(User.name.in_(['Jack', 'rain'])).count()
分组
from sqlalchemy import func Session.query(func.count(User.name),User.name).group_by(User.name).all()
第二种建表方式 不常用 了解即可
1 from sqlalchemy import Table, MetaData, Column, Integer, String, ForeignKey 2 from sqlalchemy.orm import mapper 3 4 metadata = MetaData() 5 #表结构 通过Table创建表 6 user = Table('user', metadata, 7 Column('id', Integer, primary_key=True), 8 Column('name', String(50)), 9 Column('fullname', String(50)), 10 Column('password', String(12)) 11 ) 12 13 14 class User(object): #不继承Base 自定义类 15 def __init__(self, name, fullname, password): 16 self.name = name 17 self.fullname = fullname 18 self.password = password 19 20 21 mapper(User, user) #把这个类和表结果关联一下