Jingle Bell Rails: Associations and Nested Forms All the Way

Grace Yuiko Nakano
3 min readDec 25, 2020

--

What a rewarding project to complete by Christmas! I had so much fun creating this Ruby on Rails application. There were many challenges but I learned so much in the process, including the the wonderful convenience of the Active Record method, build, and nested forms.

I developed an application for musicians, where active contractors and musicians could connect for the same concern; finding work and finding employees . Users have access to a listing of gigs, authorization to submit applications upon interest of gigs, and views to fellow musician and contractor’s profiles. Users have the option to sign up as a contractor and are given authorization to post gigs, receive requests for gigs from applicants, and a direct link to the applicant’s page. These features aid the contractor in the hiring process.

Developing the associations with the desired features was the first challenge. Thanks to many draw.io drafts and my friends in the Flatiron cohort, I concluded on 5 models with belongs_to, has_many, has_many: :through, and many to many relationships to establish the desired functions.

I initially struggled to figure out how to make my model associations work based on my set user attributes. The User model has a contractor attribute with a boolean datatype that defaults to false, providing the user the option to sign up as contractor.

In order to allow different functions for the type of user, I set my associations so that a Gig could belong_to :user AND has_many :users, through: :requests.

class Gig < ApplicationRecord

belongs_to :user

has_many :gig_instruments
has_many :instruments, through: :gig_instruments
has_many :requests
has_many :users, through: :requests

end

and

class User < ApplicationRecord

has_many :requests
has_many :posted_gigs, through: :requests, source: :gigs

has_many :gigs
end

I had issues when calling has_many :gigs, through: :requests because it conflicted with my has_many: gigs association. That made sense because there was no way for Rails to know which association I was referring to when querying the database. With source:, I was able to distinguish these associations by renaming to :posted_gigs while providing the source, :gigs to distinguish the associations on the User model.

Developing functioning nested forms was another trip. The Form Builder, fields_for creates a scope around another object outside of its class in which it is associated with. So in reference to my models, a gig is associated to instruments by has_many :instruments. With fields_for , we can nest a form inside the Gig form and scope in on the instrument class and its attributes to create instruments with a gig object. That’s it, right? WELL now in your controllers, you need ensure that you have instantiated this newly associated object in the new action in the Gigs Controller.

What if we want to make sure that this new instrument form that is nested inside the gig form is associated to a user? No problem! In the controllers, we can query IF the nested user is in fact the current user that I would like to create this new gig object on, then we can instantiate that object and instantiate the object to build an instrument on the gig form.

class GigsController < ApplicationController

def new
if params[:user_id] && @user = User.find_by_id(params[:user_id])
@gig = @user.gigs.build
else
@gig = Gig.new
end
@gig.instruments.build
end

and then in the views:

<%= form_for @gig do |f| %>
<%= f.label :title %>
<%= f.text_field :title %>
<%= f.label :datetime %>
<%= f.datetime_local_field :datetime %>
.
.
.
.
<p>Instruments required: </p>
<%= f.label “Select Existing Instrument”%>

<%= f.collection_check_boxes :instrument_ids, Instrument.all, :id, :name %>

<p> Or create new Instrument: </p>

<%=f.fields_for :instruments, @gig.instruments.build do |i| %>
<%= i.label :name %>
<%= i.text_field :name %>
<% end %>
<%= f.submit %><% end %>

Building this project challenged me to explore and expand my knowledge on Rails. I look forward to ringing into the new year with Javascript!

Sign up to discover human stories that deepen your understanding of the world.

Free

Distraction-free reading. No ads.

Organize your knowledge with lists and highlights.

Tell your story. Find your audience.

Membership

Read member-only stories

Support writers you read most

Earn money for your writing

Listen to audio narrations

Read offline with the Medium app

--

--

Grace Yuiko Nakano
Grace Yuiko Nakano

Written by Grace Yuiko Nakano

Fullstack Software Engineer | Musician | Food Lover | Coffee Addict

No responses yet

Write a response