diff --git a/jooby-ftl/src/main/java/org/jooby/internal/ftl/Engine.java b/jooby-ftl/src/main/java/org/jooby/internal/ftl/Engine.java index 1e4e125068..14f0fdbdfb 100644 --- a/jooby-ftl/src/main/java/org/jooby/internal/ftl/Engine.java +++ b/jooby-ftl/src/main/java/org/jooby/internal/ftl/Engine.java @@ -24,6 +24,7 @@ import java.io.StringWriter; import java.nio.charset.Charset; import java.util.HashMap; +import java.util.Locale; import java.util.Map; import org.jooby.MediaType; @@ -62,8 +63,13 @@ public void render(final View view, final Renderer.Context ctx) throws Exception hash.put("_vpath", template.getName()); hash.put("xss", xss); + // Locale: + Locale locale = (Locale) hash.getOrDefault("locale", ctx.locale()); + hash.putIfAbsent("locale", locale); + // locals - hash.putAll(ctx.locals()); + Map locals = ctx.locals(); + hash.putAll(locals); // model hash.putAll(view.model()); @@ -72,6 +78,9 @@ public void render(final View view, final Renderer.Context ctx) throws Exception // TODO: remove string writer StringWriter writer = new StringWriter(); + // Locale: + template.setLocale(locale); + // output template.process(model, writer); ctx.type(MediaType.html) @@ -97,5 +106,4 @@ public String toString() { return name(); } - } diff --git a/jooby-hbs/src/main/java/org/jooby/internal/hbs/HbsEngine.java b/jooby-hbs/src/main/java/org/jooby/internal/hbs/HbsEngine.java index 8b598adebc..7ab145da3f 100644 --- a/jooby-hbs/src/main/java/org/jooby/internal/hbs/HbsEngine.java +++ b/jooby-hbs/src/main/java/org/jooby/internal/hbs/HbsEngine.java @@ -20,6 +20,7 @@ import static java.util.Objects.requireNonNull; +import java.util.Locale; import java.util.Map; import org.jooby.MediaType; @@ -52,6 +53,10 @@ public void render(final View view, final Renderer.Context ctx) throws Exception locals.putIfAbsent("_vname", vname); locals.putIfAbsent("_vpath", source.filename()); + // Locale: + Locale locale = (Locale) locals.getOrDefault("locale", ctx.locale()); + locals.put("locale", locale); + com.github.jknack.handlebars.Context context = com.github.jknack.handlebars.Context .newBuilder(view.model()) // merge request locals (req+sessions locals) diff --git a/jooby-jade/src/main/java/org/jooby/jade/Engine.java b/jooby-jade/src/main/java/org/jooby/jade/Engine.java index 8e96db024b..35ba05921c 100644 --- a/jooby-jade/src/main/java/org/jooby/jade/Engine.java +++ b/jooby-jade/src/main/java/org/jooby/jade/Engine.java @@ -20,6 +20,7 @@ import java.io.FileNotFoundException; import java.util.HashMap; +import java.util.Locale; import java.util.Map; import org.jooby.MediaType; @@ -45,13 +46,19 @@ public void render(final View view, final Context ctx) throws FileNotFoundExcept JadeTemplate template = jadeConfiguration.getTemplate(name); + Map locals = ctx.locals(); + Map hash = new HashMap<>(); hash.put("_vname", view.name()); hash.put("_vpath", name); + // Locale: + Locale locale = (Locale) locals.getOrDefault("locale", ctx.locale()); + hash.put("locale", locale); + // locals & model - hash.putAll(ctx.locals()); + hash.putAll(locals); hash.putAll(view.model()); String output = jadeConfiguration.renderTemplate(template, hash); diff --git a/jooby-pebble/src/main/java/org/jooby/pebble/PebbleRenderer.java b/jooby-pebble/src/main/java/org/jooby/pebble/PebbleRenderer.java index 5ba344ad01..0e91412f39 100644 --- a/jooby-pebble/src/main/java/org/jooby/pebble/PebbleRenderer.java +++ b/jooby-pebble/src/main/java/org/jooby/pebble/PebbleRenderer.java @@ -22,6 +22,7 @@ import java.io.StringWriter; import java.io.Writer; import java.util.HashMap; +import java.util.Locale; import java.util.Map; import org.jooby.MediaType; @@ -44,18 +45,26 @@ public PebbleRenderer(final PebbleEngine pebble) { public void render(final View view, final Renderer.Context ctx) throws Exception { String vname = view.name(); try { + Map locals = ctx.locals(); + PebbleTemplate template = pebble.getTemplate(vname); Writer writer = new StringWriter(); Map model = new HashMap<>(); + // push locals - model.putAll(ctx.locals()); + model.putAll(locals); model.putIfAbsent("_vname", vname); + // Locale: + Locale locale = (Locale) locals.getOrDefault("locale", ctx.locale()); + model.putIfAbsent("locale", locale); + // put model model.putAll(view.model()); // render and send - template.evaluate(writer, model); + template.evaluate(writer, model, locale); + ctx.type(MediaType.html) .send(writer.toString()); } catch (LoaderException x) { diff --git a/jooby-pebble/src/test/java/org/jooby/pebble/Issue725.java b/jooby-pebble/src/test/java/org/jooby/pebble/Issue725.java index d1aea6f663..0f1fcbfa8c 100644 --- a/jooby-pebble/src/test/java/org/jooby/pebble/Issue725.java +++ b/jooby-pebble/src/test/java/org/jooby/pebble/Issue725.java @@ -7,6 +7,7 @@ import java.io.FileNotFoundException; import java.io.StringWriter; import java.util.HashMap; +import java.util.Locale; import java.util.Map; import org.jooby.MediaType; @@ -31,12 +32,15 @@ public class Issue725 { public void templateNotFound() throws Exception { new MockUnit(PebbleEngine.class, View.class, Renderer.Context.class) .expect(unit -> { + Locale locale = Locale.ENGLISH; Map vmodel = unit.mock(Map.class); Map locals = unit.mock(Map.class); + expect(locals.getOrDefault("locale", locale)).andReturn(locale); Map model = unit.constructor(HashMap.class).build(); model.putAll(locals); expect(model.putIfAbsent("_vname", "vname")).andReturn(null); + expect(model.putIfAbsent("locale", locale)).andReturn(null); model.putAll(vmodel); View view = unit.get(View.class); @@ -47,11 +51,12 @@ public void templateNotFound() throws Exception { Renderer.Context ctx = unit.get(Renderer.Context.class); expect(ctx.locals()).andReturn(locals); + expect(ctx.locale()).andReturn(locale); expect(ctx.type(MediaType.html)).andReturn(ctx); ctx.send(writer.toString()); PebbleTemplate template = unit.mock(PebbleTemplate.class); - template.evaluate(writer, model); + template.evaluate(writer, model, locale); LoaderException x = new LoaderException(null, "template not found"); expectLastCall().andThrow(x); diff --git a/jooby-pebble/src/test/java/org/jooby/pebble/PebbleRendererTest.java b/jooby-pebble/src/test/java/org/jooby/pebble/PebbleRendererTest.java index 04565223b5..216cab9a3c 100644 --- a/jooby-pebble/src/test/java/org/jooby/pebble/PebbleRendererTest.java +++ b/jooby-pebble/src/test/java/org/jooby/pebble/PebbleRendererTest.java @@ -5,6 +5,7 @@ import java.io.StringWriter; import java.util.HashMap; +import java.util.Locale; import java.util.Map; import org.jooby.MediaType; @@ -28,12 +29,15 @@ public class PebbleRendererTest { public void render() throws Exception { new MockUnit(PebbleEngine.class, View.class, Renderer.Context.class) .expect(unit -> { + Locale locale = Locale.UK; Map vmodel = unit.mock(Map.class); Map locals = unit.mock(Map.class); + expect(locals.getOrDefault("locale", locale)).andReturn(locale); Map model = unit.constructor(HashMap.class).build(); model.putAll(locals); expect(model.putIfAbsent("_vname", "vname")).andReturn(null); + expect(model.putIfAbsent("locale", locale)).andReturn(null); model.putAll(vmodel); View view = unit.get(View.class); @@ -43,12 +47,13 @@ public void render() throws Exception { StringWriter writer = unit.constructor(StringWriter.class).build(); Renderer.Context ctx = unit.get(Renderer.Context.class); + expect(ctx.locale()).andReturn(locale); expect(ctx.locals()).andReturn(locals); expect(ctx.type(MediaType.html)).andReturn(ctx); ctx.send(writer.toString()); PebbleTemplate template = unit.mock(PebbleTemplate.class); - template.evaluate(writer, model); + template.evaluate(writer, model, locale); PebbleEngine pebble = unit.get(PebbleEngine.class); expect(pebble.getTemplate("vname")).andReturn(template); diff --git a/jooby-thymeleaf/src/main/java/org/jooby/thymeleaf/ThlEngine.java b/jooby-thymeleaf/src/main/java/org/jooby/thymeleaf/ThlEngine.java index 75ab2131f1..886ade0642 100644 --- a/jooby-thymeleaf/src/main/java/org/jooby/thymeleaf/ThlEngine.java +++ b/jooby-thymeleaf/src/main/java/org/jooby/thymeleaf/ThlEngine.java @@ -19,6 +19,7 @@ package org.jooby.thymeleaf; import java.io.FileNotFoundException; +import java.util.Locale; import java.util.Map; import org.jooby.Env; @@ -46,11 +47,14 @@ public void render(final View view, final Context ctx) throws FileNotFoundExcept Map vars = ctx.locals(); vars.putIfAbsent("_vname", vname); + // Locale: + Locale locale = (Locale) vars.getOrDefault("locale", ctx.locale()); + Map model = view.model(); vars.forEach(model::putIfAbsent); model.putIfAbsent("xss", new Thlxss(env)); - IContext thlctx = new org.thymeleaf.context.Context(ctx.locale(), model); + IContext thlctx = new org.thymeleaf.context.Context(locale, model); String output = this.engine.process(vname, thlctx); ctx.type(MediaType.html)