Find rows with same some_attribute but two different values for user_id - sql

These are my classes & relations
class User
has_many :conversation_participants
has_many :conversations, :through => :conversation_participants
end
class ConversationParticipant
belongs_to :user
belongs_to :conversation
end
class Conversation
has_many :messages
has_many :conversation_participants
has_many :users, :through => :conversation_participants
end
So when I want to create a conversation between user_ids 12 and 15, I first want to check if a conversation between these two already exists. So what I need to find is this:
ConversationParticipants where user_id IN (12, 15) AND "both conversationparticipant rows have the same conversation id"
I lack the proper words to explain this query but I think everyone will get what I mean. "Does a conversation between these two users exist already?". I know neither how to do it in SQL nor Rails so any answer is appreciated.
EDIT
The id of the conversation would not be known. I need to find if a conversation between those two user_ids exist.
Thanks
-- Emil

class User
has_many :conversations
has_many :conversation_participants
has_many :joined_conversations, :through => :conversation_participants, :source => :conversation
end
class ConversationParticipant
belongs_to :user
belongs_to :conversation
end
class Conversation
belongs_to :user
has_many :conversation_participants
has_many :speakers, :through => :conversation_participants, :source => :user
end

You can try this
#result = ConversationParticipants.where("user_id in ? AND conversation_id=?",[1,2,3,4],2)

Related

Excluding results in has_many :through relation in Rails 3

I am trying to select groups which the #current_user is NOT a member of
The relevant parts of my models are as follows:
class Group < ActiveRecord::Base
belongs_to :user
has_many :group_memberships
has_many :members, :class_name => "User", :through=>:group_memberships
...
class User < ActiveRecord::Base
has_many :group_memberships, :foreign_key => 'member_id'
has_many :groups, :through => :group_memberships
...
class GroupMembership < ActiveRecord::Base
belongs_to :member, :class_name=>"User"
belongs_to :group
end
Thanks!
You could try and do something like:
#groups = Group.where("id NOT IN (?)", current_user.groups)
More information can be found in the Active Record Query.
have a method like this:
def group_ids_not_a_member_of
# get all group_ids and subtract out the ids that he is a member of
Group.pluck('id') - current_user.groups.map(&:id)
end
then
user.group_ids_not_a_member_of

How can I reference the same model twice and create the association in a multiple select form?

I have two classes (Game and Report) and want to link them with an additional attribute (default = yes or no).
The game should then have default_reports and optional_reports.
The association is then updated by selecting the default and optional reports in a select (multiple) in the games create/edit form.
I have tried using has_many and through as well as polymorphic associations, but nothing seems to fit the use case, where the associated objects are fixed and you only want to manage associations.
class Game < ActiveRecord::Base
has_many :game_reports
has_many :reports, :through => :game_reports
end
class Report < ActiveRecord::Base
has_many :game_reports
has_many :games, :through => :game_reports
end
class GameReport < ActiveRecord::Base
belongs_to :game
belongs_to :report
end
Any help is appreciated!
Thanks
this is just the model. the view and form to create the records is an entirely different matter.
you can always add a conditions option to has_many. I'm assuming you're going to add default to game_reports so change your class to something like.
class Game < ActiveRecord::Base
has_many :game_reports
has_many :reports, :through => :game_reports
has_many :default_reports, through: :game_reports, source: :report, conditions: { game_reports: { default: true } }
end
Rails 4.2+, use a Polymorphic association with scope and specify the foreign_key and foreign_type options.
class GameReport
belongs_to :report, :polymorphic => true
end
class Game
has_many :game_reports, :as => :report, :dependent => :destroy
has_many :reports, -> { where attachable_type: "GameReport"},
class_name: GameReport, foreign_key: :game_report_id,
foreign_type: :game_report_type, dependent: :destroy
end
Other approachs:
Rails Polymorphic Association with multiple associations on the same model

Rails ActiveRecord Query (Cross model)

