Underscores in Thymeleaf Text Literals - thymeleaf

Question: How to escape multiple consecutive underscores in text literals?
I am using the standard Thymeleaf dialect for HTML (I am not using Spring or SpEL here).
In Thymeleaf, I can create an underscore as a text literal as follows:
<div th:text="'_'"></div>
This renders as:
<div>_</div>
I can create literals with 2 and 3 underscores in the same way:
<div th:text="'__'"></div>
<div th:text="'___'"></div>
But for 4 underscores, I get an error:
org.thymeleaf.exceptions.TemplateProcessingException: Could not parse as expression: ""
I assume (maybe incorrectly) this is because two pairs of underscores (__ followed by __) are the markers used by Thymeleaf for the expression preprocessor. And when these are removed, I am left with an empty expression - hence the error.
I can escape the underscores using the backslash (\) escape character. The following all give the required results:
<div th:text="'\_\___'"></div>
<div th:text="'\_\_\_\__'"></div>
<div th:text="'\_\_\_\___'"></div>
<div th:text="'_\_\_\_\___'"></div>
<div th:text="'\_\_\_\_\_\___'"></div>
But I can't just escape every underscore.
This displays a stray backslash:
<div th:text="'\_\_\_\_\_'"></div>
The result is:
<div>____\_</div>
So:
What are the rules for escaping underscores in text literals?
Is it really the preprocessor which is causing this behavior (inside text literals) - or is it something else?

Yeah, this is definitely part of the preprocessor.
It looks to me like the preprocessor only replaces an exact match of \_\_ with __. In any case where you have an odd number of \_'s, you will get the output \_ -- because it's not treating \_ as a real escape and instead only looking for \_\_.

I stumbled upon the same issue while providing underscore as placeholder for a code input field and found the following workarounds:
1. Insert zero width space as seperator
In the first example ('​_​_​_​_​') the zero witdh space is unescaped, but you can copy paste the string into your IDE of choice.
<div th:text="${'_​_​_​_​_​_'}"></div>
<div th:text="${'_​_​_​_​_​_'}"></div>
<div th:text="${'_​_​_​_​_​_'}"></div>
<div th:text="${'_&ZeroWidthSpace;_&ZeroWidthSpace;_&ZeroWidthSpace;_&ZeroWidthSpace;_&ZeroWidthSpace;_'}"></div>
2. Use string replace
Surprisingly, this also seems to work. You can use any character, but no underscores in the original string, I chose "......". You can also use it with a string of unknown length by specifying a variable instead of a fixed string.
<div th:text="${#strings.replace('......', '.', '_')}"></div>
<div th:text="${#strings.replace('......', '.', '_')}"></div>

Related

Rails 18n French: Special Characters appear when words with accent are being used

I added french translation using i18n gem. Most of the french words with accent characters get printed correctly but some of the words are behaving incorrectly.
Sécurité gets printed instead of Sécurité. I tried to escape the accented characters with backticks or double single quotes but was unable to achieve the correct result.
In .re file:
<h3 className="text-lg font-semibold"> {t("security") |> str} </h3>
In .yml file:
security: "Sécurité"

How can I remove easly Shortcodes inside a Google Sheet?

