1 package org.naftulin.configmgr.parsers;
2
3 import java.beans.IntrospectionException;
4 import java.io.IOException;
5 import java.net.URL;
6
7 import org.apache.commons.betwixt.io.BeanReader;
8 import org.apache.log4j.Logger;
9 import org.naftulin.configmgr.ConfigurationManagementEntryImpl;
10 import org.naftulin.configmgr.ConfigurationManagerException;
11 import org.naftulin.configmgr.ConfigurationManagementEntry;
12 import org.naftulin.configmgr.ConfigurationType;
13 import org.xml.sax.SAXException;
14
15 /***
16 * Configuration entry parser converts xml configuration record into supplied class instance configuration management entry.
17 * It parses the property file that the record describes, and stores the configuration
18 * as a properties in content of an {@link org.naftulin.configmgr.ConfigurationManagementEntry entry}.
19 *
20 * @author Henry Naftulin
21 * @since 1.0
22 */
23 public class XmlFileParserImpl implements ConfigEntryParser {
24 private static final long serialVersionUID = 1L;
25 private static final Logger log = Logger.getLogger(XmlFileParserImpl.class);
26 private final String className;
27
28 public XmlFileParserImpl(final String className) {
29 this.className = className;
30 }
31
32 /***
33 * Returns configuration management entry by parsing the record passed in.
34 * Note xml file has to match the class passed in, per betwix specfications.
35 * @param key the key configuration entry will be assigned
36 * @param fileUrl the file URL to be parsed.
37 * @return a configuration managment entry by parsing the record passed in.
38 * @throws ConfigurationManagerException if an error occurs while parsing an entry.
39 */
40 public ConfigurationManagementEntry getConfigurationManagementEntry(final String key,
41 final URL fileUrl) throws ConfigurationManagerException {
42 validateParameters(key, fileUrl);
43 Class<Object> beanClass;
44
45 try {
46 beanClass = (Class<Object>) Class.forName(className);
47 } catch (ClassNotFoundException e) {
48 throw new ConfigurationManagerException("className " + className + " could not be found in the classpath.", e);
49 }
50
51 final String fileName = fileUrl.getFile();
52 Object content = null;
53 try {
54
55
56 final BeanReader beanReader = new BeanReader();
57
58
59
60
61
62
63 log.debug("class name " + getSimpleName(beanClass));
64 beanReader.registerBeanClass(getSimpleName(beanClass), beanClass);
65
66
67 content = beanReader.parse(fileUrl);
68
69
70 log.debug("xml object parsed by XML Parser is: " + content);
71 } catch (IOException e) {
72 log.warn("Error while reading property file", e);
73 throw new ConfigurationManagerException("Error while reading property file",e);
74 } catch (IntrospectionException e) {
75 log.warn("Error while parsing xml.", e);
76 throw new ConfigurationManagerException("Error while parsing xml.",e);
77 } catch (SAXException e) {
78 log.warn("Error while parsing xml.", e);
79 throw new ConfigurationManagerException("Error while parsing xml.",e);
80 }
81 ConfigurationManagementEntry entry = new ConfigurationManagementEntryImpl(key, fileName, content, this, ConfigurationType.XML);
82
83 return entry;
84 }
85
86 private void validateParameters(final String key, final URL fileUrl)
87 throws ConfigurationManagerException {
88 if (fileUrl == null) {
89 throw new ConfigurationManagerException("file URL is null");
90 }
91 if (fileUrl.getFile() == null) {
92 throw new ConfigurationManagerException("file name passed in the URL " + fileUrl + " is null");
93 }
94 if (key == null) {
95 throw new ConfigurationManagerException("key is null for file " + fileUrl );
96 }
97 if (className == null) {
98 throw new ConfigurationManagerException("className is null for file " + fileUrl + " and key " + key );
99 }
100 }
101
102 /***
103 * Immitates the JDK 1.5 API to get the simple class name. Class is not null.
104 * @param cl class
105 * @return simple class name as defined in JDK 1.5
106 */
107 private String getSimpleName(final Class<Object> cl) {
108 final int lastDot = cl.getName().lastIndexOf(".");
109 return cl.getName().substring(lastDot +1);
110 }
111 /***
112 * Returns a string representation of this parser.
113 * @return a string representation of this parser.
114 */
115 public String toString() {
116 return "Xml file parser";
117 }
118 }
119