I have an app that lets users input dates & interests that relate to those dates .I need to send them deals (a few days before the date - Via Email) that are based off of their interests and location. I have all the models setup and recording the data properly, just wondering how to query the models for the dates and then send the appropriate deal based off of the city and interests.
Notes:
*Each city and interest category has only 1 deal
*I have several different models for types of dates (Holidays, Occasions, Friends Birthdays ect).. all are pretty much identical in structure.
*All interests for each type of date are stored in person_interests.
Models:
Class User
belongs_to :province
belongs_to :city
has_many :friends_bdays
has_many :occasions
has_many :person_interests, :as => :person
has_many :interests, :through => :person_interests
has_many :user_holidays
has_many :holidays, :through => :user_holidays
has_many :anniversaries
end
class Deal < ActiveRecord::Base
belongs_to :interest
belongs_to :city
belongs_to :store
end
class Store < ActiveRecord::Base
has_many :deals
belongs_to :city
belongs_to :province
end
class PersonInterest < ActiveRecord::Base
belongs_to :interest
belongs_to :person, :polymorphic => true
end
class Interest < ActiveRecord::Base
has_many :person_interests
has_many :deals
end
class Occasion < ActiveRecord::Base
belongs_to :user
belongs_to :admin_user
has_many :person_interests, :as => :person
has_many :interests, :through => :person_interests
end
class Anniversary < ActiveRecord::Base
belongs_to :user
has_many :person_interests, :as => :person
has_many :interests, :through => :person_interests
end
class Friend_bday < ActiveRecord::Base
belongs_to :user
has_many :person_interests, :as => :person
has_many :interests, :through => :person_interests
end
You can achieve this using a variation of the solution below:
Install the squeel gem
class User
def deals(reload=false)
#deals = nil if
#deals ||= Deal.where{
( (:city => city_id) | ( :interest_id => interest_ids) ) &
:deal_date => (Time.now..3.days.from_now)
}
end
end
Now, user.deals returns the deals that will be active in next 3 days matching the user's city OR interests.
Edit 1:
Based on your comment it looks like you don't need the squeel gem. You can achieve what you want using regular AR syntax.
class User
def deals(reload=false)
#deals = nil if reload
#deals ||= Deal.where(
:city => city_id,
:interest_id => interest_ids,
:deal_date => (Time.now..3.days.from_now)
)
end
end

What's the rails way to include a field in a join model when listing an association?

So if I have the following relationship
class Item < ActiveRecord::Base
has_many :item_user_relationships
has_many :users, :through => :item_user_relationships
end
class User < ActiveRecord::Base
has_many :item_user_relationships
has_many :items, :through => :item_user_relationships
end
class ItemUserRelationship < ActiveRecord::Base
belongs_to :item
belongs_to :user
attr_accessible :role
end
What's the rails way to include the role attribute when listing all the Users of an Item?
#users = #item.users # I want to include the role as part of a user
Thanks!
UPDATE: I'm still having trouble with this. My goal is to get an array of User models that have their role included in the attributes.
I'm note sure if I understand you correctly, but maybe this is what you want?
#users = #item.users
#users.each do |user|
puts user.item_user_relationships.first.role
end

Has_many, through association

Warning:Total Rails Newb (TRN). This should be a pretty basic question so I'm hoping someone can spare a couple mins to help shed some light.
Let's say I have the following models: User, Group, and Member
A user can have many groups (let's say friends, family, etc)
A group can have many members, namely other users.
How would I structure this?
Initially I tried this:
class User < ActiveRecord::Base
has_many :groups
has_many :groups, :through => :members
end
class Groups < ActiveRecord::Base
has_many :users, :through => :members
belongs_to :user
end
class Member < ActiveRecord::Base
belongs_to :group
belongs_to :user
end
However this gave me an error in User so I changed
has_many :groups, :through => :members
to
has_many :memberships, :through => :members, :source => :groups
Still getting an error about missing association when I try to do
group = Group.new
group.user.new
It will be useful: http://railscasts.com/episodes/47-two-many-to-many
class User < ActiveRecord::Base
has_many :members
has_many :groups, :through => :members
has_many :groups_as_owner, :class_name => "Group"
end
class Groups < ActiveRecord::Base
has_many :members
has_many :users, :through => :members
belongs_to :owner, :class_name => "User", :foreign_key => :user_id
end
class Member < ActiveRecord::Base
belongs_to :group
belongs_to :user
end
basically has_many-through associations are n:m associations (join-tables) that (shall) have more attributes than just the id's of the joined record ids...
so you have a table Groups (with an id), a table Users (with an id) and a table Members (no id, but user_id and group_id)
basically, what you did is nearly correct, just think about how you access a group from a user or vice versa....
a user would first look up its member information and through that member information get access to the group information ... and vice versa for a group
so you first set up
has_many :members
and then call
has_many :groups, :through => :members
all you need is
class User < ActiveRecord::Base
has_many :members
has_many :groups, :through => :members
end
class Groups < ActiveRecord::Base
has_many :members
has_many :users, :through => :members
end
class Member < ActiveRecord::Base
belongs_to :group
belongs_to :user
end
and you have another bug in your code above
you might want to use
user = group.users.new
instead of
user = group.user.new
Try this structure:
class User < ActiveRecord::Base
has_many :members
has_many :groups, :through => :members
end
class Groups < ActiveRecord::Base
has_many :members
has_many :users, :through => :members
end
class Member < ActiveRecord::Base
belongs_to :group
belongs_to :user
end
Also take a look at has_and_belongs_to_many, if you don't need to do with class Member then you should use has_and_belongs_to_many. In this case don't forget to create joining table in the database