Skip to content

Commit df58d80

Browse files
author
Sam Pullara
committed
_ extension requires a function
1 parent 23d559d commit df58d80

File tree

4 files changed

+72
-43
lines changed

4 files changed

+72
-43
lines changed

builder/src/main/java/com/sampullara/mustache/MustacheBuilder.java

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,9 @@
1515
import java.util.concurrent.atomic.AtomicInteger;
1616

1717
import com.google.common.base.Charsets;
18+
import com.google.common.base.Function;
19+
import com.google.common.collect.Iterables;
20+
import com.google.common.collect.Lists;
1821

1922
import com.sampullara.util.FutureWriter;
2023

@@ -150,6 +153,7 @@ protected List<Code> compile(final Mustache m, final Reader br, String tag, fina
150153
switch (ch) {
151154
case '#':
152155
case '^':
156+
case '_':
153157
case '?': {
154158
int start = currentLine.get();
155159
final List<Code> codes = compile(m, br, variable, currentLine, file);
@@ -168,6 +172,9 @@ protected List<Code> compile(final Mustache m, final Reader br, String tag, fina
168172
case '?':
169173
list.add(new IfIterableCode(m, variable, codes, file, currentLine.get()));
170174
break;
175+
case '_':
176+
list.add(new FunctionCode(m, variable, codes, file, currentLine.get()));
177+
break;
171178
}
172179
iterable = lines != 0;
173180
break;
@@ -302,6 +309,24 @@ public void execute(FutureWriter fw, Scope scope) throws MustacheException {
302309
}
303310
}
304311

312+
private static class FunctionCode extends SubCode {
313+
public FunctionCode(Mustache m, String variable, List<Code> codes, String file, int line) {
314+
super(m, variable, codes, file, line);
315+
}
316+
317+
@Override
318+
public void execute(FutureWriter fw, Scope scope) throws MustacheException {
319+
Object function = m.getValue(scope, variable);
320+
if (function instanceof Function) {
321+
execute(fw, m.function(scope, (Function) function));
322+
} else if (function == null) {
323+
execute(fw, Lists.newArrayList(scope));
324+
} else {
325+
throw new MustacheException("Not a function: " + function);
326+
}
327+
}
328+
}
329+
305330
private static class IfIterableCode extends SubCode {
306331
public IfIterableCode(Mustache m, String variable, List<Code> codes, String file, int line) {
307332
super(m, variable, codes, file, line);

core/src/main/java/com/sampullara/mustache/Mustache.java

Lines changed: 45 additions & 43 deletions
Original file line numberDiff line numberDiff line change
@@ -246,53 +246,12 @@ protected Iterable<Scope> iterable(final Scope s, final String name) {
246246
String traceName = parent == null ? s.getClass().getName() : parent.getClass().getName();
247247
event = MustacheTrace.addEvent("iterable: " + name, traceName);
248248
}
249-
final String finalName = name;
250249
final Object value = getValue(s, name);
251250
if (value instanceof Function) {
252251
if (trace) {
253252
event.end();
254253
}
255-
final Function f = (Function) value;
256-
return new Iterable<Scope>() {
257-
@Override
258-
public Iterator<Scope> iterator() {
259-
return new Iterator<Scope>() {
260-
boolean first = true;
261-
StringWriter writer = new StringWriter();
262-
263-
@Override
264-
public synchronized boolean hasNext() {
265-
if (first) {
266-
capturedWriter.set(new FutureWriter(writer));
267-
} else {
268-
try {
269-
capturedWriter.get().flush();
270-
capturedWriter.set(null);
271-
Object apply = f.apply(writer.toString());
272-
actual.get().write(apply == null ? null : String.valueOf(apply));
273-
actual.set(null);
274-
} catch (Exception e) {
275-
logger.log(Level.SEVERE, "Could not apply function: " + f, e);
276-
}
277-
}
278-
return first;
279-
}
280-
281-
@Override
282-
public synchronized Scope next() {
283-
if (first) {
284-
first = false;
285-
return s;
286-
}
287-
throw new NoSuchElementException();
288-
}
289-
290-
@Override
291-
public void remove() {
292-
}
293-
};
294-
}
295-
};
254+
return function(s, (Function) value);
296255
}
297256
if (trace) {
298257
event.end();
@@ -345,7 +304,7 @@ public Scope next() {
345304
} else {
346305
scope = new Scope(s);
347306
}
348-
scope.put(finalName, value);
307+
scope.put(name, value);
349308
return scope;
350309
}
351310

@@ -357,6 +316,49 @@ public void remove() {
357316
};
358317
}
359318

319+
public Iterable<Scope> function(final Scope s, final Function f) {
320+
return new Iterable<Scope>() {
321+
@Override
322+
public Iterator<Scope> iterator() {
323+
return new Iterator<Scope>() {
324+
boolean first = true;
325+
StringWriter writer = new StringWriter();
326+
327+
@Override
328+
public synchronized boolean hasNext() {
329+
if (first) {
330+
capturedWriter.set(new FutureWriter(writer));
331+
} else {
332+
try {
333+
capturedWriter.get().flush();
334+
capturedWriter.set(null);
335+
Object apply = f.apply(writer.toString());
336+
actual.get().write(apply == null ? null : String.valueOf(apply));
337+
actual.set(null);
338+
} catch (Exception e) {
339+
logger.log(Level.SEVERE, "Could not apply function: " + f, e);
340+
}
341+
}
342+
return first;
343+
}
344+
345+
@Override
346+
public synchronized Scope next() {
347+
if (first) {
348+
first = false;
349+
return s;
350+
}
351+
throw new NoSuchElementException();
352+
}
353+
354+
@Override
355+
public void remove() {
356+
}
357+
};
358+
}
359+
};
360+
}
361+
360362
public void setMustacheJava(MustacheJava mj) {
361363
this.mj = mj;
362364
}

src/test/resources/lambda.html

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,2 +1,3 @@
11
{{#translate}}Hello{{/translate}}
2+
{{_translate}}Hello{{/translate}}
23
{{#translate}}{{#translate}}Hello{{/translate}}{{/translate}}

src/test/resources/lambda.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,2 +1,3 @@
11
Hola
2+
Hola
23
Hello

0 commit comments

Comments
 (0)