15.Flask-SQLAlchemy-数据迁移

SQLAlchemy-数据迁移

  • 在Flask中可以使用Flask-Migrate的第三方扩展,来实现数据迁移。并且集成到Flask终端脚本中,所有操作通过flask db 命令就能完成
  • 为了导出数据库迁移命令,Flask-Migrate提供了一个MigrateCommand类,可以附加到flask框架中

安装Flask-Migrate

pip install Flask-Migrate

代码示例:

from flask import Flask
from flask_sqlalchemy import SQLAlchemy
# 导入数据迁移核心类
from flask_migrate import Migrate

app = Flask(__name__)

class Config(object):
    DEBUG = True
    # 数据库连接配置
    # SQLALCHEMY_DATABASE_URI = "数据库类型://数据库账号:密码@数据库地址:端口/数据库名称?charset=utf8mb4"
    SQLALCHEMY_DATABASE_URI = "mysql://root:123@127.0.0.1:3306/flaskdemo?charset=utf8mb4"
    # 动态追踪修改设置,如未设置只会提示警告
    SQLALCHEMY_TRACK_MODIFICATIONS = True
    # 查询时会显示原始SQL语句
    SQLALCHEMY_ECHO = True

app.config.from_object(Config)

db = SQLAlchemy(app=app)

# 初始化数据迁移
migrate = Migrate(app, db)

# migrate = Migrate()
# migrate.init_app(app, db)

"""模型类定义"""
# 关系表的声明方式
achieve = db.Table('tb_achievement',
    db.Column('student_id', db.Integer, db.ForeignKey('tb_student.id')),
    db.Column('course_id', db.Integer, db.ForeignKey('tb_course.id'))
)

class Course(db.Model):
    # 定义表名
    __tablename__ = 'tb_course'
    # 定义字段对象
    id = db.Column(db.Integer, primary_key=True)
    name = db.Column(db.String(64), unique=True)
    price = db.Column(db.Numeric(6,2))
    teacher_id = db.Column(db.Integer, db.ForeignKey('tb_teacher.id'))
    students = db.relationship('Student', secondary=achieve, backref='courses', lazy='subquery')
    # repr()方法类似于django的__str__,用于打印模型对象时显示的字符串信息
    def __repr__(self):
        return 'Course:%s'% self.name

class Student(db.Model):
    __tablename__ = 'tb_student'
    id = db.Column(db.Integer, primary_key=True)
    name = db.Column(db.String(64), unique=True)
    email = db.Column(db.String(64),unique=True)
    age = db.Column(db.SmallInteger,nullable=False)
    sex = db.Column(db.Boolean,default=1)

    def __repr__(self):
        return 'Student:%s' % self.name

class Teacher(db.Model):
    __tablename__ = 'tb_teacher'
    id = db.Column(db.Integer, primary_key=True)
    name = db.Column(db.String(64), unique=True)
    # 课程与老师之间的多对一关联
    courses = db.relationship('Course', backref='teacher', lazy='subquery')

    def __repr__(self):
        return 'Teacher:%s' % self.name

@app.route("/")
def index():
    return "ok"

if __name__ == '__main__':
    app.run(debug=True)

创建迁移版本仓库

# 切换到项目根目录下
cd ~/Desktop/flaskdemo
# 设置flask项目的启动脚本位置,例如我们现在的脚本叫manage.py
export FLASK_APP=manage.py
# 数据库迁移初始化,这个命令会在当前项目根目录下创建migrations文件夹,将来所有数据表相关的迁移文件都放在里面。
flask db init

创建迁移版本

  • 自动创建迁移版本文件中有两个函数,用于进行数据迁移同步到数据库操作的。

    • upgrade():把迁移中的改动代码同步到数据库中。

    • downgrade():则将改动代码从数据库中进行还原。

  • 自动创建的迁移脚本会根据模型定义和数据库当前状态的差异,生成upgrade()和downgrade()函数的内容。

  • 生成的迁移文件不一定完全正确,有可能代码中存在细节遗漏导致报错,需要开发者进行检查,特别在多对多的时候

# 根据flask项目的模型生成迁移文件 -m的后面你不要使用中文!!
flask db migrate -m 'initial migration'
# 这里等同于django里面的 makemigrations,生成迁移版本文件
# 完成2件事情:
# 1. 在migrations/versions生成一个数据库迁移文件
# 2. 如果是首次生成迁移文件的项目,则迁移工具还会在数据库创建一个记录数据库版本的version表

升级版本库版本

把当前ORM模型中的代码改动同步到数据库

# 从migations目录下的versions中根据迁移文件upgrade方法把数据表的结构同步到数据库中
flask db upgrade

降级版本库的版本

# 从migations目录下的versions中根据迁移文件downgrade把数据表的结构同步到数据库中
flask db downgrade

版本库的历史管理

flask db history

输出格式:<base> ->  版本号 (head), initial migration

回滚到指定的版本

flask db downgrade # 默认返回上一个版本
flask db downgrade 版本号   # 回滚到指定版本号对应的版本
flask db upgrade 版本号     # 升级到指定版本号对应的版本

  

数据迁移步骤

1. 初始化数据迁移的目录
export FLASK_APP=4-manage.py
flask db init

2. 数据库的数据迁移版本初始化,生成迁移文件
flask db migrate -m 'initial migration'

3. 升级版本[新增一个迁移记录]
flask db upgrade 

4. 降级版本[回滚一个迁移记录]
flask db downgrade

 

posted @ 2022-01-05 11:10  李爱财  阅读(524)  评论(0编辑  收藏  举报