I'd like some seasoned veteran advice on how I can find my answer. I know I have too much of the logic in my view, and I'm repeating myself but I'm still trying to "learn by doing" and this is about where I'm at to just get it working and I would learn how to refactor from there of course.
I want to iterate over a logistics created and if the logistics_title (passed through by a form of either "X", "Y", or "Z") matches "X" then display X in a div otherwise don't display anything.
<div class="container-fluid">
<div class="row-fluid">
<div class="span4 hero-unit">
<% #logistics.each do |logistic| %>
<% if logistic.logistic_title = "Practice" %><br>
<%= logistic.logistic_title %>
<%= logistic.user.full_name %>
<%= logistic.content %><br>
<%= link_to time_ago_in_words(logistic.created_at) + " ago", logistic %> |
<%= link_to "Edit", edit_logistic_path(logistic) %> |
<%= link_to "Remove", logistic, method: :delete, data: { confirm: "Remove? This action cannot be undone."} %>
<% else %>
<%= puts "" %>
<% end %>
<% end %>
</div>
<div class="span4 hero-unit">
<% #logistics.each do |logistic| %>
<% if logistic.logistic_title = "Game" %><br>
<%= logistic.logistic_title %>
<%= logistic.user.full_name %>
<%= logistic.content %><br>
<%= link_to time_ago_in_words(logistic.created_at) + " ago", logistic %> |
<%= link_to "Edit", edit_logistic_path(logistic) %> |
<%= link_to "Remove", logistic, method: :delete, data: { confirm: "Remove? This action cannot be undone."} %>
<% else %>
<%= puts "" %>
<% end %>
<% end %>
</div>
<div class="span4 hero-unit">
<% #logistics.each do |logistic| %>
<% if logistic.logistic_title = "Etc." %><br>
<%= logistic.logistic_title %>
<%= logistic.user.full_name %>
<%= logistic.content %><br>
<%= link_to time_ago_in_words(logistic.created_at) + " ago", logistic %> |
<%= link_to "Edit", edit_logistic_path(logistic) %> |
<%= link_to "Remove", logistic, method: :delete, data: { confirm: "Remove? This action cannot be undone."} %>
<% else %>
<%= puts "" %>
<% end %>
<% end %>
</div>
I know I'll need to write some helper stuff but a point in the right direction helps.
Please be gentle, this is how I learn.
Thanks for taking a look and for your attention.
You're right in that there's a lot of duplicated code and logic in your view. If I were going to do this myself, I'd probably change the controller so that your #logistics instance variable is split up into three instance variables, based on the title:
#practice = #game = #etc = []
#logistics.each do |logistic|
if logistic.title == 'Practice'
#practice << logistic
elsif logistic.title == 'Game'
#game << logistic
elsif logistic.title == 'Etc.'
#etc << logistic
end
end
Regarding helpers, I think the link_to and logistic_edit_path helpers will generally be created for your helper if you're writing a standard Rails App and your Controller names matches the Model, so you shouldn't need to add those yourself.
Be careful not to use single equals (=) when you mean the equality operator. I think your code probably should look like this:
<div class="container-fluid">
<div class="row-fluid">
<div class="span4 hero-unit">
<% #logistics.each do |logistic| %>
<% if logistic.logistic_title == "Practice" %>
<br>
<%= logistic.logistic_title %>
<%= logistic.user.full_name %>
<%= logistic.content %><br>
<%= link_to time_ago_in_words(logistic.created_at) + " ago", logistic %> |
<%= link_to "Edit", edit_logistic_path(logistic) %> |
<%= link_to "Remove", logistic, method: :delete, data: { confirm: "Remove? This action cannot be undone."} %>
<% else %>
<%= puts "" %>
<% end %>
<% end %>
</div>
<div class="span4 hero-unit">
<% #logistics.each do |logistic| %>
<% if logistic.logistic_title == "Game" %><br>
<%= logistic.logistic_title %>
<%= logistic.user.full_name %>
<%= logistic.content %><br>
<%= link_to time_ago_in_words(logistic.created_at) + " ago", logistic %> |
<%= link_to "Edit", edit_logistic_path(logistic) %> |
<%= link_to "Remove", logistic, method: :delete, data: { confirm: "Remove? This action cannot be undone."} %>
<% else %>
<%= puts "" %>
<% end %>
<% end %>
</div>
<div class="span4 hero-unit">
<% #logistics.each do |logistic| %>
<% if logistic.logistic_title == "Etc." %><br>
<%= logistic.logistic_title %>
<%= logistic.user.full_name %>
<%= logistic.content %><br>
<%= link_to time_ago_in_words(logistic.created_at) + " ago", logistic %> |
<%= link_to "Edit", edit_logistic_path(logistic) %> |
<%= link_to "Remove", logistic, method: :delete, data: { confirm: "Remove? This action cannot be undone."} %>
<% else %>
<%= puts "" %>
<% end %>
<% end %>
</div>
Related
Hi i am currently using Collection_select like so , and as you can see its working properly but i want to make it, so that when i pick 1 item from the Item field that the data from my database , bought price and sold price would automatically be added into the textfields like in the example below.
but as to how i can do it, remains a mystery to me, can anybody help me with this and thanks! any help will be helpful! and thanks again!
the code that i used
<%= form_for(#sale) do |f| %>
<% if #sale.errors.any? %>
<div id="error_explanation">
<h2><%= pluralize(#sale.errors.count, "error") %> prohibited this sale from being saved:</h2>
<ul>
<% #sale.errors.full_messages.each do |message| %>
<li><%= message %></li>
<% end %>
</ul>
</div>
<% end %>
<div class="field">
<%= f.label :item_id %><br>
<%= collection_select( :sale, :item_id, Item.all, :id, :name, {} ) %>
</div>
<div class="field">
<%= f.label :bought %><br>
<%= f.text_field :bought %>
</div>
<div class="field">
<%= f.label :sold %><br>
<%= f.text_field :sold %>
</div>
<div class="field">
<%= f.label :number %><br>
<%= f.number_field :number %>
</div>
<div class="actions">
<%= f.submit %>
</div>
<% end %>
you can do this by send ajax request and bought data from database then show "bought price" and "sold price" in there respective fields. Something like that
$("#collection_select_id").change(function () {
$.ajax({
url: "your_url_where_you_get_your_data",
method: "GET",
data: {},
success: function(data) {
$("#bought_price_id").val(data.bought_price)
$("#sold_price_id").val(data.sold_price)
}
});
});
Thanks
How to send data in database and show in needed part by using json format in ruby on rails3?
my form is like this
<%= form_for(#user) do |f| %>
<% if #user.errors.any? %>
<div id="error_explanation">
<h2><%= pluralize(#user.errors.count, "error") %> prohibited this user from being saved:</h2>
<ul>
<% #user.errors.full_messages.each do |msg| %>
<li><%= msg %></li>
<% end %>
</ul>
</div>
<% end %>
<div class="field">
<%= f.label :name %><br />
<%= f.text_field :name %>
</div>
<div class="field">
<%= f.label :email %><br />
<%= f.text_field :email %>
</div>
<div class="field">
<%= f.label :login %><br />
<%= f.text_field :login %>
</div>
<div class="actions">
<%= f.submit %>
</div>
<% end %>
In the controller:
def show
#user = User.find(params[:user_id]
respond_to do |format|
format.json { :render => #user }
end
end
You can customise the JSON output by overriding the as_json in the User model:
def as_json(options=false)
self.include_root_in_json = false
options = (options || {}).reverse_merge(
:except => [:updated_at, :created_at, :id],
:include => :some_association
)
super(options)
end
I have the following two _forms:
user form
<%= simple_form_for(#user, :url => #target) do |f| %>
<% if #user.errors.any? %>
<div id="error_explanation">
<h2><%= pluralize(#user.errors.count, "error") %> prohibited this user from being saved:</h2>
<ul>
<% #user.errors.full_messages.each do |msg| %>
<li><%= msg %></li>
<% end %>
</ul>
</div>
<% end %>
<%= f.input :email, :label => "User Email" %>
<%= f.input :password, :label => "User Password" %>
<%= f.input :first_name %>
<%= f.input :last_name %>
<%= f.button :submit %>
<% end %>
tenant form
<%= simple_form_for(#tenant, :url => #target) do |f| %>
<% if #tenant.errors.any? %>
<div id="error_explanation">
<h2><%= pluralize(#tenant.errors.count, "error") %> prohibited this tenant from being saved:</h2>
<ul>
<% #tenant.errors.full_messages.each do |msg| %>
<li><%= msg %></li>
<% end %>
</ul>
</div>
<% end %>
<%= f.input :name, :label => 'Name', :required => true %>
<%= f.input :billing_email, :label => 'Email', :required => true %>
<%= f.input :country, :label => 'Country', :required => true %>
<%= f.button :submit %>
<% end %>
I have come across the following post from stackoverflow f.error_messages in Rails 3.0
Here there is method so that error messages can be returned from the simple form by using f.error_messages but I have been unable to get this working as I am unsure whereabout this method should be saved. Anyone got any hints? The method is as follows:
class StandardBuilder < ActionView::Helpers::FormBuilder
def error_messages
return unless object.respond_to?(:errors) && object.errors.any?
errors_list = ""
errors_list << #template.content_tag(:span, "There are errors!", :class => "title-error")
errors_list << object.errors.full_messages.map { |message| #template.content_tag(:li, message) }.join("\n")
#template.content_tag(:ul, errors_list.html_safe, :class => "error-recap round-border")
end
end
Just add error: false to your inputs this will not clear the css but will clear the inline errors
f.input error: false
Edit:
From http://ruby.railstutorial.org/book/ruby-on-rails-tutorial
/app/views/shared/_error_messages.html.erb
<% if object.errors.any? %>
<div id="error_explanation">
<div class="alert alert-error">
The form contains <%= pluralize(object.errors.count, "error") %>.
</div>
<ul>
<% object.errors.full_messages.each do |msg| %>
<li>* <%= msg %></li>
<% end %>
</ul>
</div>
<% end %>
in VIEW
<%= form_for(#user) do |f| %>
<%= render 'shared/error_messages', object: f.object %>
<%= f.label :name %>
<%= f.text_field :name %>
<%= f.label :email %>
<%= f.text_field :email %>
<%= f.label :password %>
<%= f.password_field :password %>
<%= f.label :password_confirmation, "Confirmation" %>
<%= f.password_field :password_confirmation %>
<%= f.submit "Create my account", class: "btn btn-large btn-primary" %>
<% end %>
The following view shows a single post and its comments:
views/posts/show.html.erb:
<h2>posts show</h2>
<span>Title: <%= #post.title %></span><br />
<span>Content: <%= #post.content %></span><br />
<span>User: <%= #post.user.username %></span><br />
<div class="post-<%= #post.id %>">
<h3><span class="vote-count"><%= #post.total_votes %></span> votes</h3><br />
<div class='voted-user'>
<% #post.votes.each do |vote| %>
<%= link_to vote.user.username, vote.user %>
<% end %>
</div>
<%= link_to "Vote Up", vote_up_path(#votable, :votable_type => "Post"), :remote => true, :class => "vote-up" %><br />
<%= link_to "Vote Down", vote_down_path(#votable, :votable_type => "Post"), :remote => true, :class => "vote-down" %><br />
<h2>Comments</h2>
<p><%= link_to 'Order by Date', post_path(#post, :order_by => "created_at ASC") %></p>
<p><%= link_to 'Order by Votes', post_path(#post, :order_by => "total_votes DESC") %></p>
<% #comments.map do |comment| %>
<div class="comment-<%= comment.id %>">
<p>
<b>Comment:</b>
<%= comment.content %>
</p>
<p>
<b>Vote:</b>
<span class="vote-count"><%= comment.total_votes %></span>
<div class='voted-user'>
<% comment.votes.each do |vote| %>
<%= link_to vote.user.username, vote.user %>
<% end %>
</div>
</p>
<p>
<b>Commenter</b>
<%= link_to comment.user.username, comment.user %>
</p>
<p>
<b>Link</b>
<%= link_to "Show Post Comment", [#post, comment] %>
</p>
<p>
<b>Vote</b>
<%= link_to "Vote Up", vote_up_path(comment, :votable_type => "Comment"), :remote => true, :class => "vote-up" %><br />
</p>
</div>
<% end %>
<%= will_paginate #comments %>
<h2>Add a comment:</h2>
<%= form_for([#post, #post.comments.build]) do |f| %>
<div class="field">
<%= f.label :content %><br />
<%= f.text_area :content %>
</div>
<div class="actions">
<%= f.submit %>
</div>
<% end %>
<% if current_user.id == #post.user_id %>
<%= link_to 'Edit', edit_post_path(#post) %> |
<% end %>
<%= link_to 'Back', posts_path %>
I just focused on making things work so I totally forgot to make it clean.
I'm a Rails beginner and I would like some suggestions or advises to clean this view
(if you suggest to move code to another file please mention the name of the file and the directoy). Thanks in advance.
Good on you for wanting to clean it up. This is some of what I would do. I've included some examples of a few things here: Partials, Helpers, and also cleaned up the HTML a little to allow more control over the style in your stylesheets (which I left out, but you can figure out that part I'm sure). If this was my project, I would extract everything even more (for example, I would probably move the entre "edit/back" links at the bottom, as well as the "Order" links, to their own partials or helpers, since I would probably be using them in a lot of places throughout the application.) And if your comments are polymorphic (i.e., not just for posts), then definitely move that into its own view file. Also, I did this a rather quickly, so it might have some errors, sorry if you find any.
_post.html.erb
<article class="post-info">
<span class="title"><b>Title:</b> <%= post.title %></span>
<p><%= post.content %></p>
<span class="user"><b>User:</b> <%= post.user.username %></span>
</article>
<div class="post" id="post-<%=post.id%>">
<div class="vote-count"><%= post.total_votes %></span> votes
<ul class="voted-user">
<% post.votes.each do |vote| %>
<li><%= link_to vote.user.username, vote.user %></li>
<% end %>
</ul>
<ul class="voting">
<li><%= link_to "Vote Up", vote_up_path(post, :votable_type => "Post"), :remote => true, :class => "vote-up" %></li>
<li><%= link_to "Vote Down", vote_down_path(post, :votable_type => "Post"), :remote => true, :class => "vote-down" %></li>
</ul>
_comment.html.erb
<div class="comment" id="comment-<%=comment.id%>">
<article class="comment">
<b>Comment:</b> <%= comment.content %>
</article>
<div class="votes-total">
<b>Votes:</b> <span class="vote-count"><%= comment.total_votes %></span>
<ul class='voted-user'>
<% comment.votes.each do |vote| %>
<li><%= link_to vote.user.username, vote.user %></li>
<% end %>
</ul>
</div>
<div class="commenter">
<b>Commenter:</b> <%= link_to comment.user.username, comment.user %>
</div>
<div class="link">
<b>Link:</b> <%= link_to "Show Post Comment", [comment.post, comment] %>
</div>
<div class="vote">
<b>Vote:</b> <%= link_to "Vote Up", vote_up_path(comment, :votable_type => "Comment"), :remote => true, :class => "vote-up" %>
</div>
</div> <!-- .comment -->
show.html.erb
<h2>Posts</h2>
<%= render #post %>
<h2>Comments</h2>
<ul class="order">
<li><%= link_to 'Order by Date', post_path(#post, :order_by => "created_at ASC") %></li>
<li><%= link_to 'Order by Votes', post_path(#post, :order_by => "total_votes DESC") %></li>
</ul>
<%= render #comments %>
<%= will_paginate #comments %>
<h2>Add a Comment</h2>
<%= form_for([#post, #post.comments.build]) do |f| %>
<div class="field">
<%= f.label :content %>
<%= f.text_area :content %>
</div>
<div class="actions">
<%= f.submit %>
</div>
<% end %>
<ul class="manage">
<li><%= edit_link_if_allowed(current_user, #post) %></li>
<li><%= link_to 'Back', posts_path %></li>
</ul>
Posts Helper
def edit_link_if_allowed(current_user, post)
link_to "Edit", edit_post_path(post) if post.user_id == current_user.id
end
You could use Partials
Hi
Im working with a form and have added :remote => true to the form and the destroy link. But when I do that this happends:
I submit the form and it makes 2 versions that are the same.
I destroy, I get prompted twice?
If i remove the :remote => true it only makes one version and only prompt once.
This is my form
<%= form_for([#comment], :remote => true) do |f| %>
<% if #comment.errors.any? %>
<div id="error_explanation">
<h2><%= pluralize(#comment.errors.count, "error") %> prohibited this comment from being saved:</h2>
<ul>
<% #comment.errors.full_messages.each do |msg| %>
<li><%= msg %></li>
<% end %>
</ul>
</div>
<% end %>
<div class="field">
<%= f.label :title %>
<br/>
<%= f.text_field :title %>
</div>
<div class="field">
<%= f.label :body %>
<br/>
<%= f.text_area :body %>
</div>
<div class="field">
<%= f.hidden_field :user_id %>
<%= f.hidden_field :retailer_id %>
<%= f.hidden_field :product_id %>
</div>
<div class="actions">
<%= f.submit %>
</div>
<% end %>
This is my destroy link
<%= link_to 'Destroy', comment, :confirm => 'Are you sure?', :method => :delete, :remote => true %>
Am I doing something very wrong here? Thanks in advance!
I think you have included your rails.js file twice. that might be the problem. check it.