You can use heredoc Show archive.org snapshot to avoid endlessly long lines of code that nobody can read. Heredoc strings preserve linebreaks and can be used like this:
def long_message
puts(<<-EOT)
Here goes a very long message...
Sincerely,
foobear
EOT
end
<<-EOT
will be somewhat of a placeholder: anything you write in the line after you used it will be its value until you write EOT
in a single line.
You can use any string to flag your heredocs. To be more verbose you can use something else -- your IDE may even be aware of it, for example RubyMine understands <<-SQL
, <<-HTML
, <<-XML
, <<-JSON
, etc and highlights correctly.
Please note:
-
Your string will end with a new-line character (
\n
). -
Your string's lines will be padded with its indentation. The string from the example above will be
" Here goes a very long message...\n Sincerely,\n foobear\n"
. Depending on where you use it, this may or may not be a problem. A possible solution is<<~
(see below). -
You can use regular string interpolation inside heredoc strings:
puts <<-TEXT Dear #{user.name}, ... TEXT
-
Your statement does not have to terminate after the placeholder. Example:
content_tag(:div, <<-TEXT, class: 'example') Dear #{user.name}, ... TEXT
<<~
vs <<-
You can use <<~
(with a tilde) to remove the string's indentation. This will keep any relative indentation in other lines.
<<~TEXT
Hello
Universe!
-foo
TEXT
# => "Hello\nUniverse!\n -foo\n"
# vs:
<<-TEXT
Hello
Universe!
-foo
TEXT
# => " Hello\n Universe!\n -foo\n"
Note that this was introduced with Ruby 2.3. On older Rubies you may use String#strip_heredoc
from ActiveSupport.
<<
vs <<-
(or <<~
)
You may also omit the dash or tilde and just write <<EOT
. If you do this, your terminating sequence must be at the very beginning of the line. It's less pretty and there is rarely a reason to use it:
def foo
puts(<<TEXT)
Hello!
TEXT
end
Multiple heredocs in one line
If you have more than one multi-line string that you want to use in one line, you can just put your heredocs strings below each other. Example:
def long_messages
html_escape(<<-ONE) + '<hr />' + html_escape(<<-TWO)
Here goes my first very long message.
Yeehaw!
ONE
This is the second message which is still long.
It is long indeed.
TWO
end