MariaDB Columnstore LAST_INSERT_ID() 备选方案
MariaDB Columnstore LAST_INSERT_ID() alternative
环境:
OS: 美分OS 7.2
数据库服务器:10.1.23-MariaDB Columnstore 1.0.9-1
2 个测试数据库,一个 InnoDB 和一个 Columnstore:
CREATE TABLE `test_innodb` (
`ctlid` bigint(20) NOT NULL AUTO_INCREMENT,
`rfid` varchar(100) DEFAULT NULL,
PRIMARY KEY (`ctlid`)
) ENGINE=InnoDB
CREATE TABLE `test_cs` (
`ctlid` bigint(20) DEFAULT NULL COMMENT 'autoincrement=1',
`rfid` varchar(100) DEFAULT NULL
) ENGINE=Columnstore
问题:
我运行几次插入InnoDBtable:
insert into test_innodb (rfid) values ('a1');
...
insert into test_innodb (rfid) values ('aX');
当我想得到最后插入的id时我运行这个:
select last_insert_id();
并且结果正确显示了在当前会话期间插入的最后一个 ctlid 值,无论是否有其他并发会话 运行 插入该 InnoDB table 并触发创建额外的 ctlid 值。到目前为止一切顺利..
现在,我在 Columnstore 中执行了几次插入 table:
insert into test_cs (rfid) values ('a1');
...
insert into test_cs (rfid) values ('aX');
我想实现与上面相同的行为,但不幸的是,这被 Columnstore 忽略了:
select last_insert_id();
我使用了以下替代方法:
-- this will return the next value
select nextvalue from calpontsys.syscolumn cs where cs.schema='my_test_database' and cs.tablename='test_cs' and cs.columnname='ctlid';
- this will return the last inserted id
select callastinsertid('test_cs');
但两者都显示出一个主要限制:如果其他并发会话 运行 插入,则上述两个查询的结果会受到这些插入生成的自动增量值的影响。基本上我可能得不到预期的最后插入的 id,但是一个更大的 id 以防其他会话并行创建自动增量值。
我也试过:
锁定table
执行插入
使用select callastinsertid('test_cs')
获取最后插入的id
之后解锁table
但是列存储似乎不支持锁定 tables。
是否有可能使用 Columnstore 实现一致的最后插入 ID(每个会话)?
我们的计划是将我们的一些功能从 MariaDB/MySQL 切换到 Columnstore,但上面的限制非常阻碍。
为了高速插入,插入一个单独的table,然后周期性地将数据从那个table复制到真正的table。通过使用这个额外的 table,您可以更轻松地控制规范化以及其他可能需要 AUTO_INCREMENT
值的东西。
并且一定要在单线程而不是多线程中执行 'copy'。
这里讨论了很多细节。 ColumnStore 需要一些调整,但我认为它对您有用。 http://mysql.rjweb.org/doc.php/staging_table
注意乒乓两个 table 的使用。这允许在并行复制到 ColumnStore 时连续摄取。
环境:
OS: 美分OS 7.2
数据库服务器:10.1.23-MariaDB Columnstore 1.0.9-1
2 个测试数据库,一个 InnoDB 和一个 Columnstore:
CREATE TABLE `test_innodb` (
`ctlid` bigint(20) NOT NULL AUTO_INCREMENT,
`rfid` varchar(100) DEFAULT NULL,
PRIMARY KEY (`ctlid`)
) ENGINE=InnoDB
CREATE TABLE `test_cs` (
`ctlid` bigint(20) DEFAULT NULL COMMENT 'autoincrement=1',
`rfid` varchar(100) DEFAULT NULL
) ENGINE=Columnstore
问题:
我运行几次插入InnoDBtable:
insert into test_innodb (rfid) values ('a1');
...
insert into test_innodb (rfid) values ('aX');
当我想得到最后插入的id时我运行这个:
select last_insert_id();
并且结果正确显示了在当前会话期间插入的最后一个 ctlid 值,无论是否有其他并发会话 运行 插入该 InnoDB table 并触发创建额外的 ctlid 值。到目前为止一切顺利..
现在,我在 Columnstore 中执行了几次插入 table:
insert into test_cs (rfid) values ('a1');
...
insert into test_cs (rfid) values ('aX');
我想实现与上面相同的行为,但不幸的是,这被 Columnstore 忽略了:
select last_insert_id();
我使用了以下替代方法:
-- this will return the next value
select nextvalue from calpontsys.syscolumn cs where cs.schema='my_test_database' and cs.tablename='test_cs' and cs.columnname='ctlid';
- this will return the last inserted id
select callastinsertid('test_cs');
但两者都显示出一个主要限制:如果其他并发会话 运行 插入,则上述两个查询的结果会受到这些插入生成的自动增量值的影响。基本上我可能得不到预期的最后插入的 id,但是一个更大的 id 以防其他会话并行创建自动增量值。
我也试过:
锁定table
执行插入
使用
select callastinsertid('test_cs')
获取最后插入的id
之后解锁table
但是列存储似乎不支持锁定 tables。
是否有可能使用 Columnstore 实现一致的最后插入 ID(每个会话)?
我们的计划是将我们的一些功能从 MariaDB/MySQL 切换到 Columnstore,但上面的限制非常阻碍。
为了高速插入,插入一个单独的table,然后周期性地将数据从那个table复制到真正的table。通过使用这个额外的 table,您可以更轻松地控制规范化以及其他可能需要 AUTO_INCREMENT
值的东西。
并且一定要在单线程而不是多线程中执行 'copy'。
这里讨论了很多细节。 ColumnStore 需要一些调整,但我认为它对您有用。 http://mysql.rjweb.org/doc.php/staging_table
注意乒乓两个 table 的使用。这允许在并行复制到 ColumnStore 时连续摄取。