NIHVIVO-564 Going back to using toString() methods for template model dump since it already handles nested collections. Improvements to DumpDataModelDirective so it dumps out values as well as variable names.
This commit is contained in:
parent
98e5283ab1
commit
1ccde72b40
6 changed files with 111 additions and 53 deletions
|
@ -6,12 +6,17 @@ import java.io.IOException;
|
||||||
import java.io.Writer;
|
import java.io.Writer;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
|
import java.util.HashMap;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
import java.util.Set;
|
|
||||||
|
|
||||||
import edu.cornell.mannlib.vitro.webapp.utils.StringUtils;
|
import org.apache.commons.logging.Log;
|
||||||
|
import org.apache.commons.logging.LogFactory;
|
||||||
|
|
||||||
|
import edu.cornell.mannlib.vitro.webapp.controller.freemarker.FreemarkerHelper;
|
||||||
|
|
||||||
import freemarker.core.Environment;
|
import freemarker.core.Environment;
|
||||||
|
import freemarker.template.Configuration;
|
||||||
import freemarker.template.TemplateDirectiveBody;
|
import freemarker.template.TemplateDirectiveBody;
|
||||||
import freemarker.template.TemplateDirectiveModel;
|
import freemarker.template.TemplateDirectiveModel;
|
||||||
import freemarker.template.TemplateException;
|
import freemarker.template.TemplateException;
|
||||||
|
@ -22,49 +27,55 @@ import freemarker.template.utility.DeepUnwrap;
|
||||||
|
|
||||||
public class DumpDataModelDirective implements TemplateDirectiveModel {
|
public class DumpDataModelDirective implements TemplateDirectiveModel {
|
||||||
|
|
||||||
@SuppressWarnings({ "unchecked", "deprecation" })
|
private static final Log log = LogFactory.getLog(DumpDataModelDirective.class);
|
||||||
|
|
||||||
|
@SuppressWarnings({ "unchecked" })
|
||||||
@Override
|
@Override
|
||||||
public void execute(Environment env, Map params, TemplateModel[] loopVars,
|
public void execute(Environment env, Map params, TemplateModel[] loopVars,
|
||||||
TemplateDirectiveBody body) throws TemplateException, IOException {
|
TemplateDirectiveBody body) throws TemplateException, IOException {
|
||||||
|
|
||||||
if (params.size() != 0) {
|
if (params.size() != 0) {
|
||||||
throw new TemplateModelException(
|
throw new TemplateModelException(
|
||||||
"The dump directive doesn't allow parameters.");
|
"The dumpDataModel directive doesn't allow parameters.");
|
||||||
}
|
}
|
||||||
if (loopVars.length != 0) {
|
if (loopVars.length != 0) {
|
||||||
throw new TemplateModelException(
|
throw new TemplateModelException(
|
||||||
"The dump directive doesn't allow loop variables.");
|
"The dumpDataModel directive doesn't allow loop variables.");
|
||||||
}
|
}
|
||||||
if (body != null) {
|
if (body != null) {
|
||||||
throw new TemplateModelException(
|
throw new TemplateModelException(
|
||||||
"The dump directive doesn't allow nested content.");
|
"The dumpDataModel directive doesn't allow nested content.");
|
||||||
}
|
}
|
||||||
|
|
||||||
TemplateHashModel dataModel = env.getDataModel();
|
TemplateHashModel dataModel = env.getDataModel();
|
||||||
List<String> models = new ArrayList<String>();
|
Map<String, Object> models = new HashMap<String, Object>();
|
||||||
List<String> directives = new ArrayList<String>();
|
List<String> directives = new ArrayList<String>();
|
||||||
|
|
||||||
Map<String, Object> dm = (Map<String, Object>) DeepUnwrap.permissiveUnwrap(dataModel);
|
Map<String, Object> dm = (Map<String, Object>) DeepUnwrap.permissiveUnwrap(dataModel);
|
||||||
Set varNames = dm.keySet();
|
List<String> varNames = new ArrayList(dm.keySet());
|
||||||
for (Object varName : varNames) {
|
Collections.sort(varNames);
|
||||||
if (dm.get(varName) instanceof TemplateDirectiveModel) {
|
for (String var : varNames) {
|
||||||
directives.add((String) varName);
|
Object value = dm.get(var);
|
||||||
|
if (value instanceof TemplateDirectiveModel) {
|
||||||
|
directives.add((String) var);
|
||||||
} else {
|
} else {
|
||||||
models.add((String) varName);
|
models.put(var, value);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
Collections.sort(models);
|
Configuration config = env.getConfiguration();
|
||||||
Collections.sort(directives);
|
String templateName = "dump-datamodel.ftl";
|
||||||
|
|
||||||
// RY Improve by making presentation of various types more nuanced
|
Map<String, Object> map = new HashMap<String, Object>();
|
||||||
// Also merge to a template for formatting
|
map.put("models", models);
|
||||||
// get config from environment; get a template from config
|
map.put("directives", directives);
|
||||||
// merge as in FreeMarkerHttpServlet.mergeToTemplate()
|
map.put("stylesheets", dataModel.get("stylesheets"));
|
||||||
String modelNames = "<p><strong>Data model:</strong> " + StringUtils.join(models, ", ") + ".</p>";
|
map.put("dump", dataModel.get("dump"));
|
||||||
String directiveNames = "<p><strong>Directives:</strong> " + StringUtils.join(directives, ", ") + ".</p>";
|
// Put the current datamodel into the new datamodel so its values can be dumped with the dump directive
|
||||||
|
map.put("datamodel", dataModel);
|
||||||
|
|
||||||
String output = modelNames + directiveNames;
|
FreemarkerHelper helper = new FreemarkerHelper();
|
||||||
|
String output = helper.mergeMapToTemplate(templateName, map, config);
|
||||||
Writer out = env.getOut();
|
Writer out = env.getOut();
|
||||||
out.write(output);
|
out.write(output);
|
||||||
|
|
||||||
|
|
|
@ -7,24 +7,29 @@ import java.io.Writer;
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
|
|
||||||
|
import org.apache.commons.logging.Log;
|
||||||
|
import org.apache.commons.logging.LogFactory;
|
||||||
|
|
||||||
import edu.cornell.mannlib.vitro.webapp.controller.freemarker.FreemarkerHelper;
|
import edu.cornell.mannlib.vitro.webapp.controller.freemarker.FreemarkerHelper;
|
||||||
import edu.cornell.mannlib.vitro.webapp.web.templatemodels.files.Stylesheets;
|
|
||||||
import freemarker.core.Environment;
|
import freemarker.core.Environment;
|
||||||
import freemarker.template.Configuration;
|
import freemarker.template.Configuration;
|
||||||
import freemarker.template.SimpleDate;
|
|
||||||
import freemarker.template.SimpleHash;
|
|
||||||
import freemarker.template.SimpleScalar;
|
import freemarker.template.SimpleScalar;
|
||||||
import freemarker.template.SimpleSequence;
|
|
||||||
import freemarker.template.TemplateBooleanModel;
|
import freemarker.template.TemplateBooleanModel;
|
||||||
|
import freemarker.template.TemplateDateModel;
|
||||||
import freemarker.template.TemplateDirectiveBody;
|
import freemarker.template.TemplateDirectiveBody;
|
||||||
import freemarker.template.TemplateDirectiveModel;
|
import freemarker.template.TemplateDirectiveModel;
|
||||||
import freemarker.template.TemplateException;
|
import freemarker.template.TemplateException;
|
||||||
import freemarker.template.TemplateHashModel;
|
import freemarker.template.TemplateHashModel;
|
||||||
import freemarker.template.TemplateModel;
|
import freemarker.template.TemplateModel;
|
||||||
import freemarker.template.TemplateModelException;
|
import freemarker.template.TemplateModelException;
|
||||||
|
import freemarker.template.TemplateNumberModel;
|
||||||
|
import freemarker.template.TemplateScalarModel;
|
||||||
|
import freemarker.template.TemplateSequenceModel;
|
||||||
|
|
||||||
public class DumpDirective implements TemplateDirectiveModel {
|
public class DumpDirective implements TemplateDirectiveModel {
|
||||||
|
|
||||||
|
private static final Log log = LogFactory.getLog(DumpDirective.class);
|
||||||
|
|
||||||
@SuppressWarnings("unchecked")
|
@SuppressWarnings("unchecked")
|
||||||
@Override
|
@Override
|
||||||
public void execute(Environment env, Map params, TemplateModel[] loopVars,
|
public void execute(Environment env, Map params, TemplateModel[] loopVars,
|
||||||
|
@ -42,57 +47,72 @@ public class DumpDirective implements TemplateDirectiveModel {
|
||||||
Object o = params.get("var");
|
Object o = params.get("var");
|
||||||
if ( !(o instanceof SimpleScalar)) {
|
if ( !(o instanceof SimpleScalar)) {
|
||||||
throw new TemplateModelException(
|
throw new TemplateModelException(
|
||||||
"Value of 'var' must be a string.");
|
"Value of parameter 'var' must be a string.");
|
||||||
}
|
}
|
||||||
String var = ((SimpleScalar)o).getAsString();
|
String var = ((SimpleScalar)o).getAsString();
|
||||||
|
|
||||||
|
Object r = params.get("dataModelDump");
|
||||||
|
boolean dataModelDump = false;
|
||||||
|
if (r != null) {
|
||||||
|
if ( !(r instanceof TemplateBooleanModel)) {
|
||||||
|
throw new TemplateModelException(
|
||||||
|
"Value of parameter 'recursive' must be a boolean: true or false without quotation marks.");
|
||||||
|
}
|
||||||
|
dataModelDump = ((TemplateBooleanModel) r).getAsBoolean();
|
||||||
|
}
|
||||||
|
|
||||||
TemplateHashModel dataModel = env.getDataModel();
|
TemplateHashModel dataModel = env.getDataModel();
|
||||||
TemplateModel val = dataModel.get(var);
|
if (dataModelDump) {
|
||||||
|
dataModel = (TemplateHashModel) dataModel.get("datamodel");
|
||||||
|
}
|
||||||
|
|
||||||
Configuration config = env.getConfiguration();
|
TemplateModel val = null;
|
||||||
String templateName = "dump-var.ftl";
|
try {
|
||||||
String includeTemplate;
|
val = dataModel.get(var);
|
||||||
Object value = val;
|
} catch (TemplateModelException tme) {
|
||||||
|
log.error("Error getting value of template model " + var + " from data model.");
|
||||||
|
}
|
||||||
|
|
||||||
|
// Just use this for now. Handles nested collections.
|
||||||
|
String value = val.toString();
|
||||||
String type = null;
|
String type = null;
|
||||||
Writer out = env.getOut();
|
|
||||||
|
|
||||||
if (val instanceof SimpleScalar) {
|
if (val instanceof TemplateScalarModel) {
|
||||||
includeTemplate = "dump-string.ftl";
|
|
||||||
type = "string";
|
type = "string";
|
||||||
} else if (val instanceof SimpleDate) {
|
} else if (val instanceof TemplateDateModel) {
|
||||||
includeTemplate = "dump-string.ftl";
|
|
||||||
value = value.toString();
|
|
||||||
type = "date";
|
type = "date";
|
||||||
|
} else if (val instanceof TemplateNumberModel) {
|
||||||
|
type = "number";
|
||||||
} else if (val instanceof TemplateBooleanModel) {
|
} else if (val instanceof TemplateBooleanModel) {
|
||||||
includeTemplate = "dump-string.ftl";
|
|
||||||
value = ((TemplateBooleanModel) val).getAsBoolean() ? "true" : "false";
|
value = ((TemplateBooleanModel) val).getAsBoolean() ? "true" : "false";
|
||||||
type = "boolean";
|
type = "boolean";
|
||||||
} else if (val instanceof SimpleSequence){
|
} else if (val instanceof TemplateSequenceModel){
|
||||||
includeTemplate = "dump-array.ftl";
|
type = "sequence";
|
||||||
} else if (val instanceof SimpleHash) {
|
} else if (val instanceof TemplateHashModel) {
|
||||||
includeTemplate = "dump-hash.ftl";
|
type = "hash";
|
||||||
// In recursive dump, we've gotten down to a raw string
|
// In recursive dump, we've gotten down to a raw string. Just output it.
|
||||||
// } else if (val == null) {
|
// } else if (val == null) {
|
||||||
// out.write(var);
|
// out.write(var);
|
||||||
// return;
|
// return;
|
||||||
|
// Add a case for BaseTemplateModel - our template model objects will have a dump() method.
|
||||||
} else {
|
} else {
|
||||||
includeTemplate = "dump-string.ftl";
|
|
||||||
value = value.toString();
|
|
||||||
type = "object";
|
type = "object";
|
||||||
}
|
}
|
||||||
|
|
||||||
Map<String, Object> map = new HashMap<String, Object>();
|
Map<String, Object> map = new HashMap<String, Object>();
|
||||||
map.put("var", var);
|
map.put("var", var);
|
||||||
map.put("value", value);
|
map.put("value", value);
|
||||||
map.put("includeTemplate", includeTemplate);
|
|
||||||
map.put("type", type);
|
map.put("type", type);
|
||||||
|
|
||||||
map.put("stylesheets", dataModel.get("stylesheets"));
|
map.put("stylesheets", dataModel.get("stylesheets"));
|
||||||
//map.put("dump", this);
|
//map.put("dump", this);
|
||||||
|
|
||||||
|
Configuration config = env.getConfiguration();
|
||||||
|
String templateName = "dump-var.ftl";
|
||||||
FreemarkerHelper helper = new FreemarkerHelper();
|
FreemarkerHelper helper = new FreemarkerHelper();
|
||||||
String output = helper.mergeMapToTemplate(templateName, map, config);
|
String output = helper.mergeMapToTemplate(templateName, map, config);
|
||||||
|
|
||||||
|
Writer out = env.getOut();
|
||||||
out.write(output);
|
out.write(output);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -0,0 +1,24 @@
|
||||||
|
<#-- $This file is distributed under the terms of the license in /doc/license.txt$ -->
|
||||||
|
|
||||||
|
<#-- Template for dumping the template data model -->
|
||||||
|
|
||||||
|
<div class="dump datamodel">
|
||||||
|
|
||||||
|
<h4>Template data model dump</h6>
|
||||||
|
|
||||||
|
<h5>Variables</h5>
|
||||||
|
|
||||||
|
<ul>
|
||||||
|
<#list models?keys as key>
|
||||||
|
<li><@dump var="${key}" dataModelDump=true /></li>
|
||||||
|
</#list>
|
||||||
|
</ul>
|
||||||
|
|
||||||
|
<h5>Directives</h5>
|
||||||
|
<ul>
|
||||||
|
<#list directives as directive>
|
||||||
|
<li>${directive}</li>
|
||||||
|
</#list>
|
||||||
|
</ul>
|
||||||
|
|
||||||
|
</div>
|
|
@ -1,8 +1,8 @@
|
||||||
<#-- $This file is distributed under the terms of the license in /doc/license.txt$ -->
|
<#-- $This file is distributed under the terms of the license in /doc/license.txt$ -->
|
||||||
|
|
||||||
<#-- Template for dumping array values -->
|
<#-- Template for dumping sequence (list and array) values -->
|
||||||
|
|
||||||
<strong>Type:</strong> array<br />
|
<strong>Type:</strong> sequence (array/list)<br />
|
||||||
<strong>Values:</strong><br />
|
<strong>Values:</strong><br />
|
||||||
<ul>
|
<ul>
|
||||||
<#list value as item>
|
<#list value as item>
|
|
@ -6,7 +6,8 @@
|
||||||
|
|
||||||
<h6>Dump of template variable <em>${var}</em>:</h6>
|
<h6>Dump of template variable <em>${var}</em>:</h6>
|
||||||
|
|
||||||
<#include includeTemplate />
|
<strong>Type:</strong> ${type}<br />
|
||||||
|
<strong>Value:</strong> ${value}<br />
|
||||||
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
|
|
@ -46,12 +46,14 @@
|
||||||
|
|
||||||
<p><strong>Berries: </strong>${berries}</p>
|
<p><strong>Berries: </strong>${berries}</p>
|
||||||
|
|
||||||
|
<#--
|
||||||
<@dump var="now" />
|
<@dump var="now" />
|
||||||
<@dump var="urls" />
|
<@dump var="urls" />
|
||||||
<@dump var="fruit" />
|
<@dump var="fruit" />
|
||||||
<@dump var="trueStatement" />
|
<@dump var="trueStatement" />
|
||||||
<@dump var="falseStatement" />
|
<@dump var="falseStatement" /> -->
|
||||||
|
|
||||||
|
<@dump var="zoo1" />
|
||||||
<@dumpDataModel />
|
<@dumpDataModel />
|
||||||
|
|
||||||
${stylesheets.addFromTheme("/sstest.css", "/sstest2.css")}
|
${stylesheets.addFromTheme("/sstest.css", "/sstest2.css")}
|
||||||
|
|
Loading…
Add table
Reference in a new issue