Reputation: 349
I'm trying to convert the below velocity macro into a velocity Java directive, as I need to add some bells and whistles around the rendering logic:
#macro(renderModules $modules)
#if($modules)
#foreach($module in $modules)
#if(${module.template})
#set($moduleData = $module.data)
#parse("${module.template}.vm")
#end
#end
#end
#end
My equivalent Java Directive:
import org.apache.velocity.context.InternalContextAdapter;
import org.apache.velocity.exception.MethodInvocationException;
import org.apache.velocity.exception.ParseErrorException;
import org.apache.velocity.exception.ResourceNotFoundException;
import org.apache.velocity.runtime.directive.Directive;
import org.apache.velocity.runtime.parser.node.ASTBlock;
import org.apache.velocity.runtime.parser.node.Node;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.io.IOException;
import java.io.Writer;
import java.util.List;
public class RenderModulesDirective extends Directive {
private static final Logger LOGGER = LoggerFactory.getLogger(RenderModulesDirective.class);
@Override
public String getName() {
return "renderModules";
}
@Override
public int getType() {
return LINE;
}
@Override
public boolean render(InternalContextAdapter context, Writer writer, Node node) throws IOException, ResourceNotFoundException, ParseErrorException, MethodInvocationException {
for(int i=0; i<node.jjtGetNumChildren(); i++) {
Node modulesNode = node.jjtGetChild(i);
if (modulesNode != null) {
if(!(modulesNode instanceof ASTBlock)) {
if(i == 0) {
// This should be the list of modules
List<Module> modules = (List<Module>) modulesNode.value(context);
if(modules != null) {
for (Module module : modules) {
context.put("moduleData", module.getData());
String templateName = module.getTemplate() + ".vm";
try {
// ??? How to parse the template here ???
} catch(Exception e) {
LOGGER.error("Encountered an error while rendering the Module {}", module, e);
}
}
break;
}
}
}
}
}
return true;
}
}
So, I'm stuck at the point where I need the Java equivalent of the #parse("<template_name>.vm")
call. Is this the right approach? Would it help to instead extend from the Parse
directive?
Upvotes: 0
Views: 667
Reputation: 24
I believe
Template template = Velocity.getTemplate("path/to/template.vm");
template.merge(context, writer);
will accomplish what you're looking to do.
If you have access to RuntimeServices you could call createNewParser()
and then call parse(Reader reader, String templateName)
inside of the parser, the SimpleNode that comes out has a render()
method which I think is what you're looking fo
Upvotes: 1