开发者社区> 云物互联> 正文
阿里云
为了无法计算的价值
打开APP
阿里云APP内打开

Openstack_SQLAlchemy 修改数据库的表结构

简介: 目录 目录 前言 更改数据库的方法 为数据库添加一张或多张新表 删除一张或多张表 为旧表添加一个字段 为旧表更新一个字段 为旧表初始化一条新的记录 最后 前言 SQLAlchemy 的使用方法和相关基础内容也写过不少了, 有兴趣的小伙伴可以翻阅以往的博文, 本篇主要记录一下 SQLAlchemy 在 Openstack 中的使用规范.
+关注继续查看

目录

前言

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 项目的数据库, 能够更好的支持持续的集成, 和降低数据丢失的风险, 尽管这些数据是测试数据也存在这价值. 所以我们一本很少对数据库进行删除操作, 如若必须删除数据库中的数据库一定要谨慎.

版权声明:本文内容由阿里云实名注册用户自发贡献,版权归原作者所有,阿里云开发者社区不拥有其著作权,亦不承担相应法律责任。具体规则请查看《阿里云开发者社区用户服务协议》和《阿里云开发者社区知识产权保护指引》。如果您发现本社区中有涉嫌抄袭的内容,填写侵权投诉表单进行举报,一经查实,本社区将立刻删除涉嫌侵权内容。

相关文章
[数据结构]基本概念、单链表操作
1.数据在内存中的存储方式 数据在计算机程序中都是存储在内存空间中的. 连续内存空间,比如申请一个数组,申请内存的大小事先知道。
665 0
MySQL数据库基础(2)表结构管理
一、关系模型与数据表 二、MySQL数据类型 三、数据完整性约束 四、参照完整性约束
35 0
MySQL修改表结构
在MySQL v5.1和v5.5下测试部分方法不起作用。   数据表改名   ALTER TABLE `x_table` RENAME TO `y_table`; 字段改名 ALTER TABLE `x_table` RENAME `a_field` TO `b_field`;...
848 0
MySql修改表结构
ALTER TABLE `t_sale_city` MODIFY COLUMN `sale_name` varchar(255) CHARACTER SET utf8 COLLATE utf8_general_ci NOT NULL DEFAULT '' COMMENT '销售员姓名' AFT...
637 0
【转】数据结构链表操作之双链表的基本操作
//Node.h 声明类Node#ifndef Node_H#define Node_H template class LinkList;       //为是Node类的友员类而声明 template class Node{   public:            friend cla...
847 0
数据库基础(一)----- 数据库的基本概念,SQL分类
数据库基础(一)----- 数据库的基本概念,SQL分类
24 0
MySQL:如何将树形结构存储在数据库中
怎么存储这个结构?并且要获取以下信息: 1.查询小天的直接上司; 2.查询老宋管理下的直属员工; 3.查询小天的所有上司; 4.查询老王管理的所有员工。
44 0
MPEG2_TS流基本概念和数据结构
<p><strong><span style="color:windowtext;">(1)ES- Elementary Streams (</span><span style="color:windowtext;">原始流</span><span style="color:windowtext;">)</span></strong><span style="color:windowtext;
2855 0
+关注
云物互联
OpenStack Developer, Opensource Lover :- )
264
文章
0
问答
文章排行榜
最热
最新
相关电子书
更多
低代码开发师(初级)实战教程
立即下载
阿里巴巴DevOps 最佳实践手册
立即下载
冬季实战营第三期:MySQL数据库进阶实战
立即下载