jquery-ujs icon indicating copy to clipboard operation
jquery-ujs copied to clipboard

Interpret newline escape codes in dialog messages?

Open noinkling opened this issue 10 years ago • 7 comments

See rails/rails#16784

Currently, to get a newline in a data-confirm dialog, you need to either:

  1. Let it be interpreted as a newline at the Ruby string level (when using Rails helpers) or
  2. Insert an explicit newline in your HTML (when writing standard HTML) or
  3. Use an HTML escape code like 
 or 
, and make sure the string is marked as html_safe on the Rails end so those codes aren't escaped.

The issue with 1 is that any Ruby string newlines are reflected in the HTML source, so the output of both methods 1 and 2 might look like:

<body>
  <div id="main-container">
    <div class="links">
      <ul>
        <li><a href="path/to/whatever" data-confirm="I want a gap between this line...

...and this line">My link</a></li>
        <li><a href="#">Another link</a></li>
      </ul>
    </div>
  </div>
</body>

You can imagine if you had a lot of these how messy it might look, though it is apparently valid.

3 is simply a bit of an obscure/hacky workaround.

Id prefer to be able to specify something like:

<a href="path/to/whatever" data-confirm="I want a gap between this line...\n\n...and this line">My link</a>

and have jquery-ujs interpret those newlines just as calling

confirm("I want a gap between this line...\n\n...and this line");

in Javascript would. Currently it just gives literal "\n"s in the message instead.

noinkling avatar Sep 04 '14 00:09 noinkling

Newlines in confirmation dialogs will work as expected with jquery-ujs, just be sure to produce the right HTML with proper \n terminators in the data-confirm attribute. If you write your strings with double quotes ("), Ruby will interpret those terminators and produce line breaks in your HTML.

Considering the following examples, be sure to have something similar to the latter in your application code:

<%= link_to 'Click me', '#', data: { confirm: "Line\nNewLine" } %>

<!-- This call will produce the following markup, removing the `\n` tokens
<a data-confirm="Line
NewLine" href="#">Click me</a> -->

<%= link_to 'Click me', '#', data: { confirm: 'Line\nNewLine' } %>

<!-- <a data-confirm="Line\nNewLine" href="#">Click me</a> -->

lucasmazza avatar Sep 08 '14 16:09 lucasmazza

Sorry but that simply doesn't work for me. I copied and pasted your example directly:

<%= link_to 'Click me', '#', data: { confirm: 'Line\nNewLine' } %>

Does indeed result in:

<a data-confirm="Line\nNewLine" href="#">Click me</a>

But like I said ends up like this in the browser: Confirm dialog

Tested in Chrome/Firefox/IE, with both stable jquery-rails gem in Rails 4.1.5 and latest github version of jquery-rails in Rails 4.2.0 beta.

From a reply on the other issue, my understanding is that it interprets it as a piece of HTML text, not a Javascript string, and that causes HTML entities (e.g. &#10;) to work while JS escape codes won't. It just seems to me that it would be a bit nicer to have \n work from a usability perspective, like it would if you wrote console.log("Line\nNewLine");.

noinkling avatar Sep 09 '14 00:09 noinkling

Sorry, you're right. We have some inconsistencies with strings in JavaScript that maybe we can go around this. I'll dig into this later.

lucasmazza avatar Sep 09 '14 01:09 lucasmazza

Doing a .replace(/\\n/g, "\n") on what gets returned from .data('confirm') seems to work. The only issue I can think of if this was implemented, is that if you wanted a literal "\n" in your message, you'd need to double-escape it (single quotes) or triple-escape it (double quotes) in Ruby. Same for any other escape codes if you chose to support them.

noinkling avatar Sep 09 '14 01:09 noinkling

@lucasmazza it's not a JavaScript string; the current behaviour is correct.

matthewd avatar Sep 09 '14 07:09 matthewd

As per https://github.com/rails/rails/issues/16784#issuecomment-234437275

<%= link_to 'Click me', '#', data: { confirm: 'Line\nNewLine' } %>
$.rails.confirm = function(message) {
 return confirm(message.replace(/(\\n|\\r|\\r\\n)/gm,"\n"))
}

Ruxton avatar Jul 22 '16 03:07 Ruxton

Es con comilla doble :)

<%= link_to 'Click me', '#', data: { confirm: "Line\nNewLine" } %>

beslnet avatar Oct 18 '17 13:10 beslnet