How do I stop rails from dumping the entire model in the view in the index method?
Here is my code:
def index
#topics = Topic.all
end
Here is my view
https://41.media.tumblr.com/1bcf55f478094c4ef82cda7676551ffe/tumblr_nsosrw1eRI1r3syg3o1_540.png
(sorry for the bad quality but the dump is at the bottom)
If I'm not mistaken you're adding an '=' in the tag, something like this:
<%= #topics.each do |topic| %>
<%= topic.title %>
<% end %>
when you want this:
<% #topics.each do |topic| %>
<%= topic.title %>
<% end %>
Related
I've got an application.html.erb where I want move calculation of unread user messages into some decorator/helper, basically because it looks like this:
<% if current_user %>
<%= link_to 'Messages', conversations_path %>
<% counter = #conversations.map do |conversation| %>
<% unless conversation.unread_message_count(current_user).zero? %>
<% conversation.unread_message_count(current_user) %>
<% end %>
<% end %>
(<%= counter.sum %>)
I know the basic concept of decorators but I'm wondering if I have ConversationDecorator in app/decorators/conversation_decorator.rb with defined counter method with #conversations.map block there, how to use this decorator inside of application.html.erb ?
Example ConversationDecorator:
class ConversationDecorator < ApplicationDecorator
def unread_counter
#conversations.map do |conversation|
conversation.unread_message_count(current_user) unless conversation.unread_message_count(current_user).zero?
end.sum
end
end
I have a loop that looks like this
<% #user.collections.each do |collection| %>
<h1 class="impact"> <%= collection.name %><br></h1>
<%= collection.stories.count %>
<% end %>
It works perfectly to show the Collections that belongs to a User, and then show how many Stories are in each Collection.
However, I want to use a helper that does this.
in the view
<% #user.collections.each do |collection| %>
<h1 class="impact"> <%= collection.name %><br></h1>
<%= number_of_stories_in_collection %>
<% end %>
in the helper
module CollectionsHelper
def number_of_stories_in_collection
collection.stories.count
end
def render_stories_count
if number_of_stories_in_collection.zero?
'No stories in this collection yet'
else
"#{number_of_stories_in_collection} #{'story'.pluralize(number_of_stories_in_collection)}"
end
end
end
I get an error that says
undefined method `stories' for #<Collection::ActiveRecord_Relation:0x007f510f504af8>
Any help is appreciated, thanks!
The 'collection' variable isn't an instance variable, so the helper can't see it.
Change your view to this:
<% #user.collections.each do |collection| %>
<h1 class="impact"> <%= collection.name %><br></h1>
<%= number_of_stories_in(collection) %>
<% end %>
And your helper method to:
def number_of_stories_in(collection)
collection.stories.count
end
This way you are passing the variable to the helper correctly.
extending #Richard's answer and little bit of optimisation to avoid n+1 queries..
<% #user.collections.includes(:stories).each do |collection| %>
<h1 class="impact"> <%= collection.name %><br></h1>
<%= render_stories_count(collection) %>
<% end %>
helper:
module CollectionsHelper
def number_of_stories_in(collection)
collection.stories.length
end
def render_stories_count(collection)
if (count = number_of_stories_in(collection)).zero?
'No stories in this collection yet'
else
"#{count} #{'story'.pluralize(count)}"
end
end
end
i'm new into ruby on rails and i want to assign a variable to make an each like this
<% 3.times do |calendar| %>
<% test = #lessons_calendar %>
<% test.each do |lesson| %>
display html here
<% end %>
<% end %>
The thing is that in my controller i have assigned 3 variables like this #lessons_1 #lessons_2 and #lessons_3 but when i run the code it says undefined method `each' for nil:NilClass, how can i join the number created by calendar to the new variable ? Thanks
Instead of below
<% 3.times do |calendar| %>
<% test = #lessons_calendar %>
<% test.each do |lesson| %>
display html here
<% end %>
<% end %>
Make changes in your controller as well as in view as below
Controller Code
# take new variable
#lessons = []
#lessons << #lessons_1
#lessons << #lessons_2
#lessons << #lessons_3
Now do code in view file as below
<% #lessons.each do |lesson| %>
<% lesson.each do |ls| %>
your code here
<%end%>
<%end%>
Hope this will help you.
<% 3.times do |calender| %>
<%= #lessons_calendar.collect{ |lesson| Write Your Code Here }.join("").html_safe rescue 'No Record' %>
<% end %>
With in the collect iterator you can assign it to instance var if you want to. Thanks
This is so simple but isnt working. What am I missing?
controlelr
#guide = Guide.friendly.find(params[:guide_id])
#category = #guide.categories.friendly.find params[:id]
#items = #category.category_items
view
<% #items.each do |item| %>
<%= item.category_item_values.value %>
<% end %>
gives the no method error of
undefined method 'value' for #<CategoryItemValue::ActiveRecord_Associations_CollectionProxy:0x007ff9706d24c0>
There is a values column in the category_item_values table so I'm not sure what the problem is.
item.category_item_values is the CollectionProxy instance (one might think of it as of an kinda array.)
Each category_item has [likely, you did not provide sufficiently enough info to guess more precisely] many values. If the assumption above is correct, here you go:
<% #items.each do |item| %>
<% item.category_item_values.each do |value| %>
<%= value %> # or maybe (depending on your model) <%= value.value %>
<% end %>
<% end %>
You will have to loop over each of the category_item_values to get the result as this suggests <CategoryItemValue::ActiveRecord_Associations_CollectionProxy:0x007ff9706d24c0> that your category_item_value is a association.
So you could do something like
<% item.category_item_values.each do |category_item_value| %>
<%= category_item_value.value %>
<% end %>
In this case which pattern will be faster?
Obviously Pattern1 with helper looks much more sophisticated and looks clean.
But it send SQL every time when user_link method is called.
Here it calls up to 100times at one page loading.
Which way would be better for benchmark performance?
Pattern1. With helper
application_helper
def user_link(username)
link_to User.find_by_username(username).user_profile.nickname, show_user_path(username)
end
view
<% #topics.order("updated_at DESC").limit(100).each do |topic| %>
<%= user_link(topic.comment_threads.order("id").last.user.username) if topic.comment_threads.present? %>
<% end %>
Pattern2. Without helper. Just only view
<% #topics.order("updated_at DESC").limit(100).each do |topic| %>
<%= link_to(topic.comment_threads.order("id").last.user.nickname, show_user_path(topic.comment_threads.order("id").last.user.username) ) if topic.comment_threads.present? %>
<% end %>
try
# Topics model
#via scope
scope :get_topic_list, lambda do
order("updated_at DESC").joins(:comment_threads => :user).limit(100)
end
#via method
def self.get_topic_list
Topic.order("updated_at DESC").joins(:comment_threads => :user).limit(100)
end
# in your controller or move to model itself (recommened)
#topics = Topic.get_topic_list
# in you view
<% #topics.each do |topic| %>
<%= link_to(topic.comment_threads.order("id").last.user.nickname, show_user_path(topic.comment_threads.order("id").last.user.username) ) if topic.comment_threads.present? %>
<% end %>