Rails 5: Displaying object value not ID - ruby-on-rails

I have a simple app for a skydiving dropzone. Parachute packers keep track of their packsjobs. There are several packjobs for each parachute rig.
I have the Show view working perfectly by showing the rig_type_number under the rig detail (ie Reflex #2) but I can only get the rig_id to work in the same column for the index. Ideally, I'd like to so the rig_type_number as well instead of the ID.
How can I reference in the view something to the effect of #rigs.rig_type_number?
This makes sense to me, but does not work:
<td><%= link_to packjob.rig_id,rig_path(rig.rig_type_number) %>
Will I have to a where clause for the index controller?
db:
class CreatePackjobs < ActiveRecord::Migration[5.1]
def change
create_table :packjobs do |t|
t.string :packer
t.string :rig
t.references :rig, foreign_key: true
t.timestamps
end
end
end
class CreateRigs < ActiveRecord::Migration[5.1]
def change
create_table :rigs do |t|
t.boolean :rig_status
t.string :rig_type_number
t.integer :rig_season_jumpnum
t.date :rig_res_last
t.string :rig_res_who
t.timestamps
end
end
end
packjobs_controller:
class PackjobsController < ApplicationController
def index
#packjobs = Packjob.paginate(page: params[:page]).order('id DESC')
#rigs = Rig.where(rig_status: "t")
end
def show
#packjob = Packjob.find(params[:id])
#rig = Rig.find(#packjob.rig_id)
end
def new
#packjob = Packjob.new
#rigs = Rig.where(rig_status: "t")
end
def edit
#packjob = Packjob.find(params[:id])
#rigs = Rig.where(rig_status: "t")
end
def create
#packjob = Packjob.new(packjob_params)
#rigs = Rig.where(rig_status: "t")
if #packjob.save
redirect_to #packjob
else
render 'new'
end
end
def update
#packjob = Packjob.find(params[:id])
#rigs = Rig.where(rig_status: "t")
if #packjob.update(packjob_params)
redirect_to #packjob
else
render 'edit'
end
end
def destroy
#packjob = Packjob.find(params[:id])
#packjob.destroy
redirect_to packjobs_path
end
private
def packjob_params
params.require(:packjob).permit(:packer, :rig_id)
end
def rigs_params
params.require(:rig).permit(:rig_status, :rig_type_number)
end
end
show.html.erb:
<p>
<b>Datestamp:</b>
<%= #packjob.created_at.strftime("%m/%d/%Y %I:%M %P") %><br>
</p>
<p>
<strong>Packer:</strong>
<%= #packjob.packer %>
</p>
<p>
<strong>Rig:</strong>
<%= #rig.rig_type_number %><br>
</p>
<%= link_to 'Edit', edit_packjob_path(#packjob) %> |
<%= link_to 'Back', packjobs_path %>
index.html.erb:
<h1>Listing Packjobs</h1>
<%= link_to 'New Packjob', new_packjob_path %> | <br>
<br>
<div class="digg_pagination">
<%= will_paginate #packjobs, :container => false %>
</div>
<table id=listtable CELLPADDING="4" border="1">
<tr class="headerBlue" >
<th>Datestamp</th>
<th>Packer</th>
<th>Rig</th>
<th colspan="3"></th>
</tr>
<% #packjobs.each do |packjob| %>
<tr class="<%= cycle('rowA', 'rowB') %>">
<td><%= link_to packjob.created_at.strftime("%m/%d/%Y %I:%M:%S %P"),packjob_path(packjob.id) %></td>
<td><%= packjob.packer %></td>
<td><%= link_to packjob.rig_id,rig_path(packjob.rig_id) %>
<td><%= link_to 'Show', packjob_path(packjob) %></td>
<td><%= link_to 'Edit', edit_packjob_path(packjob) %></td>
<td><%= link_to 'Destroy', packjob_path(packjob),
method: :delete,
data: { confirm: 'Are you sure?' } %></td>
<% end %>
</tr>
</table>
<div class="digg_pagination">
<div class="page_info">
<%= page_entries_info #packjobs %>
</div>
<%= will_paginate #packjobs, :container => false %>
</div>
<br><%= link_to 'New Packjob', new_packjob_path %> |
EDITED:
models:
class Packjob < ApplicationRecord
belongs_to :rig
validates :packer, presence: true
validates :rig_id, presence: true
self.per_page = 25
end
class Rig < ApplicationRecord
has_many :packjobs
validates :rig_type_number, presence: true
self.per_page = 25
end

Your associations are set correctly, you can reference the associated object like this:
<td><%= link_to packjob.rig.rig_type_number,rig_path(packjob.rig_id) %>

You can call it as below in case you have has_one :rig association in PackJob model :
<td><%= link_to packjob..rig.rig_type_number,rig_path(packjob.rig_id) if packjob.rig.present? %> </td>

Related

Rails: Search bar isn't working

I'm trying to add a search bar for a database website I created, I found a tutorial and I "think" I did it correct.
When I do a search, such as "Judy Zhang", nothing shows up, even though it is in the database
my vendor.rb/concerns/models/app file
class Vendor < ApplicationRecord
has_many :fotos
def self.search(search)
if search
Vendor.where('lower(contact_name) LIKE ?', "'%#{search.downcase}%'")
else
Vendor.all
end
end
end
I believe I didn't do the coding right. Very new to ruby on rails. What did I do wrong here?
code for index.html.erb/vendors/views/layouts/app
<body>
<div class = "head">
<h1>Vendors </h1>
<div class = "image1" >
<img src= "http://dx.deucex.com/i/logo.png" >
</div>
</div>
</body>
<table>
<tr>
<%= button_to "New Vendor", new_vendor_path, :method => "get" %>
<%= button_to "Inventory", inventories_path, :method => "get" %>
<%= form_tag vendors_path, :method => 'get' do %>
<%= text_field_tag :search, params[:search] %>
<%= submit_tag "Search", :name => nil %>
<% end %>
</tr>
</table>
<table>
<tr>
<th>Company</th>
<th>Contact Name</th>
<th>Phone</th>
<th>Email</th>
</tr>
<% for vendor in #vendors %>
<tr>
<td><%= vendor.company %></td>
<td><%= vendor.contact_name %></td>
<td><%= vendor.phone %></td>
<td><%= vendor.email %></td>
<body>
<div class = "button1" >
<td><%= button_to "Show", vendor_path(vendor), :method => "get" %></td>
</div>
</body>
<td><%= button_to "Edit", edit_vendor_path(vendor), :method => "get" %></td>
<div class = "button3">
<td><%= button_to 'Delete',
vendor_path(vendor),
method: :delete,
data: { confirm: 'Are you sure?'} %></td>
</div>
</tr>
<% end %>
</table>
code for my VendorsController.rb/concerns/controller/app
class VendorsController < ApplicationController
def index
#vendors = Vendor.search(params[:search])
end
def show
#vendor = Vendor.find(params[:id])
end
def new
#vendor = Vendor.new
end
def create
#vendor = Vendor.new(vendor_params)
if #vendor.save
redirect_to #vendor
else
render 'new'
end
end
def edit
#vendor = Vendor.find(params[:id])
end
def update
#vendor = Vendor.find(params[:id])
if #vendor.update (vendor_params)
redirect_to #vendor
else
render 'edit'
end
end
def destroy
#vendor = Vendor.find(params[:id])
#vendor.destroy
redirect_to vendors_path
end
end
private
def vendor_params
params.require(:vendor).permit(:company, :contact_name, :phone, :email, :moq, :cost_per_item, :payment_method, :terms, :turnover, :returns, :notes)
end
Try changing the code in Vendor to
class Vendor < ApplicationRecord
has_many :fotos
def self.search(search)
if search
Vendor.where('lower(name) LIKE ?', "'%#{search.downcase}%'")
else
Vendor.all
end
end
end
My search bar isn't showing up
You should change the following
<% form_tag vendors_path, :method => 'get' do %>
to
<%= form_tag vendors_path, :method => 'get' do %>
# Notice that <%= %> evaluates and prints the output

undefined 'items' for nil class

on my e-store website when I try to checkout my cart, I'm getting
undefined method `items' for nil:NilClass.
Although on the error page
I know that my cart is there... but when I call it, it gives me nil
Cart Model
class Cart
attr_reader :items
def self.build_from_hash hash
items = if hash["cart"] then
hash["cart"]["items"].map do |item_data|
CartItem.new item_data["product_id"], item_data["quantity"]
end
else
[]
end
new items
end
def initialize items = []
#items = items
end
def add_item product_id
item = #items.find { |item| item.product_id == product_id }
if item
item.increment
else
#items << CartItem.new(product_id)
end
end
def empty?
#items.empty?
end
def count
#items.length
end
def serialize
items = #items.map do |item|
{
"product_id" => item.product_id,
"quantity" => item.quantity
}
end
{
"items" => items
}
end
def total_price
#items.inject(0) { |sum, item| sum + item.total_price }
end
end
Application Controller
def initialize_cart
#cart = Cart.build_from_hash session
end
Cart Controller
class CartsController < ApplicationController
before_filter :initialize_cart
def add
#cart.add_item params[:id]
session["cart"] = #cart.serialize
product = Product.find params[:id]
redirect_to :back, notice: "Added #{product.name} to cart."
end
def show
end
def checkout
#order_form = OrderForm.new user: User.new
end
end
Order Controller
class OrdersController
def create
#order_form = OrderForm.new(
user: User.new(order_params[:user]),
cart: #cart
)
if #order_form.save
redirect_to '/', notice: "Thank you for placing your order."
#cart.empty?
else
render 'carts/checkout'
end
end
Checkout View
<div class="container-checkout">
<p class="text-title"> You are checking out the following: </p>
<table class="table table-striped">
<thead class="name-table">
<tr>
<td> Image </td>
<td> Name </td>
<td> Category</td>
<td> Size </td>
<td> Item Price </td>
</tr>
</thead>
<tbody>
<% #cart.items.each do |item| %>
<tr>
<td><img src="<%= item.product.image %>" width="50px"></td>
<td><%= item.product.name.capitalize %></td>
<td><%= item.product.category.name %></td>
<td><%= item.product.size %></td>
<td class="price-item"><%= number_to_currency item.total_price %>
</td>
<% end %>
</tr>
<tr class="total-price total-price-checkout">
<td class="name-table">Total Price</td>
<td class="price-item"><%= number_to_currency #cart.total_price %></td>
</tr>
</tbody>
</table>
</div>
<div class="details-user-form">
<%= form_for #order_form, url: orders_path do |f|%>
<% f.fields_for :user, #order_form.user do |u| %>
<p class="text-title">Fill the form with your details</p>
<p><%= render "orders/errors" %></p>
<p><%= u.text_field :name, placeholder: "Name" %></p>
<p><%= u.text_field :email, placeholder: "Email" %></p>
<p><%= u.text_field :address, placeholder: "Address" %></p>
<p><%= u.text_field :postal_code, placeholder: "Postal code" %></p>
<p><%= u.text_field :city, placeholder: "City" %></p>
<p><%= u.text_field :country, placeholder: "Country" %></p>
<%= f.submit "Place order", class: "order-btn"%><br>
<% end %>
<% end %>
</div>
Any idea of why is it doing so? Also because, it was working before.. I don't know why it stopped.
I think the problem may be that the #cart variable isn't being set in the OrdersController. Setting the variable in CartsController doesn't make it available globally, as it would only be scoped to the controller that created it, in your case the CartsController.
Also, I see that your Cart model is more of a virtual model than an ActiveRecord model, is that the behaviour you were looking for as I believe ActiveRecord already has a lot of the methods you're recreating there.
I'm not totally sure but I think these may be the issues.
UPDATE
I think I found your error.
In your OrdersController you should have a
before_action :initialize_cart
That seems to be coming from your ApplicationController
If you check your checkout method in your CartController, you will see that you did not set #cart. So when you hit the checkout view, it comes to look for the value or #cart in this method. Setting it there, like the code below should clear your error.
def checkout
#order_form = OrderForm.new user: User.new
#cart = # cart object
end

How to fix level.rb to work with :committed days?

Originally I had :committed days working beautifully, but upon changing up the models a bit in order to accommodate the User's ability to check off if he missed a :committed day I now get an error message for the code relating to :committed:
undefined method to_date for nil:NilClass
Line #30 n_days = ((date_started.to_date)..Date.today).count { |date| committed_wdays.include? date.wday }
This code comes from the habit model:
class Habit < ActiveRecord::Base
belongs_to :user
has_many :levels
has_many :days, through: :levels #for being able to access Habit.find(*).days
accepts_nested_attributes_for :levels, :days
before_save :set_level
acts_as_taggable
serialize :committed, Array
def evaluate(user)
levels.each { |level| level.evaluate }
user.missed_levels << levels.where(passed: false).ids
user.missed_days << days.where(missed: true).ids
user.save
end
def self.committed_for_today
today_name = Date::DAYNAMES[Date.today.wday].downcase
ids = all.select { |h| h.committed.include? today_name }.map(&:id)
where(id: ids)
end
def levels
committed_wdays = committed.map { |day| Date::DAYNAMES.index(day.titleize) }
n_days = ((date_started.to_date)..Date.today).count { |date| committed_wdays.include? date.wday }
case n_days
when 0..9
1
when 10..24
2
when 25..44
3
when 45..69
4
when 70..99
5
else
"Mastery"
end
end
private
def set_level
self.level = levels
end
end
The logic behind it all is that a User creates a habit he wants to challenge. To achieve "mastery" in the habit he must complete 5 levels. Each level has a certain amount of :committed days that must be completed before advancing, as broken down above with n_days.
The User commits in the _form to what days (Sun thru Sat) he wants to do the habit. For example he could just choose sun, wed, sat. Then the app should only calculate n_days according to non-:missed :committed days (once 10 of those days passes it moves onto the 2nd level).
class Level < ActiveRecord::Base
belongs_to :habit
belongs_to :user
has_many :days
accepts_nested_attributes_for :days
def evaluate
if days.where(missed: true ).count == days_needed
update_attributes(passed: false)
else
update_attributes(passed: true)
end
end
end
class Day < ActiveRecord::Base
belongs_to :level
belongs_to :habit
end
class HabitsController < ApplicationController
before_action :set_habit, only: [:show, :edit, :update, :destroy]
before_action :logged_in_user, only: [:create, :destroy]
def index
if params[:tag]
#habits = Habit.tagged_with(params[:tag])
else
#habits = Habit.all.order("date_started DESC")
#habits = current_user.habits
end
end
def show
end
def new
#goal = current_user.goals.build
#habit = current_user.habits.build
#level = current_user.levels.build
3.times { #level.days.build }
end
def edit
end
def create
#habit = current_user.habits.build(habit_params)
#levels = #habit.levels
if #habit.evaluate(#user)
redirect_to #habit, notice: 'Habit was successfully created.'
else
#feed_items = []
render 'pages/home'
end
end
def update
if #habit.update(habit_params)
redirect_to #habit, notice: 'Habit was successfully updated.'
else
render action: 'edit'
end
end
def destroy
#habit.destroy
redirect_to habits_url
end
private
def set_habit
#habit = Habit.find(params[:id])
end
def correct_user
#habit = current_user.habits.find_by(id: params[:id])
redirect_to habits_path, notice: "Not authorized to edit this habit" if #habit.nil?
end
def habit_params
params.require(:habit).permit(
:user_id,
:level,
:left,
:date_started,
:trigger,
:target,
:positive,
:negative,
:tag_list,
:committed => [],
:levels_attributes => [
:passed,
:days_attributes => [
:missed,:level_id]])
end
end
<%= simple_form_for(#habit) do |f| %>
<%= f.error_notification %>
<div class="america">
<form>
<div class="committed">
<%= f.label "Committed to:" %>
<%= f.collection_check_boxes :committed, Date::DAYNAMES, :downcase, :to_s %>
</div>
<p>
<div class="date-group">
<label> Started: </label>
<%= f.date_select :date_started, :order => [:month, :day, :year], class: 'date-select' %>
</div>
</p>
<p>
<%= f.text_field :trigger, class: 'form-control', placeholder: 'Enter Trigger' %></p>
<p>
<%= f.text_field :tag_list, habit: #habit.tag_list.to_s.titleize, class: 'form-control', placeholder: 'Enter Action' %>
</p>
<p>
<%= f.text_field :target, class: 'form-control', placeholder: 'Enter Target' %>
</p>
<p>
<%= f.text_field :positive, class: 'form-control', placeholder: 'Enter Reward' %>
</p>
<% 5.times.each_with_index do |number, index| %>
<h1>Level <%= index + 1 %></h1>
<%= f.fields_for :levels do |level| %>
<%= level.fields_for :days do |day| %>
<%= day.label :missed %>
<%= day.check_box :missed %> <br/>
<% end %>
<% end %>
<% end %>
<div class="america2">
<%= button_tag(type: 'submit', class: "btn") do %>
<span class="glyphicon glyphicon-plus"></span>
<% end %>
<%= link_to habits_path, class: 'btn' do %>
<span class="glyphicon glyphicon-chevron-left"></span>
<% end %>
<%= link_to #habit, method: :delete, data: { confirm: 'Are you sure?' }, class: 'btn' do %>
<span class="glyphicon glyphicon-trash"></span>
<% end %>
</div>
</form>
</div>
<% end %>
<!-- Default bootstrap panel contents -->
<div id="valuations" class="panel panel-default">
<div class="panel-heading"><h4><b>HABITS</b></h4></div>
<!-- Table -->
<table>
<thead>
<tr>
<th>Level</th>
<th>Left</th>
<th>Strike</th>
<th>Trigger</th>
<th>Action</th>
<th>Target</th>
<th>Reward</th>
<th>Days</th>
</tr>
</thead>
<tbody>
<% #habits.each do |challenged| %>
<tr>
<td><%= challenged.level %></td>
<td><%= challenged.left %></td>
<td>
<%= link_to edit_habit_path(challenged) do %>
<%= [params[:missed]].flatten.length %>
<% end %></td>
<td><%= challenged.trigger %></td>
<td class="category">
<b><%= raw challenged.tag_list.map { |t| link_to t.titleize, taghabits_path(t) }.join(', ') %></b>
</td>
<td><%= challenged.target %></td>
<td><%= challenged.positive %></td>
<td class= "committed">
<%= challenged.committed.map { |d| d.titleize[0,3] }.join ', ' %></td>
</tr>
<% end %>
</tbody>
</table>
</div>
Thank you so much for your help!
Some of this code came from this answer here: How to integrate :missed days with :committed days in habits.rb? which messed up what worked with this answer: How to Make :level Change Based on :committed Days?
It appears that date_started is an attribute of your Habit model, probably a database column, and that there are NULLs in date_started. Open up your Rails console and see if this is the case with:
Habit.where(date_started: nil).count
If you expect that date_started should never be null, add a validation to ensure that is the case. As soon as you test the code which is saving nulls into that column, the validation errors will point you to the bug.
On the other hand, if you want to allow nulls in date_started, then rewrite your levels method to allow for that.

Rails has_and_belongs_to_many AND collection_check_boxes

So there isn't an error, my join table just isn't being populated with any information... #lead.districts returns District::ActiveRecord_Associations_CollectionProxy rather than the expected text...
Where have I made my mistake?
new.html.erb
<%= link_to("<< Back to List", {:action => 'index'}, :class => 'back-link') %>
<div class="subjects new">
<h2>Create Lead</h2>
<%= form_for(:lead, :url => {:action => 'create'}) do |f| %>
<table cellspacing="0">
<tr>
<th>First Name</th>
<td><%= f.text_field(:first_name) %></td>
</tr>
<tr>
<th>Last Name</th>
<td><%= f.text_field(:last_name)%></td>
</tr>
<tr>
<th>Phone Number</th>
<td><%= f.text_field(:phone_number)%></td>
</tr>
<tr>
<th>Email</th>
<td><%= f.text_field(:email)%></td>
</tr>
<tr>
<th>Move-in Date</th>
<td><%= f.date_field(:move_in_date, min: Date.today)%></td>
</tr>
<tr>
<th>Bedrooms</th>
<td><%= f.text_field(:beds)%></td>
</tr>
<tr>
<th>Bathrooms</th>
<td><%= f.text_field(:baths)%></td>
</tr>
<tr>
<th>Maximum Price Considered</th>
<td><%= f.text_field(:maxprice)%></td>
</tr>
<tr>
<th>Preferred Neighborhoods</th>
<td>
<%= collection_check_boxes(:lead, :district_ids, District.all.order("districts.name ASC"), :id, :name )%>
</td>
</tr>
<tr>
<th>Have you ever broken a lease?</th>
<td>
<%= f.label :broken_lease, "Yes", :value => true %>
<%= f.radio_button :broken_lease, true %>
<%= f.label :broken_lease, "No", :value => false %>
<%= f.radio_button :broken_lease, false %>
</td>
</tr>
<tr>
<th>Have you ever been convicted of a felony?</th>
<td>
<%= f.label :felon, "Yes", :value => true %>
<%= f.radio_button :felon, true %>
<%= f.label :felon, "No", :value => false %>
<%= f.radio_button :felon, false %>
</td>
</tr>
<tr>
<th>Do you have any pets?</th>
<td>
<%= f.label :pets, "Yes", :value => true %>
<%= f.radio_button :pets, true %>
<%= f.label :pets, "No", :value => false %>
<%= f.radio_button :pets, false %>
</td>
</tr>
<tr>
<th>If so, please provide a brief description</th>
<td><%= f.text_area(:pets_description)%></td>
</tr>
</table>
<div class="form-buttons">
<%= submit_tag("Create Lead") %>
</div>
<% end %>
</div>
leads_controller.rb
class LeadsController < ApplicationController
layout false
def index
#leads = Lead.order("leads.created_at DESC")
end
def show
#lead = Lead.find(params[:id])
end
def new
#lead = Lead.new
#districts = District.all.order("districts.name ASC")
end
def create
#lead = Lead.new(lead_params)
if #lead.save
redirect_to(:action => 'index')
else
render('new')
end
end
def edit
#lead = Lead.find(params[:id])
end
def update
#lead = Lead.find(params[:id])
if #lead.update_attributes(lead_params)
redirect_to(:action => 'show', :id => #lead.id)
else
render('edit')
end
end
def delete
#lead = Lead.find(params[:id])
end
def destroy
lead = Lead.find(params[:id]).destroy
flash[:notice] = "Lead '#{lead.id}' deleted successfully."
redirect_to(:action => 'index')
end
private
def lead_params
params.require(:lead).permit(:first_name, :last_name, :phone_number, :email, :move_in_date, :beds, :baths, :maxprice, :broken_lease, :felon, :pets, :pets_description, :district => [])
end
end
districts_controller.rb
class DistrictsController < ApplicationController
layout false
def index
#districts = District.order("districts.name ASC")
end
def show
#district = District.find(params[:id])
end
def new
#district = District.new
end
def create
#district = District.new(district_params)
if #district.save
flash[:notice] = "District created successfully."
redirect_to(:action => 'index')
else
render('new')
end
end
def edit
#district = District.find(params[:id])
end
def update
#district = District.find(params[:id])
if #district.update_attributes(district_params)
flash[:notice] = "District updated successfully."
redirect_to(:action => 'show', :id => #district.id)
else
render('edit')
end
end
def delete
#district = District.find(params[:id])
end
def destroy
district = District.find(params[:id]).destroy
flash[:notice] = "District '#{district.name}' deleted successfully."
redirect_to(:action => 'index')
end
private
def district_params
params.require(:district).permit(:name)
end
end
district.rb
class District < ActiveRecord::Base
has_and_belongs_to_many :leads
end
lead.rb
class Lead < ActiveRecord::Base
has_and_belongs_to_many :districts
end
Join table migration:
class CreateDistrictsLeadsJoin < ActiveRecord::Migration
def change
create_table :districts_leads, :id => false do |t|
t.integer "district_id"
t.integer "lead_id"
end
add_index :districts_leads, ["district_id", "lead_id"]
end
end
My error was in mass assigning my params (used :district should have been :district_ids)
Correct params function:
# leads_controller.rb
private
def lead_params
params.require(:lead).permit(:first_name, :last_name, :phone_number, :email, :move_in_date, :beds, :baths, :maxprice, :broken_lease, :felon, :pets, :pets_description, :district_ids => [])
end
You will need to add leads to district and districts to leads in both create methods.
def create # in LeadsController
#lead = Lead.new(lead_params)
if #lead.save
district = District.find(...) #find district to associate
district.leads << #lead #add lead to district
redirect_to(:action => 'index')
else
render('new')
end
end
#leads_controller.rb
def create
#lead = Lead.new(lead_params)
if #lead.save
selected_dis = params['lead_district_ids'] #[3,4,5]
districts = District.where(id: selected_dis).first
#check how you getting district params and use that to fetch orders.
districts.each do |d|
#lead.districts << d
#assumming your one lead can have many districts.
end
redirect_to leads_path
else
render :new
end
end

Nested class is saving but not displaying correctly.

I'm working through the rails intro guide but using 'stocks' instead of 'articles' and 'time_detlas' instead of 'comments' my issue is that it seems to be saving time_deltas correctly, I think I checked that correctly but the show of the stock just adds an extra blank row to the table of time_deltas no numbers show. Any suggestions why?
Stocks controller:
class StocksController < ApplicationController
def new
#stock = Stock.new
end
def index
#stocks = Stock.all
end
def create
# XXX Add columns for delta and current standing when we get there
# they can intiate to nil
#stock = Stock.new(stock_params)
if #stock.save
redirect_to #stock
else
render 'new'
end
end
def show
#stock = find_stock
#time_delta = #stock.time_deltas.build
end
def edit
#stock = find_stock
end
def update
#stock = find_stock
if #stock.update(stock_params)
redirect_to #stock
else
render 'edit'
end
end
def destroy
#stock = find_stock
#stock.destroy
redirect_to stocks_path
end
private
def stock_params
params.require(:stock).permit(:name, :hashtag)
end
def find_stock
return Stock.find(params[:id])
end
end
Time Delta Controller
class TimeDeltasController < ApplicationController
def create
#stock = Stock.find(params[:stock_id])
#time_delta = #stock.time_deltas.create(time_delta_params)
redirect_to stock_path(#stock)
end
private
def time_delta_params
params.require(:time_delta).permit(:start, :length)
end
end
Show for the stock
<h1> Stock </h1>
<table>
<tr>
<th>Stock</th>
<th>Hashtag</th>
</tr>
<tr>
<td><%= #stock.name %></td>
<td><%= #stock.hashtag %></td>
</tr>
</table>
<h3>TimeDeltas: </h2>
<table>
<tr>
<th>Start</th>
<th>Length</th>
</tr>
<% #stock.time_deltas.each do |time_delta| %>
<tr>
<td><%= #time_delta.start %></td>
<td><%= #time_delta.length %></td>
</tr>
<% end %>
</table>
<h3>Add a TimeDelta:</h2>
<%= form_for([#stock, #stock.time_deltas.build]) do |f| %>
<p>
<%= f.label :start %><br>
<%= f.text_field :start %>
</p>
<p>
<%= f.label :length %><br>
<%= f.text_field :length %>
</p>
<p>
<%= f.submit %>
</p>
<% end %>
<%= link_to 'Back', stocks_path%>
<%= link_to 'Edit', edit_stock_path(#stock)%>
Any help is appreciated, thank you!
just remove # from time_delta
<% #stock.time_deltas.each do |time_delta| %>
<tr>
<td><%= time_delta.start %></td>
<td><%= time_delta.length %></td>
</tr>
<% end %>
up
You need # only to be able to share this var with your view. Eg: If you add this to your show action: #time_deltas = TimeDelta.all
you can show time_deltas in your view.
like:
<% #time_deltas.each do |td|%>
<%= td.start%>
<% end %>

Resources