Openstack_SQLAlchemy 修改数据库的表结构
目录
前言
SQLAlchemy 的使用方法和相关基础内容也写过不少了, 有兴趣的小伙伴可以翻阅以往的博文, 本篇主要记录一下 SQLAlchemy 在 Openstack 中的使用规范.
更改数据库的方法
在开发 Openstack 项目的过程中, 对 models class 进行直接修改是不被允许的. 这不符合持续集成的规范, 也可能导致原始数据的丢失. 所以我们会使用一种类似打补丁的方式来对 Openstack 项目的数据库进行持续更新, 这也就是为什么在 /opt/stack/nova/nova/db/sqlalchemy/migrate_repo/versions
路径下存在这么多文件的原因.
为数据库添加一张或多张新表
当需要为 Openstack 项目新添一张表时, 我们会 /opt/stack/nova/nova/db/sqlalchemy/migrate_repo/versions
目录下新建一个文件, 并且需要为文件名指定一个有序的编号, EG. 016_add_new_table.py
from sqlalchemy import Boolean, Column, DateTime, BigInteger
from sqlalchemy import MetaData, String, Table
from oslo_log import log as logging
LOG = logging.getLogger(__name__)
def define_tables(meta):
# 定义一个 Table 对象
new_table_name = Table(
"new_table_name", meta,
Column("created_at", DateTime),
Column("updated_at", DateTime),
Column("deleted_at", DateTime),
Column("deleted", Boolean),
mysql_engine="InnoDB")
...
return [new_table_name, ...]
def upgrade(migrate_engine):
meta = MetaData()
meta.bind = migrate_engine
# create all tables
# Take care on create order for those with FK dependencies
tables = define_tables(meta)
# 循环创建表列表
for table in tables:
try:
table.create()
except Exception:
LOG.info(_LE('Exception while creating table.'))
raise
def downgrade(migrate_engine):
meta = MetaData()
meta.bind = migrate_engine
tables = define_tables(meta)
tables.reverse()
for table in tables:
table.drop()
删除一张或多张表
from sqlalchemy import MetaData
from sqlalchemy import Table
def upgrade(migrate_engine):
meta = MetaData(migrate_engine)
meta.reflect(migrate_engine)
table_names = ['compute_node_stats', 'compute_nodes', 'instance_actions',
'instance_actions_events', 'instance_faults', 'migrations']
for table_name in table_names:
# 创建表对象, 然后在通过表对象来调用 drop() 方法实现删除.
table = Table('dump_' + table_name, meta)
table.drop(checkfirst=True)
为旧表添加一个字段
from sqlalchemy import Column, MetaData, String, Table
NEW_COLUMN_NAME = 'initiator_name'
def upgrade(migrate_engine):
meta = MetaData()
meta.bind = migrate_engine
# 定义一个表对象, 因为是更新操作, 所以表 exsi_hypervisors 需要已经存在于数据库中
exsi_hypervisors = Table('exsi_hypervisors', meta, autoload=True)
# 定义一个字段对象
initiator_protocol = Column(NEW_COLUMN_NAME, String(length=255))
# 如果表中还没有该字段, 则添加一个新的字段
if not hasattr(exsi_hypervisors.c, NEW_COLUMN_NAME):
# 表对象调用 create_column() 方法来将字段插入
exsi_hypervisors.create_column(initiator_protocol)
为旧表更新一个字段
from sqlalchemy import Column, MetaData, String, Table
NEW_COLUMN_NAME = 'initiator_name'
def upgrade(migrate_engine):
meta = MetaData()
meta.bind = migrate_engine
# 获取一个表对象
exsi_hypervisors = Table('exsi_hypervisors', meta, autoload=True)
# 如果表对象中已经存在了 metadata_reserve 属性(字段), 则 alter 该属性(字段)
if hasattr(exsi_hypervisors.c, 'metadata_reserve'):
# 获取 metadata_reserve 属性对象
exsi_hypervisors_metadate_reserve = getattr(exsi_hypervisors.c,
'metadata_reserve')
# 通过属性对象来调用 alter() 方法, 并且传入需要更新的字段名和类型作为实参
exsi_hypervisors_metadate_reserve.alter(name='initiator_protocol',
type=String(255))
为旧表初始化一条新的记录
from datetime import datetime
from uuid import uuid4
from sqlalchemy import MetaData, Table
def upgrade(migrate_engine):
meta = MetaData()
meta.bind = migrate_engine
# 定义要插入的记录数据
values = [{'created_at': datetime.utcnow(),
'id': str(uuid4()),
'group': 'global',
'setting_option': 'cpu_over_allocate',
'setting_value': '6',
'description': 'Over allocate CPU'}]
# 创建一个 table 对象, 该表必须是已经存在于数据库内的表, 才能够被插入
system_settings = Table('system_settings', meta,
autoload=True)
# 通过表对象来调用 insert() 方法实现插入数据
for value in values:
system_settings.insert().values(value).execute()
def downgrade(migrate_engine):
meta = MetaData()
meta.bind = migrate_engine
system_settings = Table('system_settings', meta,
autoload=True)
try:
system_settings.delete().\
where(system_settings.c.setting_option == 'cpu_over_allocate').\
execute()
except Exception as e:
raise e
最后
在实现了数据库修改的文件之后执行指令:
serviceName-manager db dync
就能够对现有的数据库进行更新.
以这种补丁的方式来修改 Openstack 项目的数据库, 能够更好的支持持续的集成, 和降低数据丢失的风险, 尽管这些数据是测试数据也存在这价值. 所以我们一本很少对数据库进行删除操作, 如若必须删除数据库中的数据库一定要谨慎.
Openstack_SQLAlchemy 修改数据库的表结构的更多相关文章
- 07_MySQL修改数据库的表结构
修改数据库的表结构
- MySQL 对比数据库的表结构
有时候,需要对比一下测试环境和生产环境中,数据库的表结构是否有所差异.有两个常用的工具. AmpNmp.DatabaseCompare GUI 界面,支持多种数据库(MySQL.SQL Server. ...
- 通过EA导入数据库存在表结构并生成文档
通过EA导入数据库存在表结构并生成文档 慕课网,程序员升职加薪神器,点击免费学习 目录[-] 导入数据源,表结构 生成表结构的文档 Enterprise Architect 是超级强大项目管理功能 ...
- 导入导出Mysql数据库、表结构、表数据
由sql文件导入 mysql -uusername -ppwd < ./abc.sql 导出整个数据库的表结构 mysqldump -uroot -pdbpasswd -d dbname > ...
- MySQL修改数据库、表、列、外键字符编码和排序编码
在重启Confluence应用时,突然遇见这个检查错误,查询总结需要修改Mysql数据库的所有字符编码和排序编码,报错如下: Confluence Help – This installation o ...
- SQL Server 不清空数据,修改数据库字段、结构,阻止保存要求重新创建表的更改
当数据库有数据修改数据库字段时,默认是阻止的! 工具---选项---设计器---阻止保存要求重新创建表的更改(取消钩)
- ORACLE数据库对比表结构
有时候会有某种需求:需要对比两个表的表结构是否一致,有时候甚至是整个数据库所有表的表结构对比.......表结构对比无非就是字段名.字段类型.字段数据类型.以及字段的顺序的对比.如果需要对比表结构,可 ...
- ***电商数据库设计参考:ecshop数据库+订单表结构等
ecshop订单表结构ecs_order_info说明 -- 表的结构 `ecs_order_info` CREATE TABLE IF NOT EXISTS `ecs_order_info` ...
- 导出db2数据库的表结构和数据(转载)
对于db2数据库,导入和导出表结构和数据其实很简单,只需要用到db2look和db2move两个命令即可.这两个命令都需要在客户端的命令行处理器 中执行,但对于数据库服务器和客户端不在同一机器上的 ...
随机推荐
- Redis数据类型:Hashes、Geo操作指令
Redis数据类型:Hashes.Geo操作指令 Hashes常用操作指令 Redis Hashes是一个键值对的映射表,最对能存储2^32-1(约40亿)个键值对. HSET HGET HSET:将 ...
- linux驱动模型——platform(1)
一.驱动模型包含什么? 1.1. 类class 1.1.2. 它能够自动创建/dev下的设备节点,不需要mknod /dev/xxx c x x创建.当然class还有其另外的作用,且自动创建设备节点 ...
- Nodejs中request出现ESOCKETTIMEDOUT解决方案
做需求的时候,使用Nodejs的request批量请求某一个接口,由于接口超时,出现 ESOCKETTIMEDOUT,程序中断 为了让程序遇到 ESOCKETTIMEDOUT 之后能够继续执行下去,需 ...
- 被我误解的max_connect_errors
第一节 什么是max_connect_errors 一开始接触这个参数的时候,感觉他和max_connections的含义差不多,字面意思简单明了,这个参数的含义是最大连接错误数,翻翻mysql的文 ...
- Javascript | DOM\DOM树浅析
DOM Document Object Model(文档对象模型) 定义了表示和修改文档所需的方法. DOM对象即为宿主对象,由浏览器厂商定义,用来操作html和xml功能的一类对象的集合.也有人称D ...
- 行人重识别(ReID) ——基于Person_reID_baseline_pytorch修改业务流程
下载Person_reID_baseline_pytorch地址:https://github.com/layumi/Person_reID_baseline_pytorch/tree/master/ ...
- VirtualBox中安装CentOS 7
1.如下所示图,点击“新建”,创建一个新的虚拟机 2.类型选择Linux,版本选择Red Hat,下一步 3.分配内存大小,电脑8G内存,所以分给虚拟机2G,选择下一步 4.选择“现在创建虚拟硬盘” ...
- unity2017 光照与渲染(二)FAQs
FAQ: 场景里的物体没有影子? 1)灯光是否开了影子 2)QualitySettings 中 shadows 的设置 3) 模型MeshRenderer 的 ReciveShadows 和 Cast ...
- KNN算法项目实战——改进约会网站的配对效果
KNN项目实战——改进约会网站的配对效果 1.项目背景: 海伦女士一直使用在线约会网站寻找适合自己的约会对象.尽管约会网站会推荐不同的人选,但她并不是喜欢每一个人.经过一番总结,她发现自己交往过的人可 ...
- 分布式锁的实现【基于ZooKeeper】
引言 ZooKeeper是一个分布式的,开放源码的分布式应用程序协调服务,是Google的Chubby一个开源的实现,是Hadoop和Hbase的重要组件.它是一个为分布式应用提供一致性服务的软件,提 ...