代码之家  ›  专栏  ›  技术社区  ›  Sybil

为什么表databasechangelog上没有索引和/或pk?

  •  1
  • Sybil  · 技术社区  · 6 年前

    引用 MariaDB Galera Cluster - Known Limitations

    所有表都应该有主键(多列主键是 支持)。不支持对没有 主键。此外,表中没有主键的行可能出现在 不同节点上的不同顺序。

    galera要求每个表都有一个pk,或者至少有一个索引。这种气候主要是由于复制(wsrep插件)。

    我们经营Galera/Mariadb集群,我看到客户 DATABASECHANGELOG 没有索引和pk。我想这个表是只追加的(没有更新或删除操作)

    我不知道Liquibase,这就是为什么我要问这里缺少索引和/或pk的原因。我应该打开一个bug报告还是不理解这个用例?

    +----------------------------------------------------------------------------------------+------------+------------+-------------+---------------------+-----------------------+
    | schema                                              | table_rows | non_unique | cardinality | medium distribution | replication row reads |
    +----------------------------------------------------------------------------------------+------------+------------+-------------+---------------------+-----------------------+
    (...)
    | xxx.DATABASECHANGELOG                               |        571 |       NULL |        NULL |            571.0000 |           326041.0000 |
    | xxxx.DATABASECHANGELOG                              |        491 |       NULL |        NULL |            491.0000 |           241081.0000 |
    | xxxxx.DATABASECHANGELOG                             |        433 |       NULL |        NULL |            433.0000 |           187489.0000 |
    +----------------------------------------------------------------------------------------+------------+------------+-------------+---------------------+-----------------------+
    
    1 回复  |  直到 6 年前
        1
  •  2
  •   htshame    6 年前

    看看这个 Jira ticket

    Liquibase在数据库更新表中更改为不创建主键,因为它引入了密钥大小的问题,并不是真正必要的。我还没有检查并删除现有的主键。它应该被删除,但不会造成问题,除非您遇到一个边缘情况,其中您有非常长的id、作者和/或文件路径。

    还描述了一种可能的解决方法:

    一个简单的解决方法是使用not PrimaryKeyExists前置条件和AddPrimaryKey更改。多一点 所涉及的解决方法可能是创建一个插件来覆盖 CreateDatabaseChangeLogTableGenerator和/或 实现优先级服务的StandardChangeLogHistoryService。

    下面是一个简单的解决方法示例。我已经优化了 索引以减少SQL上的表扫描、排序和书签查找 服务器,但它可能同样适用于Oracle。我不是 真的很担心sql的最大密钥长度为900字节 超过服务器。

    <?xml version="1.0" encoding="UTF-8" ?>
    <databaseChangeLog
      xmlns="http://www.liquibase.org/xml/ns/dbchangelog" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
      xsi:schemaLocation="
          http://www.liquibase.org/xml/ns/dbchangelog http://www.liquibase.org/xml/ns/dbchangelog/dbchangelog-3.4.xsd">
    
      <property name="liquibaseCatalogName" value=""/>
      <property name="liquibaseSchemaName" value="${database.liquibaseSchemaName}"/>
      <property name="databaseChangeLogTableName" value="${database.databaseChangeLogTableName}"/>
      <property name="liquibaseTablespaceName" value=""/>
    
      <changeSet id="1" author="your-name">
          <preConditions onFail="MARK_RAN">
              <primaryKeyExists
                  catalogName="${liquibaseCatalogName}"
                  schemaName="${liquibaseSchemaName}"
                  tableName="${databaseChangeLogTableName}"
                  primaryKeyName="PK_${databaseChangeLogTableName}"/>
          </preConditions>
          <dropPrimaryKey
              catalogName="${liquibaseCatalogName}"
              schemaName="${liquibaseSchemaName}"
              tableName="${databaseChangeLogTableName}"
              constraintName="PK_${databaseChangeLogTableName}"/>
      </changeSet>
    
      <changeSet id="2" author="your-name">
          <createIndex
              catalogName="${liquibaseCatalogName}"
              schemaName="${liquibaseSchemaName}"
              tableName="${databaseChangeLogTableName}"
              indexName="IX_${databaseChangeLogTableName}_DATEEXECUTED_ORDEREXECUTED"
              tablespace="${liquibaseTablespaceName}"
              clustered="true">
    
              <column name="DATEEXECUTED"/>
              <column name="ORDEREXECUTED"/>
          </createIndex>
      </changeSet>
    
      <changeSet id="3" author="your-name">
          <addPrimaryKey
              catalogName="${liquibaseCatalogName}"
              schemaName="${liquibaseSchemaName}"
              tableName="${databaseChangeLogTableName}"
              constraintName="PK_${databaseChangeLogTableName}"
              tablespace="${liquibaseTablespaceName}"
              clustered="false"
              columnNames="ID,AUTHOR,FILENAME"/>
      </changeSet>
    
    </databaseChangeLog>