Passing a collection to a Freemarker template using Groovy is not working for me

1,408 views
Skip to first unread message

Cory Brownfield

unread,
Dec 5, 2016, 2:04:03 PM12/5/16
to vert.x
I can get collections to work when using Java, but my vertx-web project that uses io.vertx.groovy.ext.web.templ.FreeMarkerTemplateEngine is throwing errors like this:

SEVERE: Unexpected exception in route
FreeMarker template error:
For "#list" list source: Expected a sequence or collection, but this has evaluated to an extended_hash+string (io.vertx.core.json.JsonArray wrapped into f.e.b.StringModel):
==> context.things  [in template "templates/things.ftl" at line 9, column 8]

I've tried using groovy literals for lists and maps.  I've also tried using Java ArrayLists and HashMaps.  Here's my template and code:

Template (things.ftl):

<!doctype html>
<html>
<head>
<meta charset=utf-8>
<title>Things</title>
</head>
<body>
<ul>
<#list context.things as thing>
<li>$thing</li>
</#list>
</ul>
</body>
 
</html>
 
Code (imports excluded):
class SimpleVerticle extends GroovyVerticle {
    @Override
    void start(Future<Void> fut) {
        def router = Router.router(vertx)
        def templateEngine = FreeMarkerTemplateEngine.create()

        router.get("/things").handler({ routingContext ->
            routingContext.put('things', ['thing 1', 'thing 2'])
            templateEngine.render(routingContext, "templates/things.ftl", { res ->
                if (res.succeeded()) {
                    routingContext.response().end(res.result())
                } else {
                    routingContext.fail(res.cause())
                }
            })
        })

        // Server
        final HttpServer server = vertx.createHttpServer([
                ssl            : true,
                keyStoreOptions: [
                        path    : 'keystore.jks',
                        password: ''
                ]
        ])
        server.requestHandler(router.&accept).listen(8443, { result ->
            if (result.succeeded()) {
                fut.complete()
            } else {
                fut.fail(result.cause())
            }
        })
    }
}

Thomas SEGISMONT

unread,
Dec 9, 2016, 6:37:01 AM12/9/16
to ve...@googlegroups.com
This happens because the template engine does not know how to deal with JsonArray objects

In your template file, change:

<#list context.things as thing>

to

<#list context.things.getList() as thing>

and it should work (except I believe the list element should be ${thing} not $thing)

--
You received this message because you are subscribed to the Google Groups "vert.x" group.
To unsubscribe from this group and stop receiving emails from it, send an email to vertx+unsubscribe@googlegroups.com.
Visit this group at https://groups.google.com/group/vertx.
To view this discussion on the web, visit https://groups.google.com/d/msgid/vertx/6cdeda55-daa4-4747-84a0-3997f098c076%40googlegroups.com.
For more options, visit https://groups.google.com/d/optout.

Cory Brownfield

unread,
Dec 9, 2016, 9:49:39 AM12/9/16
to ve...@googlegroups.com
Thanks!  The call to "toList" did the trick.

--
You received this message because you are subscribed to a topic in the Google Groups "vert.x" group.
To unsubscribe from this topic, visit https://groups.google.com/d/topic/vertx/FI86Eqg5Z08/unsubscribe.
To unsubscribe from this group and all its topics, send an email to vertx+unsubscribe@googlegroups.com.
Reply all
Reply to author
Forward
0 new messages