1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17 package org.apache.log4j.chainsaw.receivers;
18
19
20 import org.apache.log4j.LogManager;
21 import org.apache.log4j.Logger;
22 import org.apache.log4j.chainsaw.plugins.PluginClassLoaderFactory;
23 import org.apache.log4j.plugins.Plugin;
24 import org.apache.log4j.plugins.PluginRegistry;
25 import org.apache.log4j.plugins.Receiver;
26 import org.apache.log4j.spi.LoggerRepository;
27 import org.apache.log4j.spi.LoggerRepositoryEx;
28 import org.w3c.dom.Document;
29 import org.w3c.dom.Element;
30
31 import javax.xml.parsers.DocumentBuilder;
32 import javax.xml.parsers.DocumentBuilderFactory;
33 import javax.xml.transform.OutputKeys;
34 import javax.xml.transform.Transformer;
35 import javax.xml.transform.TransformerFactory;
36 import javax.xml.transform.dom.DOMSource;
37 import javax.xml.transform.stream.StreamResult;
38 import java.beans.BeanInfo;
39 import java.beans.Introspector;
40 import java.beans.PropertyDescriptor;
41 import java.io.*;
42 import java.net.URL;
43 import java.util.ArrayList;
44 import java.util.Arrays;
45 import java.util.Collections;
46 import java.util.List;
47
48
49
50
51
52
53
54
55
56
57 public class ReceiversHelper {
58
59 private static final ReceiversHelper instance = new ReceiversHelper();
60
61 private final Logger logger = LogManager.getLogger(ReceiversHelper.class);
62 private List<Class> receiverClassList = new ArrayList<>();
63
64
65
66
67 private ReceiversHelper() {
68
69 URL url = this.getClass().getClassLoader().getResource(
70 this.getClass().getPackage().getName().replace('.', '/') + "/known.receivers");
71 if (url == null) {
72 logger.warn("Failed to locate known.receivers file");
73 return;
74 }
75 LineNumberReader stream = null;
76 try {
77
78 stream = new LineNumberReader(new InputStreamReader(url.openStream()));
79 String line;
80
81
82 ClassLoader classLoader = PluginClassLoaderFactory.getInstance().getClassLoader();
83
84 while ((line = stream.readLine()) != null) {
85
86 try {
87 if (line.startsWith("#") || (line.length() == 0)) {
88 continue;
89 }
90 Class receiverClass = classLoader.loadClass(line);
91 receiverClassList.add(receiverClass);
92 logger.debug("Located known Receiver class " + receiverClass.getName());
93 } catch (ClassNotFoundException e) {
94 logger.warn("Failed to locate Receiver class:" + line);
95 } catch (NoClassDefFoundError e) {
96 logger.error("Failed to locate Receiver class:" + line + ", looks like a dependent class is missing from the classpath", e);
97 }
98 }
99 } catch (Exception e) {
100 e.printStackTrace();
101 } finally {
102 if (stream != null) {
103 try {
104 stream.close();
105 } catch (IOException ioe) {
106 ioe.printStackTrace();
107 }
108 }
109 }
110 }
111
112
113 public static ReceiversHelper getInstance() {
114 return instance;
115 }
116
117
118
119
120
121
122
123
124 public List getKnownReceiverClasses() {
125 return Collections.unmodifiableList(receiverClassList);
126 }
127
128
129 public void saveReceiverConfiguration(File file) {
130 LoggerRepository repo = LogManager.getLoggerRepository();
131 PluginRegistry pluginRegistry = ((LoggerRepositoryEx) repo).getPluginRegistry();
132 List<Plugin> fullPluginList = pluginRegistry.getPlugins();
133 List<Plugin> pluginList = new ArrayList<>();
134 for (Object aFullPluginList : fullPluginList) {
135 Plugin thisPlugin = (Plugin) aFullPluginList;
136 if (thisPlugin instanceof Receiver) {
137 pluginList.add(thisPlugin);
138 }
139 }
140
141 try {
142 if (pluginList.size() > 0) {
143
144 DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
145 factory.setNamespaceAware(true);
146 DocumentBuilder builder = factory.newDocumentBuilder();
147 Document document = builder.newDocument();
148 Element rootElement = document.createElementNS("http://jakarta.apache.org/log4j/", "configuration");
149 rootElement.setPrefix("log4j");
150 rootElement.setAttribute("xmlns:log4j", "http://jakarta.apache.org/log4j/");
151 rootElement.setAttribute("debug", "true");
152
153 for (Object aPluginList : pluginList) {
154 Receiver receiver;
155
156 if (aPluginList instanceof Receiver) {
157 receiver = (Receiver) aPluginList;
158 } else {
159 continue;
160 }
161
162 Element pluginElement = document.createElement("plugin");
163 pluginElement.setAttribute("name", receiver.getName());
164 pluginElement.setAttribute("class", receiver.getClass().getName());
165
166 BeanInfo beanInfo = Introspector.getBeanInfo(receiver.getClass());
167 List<PropertyDescriptor> list = new ArrayList<>(Arrays.asList(beanInfo.getPropertyDescriptors()));
168
169 for (Object aList : list) {
170 PropertyDescriptor d = (PropertyDescriptor) aList;
171
172
173 if (d.getReadMethod().getName().equals("getLoggerRepository")) {
174 continue;
175 }
176 Object o = d.getReadMethod().invoke(receiver);
177 if (o != null) {
178 Element paramElement = document.createElement("param");
179 paramElement.setAttribute("name", d.getName());
180 paramElement.setAttribute("value", o.toString());
181 pluginElement.appendChild(paramElement);
182 }
183 }
184
185 rootElement.appendChild(pluginElement);
186
187 }
188
189 TransformerFactory transformerFactory = TransformerFactory.newInstance();
190 Transformer transformer = transformerFactory.newTransformer();
191 transformer.setOutputProperty(OutputKeys.INDENT, "yes");
192 transformer.setOutputProperty("{http://xml.apache.org/xslt}indent-amount", "4");
193 DOMSource source = new DOMSource(rootElement);
194 FileOutputStream stream = new FileOutputStream(file);
195 StreamResult result = new StreamResult(stream);
196 transformer.transform(source, result);
197 stream.close();
198 }
199
200 } catch (Exception e) {
201 e.printStackTrace();
202 }
203 }
204 }