1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19 package org.apache.maven.internal.xml;
20
21 import java.io.IOException;
22 import java.io.InputStream;
23 import java.io.Reader;
24 import java.util.ArrayList;
25 import java.util.HashMap;
26 import java.util.List;
27 import java.util.Map;
28
29 import org.apache.maven.api.xml.XmlNode;
30 import org.codehaus.plexus.util.xml.pull.MXParser;
31 import org.codehaus.plexus.util.xml.pull.XmlPullParser;
32 import org.codehaus.plexus.util.xml.pull.XmlPullParserException;
33
34
35
36
37
38 public class XmlNodeBuilder {
39 private static final boolean DEFAULT_TRIM = true;
40
41 public static XmlNodeImpl build(Reader reader) throws XmlPullParserException, IOException {
42 return build(reader, (InputLocationBuilder) null);
43 }
44
45
46
47
48
49
50
51
52
53 public static XmlNodeImpl build(Reader reader, InputLocationBuilder locationBuilder)
54 throws XmlPullParserException, IOException {
55 return build(reader, DEFAULT_TRIM, locationBuilder);
56 }
57
58 public static XmlNodeImpl build(InputStream is, String encoding) throws XmlPullParserException, IOException {
59 return build(is, encoding, DEFAULT_TRIM);
60 }
61
62 public static XmlNodeImpl build(InputStream is, String encoding, boolean trim)
63 throws XmlPullParserException, IOException {
64 XmlPullParser parser = new MXParser();
65 parser.setInput(is, encoding);
66 return build(parser, trim);
67 }
68
69 public static XmlNodeImpl build(Reader reader, boolean trim) throws XmlPullParserException, IOException {
70 return build(reader, trim, null);
71 }
72
73
74
75
76
77
78
79
80
81
82 public static XmlNodeImpl build(Reader reader, boolean trim, InputLocationBuilder locationBuilder)
83 throws XmlPullParserException, IOException {
84 XmlPullParser parser = new MXParser();
85 parser.setInput(reader);
86 return build(parser, trim, locationBuilder);
87 }
88
89 public static XmlNodeImpl build(XmlPullParser parser) throws XmlPullParserException, IOException {
90 return build(parser, DEFAULT_TRIM);
91 }
92
93 public static XmlNodeImpl build(XmlPullParser parser, boolean trim) throws XmlPullParserException, IOException {
94 return build(parser, trim, null);
95 }
96
97
98
99
100
101
102
103
104
105
106 public static XmlNodeImpl build(XmlPullParser parser, boolean trim, InputLocationBuilder locationBuilder)
107 throws XmlPullParserException, IOException {
108 boolean spacePreserve = false;
109 String name = null;
110 String value = null;
111 Object location = null;
112 Map<String, String> attrs = null;
113 List<XmlNode> children = null;
114 int eventType = parser.getEventType();
115 boolean emptyTag = false;
116 while (eventType != XmlPullParser.END_DOCUMENT) {
117 if (eventType == XmlPullParser.START_TAG) {
118 emptyTag = parser.isEmptyElementTag();
119 if (name == null) {
120 name = parser.getName();
121 location = locationBuilder != null ? locationBuilder.toInputLocation(parser) : null;
122 int attributesSize = parser.getAttributeCount();
123 if (attributesSize > 0) {
124 attrs = new HashMap<>();
125 for (int i = 0; i < attributesSize; i++) {
126 String aname = parser.getAttributeName(i);
127 String avalue = parser.getAttributeValue(i);
128 attrs.put(aname, avalue);
129 spacePreserve = spacePreserve || ("xml:space".equals(aname) && "preserve".equals(avalue));
130 }
131 }
132 } else {
133 if (children == null) {
134 children = new ArrayList<>();
135 }
136 XmlNode child = build(parser, trim, locationBuilder);
137 children.add(child);
138 }
139 } else if (eventType == XmlPullParser.TEXT) {
140 String text = parser.getText();
141 if (trim && !spacePreserve) {
142 text = text.trim();
143 }
144 value = value != null ? value + text : text;
145 } else if (eventType == XmlPullParser.END_TAG) {
146 return new XmlNodeImpl(
147 name,
148 children == null ? (value != null ? value : emptyTag ? null : "") : null,
149 attrs,
150 children,
151 location);
152 }
153 eventType = parser.next();
154 }
155 throw new IllegalStateException("End of document found before returning to 0 depth");
156 }
157
158
159
160
161
162
163 public interface InputLocationBuilder {
164 Object toInputLocation(XmlPullParser parser);
165 }
166 }