我有一个奇怪的问题,我无法弄清楚。
我想利用 mysql 的集群能力将相关记录并排存储在磁盘上。Mysql 通过表上的主键进行集群,默认的 rails 模型是 ID。
但是,对于很多表来说,表的主键可能是有意义的,例如 user_id、subscription_id,将相关记录聚集在每个表旁边,并在您向数据库查询所有数据时进行非常有效的查找用户的订阅。
为此,我创建了一个 mysql 表,如:
execute('create table subscriptions (
id integer not null auto_increment,
user_id integer not null,
feed_id integer not null,
folder_id integer,
created_at datetime,
updated_at datetime,
primary key (user_id, feed_id),
key id (id)
) engine=InnoDB default charset=utf8');
请注意,我的 PK 是 user_id, feed_id 但我仍然有 ID 列,我希望 rails 仍然使用它,因为它认为是表的 PK。
首先,这在我设置之前根本不起作用:
class Subscription < ActiveRecord::Base
self.primary_key = 'id'
...
end
现在是奇怪的部分。
当我运行测试时,我收到一个奇怪的错误:
Mysql::Error: Field 'id' doesn't have a default value: INSERT INTO `subscriptions`
但是 - 如果我将应用程序置于开发模式并通过网页进行操作,它就可以正常工作。
经过大量的谷歌搜索,我找到了一个猴子补丁来阻止 Rails 将 MySQL 设置为更严格的模式:
class ActiveRecord::ConnectionAdapters::MysqlAdapter
private
alias_method :configure_connection_without_strict_mode, :configure_connection
def configure_connection
configure_connection_without_strict_mode
strict_mode = "SQL_MODE=''"
execute("SET #{strict_mode}", :skip_logging)
end
end
如果我添加它,我的测试套装似乎可以工作(对于大多数测试,但不是全部),但任何创建的模型的 ID 都为零。
再次在生产模式下,通过网页一切正常,模型按预期获得一个 auto_increment ID。
有没有人知道我可以做什么让我的测试套件在这个设置中正常工作?