ClickHouse与PostgreSQL共存时ActiveRecord时间精度兼容问题
兼容ClickHouse与PostgreSQL时间精度的解决方案
问题根源
clickhouse-activerecord适配器默认未适配DateTime64(6)的微秒输出需求,而pg适配器本身会自动处理时间微秒,全局修改Time::DATE_FORMATS[:db]会导致PostgreSQL生成的SQL出现重复微秒的错误格式。
解决方案:重写ClickHouse适配器的时间格式化逻辑
在Rails项目的初始化目录下创建config/initializers/clickhouse_time_format.rb,添加以下代码:
ActiveRecord::ConnectionAdapters::ClickhouseAdapter.class_eval do def quoted_date(value) if value.respond_to?(:usec) && value.usec > 0 "'#{value.strftime('%Y-%m-%d %H:%M:%S.%6N')}'" else super end end end
原理说明
- 该代码仅针对ClickHouse数据库适配器重写
quoted_date方法,确保插入DateTime64(6)类型字段时,生成带6位微秒的时间格式。 - PostgreSQL适配器保持原生逻辑,不会出现重复微秒的问题,无需额外修改。
- 无需使用
around_create回调,适配所有时间字段的插入/更新操作。
验证效果
- 执行
Test.create时,生成的SQL会包含微秒精度:INSERT INTO tests (created_at) VALUES ('2023-06-10 08:41:57.123123') - 执行
PgTest.create时,PostgreSQL的SQL格式正常,无重复微秒:INSERT INTO pg_tests (created_at) VALUES ('2023-06-10 08:41:57.123123')
内容的提问来源于stack exchange,提问作者romushqa
相关产品推荐
相关产品推荐

