KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > mmbase > util > transformers > RegexpReplacer


1 /*
2
3 This software is OSI Certified Open Source Software.
4 OSI Certified is a certification mark of the Open Source Initiative.
5
6 The license (Mozilla version 1.0) can be read at the MMBase site.
7 See http://www.MMBase.org/license
8
9 */

10 package org.mmbase.util.transformers;
11
12 import java.util.*;
13 import java.io.*;
14 import java.util.regex.*;
15 import org.mmbase.util.ResourceWatcher;
16 import org.mmbase.util.xml.UtilReader;
17 import org.mmbase.util.Entry;
18 import org.mmbase.util.Casting;
19
20 import org.mmbase.util.logging.*;
21
22
23 /**
24  * Finds regexps in the Character String, and replaces them. The replaced regexps can be found in a configuration file 'regexps.xml' (if it is present).
25  * It ignores existing XML markup, and also avoids trailing dots and comments and surrounding quotes and parentheses.
26  *
27  * @author Michiel Meeuwissen
28  * @since MMBase-1.8
29  */

30
31 public class RegexpReplacer extends ChunkedTransformer {
32     private static final Logger log = Logging.getLoggerInstance(RegexpReplacer.class);
33
34     /**
35      * Every extension of regexp-replacer can make use of this.
36      */

37     private static final Map utilReaders = new HashMap(); // class -> utilreader
38

39     /**
40      * The regexps for the unextended RegexpReplacer
41      */

42     protected static final Collection regexps = new ArrayList();
43
44     protected static abstract class PatternWatcher extends ResourceWatcher {
45         protected Collection patterns;
46         PatternWatcher(Collection p) {
47             patterns = p;
48         }
49     }
50
51
52
53     static {
54         new RegexpReplacer().readPatterns(regexps);
55     }
56
57
58     public RegexpReplacer(int i) {
59         super(i);
60     }
61
62     public RegexpReplacer() {
63         super(WORDS);
64     }
65     /**
66      * This on default gives the regexps configured for the base-class (a static member). You can
67      * override this method to return another Collection.
68      */

69     protected Collection getPatterns() {
70         return regexps;
71     }
72
73     /**
74      * This can be overridden if the implementation must use its own configuration file.
75      */

76     protected String JavaDoc getConfigFile() {
77         return "regexps.xml";
78     }
79
80     /**
81      * Reads defaults translation patterns into the given collection patterns. Override this for
82      * other default patterns.
83      */

84     protected void readDefaultPatterns(Collection patterns) {
85     }
86
87     /**
88      * Reads patterns from config-file into given Collection
89      */

90     protected final void readPatterns(Collection patterns) {
91         UtilReader utilReader = (UtilReader) utilReaders.get(this.getClass().getName());
92         if (utilReader == null) {
93             utilReader = new UtilReader(getConfigFile(),
94                                         new PatternWatcher(patterns) {
95                                             public void onChange(String JavaDoc file) {
96                                                 readPatterns(patterns);
97                                             }
98                                         });
99             utilReaders.put(this.getClass().getName(), utilReader);
100         }
101
102         patterns.clear();
103
104         Collection regs = (Collection) utilReader.getProperties().get("regexps");
105         if (regs != null) {
106             addPatterns(regs, patterns);
107         } else {
108             readDefaultPatterns(patterns);
109         }
110     }
111
112     /**
113      * Utility function to create a bunch of patterns.
114      * @param list A Collection of Map.Entry (like {@link java.util.Map#entrySet()}), containing
115      * pairs of Strings
116      * @param patterns This the Collection of Entries. The key of every entry is a compiled regular
117      * expression. The value is still a String. New entries will be added to this collection
118      * by this function.
119      */

120     protected static void addPatterns(Collection list, Collection patterns) {
121         if (list != null) {
122             Iterator i = list.iterator();
123             while (i.hasNext()) {
124                 Object JavaDoc next = i.next();
125                 Pattern p;
126                 String JavaDoc result;
127                 if (next == null) {
128                     log.warn("Found null in " + list);
129                     continue;
130                 } else if (next instanceof Map.Entry) {
131                     Map.Entry entry = (Map.Entry) next;
132                     p = Pattern.compile(Casting.toString(entry.getKey()));
133                     Object JavaDoc value = entry.getValue();
134                     if (value instanceof Collection) {
135                         result = null;
136                         Iterator j = ((Collection) value).iterator();
137                         while (j.hasNext()) {
138                             Object JavaDoc n = j.next();
139                             if (! (n instanceof Map.Entry)) {
140                                 log.warn("Could not understand " + n.getClass() + " '" + n + "' (in collection " + value + "). It should be a Map.Entry.");
141                                 continue;
142                             }
143                             Map.Entry subEntry = (Map.Entry) n;
144                             Object JavaDoc key = subEntry.getKey();
145                             if ("key".equals(key)) {
146                                 p = Pattern.compile(Casting.toString(subEntry.getValue()));
147                                 continue;
148                             }
149                             if ("value".equals(key)) {
150                                 result = Casting.toString(subEntry.getValue());
151                             }
152                         }
153                         if (result == null) result = "";
154                     } else {
155                         result = Casting.toString(value);
156                     }
157                 } else {
158                     log.warn("Could not understand " + next.getClass() + " '" + next + "'. It should be a Map.Entry.");
159                     continue;
160                 }
161                 patterns.add(new Entry(p, result));
162             }
163         }
164     }
165
166     protected boolean replace(String JavaDoc string, Writer w, Status status) throws IOException {
167         Iterator i = getPatterns().iterator();
168
169         while (i.hasNext()) {
170             Entry entry = (Entry) i.next();
171             Pattern p = (Pattern) entry.getKey();
172             if (replaceFirstAll && status.used.contains(p)) continue;
173             Matcher m = p.matcher(string);
174             if (m.matches()) {
175                 String JavaDoc result = (String JavaDoc) entry.getValue();
176                 for (int j = m.groupCount(); j >= 0; j--) {
177                     if (replaceFirst) {
178                         result = result.replaceFirst("\\$" + j, m.group(j));
179                     } else {
180                         result = result.replaceAll("\\$" + j, m.group(j));
181                     }
182                     status.replaced++;
183                 }
184                 if (replaceFirstAll) status.used.add(p);
185                 w.write(result);
186                 return true;
187             }
188         }
189         w.write(string);
190         return false;
191
192     }
193     protected final String JavaDoc base() {
194         return "REGEXPS";
195     }
196
197     public String JavaDoc toString() {
198         return getEncoding() + " " + getPatterns();
199     }
200
201
202
203 }
204
Popular Tags