Java/XML: createTextNode with null parameters causes TransformerException (NullPointerException).
Development/기타 2014. 9. 24. 00:55Development environment: Oracle Java 1.7
This post shows a case when the "createTextNode" method with the null parameter causes "javax.xml.transform.TransformerException: java.lang.NullPointerException" without detailed information (difficult to find the exact line of code causing NullPointerException).
Using DocumentBuilderFactory and TransformerFactory, users can create an XML document with user-defined tags. Usually, I convert a user-defined object into the XMlL representation in String using DocumentBuilderFactory and TransformerFactory. Below is a simple example which causes a NullPointerException:
/* Person.java */
public class Person {
String name;
String phone;
public Person(){ }
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getPhone() {
return phone;
}
public void setPhone(String phone) {
this.phone = phone;
}
}
/* TestMain.java */
public class TestMain {
public static void main(String[] args){
Person person = new Person();
// person.setName("Smith"); // commented for making NullPointerException
person.setPhone("01011112222");
try {
DocumentBuilderFactory dbfac = DocumentBuilderFactory.newInstance();
DocumentBuilder docBuilder = dbfac.newDocumentBuilder();
Document doc = docBuilder.newDocument();
// root (person) tag
Element ePerson = doc.createElement("person");
doc.appendChild(ePerson);
// name tag
Element eName = doc.createElement("name");
ePerson.appendChild(eName);
Text nameText = doc.createTextNode(person.getName());
eName.appendChild(nameText);
// phone tag
Element ePhone = doc.createElement("phone");
ePerson.appendChild(ePhone);
Text phoneText = doc.createTextNode(person.getPhone());
ePhone.appendChild(phoneText);
//set up a transformer
TransformerFactory transfac = TransformerFactory.newInstance();
Transformer trans = transfac.newTransformer();
trans.setOutputProperty(OutputKeys.OMIT_XML_DECLARATION, "yes");
trans.setOutputProperty(OutputKeys.INDENT, "yes");
//create string from xml tree
StringWriter sw = new StringWriter();
StreamResult result = new StreamResult(sw);
DOMSource source = new DOMSource(doc);
trans.transform(source, result); // the line where the Exception indicates
// print the XML output
System.out.println(sw.toString());
} catch (Exception e) {
e.printStackTrace();
}
}
}
As the TestMain.java shows, if the member variable "name" in the Person class is not set, it generates an exception like below:
ERROR: ''
javax.xml.transform.TransformerException: java.lang.NullPointerException
at com.sun.org.apache.xalan.internal.xsltc.trax.TransformerImpl.transform(Unknown Source)
at com.sun.org.apache.xalan.internal.xsltc.trax.TransformerImpl.transform(Unknown Source)
at org.usera.xml.TestMain.main(TestMain.java:39)
Caused by: java.lang.NullPointerException
at com.sun.org.apache.xml.internal.serializer.ToUnknownStream.characters(Unknown Source)
at com.sun.org.apache.xalan.internal.xsltc.trax.DOM2TO.parse(Unknown Source)
at com.sun.org.apache.xalan.internal.xsltc.trax.DOM2TO.parse(Unknown Source)
at com.sun.org.apache.xalan.internal.xsltc.trax.DOM2TO.parse(Unknown Source)
at com.sun.org.apache.xalan.internal.xsltc.trax.DOM2TO.parse(Unknown Source)
at com.sun.org.apache.xalan.internal.xsltc.trax.DOM2TO.parse(Unknown Source)
at com.sun.org.apache.xalan.internal.xsltc.trax.TransformerImpl.transformIdentity(Unknown Source)
... 3 more
---------
java.lang.NullPointerException
at com.sun.org.apache.xml.internal.serializer.ToUnknownStream.characters(Unknown Source)
at com.sun.org.apache.xalan.internal.xsltc.trax.DOM2TO.parse(Unknown Source)
at com.sun.org.apache.xalan.internal.xsltc.trax.DOM2TO.parse(Unknown Source)
at com.sun.org.apache.xalan.internal.xsltc.trax.DOM2TO.parse(Unknown Source)
at com.sun.org.apache.xalan.internal.xsltc.trax.DOM2TO.parse(Unknown Source)
at com.sun.org.apache.xalan.internal.xsltc.trax.DOM2TO.parse(Unknown Source)
at com.sun.org.apache.xalan.internal.xsltc.trax.TransformerImpl.transformIdentity(Unknown Source)
at com.sun.org.apache.xalan.internal.xsltc.trax.TransformerImpl.transform(Unknown Source)
at com.sun.org.apache.xalan.internal.xsltc.trax.TransformerImpl.transform(Unknown Source)
at org.usera.xml.TestMain.main(TestMain.java:39)
The exception guides me to "trans.transform(source, result)", but it doesn't seem to contain any null parameter. This means the other parts in the XML document object contains null values.
In this example, we can quickly find that the member variable "name" should be initialized with a valid String because it is a very simplified code. However, if I handle complex objects including tens of member variables, it is not easy to find which variables are set to null.
Thus, I tried to make a wrapping method which make the "createTextNode" always get a "not null" parameter. The simple solution might be like below:
public static Text createTextNodeWithoutNull(Document doc, String str)
{
Text textNode;
if(str != null) textNode = doc.createTextNode(str);
else textNode = doc.createTextNode("null");
return textNode;
}
Then the modified code (a part of TestMain) is:
// name tag
Element eName = doc.createElement("name");
ePerson.appendChild(eName);
Text nameText = createTextNodeWithoutNull (doc, person.getName());
eName.appendChild(nameText);
// phone tag
Element ePhone = doc.createElement("phone");
ePerson.appendChild(ePhone);
Text phoneText = createTextNodeWithoutNull (doc, person.getPhone());
ePhone.appendChild(phoneText);
Likewise, the XML Document object won't contain any null values inside.
'Development > 기타' 카테고리의 다른 글
이클립스(Eclipse) Subversive 플러그인 삭제/재설치 방법 (0) | 2015.06.20 |
---|---|
이클립스(Eclipse): Package Explorer 창에서 SVN 관련 정보(label)가 사라졌을 때 복구 방법 (0) | 2015.01.02 |
MFC / 간단한 히스토그램 그리기 (0) | 2014.03.24 |
각종 개발환경 텍스트 편집기에서 라인 이동 단축키 (0) | 2014.02.28 |
Eclipse / SVN Connector (SVN Kit, Native JavaHL) 수동 설치(재설치) 방법 (0) | 2014.01.22 |