How to simplify this Rails helper function? - ruby-on-rails

I made this helper function in my application_helper.rb file:
def link_to_related(path)
link_to "Show", path
end
So I can use it in my forms like this:
<%= link_to_related(person_path(f.object.person)) %>
Is there a way to further simplify this so I can just say:
<%= link_to_related(:person) %>
I've been trying to get my head around this, but to no avail.
Thanks for any help.

If you're only using this helper to link to show actions, you don't need to specify the path, passing in the object should be enough:
def link_to_related(object)
link_to "Show", object
end
<%= link_to_related f.object.person %>
Although that's about as long as typing link_to "Show", f.object.person :)

Related

Why is my RoR link pointing to the wrong controller action?

I have the following in my projects_controller.rb:
def destroy
#project = Project.find_by_slug(params[:id])
#project.destroy
redirect_to projects_url
end
And I have the following in my routes.rb file:
delete "projects/:id", to: "projects#destroy", as: "destroy_project"
I have the following link (inside the show.html.erb file):
<%= link_to destroy_project_path(#project), method: :delete, class: "btn-gradient btn-red" do %>
<span>Delete Project</span>
<% end %>
Upon clicking the button, the page reloads. The show action is called upon clicking the button. I've added console logs in each method, and it is clear that the destroy action is never called.
Can anyone point me in the right direction?
the link_to helper receives 2 different sets of hashes for the options.
The first set is for things like the http method, and the second for the html attributes (class, id and so on)
The way you wrote it, you probably have method=delete in your query params, which is wrong. You have to explicitly enclose the method: :delete within its own options hash:
<%= link_to destroy_project_path(#project), { method: :delete }, class: "btn-gradient btn-red" do %>
<span>Delete Project</span>
<% end %>
If you use rails 7 with turbo framework you can try below for buttons.
<%= button_to "Delete this project", destroy_project_path(#project), method: :delete %>
Or you can try below for links.
<%= link_to destroy_project_path(#project.id) , data: { turbo_method: :delete } do %>
<span>Delete Project</span>
<% end %>
the problem that you are having is with the JS. there is a problem where something is not loading properly.
For testing try to remove your JS and use something like this
<%= javascript_include_tag "https://cdnjs.cloudflare.com/ajax/libs/jquery/3.6.0/jquery.js" %>
When you get the delete method working, then you can debug where in your JS there is a problem.
at this time there is not sufficient info on your question to be able to know what it is.

Using a custom tag helper for ruby on rails with a bootstrap navbar

My problem is that I can't get this helper tag to display at all.
So in application_helper.rb I want to have a <% nav_link(name, path) %> tag helper to append bootstrap's .active class dynamically.
My code is the following:
def nav_link(name, path)
content_tag(:li, :class => active_class(path)) do
link_to name, path
end
end
def active_class(path)
(current_page?(path) ? "active" : "").html_safe
end
and I would like to use it like so
<% nav_link("Users", users_path) %>
My hunch is that there's a variable somewhere that's not properly sanitized. How do I fix this? Is the html_safe call necessary?
Unless it's a typo, you should use <%= nav_link("Users", users_path) %>.
Without =, nothing will be displayed
I think that your problem is that you have written <% nav_link(name, path) %> this executes the code but doesn't print anything.
It should be <%= nav_link(name, path) %>
I highly recommend this Gem, it will do exactly what you want.
https://github.com/vigetlabs/nav_lynx
And here is a method it provides:
<%= nav_link_to 'Page', my_path, {}, { :wrapper => 'li' } %>

Best way to highlight current page in Rails 3? -- apply a css class to links conditionally

For the following code:
<%= link_to "Some Page", some_path %>
How do I apply a css class current using the current_page?‎ helper method?
Or if some other better way is available?
In app/helpers/application_helper.rb
def cp(path)
"current" if current_page?(path)
end
In your views:
<%= link_to "All Posts", posts_path, class: cp(posts_path) %>
Basically write a simple wrapper around it. Additionally you could extend the method to allow additional classes to be applied by adding arguments. Keeps the views concise/dry. Or, without extending the method, you could just do simple String interpolation like so to add additional classes:
<%= link_to "All Posts", posts_path, class: "#{cp(posts_path)} additional_class" %>
In my case I have a lot of name spaced controllers, that is why I like to show if the current view also is in the Menu Path, I had use the solution of Michael van Rooijen and then I customize for my case.
Helper
def cp(path)
"current" if request.url.include?(path)
end
View
<%= link_to "All Posts", posts_path, class: cp(posts_path) %>
Now if my menu bar is /users and my current page is /users/10/post also the link /users is set with "current" class
I branched off of Michael's answer and tweaked the helper:
def active_class?(*paths)
active = false
paths.each { |path| active ||= current_page?(path) }
active ? 'active' : nil
end
Here's how you'd use it:
<%= link_to "Bookings", bookings_path, class: active_class?(bookings_path) %>
You can pass multiple paths to it in case you have a tab which could be rendered by multiple views:
<%= content_tag :li, class: active_class?(bookings_path, action: 'new') %>
And the great thing about this is if the conditions are false, it will insert nil. Why is this good? Well, if you provide class with nil it won't include the class attribute on the tag at all. Bonus!
In the interest of not having to repeat your self too much by having to check current_page inside the link_to method all the time, here's a custom helper that you can use (put this in app/views/helpers/application_helpers.rb
def link_to_active_class(name, active_class_names, options = {}, html_options = {}, &block)
html_options[:class] = html_options[:class].to_s + active_class_names if current_page?(options.to_s)
link_to name, options, html_options, &block
end
Example usage:
<div> <%= link_to_active_class('Dashboard', 'bright_blue', dashboard_path, class: 'link_decor') </div>
if you are on http://example.com/dashboard, then it should return:
<div> <a href='/dashboard' class='link_decor bright_blue'>Dashboard</a> </div>
Regards.
I'd do it this way :
<%= link_to "Some Page", some_path, :class => current_page? ? "current" : "" %>
I tried to combine a couple of the mentioned techniques with my own needs.
def current_page(path)
'current' if current_page?(path)
end
def create_nav_link(string, path, method)
link_to string, path, data: { hover: string }, method: method
end
def create_nav_item(string, path, method = nil)
content_tag :li, create_nav_link(string, path, method), class: current_page(path)
end
Basically it allows you to use it like this:
create_nav_item("profile", profile_path) which will result in:
<li>Profile</li>,
or <li class="current">Profile</li> if this is the current page.
I didn't use request.url.include?(path) since it will also always highlight the "Home" button, and I couldn't think of a work around by far.
A variant to Eric Boehs solution (the most robust one IMHO), if you are linking directly to an object of the class (i.e. you don't show the index), with an added application helper:
def booking_link
Booking.find(8)
end
You can use the following in the view (the dd is used in the context of zurb foundation)
<%= content_tag :dd, link_to(t('hints.book'), booking_link), class: active_class?(booking_path) %>-
I think if would be good idea if you generate whole link_to from your helper method. Why to repeat the same code ( :-) DRY principle)
def create_link(text, path)
class_name = current_page?(path) ? 'current' : 'any_other_class'
link_to text, path, class: class_name
end
Now you can use like:
<%= create_link 'xyz', any_path %> (in views) which would render as xyz
Hope it helps!

create large a tag in rails

I have this tag: <%= link_to 'Show', user_listing_url(listing.user, listing) %> but instead of simply having it say 'Show' I actually want to place HTML inside of the <a> tag. Is this possible?
Example:
<div><div><img /></div></div>
yes you can pass a block to link_to
try something like this:
<%= link_to(user_listing_url(listing.user, listing)) do %>
<div><div><img/></div></div>
<% end %>
I totally recommend marflar's answer above.
However I would add one comment which is that if you are using html elements within a link_to block this may apply rails default link styling which may not be desirable.
One alternative is to use a button_to link but don't forget the default method for this is POST so specify the options as GET:
button_to(user_listing_url(listing.user, listing), method: :get) do %>
<div></div>
<% end %>

Link_to doesn't work when using acts-as-taggable-on with custom method

Or rather I don't know how to specify the route for it.
I have my controller setup us:
def tags
#clients = current_user.clients.find_tagged_with(params[:tag])
end
and my views
Tags:
<% for tag in #client.tags %>
<%= link_to tag.name, clients_path(:view =>'tag', :tag => tag.name) %>
<% end %>
Only problem is that the link (clients_path) goes back to index and not 'all.' I know it has to do with changing the clients_path to somehow tell it to use 'all'. But I don't know how.
Any help?
Thanks
You can check your routes using rake routes.
I'm not sure what you mean by 'all' but if this is a custom method added to routes, then you should be able to use all_clients_path instead of clients_path.

Resources