I'm new to FreeMarker and have string I want to perform two built-ins on. For example, I have a string that needs all instances of the pipe symbol replacing with a comma and capitalizing the first letter.
I thought the syntax would be ${string?cap_first?replace("|",", ")}
But only the first built in works. I've had a look around and can't find any examples other than perhaps assigning the value to a variable and then performing the two built-ins separately.
Anybody have any ideas?
Thanks
You are using the correct syntax. Furthermore your example works for me as is. What error message you get?
There is an easy but not very elegant solution. You can chain Built-ins by wrapping them into parentheses. For instance this will work as you'd expect:
${(string?cap_first)?replace(oldString, newString)}
Hope this helps!
Related
While debugging abap code I found an interessting code construct.
method_name(: Parameter1 ), Parameter2 ).
As far as I can tell this one calls the method twice. The first time with the first parameter and the second time with the second.
Unfortunately I have no idea how this construct is called and so I can't find any documentation in the SAP docu or with google.
I can tell that this works but is this an official construct?
Does it work with more than two parameters? (E.g. four times)
Best regards,
Dirk
Congratulations, you've found an obscure and most certainly discouraged use of a so-called chained statement. Using this for method calls is not recommended, but since it was once allowed, SAP will be very reluctant to remove this again...
When the ABAP compiler finds a colon, it first expands it blindly without any syntax check (expanding A:B,C,D. into A B. A C. A D.).
And only then it analyses the syntax of each of them - to tell whether it is an assignment, method call or whatever. Pavel
I'm currently running into a bog-standard Bobby Tables problem, but the environment is Chef + Ruby + powershell.
All of the solutions I've seen so far appear inadequate: they surround the arguments with quotes, but do not fully escape the arguments. Shellwords and shellescape look promising, but they appear to be bash-specific.
For example, I may want to construct in Chef this windows shell command:
.\foo.exe BAR="#{node['baz']}"
Generalizing from the SQL dev world I'd naively anticipate an interface something like this:
cmd = "foo.exe BAR=?"
args = (node['baz'])
run-command(cmd, args)
Where run-command would handle escaping any arguments. Instead I see interfaces that remind me of the bad old SQL days when developers had to construct SQL as a string, and escape any arguments "by hand".
Any pointers to best practices on how to proceed? Use system? Thanks!
Edit: to be clear, the argument baz above can be expected to include arbitrary text, including possibly any combination of characters. Think of it as being identical to the Bobby Tables problem.
The easiest generic solution is to use the array form for the execute resource's command property. This avoids all shell parsing an runs the command verbatim.
execute 'whatever' do
command ['foo.exe', "BAR=#{node['baz']}"]
end
This doesn't work for script style resources though, which take a string for the script chunk to run, including powershell_script. There you would need something more tailored to PowerShell and I don't know its rules well enough to say if Shellwords would match.
I am curious about parsing C++ code using regexp. What I have so far (using ruby) allows me to extract class declarations and their parent classes (if any):
/(struct|class)\s+([^{:\s]+)\s*[:]?([^{]+)\s*\{/
Here is an example in Rubular. Notice I can capture correctly the "declaration" and "inheritance" parts.
The point at where I am stuck is at capturing the class body. If I use the following extension of the original regex:
/(struct|class)\s+([^{:\s]+)\s*[:]?([^{]+)\s*\{[^}]*\};/
Then I can capture the class body only if it does not contain any curly braces, and therefore any class or function definition.
At this point I have tried many things but none of them make this better.
For instance, if I include in the regexp the fact that the body can contain braces, it will capture the first class declaration and then all the subsequent classes as if they were part of the first class' body!
What am I missing?
Regular expressions are not the recommended way to parse code.
Most compilers and interpreters use lexers and parsers to convert code into an abstract syntax tree before compiling or running the code.
Ruby has a few lexer gems, like this, you can try and incorporate into your project.
The group capturing might help:
# named v backref v
/(struct|class)\s+(?<match>{((\g<match>|[^{}]*))*})/m
Here we find the matching curly bracket for the one following struct/class declaration. You probably will want to tune the regexp, I posted this to make the solution as clear as possible.
What I can offer you is this:
(struct|class)\s+([^{:\s]+)\s*[:]?([^{]+)\{([^{}]|\{\g<4>\})*\};
Where \g<4> is a recursive application of the fourth capture group, which is ([^{}]|\{\g<4>\}).
Matching non-regular languages with regular expressions is never pretty. You might want to consider switching to a proper recursive descent parser, especially if you plan to do something with the stuff you just captured.
I'm writing xquery on eXist.
Usually I use this way to select item in xml:
fn:doc($document_name)/root/a
But now I wants to get the xpath from a string variable:
let $xpath := request:get-parameter("xpath", "")
fn:doc($document_name)/$xpath
Of course it doesn't work.
The only way I found now is using eval:
util:eval(fn:concat("fn:doc($document_name)", $xpath)):)
but i don't want to use eval because it's slow and not safe.
I know there's something like:
fn:doc($document_name)/*[name()='node_name']
but I want to select item via the whole path but not only the name of node
and I also have tried to use node-xpath() but don't know how to use it just like name()
You want to do what the eval() function does, so any solution is going to have the same problems as eval. The other approach you could consider is generating a query and then executing it, but it will have exactly the same problems. If you think it might be safer to restrict the string to a subset of XPath expressions (e.g. with no predicates, or no function calls) then you could try testing for those conditions using simple regular expressions.
despite Michael Kay being right, maybe the functx:dynamic-path() is of some help.
It might be a good intermediate solution sitting between fn:eval and generating the query dynamically.
Hope this helps
Michael
What I like to do is remove all functions which has specific word for example, if the word is 'apple':
void eatapple()
{
// blah
// blah
}
I'd like to delete all code from 'void' to '}'.
What I tried is:
^void.*apple(.|\n)*}
But it took very long time I think something is wrong here.
I'm using Visual Studio. Thank you.
To clarify jeong's eventual solution, which I think is pretty clever: it works, but it depends on the code being formatted in a very particular way. But that's OK, because most IDE's can enforce a particular formatting standard anyway. If I may give a related example - the problem that brought me here - I was looking to find expressions of the form (in Java)
if (DEBUG) {
// possibly arbitrary statements or blocks
}
which, yes, isn't technically regular, but I ran the Eclispe code formatter on the files to make sure they all necessarily looked like this (our company's usual preferred code style):
if (DEBUG) {
statement();
while (whatever) {
blahblahblah(etc);
}
// ...
}
and then looking for this (this is Java regex syntax, of course)
^(\s*)if \(DEBUG.*(?:\n\1 .*)*\n\1\}
did the trick.
Finally did it.
^void.*(a|A)pple\(\)\n\{\n((\t.*\n)|(^$\n))*^\}
Function blocks aren't regular, so using a regular expression in this situation is a bad idea.
If you really have a huge number of functions that you need to delete (more than you can delete by hand (suggesting there's something wrong with your codebase — but I digress)) then you should write a quick brace-counting parser instead of trying to use regular expressions in this situation.
It should be pretty easy, especially if you can assume the braces are already balanced. Read in tokens, find one that matches "apple", then keep going until you reach the brace that matches with the one immediately after the "apple" token. Delete everything between.
In theory, regular language is not able to express a sentence described by context free grammar. If it is a one time job, why don't you just do it manually.
Switch to VI. Then you can select the opening brace and press d% to delete the section.