ruby on rails has_many through relationship
- by BennyB
Hi i'm having a little trouble with a has_many through relationship for my app and was hoping to find some help. So i've got Users & Lectures. Lectures are created by one user but then other users can then "join" the Lectures that have been created. Users have their own profile feed of the Lectures they have created & also have a feed of Lectures friends have created. This question however is not about creating a lecture but rather "Joining" a lecture that has been created already. I've created a "lecturerelationships" model & controller to handle this relationship between Lectures & the Users who have Joined (which i call "actives"). Users also then MUST "Exit" the Lecture (either by clicking "Exit" or navigating to one of the header navigation links). I'm grateful if anyone can work through some of this with me...
I've got:
Users.rb model
Lectures.rb model
Users_controller
Lectures_controller
then the following model
lecturerelationship.rb
class lecturerelationship < ActiveRecord::Base
attr_accessible :active_id, :joinedlecture_id
belongs_to :active, :class_name => "User"
belongs_to :joinedlecture, :class_name => "Lecture"
validates :active_id, :presence => true
validates :joinedlecture_id, :presence => true
end
lecturerelationships_controller.rb
class LecturerelationshipsController < ApplicationController
before_filter :signed_in_user
def create
@lecture = Lecture.find(params[:lecturerelationship][:joinedlecture_id])
current_user.join!(@lecture)
redirect_to @lecture
end
def destroy
@lecture = Lecturerelationship.find(params[:id]).joinedlecture
current_user.exit!(@user)
redirect_to @user
end
end
Lectures that have been created (by friends) show up on a users feed in the following file
_activity_item.html.erb
<li id="<%= activity_item.id %>">
<%= link_to gravatar_for(activity_item.user, :size => 200), activity_item.user %><br clear="all">
<%= render :partial => 'shared/join', :locals => {:activity_item => activity_item} %>
<span class="title"><%= link_to activity_item.title, lecture_url(activity_item) %></span><br clear="all">
<span class="user">
Joined by <%= link_to activity_item.user.name, activity_item.user %>
</span><br clear="all">
<span class="timestamp">
<%= time_ago_in_words(activity_item.created_at) %> ago.
</span>
<% if current_user?(activity_item.user) %>
<%= link_to "delete", activity_item, :method => :delete,
:confirm => "Are you sure?",
:title => activity_item.content %>
<% end %>
</li>
Then you see I link to the the 'shared/join' partial above which can be seen in the file below
_join.html.erb
<%= form_for(current_user.lecturerelationships.build(:joinedlecture_id => activity_item.id)) do |f| %>
<div>
<%= f.hidden_field :joinedlecture_id %>
</div>
<%= f.submit "Join", :class => "btn btn-large btn-info" %>
<% end %>
Some more files that might be needed:
config/routes.rb
SampleApp::Application.routes.draw do
resources :users do
member do
get :following, :followers, :joined_lectures
end
end
resources :sessions, :only => [:new, :create, :destroy]
resources :lectures, :only => [:create, :destroy, :show]
resources :relationships, :only => [:create, :destroy] #for users following each other
resources :lecturerelationships, :only => [:create, :destroy] #users joining existing lectures
So what happens is the lecture comes in my activity_feed with a Join button option at the bottom...which should create a lecturerelationship of an "active" & "joinedlecture" (which obviously are supposed to be coming from the user & lecture classes. But the error i get when i click the join button is as follows:
ActiveRecord::StatementInvalid in LecturerelationshipsController#create
SQLite3::ConstraintException: constraint failed: INSERT INTO "lecturerelationships" ("active_id", "created_at", "joinedlecture_id", "updated_at") VALUES (?, ?, ?, ?)
Also i've included my user model (seems the error is referring to it)
user.rb
class User < ActiveRecord::Base
attr_accessible :email, :name, :password, :password_confirmation
has_secure_password
has_many :lectures, :dependent => :destroy
has_many :lecturerelationships, :foreign_key => "active_id", :dependent => :destroy
has_many :joined_lectures, :through => :lecturerelationships, :source => :joinedlecture
before_save { |user| user.email = email.downcase }
before_save :create_remember_token
validates :name, :presence => true, :length => { :maximum => 50 }
VALID_EMAIL_REGEX = /\A[\w+\-.]+@[a-z\d\-.]+\.[a-z]+\z/i
validates :email, :presence => true,
:format => { :with => VALID_EMAIL_REGEX },
:uniqueness => { :case_sensitive => false }
validates :password, :presence => true, :length => { :minimum => 6 }
validates :password_confirmation, :presence => true
def activity
# This feed is for "My Activity" - basically lectures i've started
Lecture.where("user_id = ?", id)
end
def friendactivity
Lecture.from_users_followed_by(self)
end
# lECTURE TO USER (JOINING) RELATIONSHIPS
def joined?(selected_lecture)
lecturerelationships.find_by_joinedlecture_id(selected_lecture.id)
end
def join!(selected_lecture)
lecturerelationships.create!(:joinedlecture_id => selected_lecture.id)
end
def exit!(selected_lecture)
lecturerelationships.find_by_joinedlecture_id(selected_lecture.id).destroy
end
end
Thanks for any and all help - i'll be on here for a while so as mentioned i'd GREATLY appreciate someone who may have the time to work through my issues with me...