Question

I'm trying to create relationships between models in which a user is able to attend or unattend a certain a event.

In my Presence model I have:

class Presence < ActiveRecord::Base
  belongs_to :member, class_name: "User"
  belongs_to :event, class_name: "Events"
  validates :member_id, presence: true
  validates :event_id, presence: true
end

My User model:

class User < ActiveRecord::Base
  ...
      has_many :presences, foreign_key: "member_id", dependent: :destroy
      has_many :event_presence, through: :presences, source: :event
  ...
end

And the Events model:

class Events < ActiveRecord::Base
    has_many :presences, foreign_key: "event_id"
    has_many :reverse_presences, foreign_key: "event_id",
                                       class_name:  "Presence",
                                       dependent:   :destroy
    has_many :members, through: :reverse_presences, source: :member

  def event?(other_event)
    presences.find_by(event_id: other_events.id)
  end
end

When I try to use the event? method in my partial:

<div id="attend_form">
  <% if event?(@events) %>
    <%= render 'unattend' %>
  <% else %>
    <%= render 'attend' %>
  <% end %>
</div>

I get the error: undefined method "event?"'

When I move the method to my the controller's helper the error doesn't show however I get a undefined method "presences". I'm new to rails, but I understand that in the second case the method is not recognized because there is no relationship between the models in the helper but I can't figure out why it doesn't work when the method is in the model.

Thanks

EDIT

class EventsController < ApplicationController

def event1
  @events = Events.find(params[:id])
    end
end
Was it helpful?

Solution 2

For starters, your model should be called Event. Models in Rails are always singular.


The event? method is defined in the model, and you're attempting to call it in the view. Models and views are not connected in that way.

What you probably want to do is to determine if the person is attending or not attending the event already. What I would do in this instance, is call a method such as current_user.attending?(@event). That's really what you want to do: determine if the current user is attending the current event.

The method would be defined like this:

def attending?(event)
  presences.exists?(event_id: event.id)
end

OTHER TIPS

event?(other_event) is a model attribute. just like any of your other model attributes. you have to call object on it. Like this

#index.html.erb:

<% @events.each do |event| %>  #this line should go inside the index view
  <% render partial %>
<% end %>

#partial

  <div id="attend_form">
   <% if event.event?(event) %>
     <%= render 'unattend' %>
   <% else %>
     <%= render 'attend' %>
   <% end %>
 </div>

you can't pass @vents as an argument to the method: (event?(@events) because @events is an array of objects. so you want a singular instance.

Also, I think you have a TYPO in your def event?(other_event) method. it should be other_event.id not other_events.id.

UPDATE:

@events = Events.find(params[:id]) is not an array and therefore CANNOT call the each method on it. This is a singular event. to follow the convention and avoid confusions, rename @events to @event.

@event = Events.find(params[:id])

Then in the view, do this:

<div id="attend_form">
   <% if @event.event?(@event) %>
     <%= render 'unattend' %>
   <% else %>
     <%= render 'attend' %>
   <% end %>
 </div>
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top