Rails Helper create unintended Array ouput - ruby-on-rails

I have created a rails helper method, So far so good the only problem is it created an unexpected array ouput.
I did try the key value pair using the each method but the array still there.
I'm trying to figure it out how to remove the unexpected array
My application_helper.rb
def bid_items(origin, destination)
item = Item.where(item_deliver_from: origin).where(item_deliver_to: destination).where(shopper_id: current_user)
end
My search_results.html.rb
<%= bid_items(trip.origin, trip.destination).each do |item| %>
<div class="card border-0">
<%= image_tag item.cover_image_url(:cover_image_medium), class: "card-img-top" %>
<div class="card-body">
<h5 class="card-title"><%= item.name %></h5>
</div>
</div>
<% end %>
Though I got the intended results still, there's an unexpected array
check the image
I just want to remove this area
See Red X

Remove = sign from <%= bid_items(trip.origin, trip.destination).each do |item| %>
So, make it <% bid_items(trip.origin, trip.destination).each do |item| %>

Related

Strange output from rails each do

Rails each do method is acting strangely and I do not know why.
controller
def index
#fabric_guides = FabricGuide.with_attached_image.all.order(:name)
end
index.html.erb
<div class="guide-items">
<%= #fabric_guides.each do |fabric| %>
<div class="guide-container">
<%= link_to fabric_guide_path(slug: fabric.slug) do %>
<%= image_tag fabric.image if fabric.image.attached? %>
<% end %>
<div class="guide-info">
<p class="g-name">
<%= link_to fabric.name,
fabric_guide_path(slug: fabric.slug) %>
</p>
</div>
</div>
<% end %>
</div>
I have two FabricGuide records so I expect two "guide-container" but I get three. Or more precisely I get two guide containers and a third block of text containing all the content from the last FabricGuide record.
I have almost an identical setup for articles and have never encountered this problem. I'd happily share more information if needed. Thank you!
Please remove = equal sign from your each loop of view code
like below :-
<% #fabric_guides.each do |fabric| %>
...
...
<% end %>
you have used this <%= #fabric_guides.each do |fabric| %> in your view that's why it shows all record in DOM.
The expression for erb tags is <% %>
now if we want to print that tag too then we apply <%= %>

I want to display a random object

