Convert a hash string to a formatted number? - freemarker

I'm trying to output prettier numbers from my FreeMarker template in GeoServer:
<#list features as feature>
<#if attribute.name="lon" || attribute.name="lat">
<td>${feature[attribute.name].value?round}</td>
<#else>
<td>${feature[attribute.name].value}</td>
</#if>
</#list>
If I take out the ?round, I get things like "-121.469166666667". I simply wish to format that number a bit, say by rounding it to 4 decimal places.
I've tried a couple things:
${feature[attribute.name].value?number}
${(feature[attribute.name].value)?number.string("0.0000")}
But those complain of "Expected hash.", so I'm feeling like it's just a syntax issue of conveying the string in the hash to the ? operator correctly, so that I'm actually executing methods on the string... but that has stumped me.

If you always want 4 decimals:
${feature[attribute.name].value?string("0.0000")}
If you want at most 4 decimals, then ?string("0.####")
The ?number part is only needed if value is a string. In that case you should write [...].value?number?string("0.0000"). There's no such thing as ?number.string, hence the "expected hash" error message.

Related

Replace the last character or number of a string | Freemarker

I need to check if the last number of character of a ${string} is equal to 9.
The string or numbers that I have to handle with is something 831, 519 or 1351.
However I dont know how do do it properly. I tried already something like:
${string?replace((string.length)-1,"9")}
At the end there should be instead of 831 --> 839 or 1351 --> 1359 and so on.
Any sugestions about how I can archive this ?
Oh and by the way. If I use the fuction above this error massage comes up:
Script error: You have used ?number on a string-value which is not a number (or is empty or contains spaces).
And what I tried also was:
code snippet
Because the original number is somethink like 831.896.
You could use string slicing to keep all characters except for the last one like this:
<#assign string = "1234">
<#assign string = string[0..<string?length-1] + "9">
${string}
Results in:
1239
Since you want to replace that thing, use ?replace. This replaces the last character with 9, if the last character is a digit that's not already 9:
${s?replace("[0-8]$", '9', 'r')}

Print only 5 line of each having 32 chars using Freemarker

How to print only 5 line of each having 32 chars using Freemarker. Currently i have the below solution. Is there any better way of doing using split or substring
<#assign msg="Tell FreeMarker to convert string to real date-time value Convert date-time value to date-only value Let FreeMarker format it according the date_format setting">
<#assign len=msg?length>
<#list 1..5 as i>
<#assign start=(i-1)*32>
<#assign end=i*32>
<#if (end <len)>
${msg[start..end]}
<#else>
${msg[start..len-1]}
</#if>
</#list>
result is
Tell FreeMarker to convert string
g to real date-time value Convert
t date-time value to date-only va
alue Let FreeMarker format it acc
cording the date_format setting
Like this:
<#list msg?matches(".{1,32}")[0..*5] as row>
${row}
</#list>
Note that the "length limited range" operator, ..*, doesn't give error if the length is less than what you asked for. So even with your approach, you can remove the end assignment and the #if/#else, and just use ${msg[start..*32]}.

The code always outputs "not"

The following code always outputs "not":
print "input a number please. "
TestNumber = gets
if TestNumber % 2 == 0
print "The number is even"
else
print "The number is not even"
end
What is going wrong with my code?
The gets() method returns an object of type String.
When you call %() on a String object, the return value is a new String object (usually it changes the text. You can read more about string formatting here).
Since there are no String objects that == 0, the if/else will always take the same path.
If you want to use the return value of gets() like a number, you will need to transform it into one first. The simplest approach is probably to use the to_i() method on String objects, which returns a new 'Integer' object. If you're doing something where the user input will not always be an integer (e.g. 3.14 or 1.5), you might need to use a different approach.
One last thing: in your example the result of gets() is saved into a constant called TestNumber. Constants are different to normal variables, and they will probably cause problems if you're not using them intentionally. Normal variables don't start with capital letters. (You can read more about ruby variables here). In ruby you need to write you variable names like this: test_number.
I suspect your Testnumber variable might be interpreted as a string during the operation. make sure the testnum is converted to an integer first even if you put in say 100 it could be its being interpreted as the stirng "100" and not the integer 100.
A similar issue can be found here: Ruby Modulo Division
You have to convert TestNumber from string to integer, as your input has linefeed and/or other unwanted characters that do not match an integer.
Use TestNumber = gets.to_i to convert to integer before testing.

Freemarker: Output comma separated list as an array

I have a table that has a field that contains a comma separated list of order IDs. What I am trying to do is output each of those IDs separately so that I can use them to look up their corresponding order details in another table.
Does anyone know of a good way to do this?
So far I have tried:
<#data Alerts_test_table as alerts_test>
<#filter
CUSTOMER_ID_=CONTACTS_LIST.CUSTOMER_ID_1>
<#fields AD_ID_LIST>
<#assign seq = ['${alerts_test.AD_ID_LIST}']>
<#list seq?chunk(1) as row><#list row as cell>
${cell}
</#list> </#list>
</#data>
But this just outputs it as a line of text.
Let's say you have comma separated ID-s in idsString, and you want to iterate though the ID-s one by one. Then:
Data-model (with http://try.freemarker.org/ syntax):
idsString = "11, 22, 33"
Template:
<#list idsString?split(r'\s*,\s*', 'r') as idString>
${idString}
</#list>
However, in the template you have posted I see many strange things, so some ideas/pointers:
Be sure that alerts_test.AD_ID_LIST is indeed a String, not a List that you can list directly, without ?split-ing. If it's a String, then '${alerts_test.AD_ID_LIST}' is ultimately the same as alerts_test.AD_ID_LIST. In general, you never need an empty string literal and an ${} in it. It's not useful (but sometimes harmful, as it converts non-string values to string).
?chunk(1) is not useful. The point of ?chunk is to slice a list to smaller lists, but if those smaller lists are to be 1 long, then you might as well just list the items of the original list.
There are no such directives as #data and #filter. Is this some forked FreeMarker version?
If the ID is a number that you need to pass to some API that expects a number, then you will have to convert it to number like idString?number.

How to Convert a string to number in freemarker template

I want to convert a string to number in freemarker. I want to put some conditional check based on the value of the number. ?number doesn't seems to work.
Any suggestions?
Sorry, ?number does work fine. I was not able to compare the converted number with another number.
This didn't work for me:
<#assign num = numString?number>
<#if num > 100>
</#if>
When I enclosed (num > 100) inside the brackets it worked:
<#if (num > 100)>
</#if>
Since the comparison was not working, I was assuming that conversion was not happening.
My bad.
In your code, you use the closed bracket, so freemarker is evaluating
<#if num >
you should instead use
<#if num gt 100>
This is discussed at the end of this documentation on if statements
https://freemarker.apache.org/docs/ref_directive_if.html
The reason this is working for some and not others is because of the parentheses, which is also explained at the bottom of the documentation
I think you can use it like this:string?eval
Use the below code
<#if num?string > 100?string>
</#if>
It worked for me.

Resources