leikind / wice_grid

A Rails grid plugin to create grids with sorting, pagination, and (automatically generated) filters
MIT License
536 stars 215 forks source link

How to create this association? #306

Closed Nickk4 closed 8 years ago

Nickk4 commented 8 years ago

I've updated the gem from 3.5.0 to 3.6.2 and adjusted all the associations where I used model: '...' to assoc: :.... However, for one more complex association, I don't seem to be able to get it to work for the new version. What am I missing?

Member model:

has_many   :relationships, inverse_of: :member
has_many   :organizations, through: :relationships, inverse_of: :members
belongs_to :default_relationship, class_name: "Relationship", foreign_key: :default_relationship_id, inverse_of: :default_for_member
has_one    :default_organization, through: :default_relationship, source: :organization

Controller:

def index
  @members_grid = initialize_grid(Member,
    conditions:      ['premium = ? and activated =?', true, true],
    per_page:        25,
    order:           'members.username',
    order_direction: 'desc')
end

View:

<%= grid(@members_grid, show_filters: :when_filtered, html: {class: 'my-grid'}) do |g|
  g.column name: 'Fullname', attribute: 'fullname', auto_reload: true, html: {id: 'grid-cells'}
  g.column name: 'Organization', assoc: [:default_relationship, :default_organization], attribute: 'name', auto_reload: true, html: {id: 'grid-cells'} do |member|
    link_to(
      member.default_organization.name, 
      organization_path(member.default_organization)
    )
  end
end %>

This produces the error:

ActionView::Template::Error: WiceGrid: Association default_organization not found in Relationship

If instead of assoc: [:default_relationship, :default_organization] I specify the association as assoc: :default_organization, it still produces an error, namely:

ActionView::Template::Error: PG::AmbiguousColumn: ERROR: column reference "activated" is ambiguous

(activated is a key in both the member and the organization table)

What would be the correct way to code this association in version 3.6.2? P.S. I use ruby 2.3.1 and rails 4.2.6.

noahc commented 8 years ago

What does that line look like in your view? Maybe it needs to look like model.activated or whatever your variable is of the block in the view.

Nickk4 commented 8 years ago

The code below "In my grid:" is the code in my view. Or is that not what you meant? The whole activated variable isn't used in the view.

noahc commented 8 years ago

No, that's what I meant. Sorry.

Nickk4 commented 8 years ago

I've updated the question with the full view (I've shortened my view for testing purposes). If I remove the g.column name: 'Organization' ... part, it renders without error.

leikind commented 8 years ago

Could you please post the code which worked with version 3.5.0?

Nickk4 commented 8 years ago

Absolutely, I had the code below, which worked with version 3.5.0. All other code has remained the same.

g.column name: 'Organization', model: 'Organization', attribute: 'name', auto_reload: true, html: {id: 'grid-cells'} do |member|
    link_to(
      member.default_organization.name, 
      organization_path(member.default_organization)
    )
end
leikind commented 8 years ago

Code

assoc: [:default_relationship, :default_organization]

means that the main model (Member in your case) has association :default_relationship, and that Relationship has association default_organization. This is not the case. Both :default_relationship and :default_organization are associations of Member, and I don't know what you thought putting both into assoc meant.

So yes, the correct code is

assoc: :default_organization

and the actual problem is

ActionView::Template::Error: PG::AmbiguousColumn: ERROR: column reference "activated" is ambiguous

All you need to do is replace

conditions:      ['premium = ? and activated =?', true, true],

by

conditions:      ['premium = ? and THE_CORRECT_TABLE_HERE.activated =?', true, true],
Nickk4 commented 8 years ago

Thanks, so I now have:

g.column name: 'Organization', assoc: :default_organization, attribute: 'name', auto_reload: true, html: {id: 'grid-cells'} do |member|
  link_to(
    member.default_organization.name, 
    organization_path(member.default_organization)
  )
end

and

def index
  @members_grid = initialize_grid(Member,
    conditions:      ['premium = ? and Member.activated =?', true, true],
    per_page:        25,
    order:           'members.username',
    order_direction: 'desc')
end

It now generates the error:

ActionView::Template::Error: PG::UndefinedTable: ERROR: missing FROM-clause entry for table "member"

leikind commented 8 years ago

Of course. You don't have table Member. Member is your model. Your table is called members.

Nickk4 commented 8 years ago

Thanks so much! It now works. That there's a difference between a model and a table is new to me, so that's good to learn about!