I am working with an open source school management software, Fedena and I am trying to sort a list of users by their surnames. The software currently shows all users with their first names. I've found these two files to be responsible for showing the information I intend to change.
student_controller.rb
def list_students_by_course
#students = Student.find_all_by_batch_id(params[:batch_id], :order => 'last_name ASC')
render(:update) { |page| page.replace_html 'students', :partial => 'students_by_course' }
end
When I delete the above section of the file, the users names don't show up so I believe this section to be responsible for populating the table with the usernames.
_students_by_course.erb
<div class="students-table">
<table align="center" width="100%" cellpadding="1" cellspacing="1">
<tr class="tr-head">
<td><%= t('sl_no') %></td>
<td><%= t('name') %></td>
<td><%= t('adm_no') %></td>
<td></td>
</tr>
<tr>
<td></td>
<td></td>
<td></td>
<td></td>
</tr>
<% #students.each_with_index do |r, i| %>
<tr class="tr-<%= cycle('odd', 'even') %>">
<td class="col-1">
<%= i+1 %>
</td>
<td class="col-2">
<%= link_to r.full_name,:controller => "student", :action => "profile", :id => r.id %>
</td>
<td class="col-1">
<%= r.admission_no %>
</td>
<td class="col-7">
<%= link_to "#{t('view_profile')}", :controller => "student", :action => "profile", :id => r.id %>
</td>
</tr>
<% end %>
</table>
</div>
I have tried changing 'last_name ASC' to 'last_name DESC' but nothing changed.
Any help is appreciated.
You've clarified in the comments that you want not sort order (I take it you've figured that out?) but the format of full name displayed for each instance of a model Student.
It's not hard if traced to the source. Let's start with a view, since that's what we see.
#students.each_with_index do |r, i|
We start a loop, each iteration of which processes an entry r with an index i. Since we're looping on a collection of Students (seems like a valid assumption), r is an instance of Student. The problematic line is:
<%= link_to r.full_name,:controller => "student", :action => "profile", :id => r.id %>
Actually, we should only look at r.full_name since that's what we get as a link label. It's a Student's method. Here it is.
def full_name
"#{first_name} #{middle_name} #{last_name}"
end
You might be wondering where is a second space, since such implementation implies that if middle_name is absent, we'd have two. Look at the source of the page and you'll see that there are actually two! So in order to change how the full name looks, you'll have to modify this method.
Related
I have been fighting this for a while.
I have a simple app that use users, timesheets and entries. timesheets belong to to users and an user has many time sheets. Entries belong to time sheets.
A user can click on a time sheet and be presented with the entries from that time sheet. I can create entries in the rails console and they show up correctly. But I am having trouble inserting the correct timesheet ID on the entries.
I may not be doing this correctly, but I have a link on the time sheet view to the entry view. I am having trouble bringing over the time sheet id to insert it in the the create entry view.
I am using a form_for that looks like this.
<%= form_for(:entry, :url => {:action => 'create'}) do |f| %>
<table summary="Subject form fields">
<tr>
<th>Customer</th>
<td><%= f.text_field(:customer_name) %></td>
</tr>
<tr>
<th>Order Number</th>
<td><%= f.text_field(:order_number) %></td>
</tr>
<tr>
<th>Time In</th>
<td><%= f.text_field(:time_in) %></td>
</tr>
<tr>
<th>Time Out</th>
<td><%= f.text_field(:time_out) %></td>
</tr>
<tr>
<th>Time Sheet ID</th>
<td><%= f.text_field(:time_sheet_id, :value => #sheet_id ) %></td>
</tr>
</table>
<div class="form-buttons">
<%= submit_tag("Add Entry") %>
</div>
<% end %>
This is my entry controller.
def create
#time_id = TimeSheet.find(1)
#new_entry = Entry.new(entry_params)
if #new_entry.save
flash[:notice] = "New Entry has been Added!"
redirect_to(:action => 'index')
else
render('new')
end
end
Do instead:
#new_entry = time_id.build_entry(entry_params)
Sorry, I Am closing this.
It was poorly worded and I figured out the problem.
All I needed to do is run the form_for from my timesheets controller and redirect it to the entries controller.
I am trying to find my time sheet id to pass into a form_for
here is my controller
def show
#time_id = current_user.time_sheets.find(params[:id])
if current_user
#current = current_user.time_sheets
else
redirect_to new_user_session_path, notice: 'You are not logged in.'
end
end
This is my form_for in my view:
<%= form_for(:entry, :url => {:controller => Entry, :action => 'create'}) do |f| %>
<table summary="Subject form fields">
<tr>
<th>Customer</th>
<td><%= f.text_field(:customer_name) %></td>
</tr>
<tr>
<th>Order Number</th>
<td><%= f.text_field(:order_number) %></td>
</tr>
<tr>
<th>Time In</th>
<td><%= f.text_field(:time_in) %></td>
</tr>
<tr>
<th>Time Out</th>
<td><%= f.text_field(:time_out) %></td>
</tr>
<tr>
<th>Time Sheet ID</th>
<td><%= f.hidden_field :time_sheet_id, value: #time_id.id %></td>
</tr>
</table>
<div class="form-buttons">
<%= submit_tag("Add Entry") %>
</div>
<% end %>
What needs to happen is that the timesheet id needs to get passed into the form_for so the entry can have the timesheet id.
I have user, timesheets and entries. user has_many time sheets, timesheets belongs to users and users have many time sheets. Entry belongs to timesheet.
I am getting this error "Couldn't find TimeSheet without an ID"
You should use "Nested Resources", eg. see here: Rails 3: How to create a new nested resource?
You could use form_for([#timesheet, #entry]) to pass the id of the timesheet without using a hidden field. If you do this, the :url param also become obsolete.
Try adding:
<%= #time_id.id %>
to output your variable and make sure it's exactly what you think it is. If #time_id is a timesheet, you should probably rename that variable to #time_sheet.
i am using vestal_version in my rails app. And i am wondering how do I show the previous versions edit links with respect to what is at the above entry. My html.erb code is
<tbody>
<% #page.versions.each do |page| %>
<tr class="odd">
<td><input type="checkbox" /></td>
<td> </td>
<td><%= page.created_at%></td>
<td>
<% if params[:version] %>
<%= link_to "Previous Version", :version => #page.version-1 %>
<%end%>
</td>
</tr>
</div>
<% end %>
and in controller i have #page.revert_to(params[:version].to_i) if params[:version]
I have attached a link to the screenshot. And if closely observe. the ?version=5 for all the entries. I want to have all the versions that is 1,2,3,4 and 5. How do i do that ?
Update : Image is hyper linked in the comment. I am not allowed add an image as of now.
Use page instead of #page.
<%= link_to "Previous Version", :version => page %>
page changes with each iteration, while #page stays the same.
EDIT:
Since #page.versions.each iterates a collection of versions, it should be passed into the block as version, not page.
<% #page.versions.each do |version| %>
<tr class="odd">
<td><input type="checkbox" /></td>
<td> </td>
<td><%= version.created_at%></td>
<td>
<%= link_to "Show Version", :version => version %>
</td>
</tr>
<% end %>
This method only shows the version. Actually reverting a version should be done via POST, since you are making changes to the database.
Reverting negates changes, it does not discard changes. If page is at version 4, and you revert to version 2, it does not delete versions 3 and 4. The version number will revert to 2, but will count as a version itself.
#revert_to does the reversion but does not save. To revert and save, use #revert_to!
To properly use #revert_to!, you need to put it in a controller action.
Example, in your pages controller:
def revert
#page = Page.find params[:id]
if #page.revert_to!(params[:version_id]) # <= revert_to!
redirect_to #page
else
render :text => "Did not revert"
end
end
In your routes.rb:
resources :pages do
member do
post 'revert_to/:version_id' => 'pages#revert', :as => :revert
end
end
then in your view:
<% #page.versions.each do |version| %>
<tr class="odd">
<td><input type="checkbox" /></td>
<td> </td>
<td><%= version.created_at %></td>
<td>
<%= link_to "Show Version", :version => version %>
</td>
<td>
<%= button_to "Revert to this version", revert_page_path(#page, version.id) %>
</td>
</tr>
<% end %>
Beneficiaries
id (PK)
name
age
income
Beneficiary_loans
id (PK)
beneficiary_id (FK)
amount
rate
period
What I'm doing is, selecting a list of beneficiary from [Beneficiaries] table and displaying as follows
<%= form_tag({:action => 'update_survey_list_status', :status=>4}) do %>
<table width="100%">
<tr>
<th>Beneficiary Details</th>
<th>Amount</th>
<th>Rate</th>
<th>Period</th><th>
<input type='checkbox' name='checkall' onclick='checkedAll();'>
</th>
</tr>
<% #publishedlist.each do |b| %>
<tr>
<td><%= b.firstname %></td>
<%= fields_for :beneficiaryloan do |bloan| %>
<td> <%= bloan.text_field :amount%></td>
<td> <%= bloan.text_field :rate%></td>
<td> <%= bloan.text_field :period%></td>
<% end %>
<td><%= check_box_tag "benificiary_ids[]",b.id, :name => "benificiary_ids[]"%> </td>
</tr>
<% end %>
</table> <%= submit_tag "Approve", :class=>'form_buttons' %>
<% end %>
In controller,
#beneficiaries=Beneficiary.find(:all, :conditions => ["id IN (?)", params[:benificiary_ids]])
#beneficiaries.each do |b|
#beneficiaryloan = Beneficiaryloan.new(params[:beneficiaryloan])
#beneficiaryloan.beneficiary_id=b.id
#beneficiaryloan.hfi_id=session[:id].to_s
#beneficiaryloan.status_id=params[:status]
#beneficiaryloan.save
end
What I'm not getting is
params[:beneficiaryloan]
Values are coming as NULL
Am I missing something here in this form?
Check the following,
With the help of any browser tool(eg:firebug), make sure that the form has been rendered properly. Sometimes due to some misplaced tags(generally happens with table structure) the form does not renders properly.
Try to remove the table structure and see if the form works.
Make sure your association is fine, i guess it should be Beneficiary has many Beneficiaryloan
If none of the above helps, please post the request parameters over here.
Learning rails and something smells a little funny.
I have the following form for updating quantities in a shopping cart.
<% form_for(:cart, #cart.items, :url => { :action => "update_cart" }) do |f| %>
<table>
<tr>
<th>Item</th>
<th>Quantity</th>
<th>Price</th>
</tr>
<% for item in #cart.items %>
<% f.fields_for item, :index => item.id do |item_form| %>
<tr>
<td><%=h item.title %></td>
<td><%=item_form.text_field :quantity, :size => 2 %>
<span># <%=h number_to_currency(item.item_price) %></span></td>
<td><%=h number_to_currency(item.line_price) %></td>
</tr>
<% end %>
<% end %>
<tr>
<td colspan="2">Total:</td>
<td><%=h number_to_currency(#cart.total_price) %></td>
</tr>
</table>
<%=submit_tag 'Update Cart' %>
<% end %>
In my update_cart action, I iterate through the existing cart items and set the new quantity:
def update_cart
#cart = find_cart
#cart.items.each do |item|
quantity = params[:cart][:cart_item][item.id.to_s][:quantity].to_i
#cart.update_quantity_for(item, quantity)
end
redirect_to :action => 'cart'
end
I dont have a REST interface controller for carts or cart items. Is there a better way to deal with this deep params data structure? The expression params[:cart][:cart_item][item.id.to_s][:quantity].to_i strikes me as dangerous for invalid form data.
The correct way to do this is the use the "accepts_nested_attributes" attribute in the cart model. Then you can just use CartController's update method to save your items. (http://railscasts.com/episodes/196-nested-model-form-part-1)
Also, your total price should probably be a method defined in the Cart model.