KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > dbforms > taglib > EmbeddedData


1 /*
2  * $Header: /cvsroot/jdbforms/dbforms/src/org/dbforms/taglib/EmbeddedData.java,v 1.38 2004/10/21 10:44:43 hkollmann Exp $
3  * $Revision: 1.38 $
4  * $Date: 2004/10/21 10:44:43 $
5  *
6  * DbForms - a Rapid Application Development Framework
7  * Copyright (C) 2001 Joachim Peer <joepeer@excite.com>
8  *
9  * This library is free software; you can redistribute it and/or
10  * modify it under the terms of the GNU Lesser General Public
11  * License as published by the Free Software Foundation; either
12  * version 2.1 of the License, or (at your option) any later version.
13  *
14  * This library is distributed in the hope that it will be useful,
15  * but WITHOUT ANY WARRANTY; without even the implied warranty of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
17  * Lesser General Public License for more details.
18  *
19  * You should have received a copy of the GNU Lesser General Public
20  * License along with this library; if not, write to the Free Software
21  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
22  */

23 package org.dbforms.taglib;
24 import org.apache.commons.logging.Log;
25 import org.apache.commons.logging.LogFactory;
26
27 import org.dbforms.config.DbFormsConfig;
28 import org.dbforms.config.DbFormsConfigRegistry;
29 import org.dbforms.config.ResultSetVector;
30
31 import org.dbforms.util.IEscaper;
32 import org.dbforms.util.IFormatEmbeddedData;
33 import org.dbforms.util.KeyValuePair;
34 import org.dbforms.util.MessageResources;
35 import org.dbforms.util.ReflectionUtil;
36 import org.dbforms.util.SqlUtil;
37 import org.dbforms.util.Util;
38
39 import java.sql.Connection JavaDoc;
40 import java.sql.SQLException JavaDoc;
41
42 import java.util.List JavaDoc;
43
44 import javax.servlet.http.HttpServletRequest JavaDoc;
45 import javax.servlet.jsp.JspException JavaDoc;
46 import javax.servlet.jsp.PageContext JavaDoc;
47
48
49
50 /**
51  * DOCUMENT ME!
52  *
53  * @author $author$
54  * @version $Revision: 1.38 $
55  */

