Ruby 3.0.2 error: when concating to relation with default scope
Closed this issue · 5 comments
Hi,
Trying to upgrade to ruby 3.0.2 and I am getting an error when I am trying to concat to has_many
with default-scope when torque is installed:
Reproduce script:
# frozen_string_literal: true
require "bundler/inline"
gemfile(true) do
source "https://rubygems.org"
git_source(:github) { |repo| "https://github.com/#{repo}.git" }
# Activate the gem you are reporting the issue against.
gem "activerecord"
gem "torque-postgresql"
gem "pg"
end
require "active_record"
require "minitest/autorun"
require "logger"
ActiveRecord::Base.establish_connection(
adapter: "postgresql",
database: "test",
encoding: "unicode",
host: "localhost",
port: "5432",
password: "12345",
username: "test")
ActiveRecord::Schema.define do
drop_table "projects"
drop_table "managers"
create_table "projects" do |t|
t.string "title"
t.timestamps
end
create_table "managers" do |t|
t.string "name"
t.integer :project_id
t.integer "position"
t.timestamps
end
end
class Manager < ActiveRecord::Base
belongs_to :project
end
class Project < ActiveRecord::Base
# If we remove the "order" here the test will pass
has_many :managers, -> { order(position: :asc) }
end
class BugTest < Minitest::Test
def test_concat
project = Project.create!
project.managers << Manager.new
project.save
end
end
Output (removes lines of gem install)
ruby 3.0.2p107 (2021-07-07 revision 0db68f0233) [x86_64-darwin20]
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/torque-postgresql-2.2.0/lib/torque/postgresql/attributes/builder/enum.rb:119: warning: assigned but unused variable - type
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/torque-postgresql-2.2.0/lib/torque/postgresql/attributes/builder/period.rb:47: warning: method redefined; discarding old threshold
-- drop_table("projects")
-> 0.0188s
-- drop_table("managers")
-> 0.0016s
-- create_table("projects")
-> 0.0063s
-- create_table("managers")
-> 0.0056s
Run options: --seed 36840
# Running:
E
Error:
BugTest#test_concat:
ArgumentError: wrong number of arguments (given 2, expected 1)
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activerecord-6.1.4.1/lib/active_record/relation.rb:27:in `initialize'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/torque-postgresql-2.2.0/lib/torque/postgresql/relation.rb:121:in `initialize'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activerecord-6.1.4.1/lib/active_record/relation/delegation.rb:118:in `new'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activerecord-6.1.4.1/lib/active_record/relation/delegation.rb:118:in `create'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activerecord-6.1.4.1/lib/active_record/reflection.rb:285:in `build_scope'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activerecord-6.1.4.1/lib/active_record/associations/association_scope.rb:165:in `eval_scope'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activerecord-6.1.4.1/lib/active_record/associations/association_scope.rb:129:in `block (2 levels) in add_constraints'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activerecord-6.1.4.1/lib/active_record/associations/association_scope.rb:128:in `each'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activerecord-6.1.4.1/lib/active_record/associations/association_scope.rb:128:in `block in add_constraints'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activerecord-6.1.4.1/lib/active_record/associations/association_scope.rb:125:in `reverse_each'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activerecord-6.1.4.1/lib/active_record/associations/association_scope.rb:125:in `add_constraints'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activerecord-6.1.4.1/lib/active_record/associations/association_scope.rb:29:in `scope'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activerecord-6.1.4.1/lib/active_record/associations/association_scope.rb:7:in `scope'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activerecord-6.1.4.1/lib/active_record/associations/association.rb:244:in `association_scope'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activerecord-6.1.4.1/lib/active_record/associations/collection_association.rb:282:in `add_to_target'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activerecord-6.1.4.1/lib/active_record/associations/collection_association.rb:437:in `block in concat_records'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activerecord-6.1.4.1/lib/active_record/associations/collection_association.rb:435:in `each'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activerecord-6.1.4.1/lib/active_record/associations/collection_association.rb:435:in `concat_records'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activerecord-6.1.4.1/lib/active_record/associations/has_many_association.rb:130:in `concat_records'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activerecord-6.1.4.1/lib/active_record/associations/collection_association.rb:120:in `block in concat'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activerecord-6.1.4.1/lib/active_record/associations/collection_association.rb:135:in `block in transaction'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activerecord-6.1.4.1/lib/active_record/connection_adapters/abstract/database_statements.rb:320:in `block in transaction'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activerecord-6.1.4.1/lib/active_record/connection_adapters/abstract/transaction.rb:319:in `block in within_new_transaction'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activesupport-6.1.4.1/lib/active_support/concurrency/load_interlock_aware_monitor.rb:26:in `block (2 levels) in synchronize'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activesupport-6.1.4.1/lib/active_support/concurrency/load_interlock_aware_monitor.rb:25:in `handle_interrupt'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activesupport-6.1.4.1/lib/active_support/concurrency/load_interlock_aware_monitor.rb:25:in `block in synchronize'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activesupport-6.1.4.1/lib/active_support/concurrency/load_interlock_aware_monitor.rb:21:in `handle_interrupt'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activesupport-6.1.4.1/lib/active_support/concurrency/load_interlock_aware_monitor.rb:21:in `synchronize'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activerecord-6.1.4.1/lib/active_record/connection_adapters/abstract/transaction.rb:317:in `within_new_transaction'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activerecord-6.1.4.1/lib/active_record/connection_adapters/abstract/database_statements.rb:320:in `transaction'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activerecord-6.1.4.1/lib/active_record/transactions.rb:209:in `transaction'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activerecord-6.1.4.1/lib/active_record/associations/collection_association.rb:134:in `transaction'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activerecord-6.1.4.1/lib/active_record/associations/collection_association.rb:120:in `concat'
/Users/yosi/.rvm/gems/ruby-3.0.2/gems/activerecord-6.1.4.1/lib/active_record/associations/collection_proxy.rb:1027:in `<<'
repro.rb:58:in `test_concat'
I did monkey patch for now to fix it -
::Torque::PostgreSQL::Relation::Initializer.class_eval do
def initialize(
klass,
table: klass.arel_table,
predicate_builder: klass.predicate_builder,
values: {}
)
super
if klass.define_attribute_methods &&
klass.superclass != ActiveRecord::Base &&
!klass.superclass.abstract_class?
klass.superclass.send(:relation)
end
end
end
The important change is initialize
method signature, @crashtech if you want I can submit PR for that
@crashtech Can you please give it a look?
Hey, sorry for the delay, I was moving to a new place and keeping up with my work. Hard times.
I'll push a fix for this tomorrow, but just so you know, the thing is that there is no need to specify the signature of the method, a simple def initialize(klass, *, **)
will fix the problem.
@crashtech hope everything is well with moving to new place!
Thanks for the fix and explanation I always learn from your PRs :)