Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fails on Rails 4.1 + PostgreSQL: bind supplies 2 parameters, but prepared statement requires 1 #8

Open
glebm opened this issue Apr 8, 2016 · 6 comments
Labels

Comments

@glebm
Copy link
Collaborator

glebm commented Apr 8, 2016

https://travis-ci.org/thredded/thredded/jobs/121800665

ActiveRecord::StatementInvalid:
PG::ProtocolViolation: ERROR: bind message supplies 2 parameters, but prepared statement "a253" requires 1
: SELECT "thredded_topics".* FROM ( (SELECT "thredded_topics".* FROM "thredded_topics" WHERE "thredded_topics"."messageboard_id" = $1 AND (to_tsvector('english', "thredded_topics"."title") @@ plainto_tsquery('english', 'Rando thread'))) UNION (SELECT "thredded_topics".* FROM "thredded_topics" INNER JOIN "thredded_posts" ON "thredded_posts"."postable_id" = "thredded_topics"."id" WHERE "thredded_topics"."messageboard_id" = $1 AND (to_tsvector('english', "thredded_posts"."content") @@ plainto_tsquery('english', 'Rando thread'))) ) "thredded_topics" ORDER BY "thredded_topics"."updated_at" DESC, "thredded_topics"."id" DESC LIMIT 50 OFFSET 0

Only getting this error on the specific combination of PostgreSQL + Rails 4.1. All the other builds are passing.

@glebm
Copy link
Collaborator Author

glebm commented Apr 8, 2016

Thredded dropped 4.1 compatibility finally.
If this gem doesn't support 4.1, the dependency version in gemspec should be bumped though.

@brianhempel
Copy link
Owner

I'm just going to add a note to the README since I can't say affirmatively which combos work and don't work.

ActiveRecordUnion is tested against Rails 4.2 and Rails 5.0. It may or may not work on Rails 4.0/4.1.

@kapluni
Copy link

kapluni commented Aug 9, 2016

I am seeing a similar issue on rails 4.2.6.

  Course Load (0.4ms)  SELECT "courses".* FROM ( (SELECT "courses".* FROM "courses" INNER JOIN "enrollments" ON "courses"."id" = "enrollments"."course_id" WHERE "enrollments"."user_id" = $1) UNION (SELECT "courses".* FROM "courses" WHERE 1=0 AND "courses"."open_to_institution" = $2) ) "courses"  [["user_id", 1], ["open_to_institution", "t"], ["user_id", 1], ["open_to_institution", "t"]]

PG::ProtocolViolation: ERROR:  bind message supplies 4 parameters, but prepared statement "a31" requires 2
: SELECT "courses".* FROM ( (SELECT "courses".* FROM "courses" INNER JOIN "enrollments" ON "courses"."id" = "enrollments"."course_id" WHERE "enrollments"."user_id" = $1) UNION (SELECT "courses".* FROM "courses" WHERE 1=0 AND "courses"."open_to_institution" = $2) ) "courses"' duration=55.75 view=0.00 db=5.57 params={"include"=>"courses", "id"=>"1"} log_level=exception timestamp=2016-08-09 13:34:43 UTC transaction_id=06def7abb5a345343b76 user_id=1 exception_message=ERROR:  bind message supplies 4 parameters, but prepared statement "a31" requires 2

user.rb:

  has_many :enrollments
  has_many :enrolled_courses, through: :enrollments

  def courses
    enrolled_courses.union(Course.open_to_institution(institution_ids))
  end

course.rb

class Course < ActiveRecord::Base
  include Taggable

  belongs_to :institution
  has_many :enrollments

  scope :open_to_institution, ->(institution_id) { where(institution_id: institution_id).where(open_to_institution: true) }
end

@brianhempel
Copy link
Owner

Oh, that looks like a real bug. Thanks for the detailed report.

@brianhempel brianhempel reopened this Aug 9, 2016
@glebm glebm added the bug label Aug 9, 2016
@brianhempel
Copy link
Owner

@kapluni can you provide more insight into this error? I've tried to recreate the query you posted as well as the my_user.courses query and everything works fine. I am having no problems with Postgres.

  1. What version of the pg gem are you using? (I'm on 0.18.4)
  2. What version of active_record_union are you using? (Latest is 1.2.0)
  3. What exactly is the Ruby code that produces the problem query? It can't be my_user.courses because the SQL query you posted doesn't include institution_id anywhere...unless there's some weird eager loading or something going on.

With "group" == "course", "category" == "institution", this is what I get:

User.new(id: 1).groups.union(Group.in_category([1,2,3])).to_a
Group Load (0.5ms) 
  SELECT "groups".* FROM (
    (SELECT "groups".* FROM "groups" INNER JOIN "enrollments"
      ON "groups"."id" = "enrollments"."group_id"
      WHERE "enrollments"."user_id" = $1 AND (1=0))
    UNION
    (SELECT "groups".* FROM "groups"
      WHERE "groups"."category_id" IN (1, 2, 3)
      AND "groups"."public" = $2)
  ) "groups"
  [["user_id", 1], ["public", "t"]]
class User < ActiveRecord::Base
  has_many :enrollments
  has_many :groups, through: :enrollments
end

class Enrollment < ActiveRecord::Base
  belongs_to :user
  belongs_to :group
end

class Group < ActiveRecord::Base
  belongs_to :category
  has_many :enrollments

  scope :in_category, ->(category_id) { where(category: category_id).where(public: true) }
end

class Category < ActiveRecord::Base
  has_many :groups
end

@kapluni
Copy link

kapluni commented Aug 31, 2016

sorry for the slow respone

What version of the pg gem are you using? (I'm on 0.18.4)

same

What version of active_record_union are you using? (Latest is 1.2.0)

same

What exactly is the Ruby code that produces the problem query? It can't be my_user.courses because the SQL query you posted doesn't include institution_id anywhere...unless there's some weird eager loading or something going on.

i am using jsonapi-resources , and it's loading the relationship as a related resource, via:

 define_method foreign_key do
              records = public_send(associated_records_method_name)
              return records.collect do |record|
                record.public_send(relationship.resource_klass._primary_key)
              end
            end unless method_defined?(foreign_key)

record in this case would be the user, and course is the relationship.

i just ran into a similar case with another, similar pattern in my code.

thanks very much for looking into this!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

3 participants