Home / java templ4docx docx apache-poi / Templ4docx - Easy way to fill docx templates

Templ4docx - Easy way to fill docx templates

13 July 2015 on java, templ4docx, docx, and apache-poi 6 minutes

A few days ago, I had to prepare Proof-of-Concept connected with filling templates prepared in docx. I took into account two libraries: org.docx4j and apache-poi. After a short play with them, the second library appears to be more suitable in my case. In order to compare these two libraries I’ve prepared two classes that perform the same operations:

  • reading docx file
  • finding all variables in docx file
  • replacing (filling) variables in the template
  • saving filled template
  Docx4j Apache-poi
Operation    
Reading 5599 ms 921,3 ms
Finding variables 205,8 ms 34,51 ms
Filling template 65,46 ms 129,6 ms
Saving template 99,38 ms 267,7 ms

Test docx template

Docx template

Doc4j test classes

Stopwatch stopwatch = Stopwatch.createStarted();
WordprocessingMLPackage wordMLPackage = WordprocessingMLPackage.load(new java.io.File(path));
MainDocumentPart documentPart = wordMLPackage.getMainDocumentPart();
stopwatch.stop();
System.out.println("READ FILE : " + stopwatch);

stopwatch = Stopwatch.createStarted();
List<String> tagValues = getTagValues(documentPart.getXML());
stopwatch.stop();
System.out.println("FIND VARIABLES : " + stopwatch);

stopwatch = Stopwatch.createStarted();
documentPart.variableReplace(mappings);
stopwatch.stop();
System.out.println("REPLACE VARIABLES : " + stopwatch);

stopwatch = Stopwatch.createStarted();
wordMLPackage.save(new java.io.File(outputPath));
stopwatch.stop();
System.out.println("SAVE DOCUMENT : " + stopwatch);

...

private static List<String> getTagValues(final String str) {
	final List<String> tagValues = new ArrayList<String>();
	Pattern pattern = Pattern.compile("\\$\\{(.*?)\\}");
	Matcher matcher = pattern.matcher(str);
	while (matcher.find()) {
		tagValues.add(matcher.group());
	}

	return tagValues;
}

Apache-POI test classes

Stopwatch stopwatch = Stopwatch.createStarted();
FileInputStream fis = new FileInputStream(path);
XWPFDocument xdoc = new XWPFDocument(OPCPackage.open(fis));
stopwatch.stop();
System.out.println("READ FILE : " + stopwatch);

XWPFWordExtractor extractor = new XWPFWordExtractor(xdoc);

stopwatch = Stopwatch.createStarted();
List<String> tags = getTagValues(extractor.getText());
stopwatch.stop();
System.out.println("FIND VARIABLES: " + stopwatch);

stopwatch = Stopwatch.createStarted();
replace(xdoc, mappings);
stopwatch.stop();
System.out.println("REPLACE VARIABLES: " + stopwatch);

stopwatch = Stopwatch.createStarted();
xdoc.write(new FileOutputStream(outputPath));
stopwatch.stop();
System.out.println("SAVE DOCUMENT: " + stopwatch);
extractor.close();

...

private List<String> getTagValues(final String str) {
	final List<String> tagValues = new ArrayList<String>();
	Pattern pattern = Pattern.compile("\\$\\{(.*?)\\}");
	Matcher matcher = pattern.matcher(str);
	while (matcher.find()) {
		tagValues.add(matcher.group());
	}

	return tagValues;
}


Templ4docx

Given these results, I’ve chosen apache-poi library. Unfortunately, this library hasn’t any method to find variables in template and replace variables. For this reason I’ve decided to write utility library to work with templates in docx. The heart of the library is Template class which allows you to read docx, find all variables for given pattern, replace variables and save filled template. The example usage of templ4docx is presented below:

Deprecated

The following section concerns the version 1.0.1 The current version is 2.0.0. Read more about this version:

Text Variables
Image Variables
Bullet list Variables
Table Variables



// create new instance of docx template
DocxTemplate template = new DocxTemplate(); 

// set the variable pattern. In this example the pattern is as follows: #{variableName}
template.setVariablePattern(new VariablePattern("#{", "}"));  

// path to docx template
String path = "C://document.docx"; 

// open docx file
Docx openedTemplate = template.openTemplate(path); 

// read docx content as simple text
String content = template.readTextContent(openedTemplate); 

// and display it
System.out.println(content); 

// find all variables satisfying the pattern #{...}
List<String> findVariables = template.findVariables(openedTemplate); 

// and display it
for (String var : findVariables) {
        System.out.println("VARIABLE => " + var);
}

// prepare map of variables for template
Map<String, String> variables = new HashMap<String, String>();
variables.put("#{firstName}", "John");
variables.put("#{lastName}", "Sky");

// fill template by given map of variables
Docx filledTemplate = template.fillTemplate(path, variables); 

// save filled document
template.save(filledTemplate, "C://filledDocument.docx");

How to start ?

The recommended way to get started using templ4docx in your project is a dependency management system – the snippet below can be copied and pasted into your build.

<dependency>
    <groupId>pl.jsolve</groupId>
    <artifactId>templ4docx</artifactId>
    <version>1.0.1</version>
</dependency>

Previous

Sweetener - Strings

There is no person who would not know the String class. To facilitate the work of this class, has been created ‘Strings’. We have created such methods as : join, numberOfOccurrences, removeAllOccurrences, indexesOf, groups, random, pad, capitalize, capitalizeAllWords, isWhitespace, containsOnly, isEmpty, singleLine, removeNewLines, reverse, repeat, isAlpha, isAlphaWithWhitespace, isNumeric, isAlphanumeric, isAlphanumericWithWhitespace...

Next

Templ4docx 2.0.0 - Text Variables

The most common situation is when we want to replace simple text variable. Imagine that you have an invitation template and you want to prepare filled invitation with firstname and lastname. So the only thing you need is to find variables in the template and then replace them with the...