try {
Validate.notNull(templateName, "Template name cannot be null");
Validate.notNull(processingContext, "Processing context cannot be null");
final IContext context = processingContext.getContext();
final long startNanos = System.nanoTime();
if (logger.isDebugEnabled()) {
logger.debug("[THYMELEAF][{}] STARTING PROCESS OF TEMPLATE \"{}\" WITH LOCALE {}", new Object[] {TemplateEngine.threadIndex(), templateName, context.getLocale()});
}
// Add context execution info
context.addContextExecutionInfo(templateName);
final TemplateProcessingParameters templateProcessingParameters =
new TemplateProcessingParameters(this.configuration, templateName, processingContext);
process(templateProcessingParameters, fragmentSpec, writer);
final long endNanos = System.nanoTime();
if (logger.isDebugEnabled()) {
logger.debug("[THYMELEAF][{}] FINISHED PROCESS AND OUTPUT OF TEMPLATE \"{}\" WITH LOCALE {}", new Object[] {TemplateEngine.threadIndex(), templateName, context.getLocale()});
}
if (timerLogger.isDebugEnabled()) {
final BigDecimal elapsed = BigDecimal.valueOf(endNanos - startNanos);
final BigDecimal elapsedMs = elapsed.divide(BigDecimal.valueOf(NANOS_IN_SECOND), RoundingMode.HALF_UP);
timerLogger.debug(
"[THYMELEAF][{}][{}][{}][{}][{}] TEMPLATE \"{}\" WITH LOCALE {} PROCESSED IN {} nanoseconds (approx. {}ms)",
new Object[] {TemplateEngine.threadIndex(),
templateName, context.getLocale(), elapsed, elapsedMs,
templateName, context.getLocale(), elapsed, elapsedMs});
}
} catch (final TemplateOutputException e) {
logger.error("[THYMELEAF][{}] Exception processing template \"{}\": {}", new Object[] {TemplateEngine.threadIndex(), templateName, e.getMessage()});