Topic: Getting confused declaring models and their associations

I only just got started with Rails, and working on my first "production" app. The app will allow a user to schedule when the central Twilio number should call one of our doctors - basically, when he's on call.

I currently have 2 models:
Doctor
- id:int
- name:string
- phone:string

Schedule
- id:int
- doctor_id:int
- date:date
- forwarded_from:string

Note that this forwarded_from is currently just the form input, but I might hardcode the phone numbers in the app. There will be 10 of them, but these obviously shouldn't change at all. If you think this is wrong, feel free to point out how you think I should handle this.

Now, I'm completely confused when I try to figure out what kind of association I should use between these models. The schedule will have a composite index on date and forwarded_from because you obviously can't forward a phone number to two different doctors on the same day. Is this a 1:many association, or many:many? In what direction? Maybe there's more than one possibility, and that's why I'm confused?

Thank you!


EDIT: currently thinking doctors has_many schedules, so that I can look up Doctor.schedules - I won't need to look up all Schedule.doctors as that makes no sense... right?

Last edited by hafos (2012-03-26 17:34:54)

Re: Getting confused declaring models and their associations

Here's how I'd do it.

Doctor
- id:int
- name:string
- phone:string

OnCall
- id:int
- doctor_id:int
- schedule_id:int
- forwarded_from:string

Schedule
- id:int
- date:datetime

class Doctor < ActiveRecord::Base
  belongs_to :oncall
end
class Schedule < ActiveRecord::Base
  belongs_to :oncall
end
class Oncall < ActiveRecord::Base
  has_one :doctor
  has_one :schedule
end

Now you can do stuff like

@date = Schedule.find_by_date('1/1/2012')

@date.oncall.doctor

or

@dates = Schedule.where("date >= ? and date <= ?",'1/1/2012','12/31/2012')
@dates.each do |date|
   <%= "On #{date.strftime('%m/%d/%Y')} Doctor #{date.oncall.doctor.name}" %>
end

Then let's say in the future,  you decide to allow MORE than one doctor to be on call

class Oncall < ActiveRecord::Base
  has_many :doctors
  has_one :schedule
end

@dates = Schedule.where("date >= ? and date <= ?",'1/1/2012','12/31/2012')
@dates.each do |date|
  date.oncall.doctors.each do |doc|
     <%= "Date #{date.strftime('%m/%d/%Y')} Doctor #{doc.name}" %>
  end
end
Joe got a job, on the day shift, at the Utility Muffin Research Kitchen, arrogantly twisting the sterile canvas snout of a fully charged icing anointment utensil.

Re: Getting confused declaring models and their associations

Thank you Brad

Something like that came to mind but never gave it much thought because the application seems too simple. On top of that, are you sure it is necessary, because after all Schedule has nothing but a date? Would you add one unique id per date, or allow a date to appear multiple times in this model?

It still doesn't make a whole lot of sense to me...


An additional question: I want the user to be able to enter a range of dates for a doctor to be on call. Where and how would I enable them to do that? It probably requires a second input field in the view, and a check if that one is empty or not... but that's as far as I've gotten.

Re: Getting confused declaring models and their associations

hafos wrote:

An additional question: I want the user to be able to enter a range of dates for a doctor to be on call. Where and how would I enable them to do that? It probably requires a second input field in the view, and a check if that one is empty or not... but that's as far as I've gotten.

First off, I'm new to Rails too. But I was thinking that maybe you could have a start_time and and end_time in your schedule table, where the start_time is when the doctor comes on duty, and the end_time is when his shift ends. Then you can probably search for a doctor based on the requested time being between his/her start_time and end_time.

Last edited by Brian71 (2012-03-27 12:17:45)

Re: Getting confused declaring models and their associations

I would do what you're comfortable with.  I was just really trying to illustrate how to use associations,  thinking it might break the log jam in your mind. 

There are probably 100 different ways to tackle your problem,  think of what I posted as one example.

When there are so many ways  to approach association setup, I like to think about how those associates get used in your code.  You'll only set up the associations once,  but you'll refer to them many times as you develop your app.   Look at this line of code:

@date.oncall.doctor

That's easy to read,  it's pretty clear what that line of code will yield,  that's why I proposed the associations I did,  so the code is easy to read.

But!  That may of been a bit advanced for someone just starting out,  and if your app isn't intended to grow into a larger system in the future,  but forever remain the simple app you described,  then you can easily make it work the way you've described.

As far as relationships for the two models you described,  you could start with the minimal

class Doctor < ActiveRecord::Base
  belongs_to :schedule
end

So now you can do this:

@date = Schedule.find_by_date('1/1/2012')

@date.doctor.name

When you create a Schedule instance,  you could do this:

def create
  @schedule = Schedule.new(params[:schedule])
  @doctor = Doctor.find(params[:doctor])
  @schedule << @doctor
  @schedule.save
end

The new view would have a pulldown menu where you select the doctor,  Then a form for the schedule model.

To make it have a date range,  you could remove the date attribute from the schedule form,  and add two date fields OUTSIDE the schedule form, start_date, end_date,  and do something like this:

def create
  @doctor = Doctor.find(params[:doctor]) 
  @start  = Time.new(params[:start_date][0]....   # I forget the exact sequence
  @end = Time.new(params[:end_date]....  # ditto 
  @range = @start..@end
  @range.each do |date|
    @schedule = Schedule.new(params[:schedule])
    @schedule.date = date
    @schedule << @doctor
    @schedule.save
  end
end

Joe got a job, on the day shift, at the Utility Muffin Research Kitchen, arrogantly twisting the sterile canvas snout of a fully charged icing anointment utensil.

Re: Getting confused declaring models and their associations

Thanks again Brad. I'll go with that last option, it's becoming a lot more clear.

Last question... what would my view look like to have those input fields that do not correspond with the model, yet expose them to the controller?

Re: Getting confused declaring models and their associations

Here's how I'd do it. http://www.bosin.info/g.gif

Re: Getting confused declaring models and their associations

Which language is this C sharp?




High School Diploma

Last edited by johnw2738 (2012-04-03 11:12:23)