1

Extreme Ruby/Rails novice here: I'm trying to link_to a search action for each individual post contained in a block:

<% split_tags = post.tags.split(',') %> # returns ["food", "computers", "health"] %>
<p>Keywords: <%= split_tags.each {|tag| link_to(tag, front_search_tag_path(:tag => tag))}) %></p>

but all it returns is Keywords: ["food", "computers", "health"]. Shouldn't .each iterate over the array and provide a link to each search_tag_path with the tag as a parameter?

3
  • Maybe try #map instead of #each? Commented Aug 16, 2012 at 22:01
  • 1
    <%= ... %> returns the last expression evaluated. .each returns the original Array, so you want <% .each do |tag| %><%= link_to ... %><% end %> Commented Aug 16, 2012 at 22:01
  • Shoot, can't believe I made that novice mistake. Thanks. Commented Aug 16, 2012 at 22:07

3 Answers 3

4

Nope, #each just performs a block, it does not accumulate any data.

[1, 2, 3].each{ |n| "Link to item #{n}" } #=> [1, 2, 3]

You have two options, use map to accumulate data:

[1, 2, 3].map{ |n| "Link to item #{n}" }.join("\n") #=> "Link to item 1\nLink to item 2\nLink to item 3"

Or output directly in the block:

[1, 2, 3].each{ |n| puts "Link to item #{n}" }

Prints:

Link to item 1
Link to item 2
Link to item 3

In your case this would be the following two options. I prefer the latter.

<p>Keywords: <%=raw split_tags.map{|tag| link_to(tag)}.join %></p>

<p> Keywords:
  <% split_tags.each do |tag| %>
    <%= link_to(tag) %>
  <% end %>
</p>
Sign up to request clarification or add additional context in comments.

Comments

0

You probably meant

<% split_tags = post.tags.split(',') %> # returns ["food", "computers", "health"] %>
<p>Keywords:
  <% split_tags.each do |tag| %>
  <%= link_to(tag, front_search_tag_path(:tag => tag)) %>
  <% end %>
</p>

or

<% split_tags = post.tags.split(',') %> # returns ["food", "computers", "health"] %>
<p>Keywords:
  <%= split_tags.map{|tag| link_to(tag, front_search_tag_path(:tag => tag))}.join %>
</p>

Comments

0

No, the return value for Array#each is the array itself (see http://www.ruby-doc.org/core-1.9.3/Array.html#method-i-each)

You will want to use Array#collect (or its alias, map) which will return an array of the links (see http://www.ruby-doc.org/core-1.9.3/Array.html#method-i-map). You can then turn that array into a single string with join. So, your code would look like

<% split_tags = post.tags.split(',') %>
<p>Keywords: <%= split_tags.collect {|tag| link_to(tag, front_search_tag_path(:tag => tag))}).join %></p>

However that might require the .html_safe after the .join. Better yet, do something like:

<% split_tags = post.tags.split(',') %>
<p>Keywords: 
<% split_tags.each do |tag| %>
  <%= link_to(tag, front_search_tag_path(:tag => tag)) %>
<% end %>
</p>

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.