One-to-many relationship when one side is unnecessary - ruby-on-rails

I have a table called vital_sign which belongs to a patient (the patient has multiple vital signs) and to a physician (the physician captured this vital sign), but I don't care about getting physician.vital_signs, how do I express it in rails models?
I suspect something like this:
vital_signs (belongs_to :patient, belongs_to :physician) with patient_id, physician_id
patient (has_many :vital_signs)
physician (nil)
Is this correct?

You can try this :
class Physician < ActiveRecord::Base
has_many :appointments
has_many :patients, through: :vital_signs
end
class VitalSign < ActiveRecord::Base
belongs_to :physician
belongs_to :patient
end
class Patient < ActiveRecord::Base
has_many :appointments
has_many :physicians, through: :vital_signs
end

Related

adding a model to a joining table and calling it from a different model in rails

Let's say the has_many through is defined like this for a rails model.
class Physician < ApplicationRecord
has_many :appointments
has_many :patients, through: :appointments
has_many :tickets, through: :appointments #For calling **physicion.tickets**. Is this possible???
end
class Appointment < ApplicationRecord
belongs_to :physician
belongs_to :patient
has_many :tickets, as: ticketable
end
class Patient < ApplicationRecord
has_many :appointments
has_many :physicians, through: :appointments
end
This works fine. But let's add a ticket model to the appointment so each appointment can keep tickets belonging to that appointment.
class Ticket < ApplicationRecord
belongs_to :ticketable, polymorphic: true #so it can be used in other models other than appointments
end
appointment.tickets works fine. But how can we fetch all tickets for a particular physician/patient like physicion.tickets or patient.tickets?

Is this database relation schema correct?

I made my first project and got into problem that I couldn't get the right category_information values for specific competitions category through relations. So I started thinking that this could be the wrong schema for this task, so my question - is it actually wrong?
Current Scheme:
Assuming the following relationships between models from your image.
class Competition < ApplicationRecord
has_many :categories
has_many :informations
has_many :category_informations, through: :categories
end
class Category < ApplicationRecord
belongs_to :competetion
has_many :category_informations
has_many :information, through: :category_informations
end
class CategoryInformation
belongs_to :catagory
belongs_to :information
end
class Information < ApplicationRecord
belongs_to :competetion
has_many :category_informations
has_many :catagory, through: :category_information
end
Model can relates with one_to_many_to_many using :through option
It explains a association used to set up a many-to-many connection with another model.
you can get the category_informations from competition like
Competition.first.category_informations
It is all for doing! Pretty good, right?
And you could do get information from category too
Category.first.informations
Actually wrong schema doesn't exist, just there exists some wrong association description.
You can get more usage to use association from docs at 2.3 section and 4.3 section
Assuming the following relationships between tables,
A competition has_many categories,
A competition has_many information,
A category has_many information,
A category has_many competition,
An information has_many category
You can use has_many_through relationships
class Category < ApplicationRecord
has_many :category_competitions
has_many :competitions, through: :category_competition
has_many :category_informations
has_many :informations, through: :category_informations
end
class Information < ApplicationRecord
has_many :category_informations
has_many :categories, through: :category_informations
end
class Competition < ApplicationRecord
has_many :category_competition
has_many :categories, through: :category_competitions
end
class CategoryCompetition < ApplicationRecord
belongs_to :category
belongs_to :information
end
class CategoryInformation < ApplicationRecord
belongs_to :category
belongs_to :information
end
By this way you can access,Categories of a particular competition by #competition.categories
This article might be helpful for you to understand associations better
https://www.sitepoint.com/master-many-to-many-associations-with-activerecord/

usage of "has_many" vs "has_many, through" relation in rails

i'm new to both rails and web-dev.
currently i'm studding "active record Associations" in rails 4
and i got confused on usage of "has_many" vs "has_many, through" relation.
for example, if i have Physician, Appointment, and Patient model in my schema.(As rails guide provides)
and rails tutorial suggests me to do like this.
class Physician < ApplicationRecord
has_many :appointments
has_many :patients, through: :appointments
end
class Appointment < ApplicationRecord
belongs_to :physician
belongs_to :patient
end
class Patient < ApplicationRecord
has_many :appointments
has_many :physicians, through: :appointments
end
but what if i make relation like this
class Physician < ApplicationRecord
has_many :appointments
end
class Appointment < ApplicationRecord
belongs_to :physician
has_many :patients
end
class Patient < ApplicationRecord
belongs_to :appointment
end
i think both will work fine.
but i want to know whats the differences and why they made "has_many, through" relations.
thank you for reading my question.
has_many through is a way to join two unrelated, independent models/tables and to reduce duplicates/redundancy in tables, where has_many states more directive relation.
Maybe example with appointments and physicians isn't clear. I'll give a different one.
class Artist
has_many :paintings
has_many :purchases
has_many :buyers, through: :purchases
end
class Painting
belongs_to :artist
end
class Purchase
belongs_to :painting
belongs_to :buyer
end
class Buyer
has_many :paintings_buyers
has_many :painting, through: :purchases
end
Talking about your example.
First, there is no convenient way for you to get physician's patents. The only way is:
physician.appoitments.map(&:patient).uniq
Which will result in
poor performance
inability to filter entities with sql, only with ruby(again poor performance)
Also, did you notice I used uniq? That's because patient's table will have lots of duplicates when the same patients will be appointed multiple times to the same physician.

Active record query to get the count for nested associations in rails

How to write an ActiveRecord query to get the number of patients that share an appointment (physician can have more than one appointments)
class Hospital < ActiveRecord::Base
has_many :appointments
has_many :patients
has_many :physicians
end
class Physician < ActiveRecord::Base
has_many :appointments
has_many :patients, through: :appointments
belongs_to :hospital
end
class Appointment < ActiveRecord::Base
belongs_to :physician
belongs_to :patient
belongs_to :hospital
end
class Patient < ActiveRecord::Base
has_many :appointments
has_many :physicians, through: :appointments
belongs_to :hospital
end
I can get it like Patient.first.hospital.appointments. But really need to write a clean activerecord query and also where hospital_id is not null
Thanks
From what I understand, you want to do multiple nested joins with some conditions. This is how it is done cleanly:-
Patient.joins(:appointments => [:physician,:hospital]).where(patients:{<condition_hash_for_patient>},physicians:{<condition_hash_for_physician>},hospitals:{<condition_hash_for_hospital>})

Creating has_many :through Association conditionally

I have the following classes:
class Physician < ActiveRecord::Base
has_many :appointments
has_many :patients, through: :appointments
end
class Appointment < ActiveRecord::Base
belongs_to :physician
belongs_to :patient
end
class Patient < ActiveRecord::Base
has_many :appointments
has_many :physicians, through: :appointments
end
I want only a Physician to be able to create an Appointment, but not a Patient. Please let me know how I can have this restriction at the Model level.
Thanks!
You don't need to use the association to retrieve patients appointmets. Just create a getter method for them:
class Patient < ActiveRecord::Base
def appointments
Appointment.where(patient_id: self.id)
end
end

Resources