Non resourceful routing and dynamic segmentation - ruby-on-rails

I have this in my route file
get '/registrations/:student_id/:subject_id' => "registrations#show", :as => 'custom'
Now I want to use this in link_to helper so that I can send student_id and subject_id to show action of the controller
<%= link_to "Custom" .... %>

Assuming you have instance variables #student_id and #subject_id availeble to your view, then this should work:
<%= link_to "Custom", custom_path(#student_id, #subject_id) %>

looks like similar to this question, the same solution can be applied. Custom dynamic routing and get ids from url

Related

Rails navigation helper method

I have two rails helper on my application helper:
def active_class(link_path)
current_page?(link_path) ? 'active' : ''
end
def active_class_white(link_path)
current_page?(link_path) ? 'active-white' : ''
end
One is for regular links the other one is for the submenus. Usually I place the link like this:
<%= link_to "Home", root_path(:anchor => 'home'), class: "nav-link #{active_class('/')}", :"data-id" => "home" %>
Now here's my problem. On my homepage I got this link where it will slide to a particular section of the site thus requires a character like #about. If I place:
<%= link_to "About", root_path(:anchor => 'about'), class: "nav-link #{active_class('/#about')}", :"data-id" => "about" %>
It's still putting the active class on the home text instead of the about (the homepage is a one page slider type).
Another thing is that for complicated url like the devise edit profile, I tried to put the ff:
<%= link_to "Edit Profile", edit_user_registration_path(current_user), class: "dropdown-item #{active_class_white('/users/edit/:id')}" %>
Placing /users/edit/:id doesn't work on this kind of URL: http://localhost:3000/users/edit.13
On this two kinds of URL my code doesn't work. Any idea how to make them work or turn this around?
Anchors are purely client-side and are not sent along with the request to the server. So, the only way to implement the first part of your question is through Javascript. You can listen for a click event on links then add the active class to the one that was clicked.
The second part of your question, where you pass in the :id segment key, can be solved by passing a route helper (along with an object) to current_page? instead of an explicit string...
class: <%= active_class(edit_user_registration_path(current_user)) %>

Rails - redirect to different page in same path

In my Rails project, I have two different pages that exist within the same path - one is an index of stores, the other is a store update page (though I don't use those exact names for them). The problem that I am having is that I am trying to add dynamic links to the index page for each store to take a user to the associated update page, but I created the routes manually (rather than use :resources) and both pages are listed under the same path in my Rails routes summary. How can I use the <%= link_to %> helper in this situation?
First off, here is the relevant routing information...
stores_study_sites_path GET /stores/study_sites(.:format) stores#study_sites
GET /stores/store_details/:id(.:format) stores#store_details
And from my routes file...
get 'stores/study_sites' => 'stores#study_sites'
get 'stores/store_details/:id' => 'stores#store_details'
The first route, 'study_sites' is an index page, 'store_details' is the update page.
The redirect is rendered as a partial on the study_sites page...
<% #store.each do |store| %>
<ul>
<li>
<%= store.name %></br>
<%= store.street %></br>
<%= store.city %> <%= store.state %></br>
<%= render "shared/store_details", :store => store %>
</li>
</ul>
<% end %>
And finally, the partial that I would like to use, but does not currently work...
<%= link_to "Build store profile", stores_study_sites_path(store.id) %>
The urls generated from this look like http://localhost:3000/stores/study_sites.26 whereas I need them to be http://localhost:3000/stores/store_details/26
I've gone through this basic procedure for a number of other redirects with no problem, but I've created these custom urls/routes, and now I'm in a bit of a pickle. In a situation like this, how do I specify which url in the path I want the link to route to?
As a follow-up question (keep in mind I'm really new to Rails), why is the store_details page falling under the stores_study_sites_path?
Thank you very much.
Be RESTful
When starting out with Rails try to avoid falling off the band wagon - most real world problems can be solved with the standard CRUD routes and RESTful representations. When you start creating a bunch of custom routes just for different representations then the quality tends to dip sharply.
A better URL scheme would be:
/stores # index of stores
/stores/1 # show a single store
/stores/1/details # index of details of a store.
/stores/1/details is what you would call a nested resource. Its very clear from the URL that we are looking something which belongs to a store.
You can declare the routes with:
resources :stores, shallow: true do
resources :details
end
You can then create a link to the details of a store with:
<%= link_to "Build store profile", store_details_path(#store) %>
http://guides.rubyonrails.org/routing.html#nested-resources
You can name your routes manually:
get 'stores/study_sites' => 'stores#study_sites', as: "first_route"
get 'stores/store_details/:id' => 'stores#store_details', as: "second_route"
Then use them:
<%= link_to "one", first_route_path %>
## this will generate http://localhost:3000/stores/study_sites
<%= link_to "two", second_route_path(5) %>
## this will generate http://localhost:3000/stores/store_details/5
You really should put this setup within the context of your controller in the routes:
#config/routes.rb
resources :stores do
get :study_sites, on: :collection #-> url.com/stores/study_sites
get :store_details, on: :member #-> url.com/stores/:id/store_details
end
... and then in the view:
<%= link_to "x", stores_store_sites_path %>
<%= link_to "y", stores_store_details_path(store.id) %>

How can i send an extra parameter with my link_to

My view contains this link to redirect to the index page for people.
<%= link_to 'No', '/people' %>
I want to send an extra flag to the index method of the people controller so it will do something extra in case this link is clicked. I've tried a ton of different things, none of which work. I tried using the more complicated syntax with :controller => :people_controller, :action => :index...but since i'm coming from the show view it sends the ID and messes up my routes.
How can i send an extra parameter with this link_to?
<%= link_to 'No', people_path(extra_parameter: "Veg") %>

Links and routes in Rails

Rails 4.1
Ruby 2.1.1
I have an application where I need to display a link to the controller show method. As far as I know, something like this will do it:
<%= link_to "Agent", agents_path(:id => agent.id), :class => "btn btn-warning" %>
But when Rails generates the link, it's this:
http://mydomain/agents?id=9
What I need is
http://mydomain/agents/9.
When I enter this manually, I get the agents/show view. How do I get there?
In my routes, I do not have anything special for agents. Here's the relevant code from routes.rb:
resources :agents
Which means it will generate all the routes.
rake routes output:
agents GET /agents(.:format) agents#index
POST /agents(.:format) agents#create
new_agent GET /agents/new(.:format) agents#new
edit_agent GET /agents/:id/edit(.:format) agents#edit
agent GET /agents/:id(.:format) agents#show
PATCH /agents/:id(.:format) agents#update
PUT /agents/:id(.:format) agents#update
DELETE /agents/:id(.:format) agents#destroy
and I did not get any errors generating the routes
Solution:
Apologies, but I was using agent_path, not agents_path. I did try agents_path at one point, as one of the things I tried. The problem is that I had two different views. In one, I was using the correct syntax:
<%= link_to "Agent", agent_path(agent.id), :class => "btn btn-warning" %>
and in the other I was using:
<%= link_to "Agent", agents_path(:id => agent.id), :class => "btn btn-warning" %>
I kept making changes to one of them, when the other was actually the one being rendered. I put the correct syntax in a partial and now it's working fine. The moral of the story is to always use partials, even when you think you don't need them.
You want agent_path instead of agents_path, and you don't need to specify the id. This will work just fine:
<%= link_to "Agent", agent_path(agent), :class => "btn btn-warning" %>
Whenever in doubt about what the routes are, you can always run:
bundle exec rake routes
And you'll be able to see all existing routes, and their naming.
Routing
Something you need to consider is the resourceful nature of Rails' routing:
Every time you create a resources part of the Rails routing structure, you're actually telling rails to build the above routes. This is standard practice, and means you'll be able to call article_path(article.id) as default functionality.
I believe your problem stems from this idea:
<%= link_to "Agent", agents_path(:id => agent.id), :class => "btn btn-warning" %>
--
Reference
As mentioned, you're referencing agents_path (plural), when it should be agent_path (singular).
However, you're also defining the :id parameter in the route helper itself. This can just be handled by passing the object itself to the helper:
<%= link_to article.title, article_path(article.id) %>
Or, more succinctly, Rails is able to determine the path based on the resource you pass it (hence why I mentioned resourceful routes structure):
<%= link_to article.title, article %>
This will you autimagically to the show action of the articles controller.
Simply pass your record to link_to, this will automatically generate a link to its view page
= link_to 'Agent', agent
Agent
You can do much more by using the record, example if you need a link to the edit page
= link_to 'Agent', [:edit, agent]
Agent
And so on... This technique is very useful when writing helpers that must be compatible with different models

link_to problem

I want to display product count in a link_to, the link_to is a part of partial displayed in application.erb.html, the problem is, I have a method in my application controller named products_on_cart which return products count, when I try this code:
<%= link_to "<%= products_on_cart%>", :controller=>"carts", :action=>"index"%>
rails give me an error:
"syntax error, unexpected '>'
...er=>"carts", :action=>"index"%>"
I don't really understand why, can somebody help me?
You can't use <%= .. %> inside of <%= .. %>.
<%= link_to products_on_cart, [:carts] %>
You're nesting ERb tags. Make sure products_on_cart() is available as a helper method, then rewrite your link_to code without nested ERb tags as follows:
<%= link_to products_on_cart(), :controller => "carts", :action => "index" %>
To make products_on_cart() a helper method, either move it to app/helpers/application.rb, or declare it as a helper in your controller:
def products_on_cart()
# method definition goes here
end
helper_method :products_on_cart
If you only need to access products_on_cart from your views and not from your controllers, putting it in app/helpers/application.rb is the preferred way to go. If you need to use it in both controllers and views, use the helper_method approach above instead.

Resources