56 public abstract class EmbeddedData extends DbBaseHandlerTag
57    implements javax.servlet.jsp.tagext.TryCatchFinally JavaDoc, StaticDataAddInterface {
58    private static Log logCat = LogFactory.getLog(EmbeddedData.class
59          .getName());
60    private IFormatEmbeddedData printfFormat;
61    private List JavaDoc data;
62    private String JavaDoc dbConnectionName;
63    private String JavaDoc disableCache = "false";
64    private String JavaDoc format;
65    private String JavaDoc formatClass;
66    private String JavaDoc name;
67
68    /**
69     * DOCUMENT ME!
70     *
71     * @param name DOCUMENT ME!
72     */

73    public void setDbConnectionName(String JavaDoc name) {
74       dbConnectionName = name;
75    }
76
77
78    /**
79     * DOCUMENT ME!
80     *
81     * @return DOCUMENT ME!
82     */

83    public String JavaDoc getDbConnectionName() {
84       return dbConnectionName;
85    }
86
87
88    /**
89     * Insert the method's description here. Creation date: (2001-09-21
90     * 12:20:42)
91     *
92     * @param newDisableCache java.lang.String
93     */

94    public void setDisableCache(java.lang.String JavaDoc newDisableCache) {
95       disableCache = newDisableCache;
96    }
97
98
99    /**
100     * Insert the method's description here. Creation date: (2001-09-21
101     * 12:20:42)
102     *
103     * @return java.lang.String
104     */

105    public java.lang.String JavaDoc getDisableCache() {
106       return disableCache;
107    }
108
109
110    /**
111     * DOCUMENT ME!
112     *
113     * @return DOCUMENT ME!
114     */

115    public IEscaper getEscaper() {
116       DataContainer parent = ((DataContainer) getParent());
117       IEscaper res = parent.getEscaper();
118
119       return res;
120    }
121
122
123    /**
124     * DOCUMENT ME!
125     *
126     * @param format DOCUMENT ME!
127     */

128    public void setFormat(java.lang.String JavaDoc format) {
129       this.format = format;
130    }
131
132
133    /**
134     * Sets the formatClass.
135     *
136     * @param formatClass The formatClass to set
137     */

138    public void setFormatClass(String JavaDoc formatClass) {
139       this.formatClass = formatClass;
140    }
141
142
143    /**
144     * Returns the formatClass.
145     *
146     * @return String
147     */

148    public String JavaDoc getFormatClass() {
149       return formatClass;
150    }
151
152
153    /**
154     * set the name of the embedded data. every embedded data entity on a jsp
155     * page has to have a unique name. this name is used for storing (caching)
156     * and retrieving data in Page-Scope. this is useful if a tag gets
157     * evaluated many times -> we do not want the queries etc. to be executed
158     * every time!
159     *
160     * @param name DOCUMENT ME!
161     */

162    public void setName(String JavaDoc name) {
163       this.name = name;
164    }
165
166
167    /**
168     * returns the unique name of the embedded data
169     *
170     * @return DOCUMENT ME!
171     */

172    public String JavaDoc getName() {
173       return name;
174    }
175
176
177    /**
178     * DOCUMENT ME!
179     *
180     * @param pair DOCUMENT ME!
181     */

182    public void addElement(KeyValuePair pair) {
183       data.add(pair);
184    }
185
186
187    /**
188     * @see javax.servlet.jsp.tagext.TryCatchFinally#doCatch(java.lang.Throwable)
189     */

190    public void doCatch(Throwable JavaDoc t) throws Throwable JavaDoc {
191       throw t;
192    }
193
194
195    /**
196     * DOCUMENT ME!
197     */

198    public void doFinally() {
199       name = null;
200       dbConnectionName = null;
201       format = null;
202       printfFormat = null;
203       formatClass = null;
204       disableCache = "false";
205    }
206
207
208    /**
209     * DOCUMENT ME!
210     *
211     * @return DOCUMENT ME!
212     *
213     * @throws JspException DOCUMENT ME!
214     * @throws IllegalArgumentException DOCUMENT ME!
215     */

216    public int doStartTag() throws JspException JavaDoc {
217       /**
218        * Grunikiewicz.philip 2001-09-21 Sometimes a developer may want to
219        * execute the embedded data query for each row. i.e. not cache the
220        * result set. Example: Table contains 1000+ of rows, use queryData
221        * with qualified 'where' clause. Data cannot be cached because each
222        * subsequent row need to execute a different query (whereClause with
223        * different parameters)
224        */

225       printfFormat = null;
226
227       if (!Util.isNull(format) || !Util.isNull(getFormatClass())) {
228          if (Util.isNull(getFormatClass())) {
229             setFormatClass(getConfig().getDefaultFormatterClass());
230          }
231
232          if (Util.isNull(format)) {
233             setFormat("%s");
234          }
235
236          if (format.indexOf('%') < 0) // try cheap compatibility mode for old applications without '%'// within patterns
237
{
238             StringBuffer JavaDoc newFormat = new StringBuffer JavaDoc();
239
240             for (int j = 0; j < format.length(); j++) {
241                if (format.charAt(j) == 's') {
242                   newFormat.append("%s");
243                } else {
244                   newFormat.append(format.charAt(j));
245                }
246             }
247
248             format = newFormat.toString();
249
250             // was 's bla bla s -- s' is now '%s blabla %s -- %s'
251
}
252
253          try {
254             printfFormat = (IFormatEmbeddedData) ReflectionUtil.newInstance(getFormatClass());
255             printfFormat.setLocale(MessageResources.getLocale(
256                   (HttpServletRequest JavaDoc) pageContext.getRequest()));
257             printfFormat.setFormat(format);
258          } catch (Exception JavaDoc e) {
259             logCat.error("cannot create the new printfFormat ["
260                + getFormatClass() + "]", e);
261          }
262       }
263
264       int result = SKIP_BODY;
265       data = null;
266
267       // If disableCache not activated, was the data generated by another
268
// instance on the same page yet?
269
if (useCache()) {
270          data = (List JavaDoc) pageContext.getAttribute(name, PageContext.PAGE_SCOPE);
271       }
272
273       // if not, we do it
274
if (data == null) {
275          result = EVAL_BODY_BUFFERED;
276          logCat.info("generating Embeddeddata " + name);
277
278          // take Config-Object from application context - this object should
279
// have been
280
// initalized by Config-Servlet on Webapp/server-startup!
281
DbFormsConfig config = null;
282
283          try {
284             config = DbFormsConfigRegistry.instance().lookup();
285          } catch (Exception JavaDoc e) {
286             logCat.error(e);
287             throw new JspException JavaDoc(e);
288          }
289
290          Connection JavaDoc con = null;
291
292          try {
293             con = config.getConnection(dbConnectionName);
294          } catch (Exception JavaDoc e) {
295             throw new JspException JavaDoc(e);
296          }
297
298          try {
299             data = fetchData(con);
300
301             // Always store data in pageContext - Maybe we need it later.
302
// So we can change dynamic disableCache
303
pageContext.setAttribute(name, data, PageContext.PAGE_SCOPE);
304
305             // cache result for further loops
306
} catch (SQLException JavaDoc sqle) {
307             throw new JspException JavaDoc("Database error in EmbeddedData.fetchData "
308                + sqle.toString());
309          } finally {
310             SqlUtil.closeConnection(con);
311          }
312       } else {
313          logCat.info(" Embeddeddata " + name + " already generated");
314       }
315
316       ((DataContainer) getParent()).setEmbeddedData(data);
317
318       // DbBaseMultiTag are: select, radio, checkbox!
319
return result;
320    }
321
322
323    /**
324     * this method is implemented by subclasses in order to match the user's
325     * need for specific data.
326     *
327     * @param con DOCUMENT ME!
328     *
329     * @return DOCUMENT ME!
330     */

331    protected abstract List JavaDoc fetchData(Connection JavaDoc con) throws SQLException JavaDoc;
332
333
334    /**
335     * formatEmbeddedResultRows() formats a result set accornding to a
336     * eventually given format string. If no format string is given, the output
337     * format is a comma separated list of values. This method is called by
338     * subclasses TableData and QueryData
339     *
340     * @param rsv result set vector to be formatted
341     *
342     * @return a vector of key-value pairs, the values eventually formatted
343     * according to a given format string
344     */

345    protected List JavaDoc formatEmbeddedResultRows(ResultSetVector rsv) {
346       List JavaDoc result = new java.util.Vector JavaDoc();
347       boolean resultSuccessFullyFormated = false;
348
349       if (printfFormat != null) {
350          try {
351             rsv.moveFirst();
352
353             for (int i = 0; i < rsv.size(); i++) {
354
355                String JavaDoc[] currentRow = rsv.getCurrentRow();
356                String JavaDoc htKey = currentRow[0];
357
358                Object JavaDoc[] objs = rsv.getCurrentRowAsObjects();
359
360                Object JavaDoc[] objs2 = new Object JavaDoc[objs.length - 1];
361
362                for (int j = 0; j < objs2.length; j++) {
363                   if ((objs[j] instanceof String JavaDoc) || (objs[j] instanceof Byte JavaDoc)
364                            || (objs[j] instanceof java.lang.Integer JavaDoc)
365                            || (objs[j] instanceof Short JavaDoc)
366                            || (objs[j] instanceof Float JavaDoc)
367                            || (objs[j] instanceof Long JavaDoc)
368                            || (objs[j] instanceof Double JavaDoc)) {
369                      objs2[j] = objs[(j + 1)];
370                   } else {
371                      objs2[j] = currentRow[j + 1];
372
373                      // use String representation instead
374
}
375                }
376
377                String JavaDoc htValue = printfFormat.sprintf(objs2);
378                result.add(new KeyValuePair(htKey, htValue));
379                rsv.moveNext();
380             }
381
382             resultSuccessFullyFormated = true;
383          } catch (IllegalArgumentException JavaDoc ex) {
384             logCat.error("Could not format result using format '" + format
385                + "', error message is " + ex.getMessage());
386             logCat.error(
387                "Using fallback method of comma separated list instead");
388             result = new java.util.Vector JavaDoc();
389          } catch (NullPointerException JavaDoc npe) // npe will be thrown if null// value returned from database
390
{
391             logCat.error("Could not format result using format '" + format
392                + "', error message is " + npe.getMessage());
393             logCat.error(
394                "Using fallback method of comma separated list instead");
395             result = new java.util.Vector JavaDoc();
396          }
397       }
398
399       if (!resultSuccessFullyFormated) // no format given or formatting failed
400
{
401          rsv.moveFirst();
402
403          for (int i = 0; i < rsv.size(); i++) {
404
405             String JavaDoc[] currentRow = rsv.getCurrentRow();
406             String JavaDoc htKey = currentRow[0];
407             StringBuffer JavaDoc htValueBuf = new StringBuffer JavaDoc();
408
409             for (int j = 1; j < currentRow.length; j++) {
410                htValueBuf.append(currentRow[j]);
411
412                if (j < (currentRow.length - 1)) {
413                   htValueBuf.append(", ");
414                }
415             }
416
417             String JavaDoc htValue = htValueBuf.toString(); //
418

419             result.add(new KeyValuePair(htKey, htValue));
420             rsv.moveNext();
421          }
422       }
423
424       return result;
425    }
426
427
428    /**
429     * DOCUMENT ME!
430     *
431     * @return DOCUMENT ME!
432     */

433    protected boolean useCache() {
434       return !(Util.getTrue(this.getDisableCache()));
435    }
436 }
437
Popular Tags