I want to display a random object in cards.
<div class="row">
<% #slots.sample(3).each do |slot| %>
<div class="col-md-4 col-sm-6">
<div class="card-image">
<%= link_to slot_path(slot) do %>
<% if slot.photo? %>
<%= cl_image_tag slot.photo, class: "img-rounded img-responsive", height: 262, width: 195 %>
<% else %>
<%= image_tag "image_placeholder.jpg", class: "fileinput-new thumbnail img-no-padding", height: 250, width: 400 %>
<% end %>
<% end %>
<div class="details">
<div class="author">
<%= link_to slot_user(slot) do %>
<%= cl_image_tag slot.user.photo, class: "img-circle img-no-padding img-responsive" %>
<span class="name"><%= slot.name %></span>
<span class="meta"><%= slot.user.first_name %> <%= slot.user.last_name %></span>
<% end %>
</div>
</div>
</div>
</div>
<% end %>
</div>
My code returns error messages like:
"undefined method `sample' for nil:NilClass",
"undefined method `photo' for nil:NilClass",
"undefined method `user' for nil:NilClass"
I don't understand. Can you help me?
You can randomize your #slots collection in the conntroller, eg:
#slots = Slot.where(id: Slot.pluck(:id).sample(3))
Then use directly in the view
<% #slots.each do |slot| %>
Getting a random object in Ruby on Rails (ActiveRecord) is not well documented but it is fairly easy.
There is the obvious: take two random objects from any array:
#users = User.all
#users.sample(2)
This will get all objects from the db, put them in an array (#users) from which two random objects are picked. If you happen to need all objects in an array this is fine. If not, you better go for something better:
User.order('RANDOM()').limit(2)
This will only read two entries from the db, using a random order. It is therefore much easier on the db than the first command.
The command syntax works for PostgreSQL - use 'RAND()' for MySQL.
There is one thing to watch out for and that is a default_scope. If you have set a default_scope for the obj class use reorder instead:
User.reorder('RANDOM()').limit(2)

Rails - conditional display of html block

On my views I use 1 form that includes a block that renders comments. I do not want to run it when creating a new record. So, I tried conditions like so...
<% unless #annotation_id.nil? %>
<hr>
<div class="row">
<div class="col-md-8">
<h4>Comments</h4>
<%= render #annotation.comments %>
</div>
<div class="col-md-4">
<%= render 'comments/form' %>
</div>
</div>
<% end %>
This however results in never displaying the block - also when the annotation record exists. What am I doing wrong?
You don't show that you have actually set #annotation_id to something.
A simpler way might be to use the .new_record? method instead, like:
<% unless #annotation.new_record? %>
...
<% end %>
use if #annotation.persisted? or unless #annotation.new_record?

Rendering only authorized (Devise) user data in Rails without excess empty space

I am trying to create a todo app that will allow the user to create lists and then "todo" items under each list. However, I want each user to only be able to see his or her lists. While I've been able to partially solve it using the current_user helper, the index page shows empty space where the other users lists are hidden.
Below please find the code for the index.html.erb page inside my todo_lists views.
<% #todo_lists.each do |todo_list| %>
<div class="index_row clearfix">
<% if todo_list.user == current_user %>
<h2 class="todo_list_title"><%= link_to todo_list.title, todo_list %></h2>
<p class="todo_list_sub_title"><%= todo_list.description %></p>
<p><%= todo_list.user.first_name %></p>
<% end %>
</div>
<% end %>
<div class="links">
<%= link_to "New Todo List", new_todo_list_path %>
</div>
Here's my repo on Github, in case you need to see more of the code: https://github.com/jramoscolon/todo
Is there a way to hide these empty spaces, as well as the non-matching todo items?
Given your current view code, you are indiscriminately emitting <div class="index_row clearfix"> elements, even when the todo_list.user does not match the current_user. Simply move the whole<div> outside the current_user check, like so:
<% #todo_lists.each do |todo_list| %>
<% if todo_list.user == current_user %>
<div class="index_row clearfix">
<h2 class="todo_list_title"><%= link_to todo_list.title, todo_list %></h2>
<p class="todo_list_sub_title"><%= todo_list.description %></p>
<p><%= todo_list.user.first_name %></p>
</div>
<% end %>
<% end %>
This way, all of those empty <div> elements aren't included on the page. This should clean up all that empty space.
If your index view is user specific than the instance variable you want should be user specific as well.
Instead of #todo_lists = ToDoList.all
Use the current_user.todo_lists functionality supplied by your has_many/belongs to

How can I reference the name of the previous array item in this Rails ERB mark-up loop?

I am a Rails noob. I am generating a menu in an ERB template, looping through the array "elements":
<% #elements.each do |element| -%>
<div class="category <%= element.category.color %>">
</div>
<% end %>
I want to add an additional class to each item (except the first, obviously), referencing the element.category.color of the PREVIOUS item, so that the final mark-up looks like:
<div class="category blue">I am the first, no extra class</div>
<div class="category green after-blue">I come after blue</div>
<div class="category yellow after-green">I come after green</div>
This is all basically a work-around to avoid using next-sibling CSS selectors, which are slow as hell in some of the browsers I need to support, and causing rendering problems when changing the background colours of the items.
Can I add the class I want directly in the ERB, or will I need to also use the controller to calculate it?
You can do this
<% #elements.each_with_index do |element, index| -%>
<div class=<%= "category #{element.category.color} " + ("after-#{#elements[index-1].category.color}" unless index == 0) %>>
</div>
<% end %>
Another way:
<% prev = '' %>
<% #elements.each do |element| -%>
<div class=<%= "category #{element.category.color}#{' after-' + prev if prev.present?}" %>>
<% prev = element.category.color %>
</div>
<% end %>

Resources