I am tryng to get rid of shortcodes inside a Google Sheet column. I have many items such as [spacer type="1" height="20"][spacer] or [FinalTilesGallery id="37"] I just would like to cancel them. Is there any simple way to do it?
Thanks !
For in-place replacement, the quick option would be to use the Find and Replace dialog (Ctrl + H) with Search Using Regular Expressions turned on, which is more powerful than your standard Find and Replace.
Find: \[.*?\] - Match anything within an open-bracket up to the very next close-bracket. This should work assuming you have no nested brackets, e.g. [[no][no]].
If you do have nested brackets, you'll have to change this to \[[^\[\]]*\]. And continue to Replace All until all the codes are gone.
Replace: Nothing.
Replace All. If you don't want to affect other sheets that may be in your document, make sure you select the right range to work with, too.
This just erases everything within the brackets.
If you want to erase any redundant spaces left by this, simply Find and Replace again (with Regular Expressions) on + (space and plus), which will match 1 or more spaces and replace with (single space).
E.g.:
string [] [] string2 -> string string2 after the shortcode replacement.
After replacing spaces, it will become string string2.
Let's say your original strings are in the range A2:A. Place the following into B2 of an otherwise completely empty Column B (or the second cell of any other empty column):
=ArrayFormula(IF(A2:A="",,TRIM(REGEXREPLACE(A2:A,"\[[^\[\]]+\]",""))))
I can't see your data, so I don't know what kind of information is between these shortcodes. If you find that this leaves you with concatenated pieces of data where there should be spaces between them, replace the above with this version:
=ArrayFormula(IF(A2:A="",,TRIM(REGEXREPLACE(SUBSTITUTE(SUBSTITUTE(A2:A,"["," ["),"]","] "),"\[[^\[\]]+\]",""))))
I can't teach regular expression language here. But I will note that, since square brackets have specific meaning within regex, your literal square brackets must be indicated with the escape character: the backslash.
Here is the regex expression alone:
\[[^\[\]]+\]
The opening \[ and the closing \], then, reference your actual opening and closing bracket sets. If we remove those, we have this left:
[^\[\]]+
Again, you see the escaped opening and closing square brackets, which I'll replace with the word these:
[^these]+
What remains there are opening and closing brackets with regex meaning, i.e., "anything in this group." And the circumflex symbol ^ as the first character within this set of square brackets means "anything except." The + symbol means "in any string length of one or more characters."
So that whole regex expression then reads: "A literal open square bracket, followed by one or more characters that are anything except square brackets, ending with a literal closing square bracket."
And we are REGEXREPLACE-ing any instance of that with "" (i.e., nothing).

Change HAML indentation from 2 to 4 spaces

Is there a way to change the indentation from 2 spaces to 4 spaces for HAML on a Ruby on Rails application?
If I failed to indent properly, I get: The line was indented 2 levels deeper than the previous line.
Taken from http://haml.info/docs/yardoc/#indentation
Haml’s indentation can be made up of one or more tabs or spaces.
However, indentation must be consistent within a given document. Hard
tabs and spaces can’t be mixed, and the same number of tabs or spaces
must be used throughout.
Here's my test:
test.haml
#content
.title
%h1 Test
Results:
haml test.haml
<div id='content'>
<div class='title'>
<h1>Test</h1>
</div>
</div>

throwing error when trying to access hashmap with key with a numeric value or special chars

throwing an error when trying to access hashmap with key with a numeric value or special chars
Here is the code I am trying to use:
<div th:include="${myMap[__${dept.code}__]}"/>
If code has letters , this works fine, but if it holds only a numeric value "1234" , this fails .
Appreciate any resolution on this. Thanks..
If the map is based on string keys you shpuld ensure that the precomputed expression is always a string.
A TextLiteral expression can only consist of a limited type of characters. A-z, underscores, minus and some others.
To ensure it's always a string you can wrap the precomputed expression in single quotes:
<div th:include="${myMap['__${dept.code}__']}"/>

How to escape whitepace in Rails?

I know that rails automatically escapes characters like '<' or '&', but this does nothing for multiple spaces next to each other. I would like to escape everything, including spaces.
I understand that normally you don't want to use and that you should use css instead. However, I'm trying to take user input and display it, so css isn't feasible.
For example, I have the user input: test . When I display it with <%=#user_input%> in the view, the extra whitespace is displayed as a single space (though it appears correctly in the source).
Is there an easy way to escape the whitespace? Should I just use h #user_input and then replace all the spaces?
The whitespace isn't removed. Browsers simply interpret multiple whitespace characters as a single space.
You could convert each space to if you want:
<%= raw #user_input.gsub(/\s/, " ") %>
You could alternatively replace each space with an empty <span class="whitespace"></span> tag, and then use CSS to style the whitespace 'characters' however you like.
Finally, you can do this with only CSS too using the white-space: pre style (example below).
http://jsfiddle.net/G3VnY/
Edit (to answer the follow-up in your comment)
<%= raw h("this is a sample & with ampersand.").gsub(/\s/, " ") %>
This escapes the & as & in the source (and will do similar for other HTML entities), and then does the " " to conversion.

Resources