KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > enhydra > barracuda > contrib > dbroggisch > display > filters > FilterFactory


1 /*
2  * Copyright (C) 2003 Diez B. Roggisch [deets@web.de]
3  *
4  * This library is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU Lesser General Public
6  * License as published by the Free Software Foundation; either
7  * version 2.1 of the License, or (at your option) any later version.
8  *
9  * This library is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12  * Lesser General Public License for more details.
13  *
14  * You should have received a copy of the GNU Lesser General Public
15  * License along with this library; if not, write to the Free Software
16  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
17  *
18  * $Id: FilterFactory.java,v 1.3 2004/02/01 05:16:27 christianc Exp $
19  */

20 package org.enhydra.barracuda.contrib.dbroggisch.display.filters;
21
22 import java.util.*;
23 import java.io.*;
24 import java.lang.reflect.*;
25 import org.enhydra.barracuda.contrib.dbroggisch.display.filters.dtd.*;
26 import org.apache.log4j.Logger;
27 import org.enhydra.barracuda.contrib.dbroggisch.display.*;
28
29 public class FilterFactory {
30     private static Logger logger = Logger.getLogger(FilterFactory.class.getName());
31     static Map s_filterMaps = new HashMap();
32     static Map s_xml2filterMap = new HashMap();
33     static Map s_classDescriptors = new HashMap();
34
35
36     public static void addMapping(InputStream file) {
37         try {
38             FiltermappingUnmarshaller um = new FiltermappingUnmarshaller();
39             Filtermapping fm = um.unmarshal(file, true);
40             String JavaDoc xmlPBase = fm.getDtdpackage();
41             if(xmlPBase != null && xmlPBase.trim().equals("")) {
42                 xmlPBase = null;
43             }
44             List mapsets = fm.getMapsetList();
45             if(logger.isDebugEnabled()) {
46                 logger.debug("XML package: " + xmlPBase);
47                 logger.debug("Found " + mapsets.size() + " mapsets.");
48             }
49
50             for(Iterator it = mapsets.iterator(); it.hasNext();) {
51                 Mapset mapset = (Mapset)it.next();
52                 String JavaDoc filterPBase = mapset.getXmlpackage();
53                 if(filterPBase != null && filterPBase.trim().equals("")) {
54                     filterPBase = null;
55                 }
56                 if(logger.isDebugEnabled()) {
57                     logger.debug("Filter package: " + filterPBase);
58                 }
59
60                 List mapentries = mapset.getMapentryList();
61                 for(Iterator mpeIt = mapentries.iterator(); mpeIt.hasNext();) {
62                     // We want to get as much as possible mappings
63
try {
64                         Mapentry mapentry = (Mapentry)mpeIt.next();
65                         if(logger.isDebugEnabled()) {
66                             logger.debug("Mapentry filterclass: " + mapentry.getFilterclass() + ", xmlclass: " + mapentry.getXmlclass());
67                         }
68                         Class JavaDoc filterClass = Class.forName(filterPBase + (filterPBase == null ? "" : ".") + mapentry.getFilterclass());
69                         Class JavaDoc xmlClass = Class.forName(xmlPBase + (xmlPBase == null ? "" : ".") + mapentry.getXmlclass());
70                         s_xml2filterMap.put(xmlClass, filterClass);
71                     } catch(ClassNotFoundException JavaDoc ex) {
72                         logger.error(ex.getMessage());
73                         ex.printStackTrace();
74                     }
75                 }
76             }
77         } catch(IOException ex) {
78             logger.error(ex.getMessage());
79             ex.printStackTrace();
80         }
81     }
82
83
84     public static void loadFilters(InputStream file)
85         throws FilterException
86     {
87         try {
88             s_filterMaps.clear();
89             FilterfactoryUnmarshaller um = new FilterfactoryUnmarshaller();
90             Filterfactory ff = um.unmarshal(file, true);
91             List ml = ff.getFiltermapList();
92             if(logger.isDebugEnabled()) {
93                 logger.debug("Found " + ml.size() + " mappings.");
94             }
95             // Create all FilterMaps
96
for(Iterator it = ml.iterator(); it.hasNext();) {
97                 // try {
98
// First we have to look if our filtemap extends
99
// an existing one.
100
Filtermap mp = (Filtermap)it.next();
101                 FilterMap fm;
102                 if(mp.getXmlextends() != null &&
103                    !mp.getXmlextends().trim().equals("")) {
104                     if(s_filterMaps.get(mp.getXmlextends()) != null) {
105                         fm = (FilterMap)((FilterMap)s_filterMaps.get(mp.getXmlextends())).clone();
106                     } else {
107                         throw new FilterException("No such filtermap: " + mp.getXmlextends());
108                     }
109                 } else {
110                     fm = new FilterMap();
111                 }
112                 fm.setName(mp.getName());
113                 // Handle the %extend.els;
114
// (look into the filter.dtd for that)
115
List removes = mp.getRemoveList();
116                 for(Iterator rit = removes.iterator(); rit.hasNext();) {
117                     Remove rem = (Remove)rit.next();
118                     if(logger.isDebugEnabled()) {
119                         logger.debug("Removing " + rem.getName());
120                     }
121                     fm.remove(rem.getName());
122                 }
123                 List remaps = mp.getRemapList();
124                 for(Iterator rit = remaps.iterator(); rit.hasNext();) {
125                     Remap rem = (Remap)rit.next();
126                     if(logger.isDebugEnabled()) {
127                         logger.debug("Remapping " + rem.getFrom() + " to " + rem.getTo());
128                         logger.debug("From exists: " + fm.get(rem.getFrom()) != null ? "yes" : "no");
129                     }
130
131                     fm.put(rem.getTo(), fm.get(rem.getFrom()));
132                 }
133                 List copies = mp.getCopyList();
134                 Map copy_map = new HashMap();
135                 for(Iterator rit = copies.iterator(); rit.hasNext();) {
136                     Copy copy = (Copy)rit.next();
137                     copy_map.put(copy.getFrom(), copy.getTo());
138                 }
139                 fm.setCopies(copy_map);
140
141                 // Add the declared filters
142
List filters = mp.getFilterList();
143                 if(logger.isDebugEnabled()) {
144                     logger.debug("Adding " + filters.size() + " filters ");
145                 }
146
147                 for(Iterator rit = filters.iterator(); rit.hasNext();) {
148                     org.enhydra.barracuda.contrib.dbroggisch.display.filters.dtd.Filter f = (org.enhydra.barracuda.contrib.dbroggisch.display.filters.dtd.Filter)rit.next();
149                     Object JavaDoc conf = getChild(f);
150                     org.enhydra.barracuda.contrib.dbroggisch.display.filters.Filter filter = createFilter(conf.getClass());
151                     if(logger.isDebugEnabled()) {
152                         logger.debug("Adding filter " + f.getName() + ", Type is: " + filter.getClass());
153                     }
154                     // Assign the configured filter - it might be
155
// a different filter.
156
filter = filter.configure(conf);
157                     fm.put(f.getName(), filter);
158                 }
159
160                 // Finally - we save the filtermap
161
if(logger.isDebugEnabled()) {
162                     logger.debug("Adding filtermap " + fm.getName());
163                 }
164
165                 s_filterMaps.put(fm.getName(), fm);
166                 // }
167
// }
168
// catch(FilterException ex) {
169
// logger.error(ex.getMessage());
170
// ex.printStackTrace();
171
// }
172

173             }
174             ml = ff.getClassdescriptorList();
175             if(logger.isDebugEnabled()) {
176                 logger.debug("Found " + ml.size() + " classdescriptors.");
177             }
178             // Create all ClassDescriptors
179
for(Iterator it = ml.iterator(); it.hasNext();) {
180                 Classdescriptor cd = (Classdescriptor)it.next();
181                 try {
182                     Class JavaDoc klass = Class.forName(cd.getClassname());
183                     ClassDescriptor clsDesc;
184                     if(cd.getXmlextends() != null &&
185                        !cd.getXmlextends().trim().equals("")) {
186                         Class JavaDoc extendee = Class.forName(cd.getXmlextends());
187                         if(s_classDescriptors.get(extendee) != null) {
188                             if(logger.isDebugEnabled()) {
189                                 logger.debug("ClassDesscriptor extends " + extendee);
190                             }
191                             clsDesc = (ClassDescriptor)((ClassDescriptor)s_classDescriptors.get(extendee)).clone();
192                         } else {
193                             throw new FilterException("No such classdescriptor: " + cd.getXmlextends());
194                         }
195                     } else {
196                         clsDesc = new ClassDescriptor();
197                     }
198                     // Resolve the maprefs
199
List maprefs = cd.getMaprefList();
200
201                     for(Iterator mit = maprefs.iterator(); mit.hasNext();) {
202                         Mapref mr = (Mapref)mit.next();
203                         FilterMap fm = (FilterMap)s_filterMaps.get(mr.getRef());
204                         clsDesc.put(mr.getChannel(), fm);
205                     }
206                     // Finally, put the classdescriptor into the map
207
if(logger.isDebugEnabled()) {
208                         logger.debug("Adding ClassDescriptor for " + klass);
209                     }
210                     s_classDescriptors.put(klass, clsDesc);
211                 } catch(ClassNotFoundException JavaDoc ex) {
212                     logger.error(ex.getMessage());
213                     ex.printStackTrace();
214                     throw new FilterException("No class " + cd.getClassname() + " found");
215                 }
216             }
217
218         } catch(IOException ex) {
219             logger.error(ex.getMessage());
220             ex.printStackTrace();
221         }
222     }
223
224     public static Map getFilterMap(String JavaDoc name) {
225         return (Map)s_filterMaps.get(name);
226     }
227
228     protected static Filter createFilter(Class JavaDoc xmlClass) {
229         if(logger.isDebugEnabled()) {
230             logger.debug("Creating Filter for " + xmlClass.getName());
231         }
232
233         Class JavaDoc [] iFaces = xmlClass.getInterfaces();
234
235         Class JavaDoc filterClass = (Class JavaDoc)s_xml2filterMap.get(xmlClass);
236         if(filterClass == null) {
237             for(int i = 0; i < iFaces.length; i++) {
238                 if(logger.isDebugEnabled()) {
239                     logger.debug("Loking up class: " + iFaces[i].getName());
240                 }
241
242                 filterClass = (Class JavaDoc)s_xml2filterMap.get(iFaces[i]);
243                 if(filterClass != null)
244                     break;
245             }
246         }
247         if(filterClass != null) {
248             if(logger.isDebugEnabled()) {
249                 logger.debug("Filterclass found: " + filterClass.getName());
250             }
251             try {
252                 return (Filter)filterClass.newInstance();
253             } catch(InstantiationException JavaDoc ex) {
254                 logger.error(ex.getMessage());
255                 ex.printStackTrace();
256             } catch(IllegalAccessException JavaDoc ex) {
257                 logger.error(ex.getMessage());
258                 ex.printStackTrace();
259             }
260         } else {
261             logger.warn("No Filterclass found for: " + xmlClass.getName());
262         }
263         return null;
264     }
265
266     private static List getters;
267     private static Object JavaDoc getChild(Object JavaDoc obj) {
268         try {
269             if(getters == null) {
270                 getters = new ArrayList();
271                 Method [] mths = obj.getClass().getMethods();
272                 Set allowedClasses = s_xml2filterMap.keySet();
273                 if(logger.isDebugEnabled()) {
274                     logger.debug("Allowed classes: " + allowedClasses);
275                 }
276                 for(int i = 0; i < mths.length; i++) {
277                     Method m = mths[i];
278                     Class JavaDoc returnType = m.getReturnType();
279
280                     if(logger.isDebugEnabled()) {
281                         logger.debug("handling method " + m.getName() + " with type " + returnType.getName());
282                     }
283                     if(m.getName().startsWith("get")
284                        && allowedClasses.contains(returnType)) {
285                         getters.add(m);
286                     }
287                 }
288             }
289             for(Iterator it = getters.iterator(); it.hasNext();) {
290                 Method m = (Method)it.next();
291                 Object JavaDoc res = m.invoke(obj, null);
292                 if(res != null) {
293                     return res;
294                 }
295             }
296
297         } catch(InvocationTargetException ex) {
298             logger.error(ex.getMessage());
299         } catch(IllegalAccessException JavaDoc ex) {
300             logger.error(ex.getMessage());
301         }
302         return null;
303     }
304
305
306     public static List accumulateChilds(Object JavaDoc obj) {
307         List res = new ArrayList();
308         try {
309             Method [] mths = obj.getClass().getMethods();
310             for(int i = 0; i < mths.length; i++) {
311                 Method m = mths[i];
312                 Class JavaDoc returnType = m.getReturnType();
313                 if(logger.isDebugEnabled()) {
314                     logger.debug("handling method " + m.getName() + " with type " + returnType.getName());
315                 }
316                 if(m.getName().startsWith("get")
317                    && returnType.equals(List.class)) {
318                     res.addAll((List)m.invoke(obj, null));
319                 }
320             }
321         } catch(InvocationTargetException ex) {
322             logger.error(ex.getMessage());
323         } catch(IllegalAccessException JavaDoc ex) {
324             logger.error(ex.getMessage());
325         }
326         return res;
327     }
328
329
330     private static class FilterMap extends HashMap {
331         String JavaDoc _name;
332         Map _copies;
333
334         public void setCopies(Map copies) {
335             _copies = copies;
336         }
337
338         public Map getCopies() {
339             return _copies;
340         }
341
342         public String JavaDoc getName() {
343             return _name;
344         }
345         public void setName(String JavaDoc name) {
346             _name = name;
347         }
348
349         public Object JavaDoc clone() {
350             FilterMap fm = new FilterMap();
351             fm.setName(_name);
352             fm.putAll(this);
353             return fm;
354         }
355     }
356
357     private static class ClassDescriptor extends HashMap implements Cloneable JavaDoc {
358         Class JavaDoc _class;
359         FilterMap _default;
360
361
362         public Object JavaDoc put(Object JavaDoc key, Object JavaDoc value) {
363             if(logger.isDebugEnabled() && value != null) {
364                 logger.debug("Setting FilterMap " + ((FilterMap)value).getName());
365             }
366
367             if(key != null) {
368                 if(logger.isDebugEnabled() && value != null) {
369                     logger.debug("... as class " + key);
370                 }
371                 return super.put(key, value);
372             } else {
373                 if(logger.isDebugEnabled() && value != null) {
374                     logger.debug("... as default");
375                 }
376                 Object JavaDoc old_d = _default;
377                 _default = (FilterMap)value;
378                 return old_d;
379             }
380         }
381
382
383
384         public Class JavaDoc getMappedClass() {
385             return _class;
386         }
387
388         public void setMappedClass(Class JavaDoc klass) {
389             _class = klass;
390         }
391
392         public FilterMap getDefault() {
393             return _default;
394         }
395
396         public void setDefault(FilterMap ddefault) {
397             _default = ddefault;
398         }
399
400         public Object JavaDoc clone()
401         {
402             ClassDescriptor cd = new ClassDescriptor();
403             cd.setMappedClass(_class);
404             cd.setDefault(_default);
405             cd.putAll(this);
406             return cd;
407         }
408
409     }
410
411
412     public static LightweightTemplateModel filter(Object JavaDoc obj,
413                                     FilterContext ctx)
414         throws FilterException
415     {
416         if(obj != null) {
417
418             LightweightTemplateModel ltm = ReflectionMapper.map(obj);
419             if(logger.isDebugEnabled()) {
420                 logger.debug("Mapping");
421                 logger.debug(ltm != null ? "...was sucsssful" : "...wasn't sucsssful");
422             }
423             ClassDescriptor clsDesc = (ClassDescriptor)s_classDescriptors.get(obj.getClass());
424             // If we have a class descriptor, try to fetch a FilertMap
425
// Otherwise simlply return the model
426
if(clsDesc != null) {
427                 if(logger.isDebugEnabled()) {
428                     logger.debug("Found ClassDescriptor for " + obj.getClass());
429                 }
430                 FilterMap fm = (FilterMap)clsDesc.get(ctx.getChannel());
431                 if(fm == null) {
432                     if(logger.isDebugEnabled()) {
433                         logger.debug("No FilterMap for channel " + ctx.getChannel() + ", using default");
434                     }
435                     fm = clsDesc.getDefault();
436                 }
437                 if(fm != null) {
438                     ltm = filter(ltm, fm, ctx);
439                 } else {
440                     if(logger.isDebugEnabled()) {
441                         logger.debug("No FilterMap found!");
442                     }
443                 }
444             } else {
445                 logger.warn("No classmapping for " + obj.getClass());
446             }
447             return ltm;
448         }
449         return null;
450     }
451
452     public static LightweightTemplateModel filter(LightweightTemplateModel ltm,
453                                     String JavaDoc fmName,
454                                     FilterContext ctx)
455         throws FilterException
456     {
457         FilterMap fm = (FilterMap)s_filterMaps.get(fmName);
458         if(fm == null) {
459             throw new FilterException("No such FilterMap " + fmName);
460         }
461         return filter(ltm, fm, ctx);
462     }
463
464     /**
465      *
466      *
467      * @param ltm a <code>LightweightTemplateModel</code> value
468      * @param fm The FilterMap to apply
469      * @param ctx the FilterContext to be used
470      * @return a <code>LightweightTemplateModel</code>
471      * @exception FilterException if an error occurs
472      */

473     public static LightweightTemplateModel filter(LightweightTemplateModel ltm,
474                                     FilterMap fm,
475                                     FilterContext ctx)
476         throws FilterException
477     {
478         HashMapModel res = new HashMapModel();
479         res.setName(ltm.getName());
480         // First, execute the copies
481
Map copies = fm.getCopies();
482         for(Iterator cp = copies.entrySet().iterator(); cp.hasNext();) {
483             Map.Entry entry = (Map.Entry)cp.next();
484             if(logger.isDebugEnabled()) {
485                 logger.debug("Copyiing " + entry.getKey() + " to " + entry.getValue());
486             }
487             res.setItem((String JavaDoc)entry.getValue(), ltm.getItem((String JavaDoc)entry.getKey()));
488         }
489         // Filter the values in ltm
490
for(Iterator it = ltm.keySet().iterator(); it.hasNext();) {
491             String JavaDoc key = (String JavaDoc)it.next();
492             Filter f = (Filter)fm.get(key);
493             if(f != null) {
494                 if(logger.isDebugEnabled()) {
495                     logger.debug("Filtering " + key);
496                 }
497                 res.setItem(key, f.filter(ltm.getItem(key), ctx));
498             } else {
499                 if(logger.isDebugEnabled()) {
500                     logger.debug("No filtering for " + key);
501                 }
502                 res.setItem(key, ltm.getItem(key));
503             }
504         }
505         // Now perform filtering on the copied values
506
for(Iterator it = copies.keySet().iterator(); it.hasNext();) {
507             String JavaDoc key = (String JavaDoc)it.next();
508             Filter f = (Filter)fm.get(key);
509             if(f != null) {
510                 res.setItem(key, f.filter(res.getItem(key), ctx));
511             }
512         }
513         return res;
514     }
515 }
516
Popular Tags