View Javadoc

1   /*
2    * $Header: /cvsroot/jdbforms/dbforms/src/org/dbforms/event/datalist/GotoEvent.java,v 1.26 2005/11/30 20:31:17 hkollmann Exp $
3    * $Revision: 1.26 $
4    * $Date: 2005/11/30 20:31:17 $
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.event.datalist;
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.FieldValue;
29  import org.dbforms.config.FieldValues;
30  import org.dbforms.config.ResultSetVector;
31  import org.dbforms.config.Table;
32  
33  import org.dbforms.event.AbstractNavigationEvent;
34  import org.dbforms.event.datalist.dao.DataSourceFactory;
35  import org.dbforms.event.datalist.dao.DataSourceSessionList;
36  import org.dbforms.interfaces.DbEventInterceptorData;
37  
38  import org.dbforms.util.ParseUtil;
39  import org.dbforms.util.Util;
40  
41  import java.io.UnsupportedEncodingException;
42  
43  import java.sql.SQLException;
44  
45  import javax.servlet.http.HttpServletRequest;
46  
47  
48  
49  /***
50   * This event forces the controller to forward the current request to a
51   * Request-Dispatcher specified by the Application-Developer in a
52   * "org.dbforms.taglib.DbGotoButton". Works with new factory classes
53   *
54   * @author Henner Kollmann
55   */
56  public class GotoEvent extends AbstractNavigationEvent {
57     // logging category for this class;
58     private static Log logCat      = LogFactory.getLog(GotoEvent.class.getName());
59     private String     childField;
60     private String     parentField;
61  
62     // where to go in associated table
63     private String  position;
64     private String  tableList   = null;
65     private String  whereClause = null;
66     private Table   srcTable;
67     private boolean singleRow   = false;
68  
69     /***
70      * Constructor - parses the event details. <br>
71      * Depending on the way the attributes where provided by the developer,
72      * different ways are used for resolving the dispatcher the user wants to
73      * get called and the position he wants the ResultSet to be scrolled to.
74      *
75      * @param action the action string
76      * @param request the request object
77      * @param config the config object
78      */
79     public GotoEvent(String action, HttpServletRequest request,
80        DbFormsConfig config) {
81        // create dummy action so that tableId will be parsed to -1!
82        // table and tableId will be parsed here!
83        super("data_data_-1", request, config);
84  
85        String destTable = ParseUtil.getParameter(request,
86              "data" + action + "_destTable");
87  
88        // if the user wants a simple, dumb link and we want no form to be navigated through
89        if (destTable == null) {
90           setTable(null);
91  
92           return;
93        }
94  
95        // # fixme: decision for *1* of the 2 approaches 
96        //          should be met soon!! (either id- OR name-based lookup)
97        setTable(config.getTableByName(destTable));
98  
99        if (getTable() == null) {
100          setTable(config.getTable(Integer.parseInt(destTable)));
101       }
102 
103       String psrcTable = ParseUtil.getParameter(request,
104             "data" + action + "_srcTable");
105 
106       singleRow = "true".equals(ParseUtil.getParameter(request,
107                "data" + action + "_singleRow"));
108 
109       if (psrcTable != null) {
110          this.srcTable = config.getTableByName(psrcTable);
111 
112          if (this.srcTable == null) {
113             this.srcTable = config.getTable(Integer.parseInt(psrcTable));
114          }
115 
116          childField    = ParseUtil.getParameter(request,
117                "data" + action + "_childField");
118          parentField = ParseUtil.getParameter(request,
119                "data" + action + "_parentField");
120       }
121 
122       // the position to go to within the destination-jsp's-table can be given
123       // more or less directly
124       String destPos = ParseUtil.getParameter(request,
125             "data" + action + "_destPos");
126 
127       // the direct way - i.e. "1:5:value"
128       if (destPos != null) {
129          this.position = destPos;
130       } else {
131          String keyToDestPos = ParseUtil.getParameter(request,
132                "data" + action + "_keyToDestPos");
133 
134          // the 1-leveled indirect way: i.e. "k_1_1" whereby k_1_1 leads to "1:2:23"
135          if (keyToDestPos != null) {
136             this.position = ParseUtil.getParameter(request, keyToDestPos);
137          } else {
138             String keyToKeyToDestPos = ParseUtil.getParameter(request,
139                   "data" + action + "_keyToKeyToDestPos");
140 
141             // the 2-leveled indirect way: i.e. "my_sel" wherby "mysel" leads to "1_1",
142             // which leads to "1:2:23"
143             if (keyToKeyToDestPos != null) {
144                String widgetValue = ParseUtil.getParameter(request,
145                      keyToKeyToDestPos); // i.e. "1_1"
146                this.position = ParseUtil.getParameter(request,
147                      "k_" + widgetValue); // i.e. "1:2:23"
148             }
149          }
150       }
151 
152       logCat.info("--->pos=" + position);
153    }
154 
155 
156    /***
157     * This constructor is not called by the controller but, actually, BY THE
158     * VIEW for example if the FormTag "gotoPrefix" attribute is set an a
159     * GotoEvent needs to be instanciated.
160     *
161     * @param table the input table
162     * @param request request the request object
163     * @param config the config object
164     * @param position the position string
165     */
166    public GotoEvent(Table table, HttpServletRequest request,
167       DbFormsConfig config, String position) {
168       super(table, request, config);
169       this.position = table.getKeyPositionString(table.getFieldValues(position));
170       // CAPIO - encode the position string, cause processing it will decode it.
171       try {
172          this.position = Util.encode(this.position, getRequest().getCharacterEncoding());
173 	  } catch (UnsupportedEncodingException e) {
174 		 logCat.error(e);
175 	  }
176    }
177 
178 
179    /***
180     * This constructer is not called by the controller but, actually, BY THE
181     * VIEW for example if the FormTag needs a free form select, this
182     * constructor is called.
183     *
184     * @param table the input table
185     * @param request request the request object
186     * @param config the config object
187     * @param whereClause the SQL where clause
188     * @param tableList the table list
189     */
190    public GotoEvent(Table table, HttpServletRequest request,
191       DbFormsConfig config, String whereClause, String tableList) {
192       super(table, request, config);
193       this.whereClause    = whereClause;
194       this.tableList      = tableList;
195    }
196 
197    /***
198     * Process the current event.
199     *
200     * @param childFieldValues FieldValue array used to restrict a set of data
201     * @param orderConstraint FieldValue array used to build a cumulation of
202     *        rules for ordering (sorting) and restricting fields to the actual
203     *        block of data
204     * @param firstPosition DOCUMENT ME!
205     * @param sqlFilterParams a string identifying the last resultset position
206     * @param count record count
207     * @param firstPosition a string identifying the first resultset position
208     * @param lastPosition DOCUMENT ME!
209     * @param dbConnectionName name of the used db connection. Can be used to
210     *        get an own db connection, e.g. to hold it during the session (see
211     *        DataSourceJDBC for example!)
212     * @param con the JDBC Connection object
213     *
214     * @return a ResultSetVector object
215     *
216     * @exception SQLException if any error occurs
217     */
218    public ResultSetVector processEvent(FieldValue[] childFieldValues,
219       FieldValue[] orderConstraint, String sqlFilter,
220       FieldValue[] sqlFilterParams, int count, String firstPosition,
221       String lastPosition, DbEventInterceptorData interceptorData)
222       throws SQLException {
223       // get the DataSourceList from the session
224       logCat.info("==> GotoEvent.processEvent");
225 
226       FieldValues fv;
227 
228       if (!Util.isNull(position)) {
229          try {
230             position = Util.decode(position, getRequest().getCharacterEncoding());
231          } catch (UnsupportedEncodingException e) {
232             logCat.error(e);
233             throw new SQLException(e.getMessage());
234          }
235 
236          if ((srcTable != null) && !Util.isNull(childField)
237                   && !Util.isNull(parentField)) {
238             fv = getTable().mapChildFieldValues(srcTable, parentField,
239                   childField, position);
240          } else {
241             fv = getTable().getFieldValues(position);
242          }
243 
244          position = getTable().getKeyPositionString(fv);
245 
246          if (singleRow && (fv != null)) {
247             childFieldValues = fv.toArray();
248          }
249       }
250 
251       DataSourceSessionList ds = DataSourceSessionList.getInstance(getRequest());
252       ds.remove(getTable(), getRequest());
253 
254       DataSourceFactory qry = new DataSourceFactory((String) interceptorData
255             .getAttribute(DbEventInterceptorData.CONNECTIONNAME),
256             interceptorData.getConnection(), getTable());
257 
258       if (Util.isNull(whereClause)) {
259          qry.setSelect(childFieldValues, orderConstraint, sqlFilter,
260             sqlFilterParams);
261       } else {
262          qry.setSelect(tableList, whereClause);
263       }
264 
265       ds.put(getTable(), getRequest(), qry);
266 
267       return qry.getCurrent(interceptorData, position, count);
268    }
269 }