antlr / stringtemplate4 Goto Github PK
View Code? Open in Web Editor NEWStringTemplate 4
Home Page: http://www.stringtemplate.org
License: Other
StringTemplate 4
Home Page: http://www.stringtemplate.org
License: Other
In version 3 we could code so that an AttributeRenderer
applied to String.class
was only called for attributes set onto the template. We are trying to create the same behaviour with version 4. However, the AttributeRenderer
seems to be called now for all text in the file.
We are unsure if this is a bug or we are making the wrong assumption
See test below to reproduce:
import static org.junit.Assert.fail;
import java.util.Locale;
import org.junit.Test;
import org.stringtemplate.v4.AttributeRenderer;
import org.stringtemplate.v4.ST;
import org.stringtemplate.v4.STGroupString;
public class StringTemplateRenderDoesNotGetAppliedToWholeStringTemplateTest {
@Test
public void rendererNotCalledWhenNoAttributesSet() {
STGroupString group = new STGroupString("stringTemplateWithNoAttributes() ::= << 1 >>");
group.registerRenderer(String.class, new AttributeRenderer() {
@Override
public String toString(Object o, String formatString, Locale locale) {
fail("The renderer must not get called. Object passed in was '" + o.toString() + "'");
throw new UnsupportedOperationException();
}
});
ST template = group.getInstanceOf("stringTemplateWithNoAttributes");
template.render();
}
}
I have a template as follows:
delimiter "$", "$"
templ(nr,alias,filename) ::= <%
*$nr$ZEND $\r$
ALI=$alias$ $\r$
FIL=$filename$ $\r$
MID=FTR000 $\r$
%>
Which gives an error for the unknown escape \r
. If i replace it with \n
it does not give an error. Looking at https://github.com/antlr/stringtemplate4/blob/master/src/org/stringtemplate/v4/compiler/STLexer.java#L367 this makes sense as it's missing as one of the alternatives in the test.
The if-attribute conditional could be enhanced to convert certain data type values to boolean. For example, python and groovy convert empty containers (empty lists, empty hash tables, empty maps) to false, the empty string to false and number zero to false (non-zero would be true, positive or negative). It looks as if nulls are already converted to false. I think this would be useful, as it would reduce the business logic when assigning template values. Right now, zeros, empty strings and empty containers have to be explicitely converted to false or null before being passed to the template.
I try to format a nested data structure:
$ddl.tables.keys:{t|$ddl.tables.(t).columns.keys:{c|$ddl.tables.(t).columns.(c).name_java$};wrap, anchor, separator=", "$}$
ddl
is an object containing an attribute called tables
which maps strings to table objects. Each table contains an attribute called columns
mapping strings to column objects. Each column object has an attribute called name_java
. Everything but the wrap
and anchor
options works fine. This means I get very long lines containing column names.
How to fix this?
I am using StringTemplate in Java source files. Having /*<
and >*/
as delimiters would be extremely useful instead of having to rely on single character delimiters. Often something unique is required as a delimiter, and two unique characters are hard to come by.
Allowing for multiple opening and closing delimiters would be even more useful; that way a /*<
& >*/
sequence would work, as well as a simple <
& >
in a sub-template.
The following template produces a warning when foo
is null
because operator &&
does not short circuit.
<if(foo && foo.attr)>
...
<endif>
Robert Hafner reports.
Maybe:
sqlTemplate.registerNullRenderer(new NullValueRenderer());
The default NullRenderer would simply output an empty string which seems to be the behavior today.
If I try to use the ignore newline operator <\\>
in a template defined in a group file, it gives a parse error:
test.stg 1:28: invalid escaped char: '>'
test.stg 1:29: expecting '>', found '
'
Where test.stg is:
tester(x) ::= <<
Hello <\\>
This is a test
>>
I know there are the template definitions that ignore all indentation and newlines, but it would be a lot more work than just being able to selectively ignore a newline. Is there some design reason for this not being implemented, or has it just not been done yet?
Currently the interpreter supports Collection<T>
and Iterator<T>
, but it does not support Iterable<T>
.
Public git repository on github doesn't contain any information for identifying release tags. Please push your tags (I assume you have them locally) with git push --tags so it's possible to checkout specific released version.
Thank you
We were having some troubles with attributes that contained foreign characters and I was able to isolate the problem to something within StringTemplate. Here is the failing unit test
@Test
public void testForeignLanguageParameterWithST() throws Exception {
ST simpleTemplate = new ST("Hi, $param$!", '$', '$');
simpleTemplate.add("param", "String");
String simpleRendered = simpleTemplate.render();
String simpleExpeceted = "Hi, String!";
assertEquals(simpleExpeceted, simpleRendered);
ST foreignTemplate = new ST("Hi, $タイプ$!", '$', '$');
foreignTemplate.add("タイプ", "Template");
String foreignRendered = foreignTemplate.render();
String foreignExpected = "Hi, Template!";
assertEquals(foreignExpected, foreignRendered);
}
At this point this we are fine with having this fixed in a newer version of StringTemplate, but for now we need to document the known character set.
TemplateGroup tg=new TemplateGroupString("test",@"
test(a,b,c) ::= <<
a = $a$
a.name = $a.name$
b = $b$
b.name = $b.name$
c = $c$
c.name = $c.name$
>>
",'$','$');
Template t=tg.GetInstanceOf("test");
object a=new { name = "A object" };
t.Add("a",a);
object b= Newtonsoft.Json.JsonConvert.DeserializeObject("{ name: \"B object\" }");
t.Add("b",b);
dynamic c=new ExpandoObject();
c.name="C object";
t.Add("c",c);
System.Console.WriteLine(t.Render());
The output is:
a = { name = A object }
a.name = A object
b =
b.name =
c = [name, C object]
c.name =
I can't find any other way to be able to preview my templates easily (user passes a JSON object, deserialized into a Dictionary<string,dynamic>
, then each dictionary KVP are sent to the template individually).
Selections are incorrect when STViz is used on Windows.
Found the following in ST 4.0.2 (the latest available on Maven Central)
The "ignore newline" expression <\\>
appears to work but causes compile errors:
Template:
test() ::= <<
hello <\\>
world
>>
Output (as expected):
hello world
Reported errors (unexpected):
test 3:29: invalid escaped char: '>'
test 3:30: expecting '>', found '
'
Why the compile errors if the syntax is valid and behavior is correct?
The following template does not compile:
foo(x=[]) ::= <<
>>
The following table shows why this default value be useful:
<x> |
<if(x)>Y<endif> |
|
---|---|---|
foo(x=true) |
true |
Y |
foo(x=false) |
false |
(empty) |
foo(x={}) |
(empty) | Y |
foo(x=[]) |
(empty) | (empty) |
In STv3 I used to have the following constructs:
Template1() ::= "text"
Template2() ::= "<Template1(); format="upper">"
I've tested this with ST 4.0.6 and it seems that the format is not applied on sub-templates results. In fact, the Interpreter directly sends the template output to the STWriter
and the format option is ignored.
I guess that the sub-template should be first evaluated and then passed to the formatter, or a warning should at least be issued if this behavior is intended.
If a template comes from a template group, and there is a cycle in the templates of the group (or the template simply calls itself) then ST.render() throws a StackOverflowError or OutOfMemoryError. I didn't find a way to detect cycles manually.
I am using ST 4.0.4 for Java.
When following any links to your documentation, I only find the github pages 404 page.
I noticed that there is a bug in implementation of copy constructor or in ST.add()
Here is how to reproduce:
Create
ST proto = new ST("simple template")
Create
ST work = new ST(proto)
work.add("some argument", argument)
work.render(); // first time it's working
Create
ST work2 = new ST(proto)
work2.add("some argument", argument); // Get nullPointerException - due to locals is null
Hello,
Here is a way to list all keys in a template ?
For exemple, with this kind of template :
<img src="$toto$" class="banner" height="61" width="560">
<img src="$tata$" class="banner" height="61" width="560">
Have a list of keys :
toto, tata
Thanks in advance
This issue prevents GitHub from automatically closing the 4.0.8 milestone before it's complete.
When the following text is loaded into a String and used to create a STGroupString, the "delimiters" line is not honored and you get the default "<", ">" delimiters instead.
I am loading my templates from the Google App Engine Blob store and the easiest way to get them into ST is with STGroupString.
delimiters "$", "$"
li(it) ::= "<li>$it.fname$ $it.lname$</li>"
ul(ulid, list) ::= "<ul$if(ulid)$ id=\"$ulid$\"$endif$>$list:li()$</ul>"
div(divid, ulid, content) ::= "<div$if(divid)$ id=\"$divid$\"$endif$>$ul(list=content, ulid=ulid)$</div>"
These are the dependencies on ST4 according to maven:
mvn dependency:tree
[...]
[INFO] - org.antlr:ST4:jar:4.0.7:compile
[INFO] - org.antlr:antlr-runtime:jar:3.5:compile
[INFO] - org.antlr:stringtemplate:jar:3.2.1:compile
[INFO] - antlr:antlr:jar:2.7.7:compile
It should only depend on antlr4 IMHO.
Why?
The latest version of StringTemplate isn't available in Maven:
http://search.maven.org/#browse%7C-1509539657
Or am I just not looking in the right place?
This is similar to #20.
I searched for "stringtemplate" which gave me org.antlr:stringtemplate, which ends at the deprecated 4.0.2 version (which promptly triggered the "does not recognize the delimiters clause in files' bug and sent me on an extended bug hunt).
The mention should go on http://www.antlr.org/wiki/display/ST4/Using+StringTemplate+with+Java#UsingStringTemplatewithJava-install .
Thanks!
Hi,
it would be nice to have ability to load/import STGroups from streams. Currently I use it to cache String of template loaded from stream loaded using java.lang.ClassLoader#getResourceAsStream(). I want to eliminate IO operations currently implemented in org.stringtemplate.v4.STGroup#importTemplates(...). Something like "template definitions registry".
Could you consider this.
Thx
Ivos
I have the following 3 template files:
mainRaw.st
Hello $name$
Then do the footer:
$footerRaw(lastLine=veryLastLineRaw())$
footerRaw.st
Simple footer. And now a last line:
$lastLine$.
veryLastLine.st
That's the last line.
As you can see footerRaw
contains the variable lastLine
, which in turn I want to initialize in mainRaw
when invoking footerRaw
. This works well if I don't use STRawGroupDir
, thus surrounding the above template files with formal specification syntax.
But now I use the raw template files and try to invoke it like this:
STGroup group = new STRawGroupDir("templatesRaw", '$', '$');
ST st = group.getInstanceOf("mainRaw");
st.add("name", "John");
String result = st.render();
System.out.println(result);
The problem I have is the following output:
context [/mainRaw] 3:1 attribute lastLine isn't defined
context [/mainRaw /footerRaw] 2:1 attribute lastLine isn't defined
Hello John
Then do the footer:
Simple footer. And now a last line:
.
This means ST isn't able to detect the parameter lastline
in contrast to use the same with non-RAW group files.
P.S.: I was asked to open a bug report in my stackoverflow question: http://stackoverflow.com/questions/21986565/how-to-init-argument-for-sub-template-in-template-with-strawgroupdir.
"Filkov, Hristo" writes:
I saw that version 4.0.4 is already released and I am glad about it. We are still working with the old version 4.0.3 and I think I found another bug, which appears also in the new 4.0.4 version.
The problem is, that on a recursive call of the templates a parameter being passed through, suddenly changes its value between the calls. In order to demonstrate the bug, I build a little directory. You can find the expected result in a file inside between sources, string templates and classes. The value change happens in particular while the "std_field_text" is being called from the "generic_field". I left the debugging messages in the code for you.
The bug appears with Java 1.5 and 1.6 on WinXp machine.
I looked over the released notes of the new version 4.0.4, but I did not understood, whether the problems I mentioned in my previous e-mails are solved. Both problems had to do with formatting by a renderer. As a memory hook, here both pieces of code that didn't work.
templateUrl() ::= << http://www.google.de?param1=2¶m2=5 >>
templateLink() ::= << <a href="$templateUrl();format="htmlattr"$">Link</a> >>
and
template1(someObject) ::= <<$someObject.someCollection:{element|$template2(element)$}$>>
template2(someElement) ::= <<$someElement;format=?someFormat?$>>
In both cases I had to use a workaround to get the outputs formatted. Could you please tell me, if the current status with these problems has changed in Version 4.0.4.
As can be see here registerRenderer clears typeToAdaptorCache
not typeToRendererCache
. This means that once a call to getAttributeRenderer
has put something in the cache you can't override that cached entry.
STGroupDir.load()
method tries to open .stg
file first. If FileNotFoundException
is thrown then it loads the template with .st
extension. I don't think that URL handler implementations are forced to use FileNotFoundException
in any situation. That is why the piece of code is wrong.
I am having problems on Jboss 5 AS. It is the same problem as discussed at http://markmail.org/message/6gckxbon2rzvxzhu . This was fixed in 42d8bb0, but unfortunatelly it got commented out in the next commit 60e1b24.
I know that this might be problem only for Jboss 5 AS (no issues in Jboss 7, but unfortunately I am stuck with version 5). On the other hand it just does not seem correct to assume that URL handler will return FileNotFoundException
.
Hi,
While building antlr4 from the git repo, I noticed that there is a missing target for STParser.g in stringtemplate4. Since I was starting from a clean checkout, I got an error because the tokens for STParser are never generated. Below is a diff of the change that I made to build.xml:
--- build.xml 2012-11-20 20:10:57.000000000 -0700
+++ ../stringtemplate4.mod/build.xml 2012-11-20 19:53:03.000000000 -0700
@@ -32,6 +32,7 @@
dir="${src.dir}/org/stringtemplate/v4/compiler">
<arg value="-make"/>
<arg value="Group.g"/>
+ <arg value="STParser.g"/>
<arg value="CodeGenerator.g"/>
<classpath>
<pathelement location="${antlr3.jar}"/>
I'm using Antlr4.StringTemplate.4.0.6.9004 on .NET (.net3.5, assembly: runtime version - v2.0.50727, version - 4.0.6.9004).
I have pretty large context object for template. Rendering is executed and I get the result, but at some moment the rendering of inner elements is not performed and the result is truncated. The size of result file is 284 916 bytes.
Maybe there are some restrictions on size of result document?
I've tried both Template.Render() and Template.Write() APIs.
If you need I'll attach the template and the result truncated file.
Could you please add maven-bundle-plugin into StringTemplate/ANTLR pom.xml and OSGify these libraries?
Given a hashmap 'var' added as an attribute to ST, and the following template.
$["0","1"]:{ x |
$x$
$if(x)$y$endif$
$if({$x$})$y$endif$
$if(({$x$}))$z$endif$
$var.(x)$
$var.({$x$})$ $! <---- error here !$
$var.(({$x$}))$
$if(var.(x))$OK$else$NO$endif$
$if(var.({$x$}))$OK$else$NO$endif$ $! <---- error here !$
$if(var.(({$x$})))$OK$else$NO$endif$ $! <---- error here !$
}$
I get the following errors (also marked out)
context [/_sub4] 8:11 attribute x isn't defined
context [/_sub6] 12:14 attribute x isn't defined
context [/_sub7] 13:15 attribute x isn't defined
This is a complete showstopper for me using v4 of stringtemplate. Is this easily fixable, and if possible, is there also currently a workaround for this?
Currently group files must contain at least 1 template or GroupParser
will report a syntax error. This requirement doesn't make sense for groups that only import other groups.
Changing the delimiters at the group file level doesn't work if the STGroupFile class is used to load templates. I tried using both the 'delimiters' command in the stg root file as well as passing in chars to the STGroupFile constructor. With both approaches, the compiler behaves as though the delimiters are still the default < and >.
Delimiters did work when I reverted to STGroupDir.
Tested with the ST 4.0.7 binary jar.
In STv3 I had the following construct to handle method calls:
method(<argumentsList:{it | <if(it.condition)><it.content><endif>}; separator=", ">);
It used to print only the arguments having the condtion attribute set, separated by commas. In ST4.0.6, the elements not matching the condition are evaluated as empty instead of null, causing separators to appear at unwanted places. The only workaround I found was to maintain multiple lists of parameters, which is very painful in my case.
We use StringTemplate in multi-threaded configuration, where we create a single STGroup
instance, and multiple threads call group.getInstanceOf
and render
.
The problem is we (sometimes) get attribute XYZ isn't defined
error, although the attribute XYZ
(which is a map/dictionary template) is clearly defined in an imported template.
My guess is that StringTemplate has thread safety issues when (but not limited to) a dictionary that is defined in an imported template file is accessed.
I went over the source code and found a few places that potentially have thread safety issue.
STGroup
(STGroupFile
) object. STGroupFile
calls load()
method lazily when necessary, so multiple thread can simultaneously initialize the object (which may or may not be a problem). I think probably load()
should be synchronized.CompiledST
object is being modified after added to the synchronized templates
dictionary.STGroup.java
in defineRegion
method code.defineArgDefaultValueTemplates(this)
and code.defineImplicitlyDefinedTemplates(this)
is called after the invocation of the rawDefineTemplate
method, which puts CompiledST
object into the synchronized map. Thus another thread may see an incomplete CompiledST
object.I did not check all the code, so there might be other places with thread safety issues. I made STGroup.getInstanceOf
, STGroup.getEmbeddedInstanceOf
, and ST.render
to be synchronized with respect to the STGroup
instance, and the attribute error went away.
I suggest that those three methods to be synchronized; but also someone should go over all the code and check if any other thread-safety issue is there. Any code that does lazy evaluation should be examined for thread safety.
When trying to inspect a main template of this group:
main(doit = true) ::= "<if(doit || other)><t(...)><endif>\"
t2() ::= "Hello"
t(x={<(t2())>}) ::= "<x>"
ST4 throws an ArrayIndexOutOfBoundsException
in STRuntimeMessage.getSourceLocation
.
Interestingly removing the "|| other" let you inspect the template.
Also making the default for x = {<t2()>}
(i.e. use lazy evaluation) and keeping the "|| other" also works fine.
I added a test case to TestEarlyEvaluation
and checked it in into Perforce.
Udo
P.S.: here the stack track
java.lang.ArrayIndexOutOfBoundsException: 17
at org.stringtemplate.v4.misc.STRuntimeMessage.getSourceLocation(STRuntimeMessage.java:70)
at org.stringtemplate.v4.misc.STRuntimeMessage.toString(STRuntimeMessage.java:81)
at javax.swing.DefaultListCellRenderer.getListCellRendererComponent(DefaultListCellRenderer.java:134)
at javax.swing.plaf.basic.BasicListUI.updateLayoutState(BasicListUI.java:1344)
at javax.swing.plaf.basic.BasicListUI.maybeUpdateLayoutState(BasicListUI.java:1294)
at javax.swing.plaf.basic.BasicListUI.getPreferredSize(BasicListUI.java:561)
at javax.swing.JComponent.getPreferredSize(JComponent.java:1634)
at javax.swing.JList.getPreferredScrollableViewportSize(JList.java:2412)
at javax.swing.ViewportLayout.preferredLayoutSize(ViewportLayout.java:75)
at java.awt.Container.preferredSize(Container.java:1599)
at java.awt.Container.getPreferredSize(Container.java:1584)
at javax.swing.JComponent.getPreferredSize(JComponent.java:1636)
at javax.swing.ScrollPaneLayout.preferredLayoutSize(ScrollPaneLayout.java:475)
at java.awt.Container.preferredSize(Container.java:1599)
at java.awt.Container.getPreferredSize(Container.java:1584)
at javax.swing.JComponent.getPreferredSize(JComponent.java:1636)
at java.awt.GridBagLayout.GetLayoutInfo(GridBagLayout.java:1092)
at java.awt.GridBagLayout.getLayoutInfo(GridBagLayout.java:893)
at java.awt.GridBagLayout.preferredLayoutSize(GridBagLayout.java:713)
at java.awt.Container.preferredSize(Container.java:1599)
at java.awt.Container.getPreferredSize(Container.java:1584)
at javax.swing.JComponent.getPreferredSize(JComponent.java:1636)
at javax.swing.JRootPane$RootLayout.preferredLayoutSize(JRootPane.java:907)
at java.awt.Container.preferredSize(Container.java:1599)
at java.awt.Container.getPreferredSize(Container.java:1584)
at javax.swing.JComponent.getPreferredSize(JComponent.java:1636)
at java.awt.BorderLayout.preferredLayoutSize(BorderLayout.java:702)
at java.awt.Container.preferredSize(Container.java:1599)
at java.awt.Container.getPreferredSize(Container.java:1584)
at java.awt.Window.pack(Window.java:706)
at org.stringtemplate.v4.gui.STViz.open(STViz.java:212)
at org.stringtemplate.v4.ST.inspect(ST.java:471)
at org.stringtemplate.v4.ST.inspect(ST.java:454)
at org.stringtemplate.v4.ST.inspect(ST.java:447)
at org.stringtemplate.v4.test.TestEarlyEvaluation.testBugArrayIndexOutOfBoundsExceptionInSTRuntimeMessage_getSourceLocation(TestEarlyEvaluation.java:138)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:597)
at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:44)
at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:15)
at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:41)
at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:20)
at org.junit.internal.runners.statements.RunBefores.evaluate(RunBefores.java:28)
at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:76)
at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:50)
at org.junit.runners.ParentRunner$3.run(ParentRunner.java:193)
at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:52)
at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:191)
at org.junit.runners.ParentRunner.access$000(ParentRunner.java:42)
at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:184)
at org.junit.runners.ParentRunner.run(ParentRunner.java:236)
at org.eclipse.jdt.internal.junit4.runner.JUnit4TestReference.run(JUnit4TestReference.java:49)
at org.eclipse.jdt.internal.junit.runner.TestExecution.run(TestExecution.java:38)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:467)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:683)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run(RemoteTestRunner.java:390)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main(RemoteTestRunner.java:197)
stringtemplate-interest mailing list
[email protected]
http://www.antlr.org/mailman/listinfo/stringtemplate-interest
Also: to avoid confusion with the Java null maybe call the constant 'undefined'?
I was kind of thinking that it should be null because it has the same semantics as passing all in to add().
Actually this is not the case as you can see in the following test case. That's why I thought mixing "null" und "undefined" isn't such a good idea.
BTW: in the implementation the "undefined" literal should probably get the value ST.EMPTY_ATTR rather than null.
public class UndefinedOrNullTest extends BaseTest {
@Test
public void testUndefinedParameter() throws Exception {
writeFile(tmpdir, "t.stg", "t(s=\"world\") ::= <<\nHello <s>\n>>");
String path = tmpdir + "t.stg";
STGroup group = new STGroupFile(tmpdir + "/t.stg");
ST st = group.getInstanceOf("t");
String s = st.render();
Assert.assertEquals("Hello world", s);
}
@Test
public void testNullParameter() throws Exception {
writeFile(tmpdir, "t.stg", "t(s=\"world\") ::= <<\nHello <s>\n>>");
String path = tmpdir + "t.stg";
STGroup group = new STGroupFile(tmpdir + "/t.stg");
ST st = group.getInstanceOf("t");
st.add("s", null);
String s = st.render();
Assert.assertEquals("Hello ", s);
}
}
Udo
On 01.08.2011, at 21:33, Terence Parr wrote:
On Aug 1, 2011, at 7:10 AM, Udo Borkowski wrote:
Not sure about the semantic of null.
E.g. assume you have this template
t(s="world") ::= "Hello <s>"
What will
<t(null)>
render?
a) "Hello " (i.e. same as <t("")>
)
b) "Hello world" (i.e. same as <t()>
)
I would assume it would render this one since the parameters missing.
c) "Hello null"
d) something else?
Also: to avoid confusion with the Java null maybe call the constant 'undefined'?
I was kind of thinking that it should be null because it has the same semantics as passing all in to add().
Ter
stringtemplate-interest mailing list
[email protected]
http://www.antlr.org/mailman/listinfo/stringtemplate-interest
stringtemplate-interest mailing list
[email protected]
http://www.antlr.org/mailman/listinfo/stringtemplate-interest
Begin forwarded message:
From: Udo Borkowski
Subject: [stringtemplate-interest] ST4: Pass Thru (...) support for indirect includes
Date: August 7, 2011 12:42:43 AM PDT
To: stringtemplate-interest List [email protected]
Is there a reason why indirect includes don't support Pass Thru (…
)?
E.g.
t1(x) ::= "<x>"
main(x="hello",t="t1") ::= "<(t)(...)>"
will emit the following error:
t.stg 2:34: mismatched input '...' expecting RPAREN
However explicitly passing the parameter (x) with the indirect include, like in this example:
t1(x) ::= "<x>"
main(x="hello",t="t1") ::= "<(t)(x)>"
works fine.
If there is no real reason for this restriction I suggest to add "Pass Thru" support for indirect calls into the next release of ST4.
Udo
P.S.: Possibly the same applies for "named arguments" and indirect includes.
P.P.S.: here the test case:
@Test
public void testIndirectCallWithPassThru() throws Exception {
String path = tmpdir + "t.stg";
// indirectly call t1, with explicit parameter passing
writeFile(tmpdir, "t.stg",
"t1(x) ::= \"<x>\"\nmain(x=\"hello\",t=\"t1\") ::= <<\n<(t)(x)>\n>>");
STGroup group = new STGroupFile(tmpdir + "/t.stg");
ST st = group.getInstanceOf("main");
String s = st.render();
Assert.assertEquals("hello", s);
// indirectly call t1, with "pass thru" (...) parameter passing
// (used to fail with:
// "t.stg 2:21: mismatched input '...' expecting RPAREN")
writeFile(tmpdir, "t.stg",
"t1(x) ::= \"<x>\"\nmain(x=\"hello\",t=\"t1\") ::= <<\n<(t)(...)>\n>>");
group = new STGroupFile(tmpdir + "/t.stg");
st = group.getInstanceOf("main");
s = st.render();
Assert.assertEquals("hello", s);
}
Due to the way getAttributeRenderer
and getModelAdaptor
are implemented the order of registration matters more than the class.
This means that if I register:
stGroup.registerRenderer(java.util.Date.class, new DateTimeRenderer());
stGroup.registerRenderer(java.sql.Date.class, new DateRenderer());
Then DateTimeRenderer
will be used to render objects of type java.sql.Date
.
This seems wrong.
Hello, I'm using ST 4.0.4 and there is a problem with last()
(and maybe with rest() and the other list functions). They are not working with primitive arrays, because it tries to cast the primitive array to Object[]
:
<== Interpreter.class line 928 ==>
else if ( v.getClass().isArray() ) {
Object[] elems = (Object[])v;
return elems[elems.length-1];
}
Exception on line 929:
com.anrisoftware.fdsanalysis.keys.project.OutputException: Error process the template: context [/head_derived_data /datacolumns] 1:35 internal error: java.lang.ClassCastException: [I cannot be cast to [Ljava.lang.Object;
Kind regards, Erwin.
Hi! I'm getting a StackOverflow error, and I'm not sure why. The error is below:
Exception in thread "main" java.lang.StackOverflowError
at org.stringtemplate.v4.InstanceScope.<init>(InstanceScope.java:72)
at org.stringtemplate.v4.Interpreter.writeObject(Interpreter.java:692)
at org.stringtemplate.v4.Interpreter.writeObjectNoOptions(Interpreter.java:635)
at org.stringtemplate.v4.Interpreter._exec(Interpreter.java:285)
at org.stringtemplate.v4.Interpreter.exec(Interpreter.java:145)
at org.stringtemplate.v4.Interpreter.writeObject(Interpreter.java:703)
at org.stringtemplate.v4.Interpreter.writeObjectNoOptions(Interpreter.java:635)
at org.stringtemplate.v4.Interpreter._exec(Interpreter.java:285)
at org.stringtemplate.v4.Interpreter.exec(Interpreter.java:145)
at org.stringtemplate.v4.Interpreter.writeObject(Interpreter.java:703)
I saw issue #9 and it looks similar, but as far as I can tell I'm not doing anything recursive. The relevant subset of my template group file is below:
whileBlock(condition, statement) ::= <<
WHILE (<condition>) DO
<statement>
ENDWHILE
>>
forBlock(initialization, condition, continuation, statement) ::= <<
<initialization>
<whileBlock(condition, {<statement> <continuation>})>
>>
I only get this error when I call forBlock
. Am I doing something silly here?
With ST 4.0.7 calling STGroup.getInstanceOf()
on a STRawGroupDir
or STGroupDir
always results in a NullPointerException
.
The impl
variable declared in STGroup
line 662 is always null and accessing it in line 663 causes the NPE. This is indeed on first invocation, so the STGroup.templates
cache has never been supplied with a CompiledST
instance.
Stack trace if it matters:
Exception in thread "pool-2-thread-1" java.lang.NullPointerException
at org.stringtemplate.v4.STGroup.loadTemplateFile(STGroup.java:663)
at org.stringtemplate.v4.STGroupDir.loadTemplateFile(STGroupDir.java:176)
at org.stringtemplate.v4.STGroupDir.load(STGroupDir.java:136)
at org.stringtemplate.v4.STGroup.lookupTemplate(STGroup.java:237)
at org.stringtemplate.v4.STGroup.getInstanceOf(STGroup.java:172)
at com.bioql.web.render.RenderingService.render(RenderingService.java:43)
at com.bioql.web.handlers.HelloWorldTemplateHandler.handle(HelloWorldTemplateHandler.java:29)
at com.bioql.web.HttpServer$DefaultContainer$1.run(HttpServer.java:60)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1110)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:603)
at java.lang.Thread.run(Thread.java:722)
Previously, v3, it was possible to use dictionaries to select templates.
auxMap ::= [
"E": "eTmpl",
"I": "impl",
"F": "fTmpl",
default: "defaultTmpl"
]
makeTmpl(type, field) ::= <<
<(auxMap.(type))(field=field)>
>>
eTmpl(field) ::= "electric <field>"
fTmpl(field) ::= "<field> force"
iTmpl(field) ::= "in <field> between"
defaultTmpl(field) ::= "<field>"
If it is not clear the troublesome bit is
<(auxMap.(type))(field=field)>
The documentation suggests that is should still work.
http://www.antlr.org/wiki/display/ST4/StringTemplate+cheat+sheet
<(expr)(argument-list)>
If this was taken away intentionally what is the recommended replacement?
The error message when this syntax is used is
'=' came as a complete surprise to me
which I don't see has anything to do with the actual problem.
The default DateRenderer
disregards the locale received as argument:
public void testLocale() {
String input = "$date; format=\"dd 'de' MMMMM 'de' yyyy\"$";
ST st = StringTemplateUtil.createTemplate(input);
Calendar cal = Calendar.getInstance();
cal.set(2012, Calendar.JUNE, 12);
st.add("date", cal.getTime());
assertEquals("25 de Junho de 2012", st.render(new Locale("pt")));
}
I think it's just a matter of modifying DateRenderer
to pass forward the locale argument to SimpleDateFormat(String pattern, Locale locale)
and DateFormat.getInstance(int style, Locale locale)
.
There seems to be a bug in 4.0.5 in iterating Lists when using STRawGroupDir. See this Unit test:
https://gist.github.com/1943633
The first test behaves as expected. The second throws an error. I expected both tests to pass.
This is the final issue to close the StringTemplate 4.0.7 milestone.
The last line in this code snipette is from ST().add(...) is a bug.
It is possible for locals to have a length of zero, you can't assign EMPTY_ATTR to an array with zero length.
It means lines in my code like:
page.add("something", "value");
Fail with an array exception. I get some other array exceptions as well, but I don't know why. See below.
arg = new FormalArgument(name);
impl.addArg(arg);
if ( locals==null ) locals = new Object[1];
//else locals = Arrays.copyOf(locals, impl.formalArguments.size());
else {
Object[] copy = new Object[impl.formalArguments.size()];
System.arraycopy(locals, 0, copy, 0,
Math.min(locals.length, impl.formalArguments.size()));
locals = copy;
}
locals[arg.index] = EMPTY_ATTR;
I also sometimes see this exception, no idea how to reproduce it though:
java.lang.ArrayIndexOutOfBoundsException: 4
org.stringtemplate.v4.ST.add():246
myapp.package.getPage():321
A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.