1
2
3
4
5
6
7
8
9
10
11 package org.mule.transformers.xml;
12
13 import org.mule.config.i18n.CoreMessages;
14 import org.mule.umo.lifecycle.InitialisationException;
15 import org.mule.umo.transformer.TransformerException;
16 import org.mule.umo.transformer.UMOTransformer;
17 import org.mule.util.ClassUtils;
18 import org.mule.util.IOUtils;
19 import org.mule.util.StringUtils;
20
21 import java.io.IOException;
22 import java.io.InputStream;
23 import java.io.StringReader;
24
25 import javax.xml.transform.ErrorListener;
26 import javax.xml.transform.OutputKeys;
27 import javax.xml.transform.Source;
28 import javax.xml.transform.Transformer;
29 import javax.xml.transform.TransformerFactory;
30 import javax.xml.transform.URIResolver;
31 import javax.xml.transform.stream.StreamSource;
32
33 import org.apache.commons.pool.BasePoolableObjectFactory;
34 import org.apache.commons.pool.impl.GenericObjectPool;
35
36
37
38
39
40
41 public class XsltTransformer extends AbstractXmlTransformer
42 {
43
44 private static final int MIN_IDLE_TRANSFORMERS = 1;
45
46 private static final int MAX_IDLE_TRANSFORMERS = 32;
47
48 private static final int MAX_ACTIVE_TRANSFORMERS = MAX_IDLE_TRANSFORMERS;
49
50 protected final GenericObjectPool transformerPool;
51
52 private volatile String xslTransformerFactoryClassName;
53 private volatile String xslFile;
54 private volatile String xslt;
55
56 public XsltTransformer()
57 {
58 super();
59 transformerPool = new GenericObjectPool(new PooledXsltTransformerFactory());
60 transformerPool.setMinIdle(MIN_IDLE_TRANSFORMERS);
61 transformerPool.setMaxIdle(MAX_IDLE_TRANSFORMERS);
62 transformerPool.setMaxActive(MAX_ACTIVE_TRANSFORMERS);
63 }
64
65
66
67
68
69 public void initialise() throws InitialisationException
70 {
71 try
72 {
73 transformerPool.addObject();
74 }
75 catch (Throwable te)
76 {
77 throw new InitialisationException(te, this);
78 }
79 }
80
81
82
83
84
85
86
87 public Object doTransform(Object src, String encoding) throws TransformerException
88 {
89 try
90 {
91 Source sourceDoc = this.getXmlSource(src);
92 if (sourceDoc == null)
93 {
94 return null;
95 }
96
97 ResultHolder holder = getResultHolder(returnClass);
98 if (holder == null)
99 {
100 holder = getResultHolder(src.getClass());
101 }
102
103 DefaultErrorListener errorListener = new DefaultErrorListener(this);
104 Transformer transformer = null;
105 Object result;
106
107 try
108 {
109 transformer = (Transformer) transformerPool.borrowObject();
110
111 transformer.setErrorListener(errorListener);
112 transformer.setOutputProperty(OutputKeys.ENCODING, encoding);
113
114 transformer.transform(sourceDoc, holder.getResult());
115 result = holder.getResultObject();
116
117 if (errorListener.isError())
118 {
119 throw errorListener.getException();
120 }
121 }
122 finally
123 {
124 if (transformer != null)
125 {
126 transformerPool.returnObject(transformer);
127 }
128 }
129
130 return result;
131 }
132 catch (Exception e)
133 {
134 throw new TransformerException(this, e);
135 }
136 }
137
138
139
140
141
142
143
144
145 public String getXslTransformerFactory()
146 {
147 return xslTransformerFactoryClassName;
148 }
149
150
151
152
153
154
155 public void setXslTransformerFactory(String xslTransformerFactory)
156 {
157 this.xslTransformerFactoryClassName = xslTransformerFactory;
158 }
159
160
161
162
163 public String getXslFile()
164 {
165 return xslFile;
166 }
167
168
169
170
171 public void setXslFile(String xslFile)
172 {
173 this.xslFile = xslFile;
174 }
175
176 public String getXslt()
177 {
178 return xslt;
179 }
180
181 public void setXslt(String xslt)
182 {
183 this.xslt = xslt;
184 }
185
186
187
188
189
190
191
192 protected StreamSource getStreamSource() throws InitialisationException
193 {
194 if (xslt != null)
195 {
196 return new StreamSource(new StringReader(xslt));
197 }
198
199 if (xslFile == null)
200 {
201 throw new InitialisationException(CoreMessages.objectIsNull("xslFile"), this);
202 }
203
204 InputStream is;
205 try
206 {
207 is = IOUtils.getResourceAsStream(xslFile, getClass());
208 }
209 catch (IOException e)
210 {
211 throw new InitialisationException(e, this);
212 }
213 if (is != null)
214 {
215 return new StreamSource(is);
216 }
217 else
218 {
219 throw new InitialisationException(CoreMessages.failedToLoad(xslFile), this);
220 }
221 }
222
223
224 public Object clone() throws CloneNotSupportedException
225 {
226 XsltTransformer clone = (XsltTransformer) super.clone();
227
228 try
229 {
230 if (clone.nextTransformer == null)
231 {
232 clone.initialise();
233 }
234 }
235 catch (Exception e)
236 {
237 throw new CloneNotSupportedException(e.getMessage());
238 }
239
240 return clone;
241 }
242
243 protected class PooledXsltTransformerFactory extends BasePoolableObjectFactory
244 {
245 public Object makeObject() throws Exception
246 {
247 StreamSource source = XsltTransformer.this.getStreamSource();
248 String factoryClassName = XsltTransformer.this.getXslTransformerFactory();
249 TransformerFactory factory = null;
250
251 if (StringUtils.isNotEmpty(factoryClassName))
252 {
253 factory = (TransformerFactory) ClassUtils.instanciateClass(factoryClassName,
254 ClassUtils.NO_ARGS, this.getClass());
255 }
256 else
257 {
258
259 factory = TransformerFactory.newInstance();
260 }
261
262 factory.setURIResolver(new URIResolver()
263 {
264 public Source resolve(String href, String base)
265 throws javax.xml.transform.TransformerException
266 {
267 try
268 {
269 return new StreamSource(IOUtils.getResourceAsStream(href, getClass()));
270 }
271 catch (IOException e)
272 {
273 throw new javax.xml.transform.TransformerException(e);
274 }
275 }
276 });
277 return factory.newTransformer(source);
278 }
279 }
280
281 protected class DefaultErrorListener implements ErrorListener
282 {
283 private TransformerException e = null;
284 private final UMOTransformer trans;
285
286 public DefaultErrorListener(UMOTransformer trans)
287 {
288 this.trans = trans;
289 }
290
291 public TransformerException getException()
292 {
293 return e;
294 }
295
296 public boolean isError()
297 {
298 return e != null;
299 }
300
301 public void error(javax.xml.transform.TransformerException exception)
302 throws javax.xml.transform.TransformerException
303 {
304 e = new TransformerException(trans, exception);
305 }
306
307 public void fatalError(javax.xml.transform.TransformerException exception)
308 throws javax.xml.transform.TransformerException
309 {
310 e = new TransformerException(trans, exception);
311 }
312
313 public void warning(javax.xml.transform.TransformerException exception)
314 throws javax.xml.transform.TransformerException
315 {
316 logger.warn(exception.getMessage());
317 }
318 }
319
320
321
322
323
324 public int getMaxActiveTransformers()
325 {
326 return transformerPool.getMaxActive();
327 }
328
329
330
331
332
333
334
335 public void setMaxActiveTransformers(int maxActiveTransformers)
336 {
337 transformerPool.setMaxActive(maxActiveTransformers);
338 }
339
340
341
342
343
344 public int getMaxIdleTransformers()
345 {
346 return transformerPool.getMaxIdle();
347 }
348
349
350
351
352
353
354
355 public void setMaxIdleTransformers(int maxIdleTransformers)
356 {
357 transformerPool.setMaxIdle(maxIdleTransformers);
358 }
359
360 }