001: /* ====================================================================
002: * The Jcorporate Apache Style Software License, Version 1.2 05-07-2002
003: *
004: * Copyright (c) 1995-2002 Jcorporate Ltd. All rights reserved.
005: *
006: * Redistribution and use in source and binary forms, with or without
007: * modification, are permitted provided that the following conditions
008: * are met:
009: *
010: * 1. Redistributions of source code must retain the above copyright
011: * notice, this list of conditions and the following disclaimer.
012: *
013: * 2. Redistributions in binary form must reproduce the above copyright
014: * notice, this list of conditions and the following disclaimer in
015: * the documentation and/or other materials provided with the
016: * distribution.
017: *
018: * 3. The end-user documentation included with the redistribution,
019: * if any, must include the following acknowledgment:
020: * "This product includes software developed by Jcorporate Ltd.
021: * (http://www.jcorporate.com/)."
022: * Alternately, this acknowledgment may appear in the software itself,
023: * if and wherever such third-party acknowledgments normally appear.
024: *
025: * 4. "Jcorporate" and product names such as "Expresso" must
026: * not be used to endorse or promote products derived from this
027: * software without prior written permission. For written permission,
028: * please contact info@jcorporate.com.
029: *
030: * 5. Products derived from this software may not be called "Expresso",
031: * or other Jcorporate product names; nor may "Expresso" or other
032: * Jcorporate product names appear in their name, without prior
033: * written permission of Jcorporate Ltd.
034: *
035: * 6. No product derived from this software may compete in the same
036: * market space, i.e. framework, without prior written permission
037: * of Jcorporate Ltd. For written permission, please contact
038: * partners@jcorporate.com.
039: *
040: * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
041: * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
042: * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
043: * DISCLAIMED. IN NO EVENT SHALL JCORPORATE LTD OR ITS CONTRIBUTORS
044: * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
045: * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
046: * TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
047: * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
048: * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
049: * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
050: * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
051: * SUCH DAMAGE.
052: * ====================================================================
053: *
054: * This software consists of voluntary contributions made by many
055: * individuals on behalf of the Jcorporate Ltd. Contributions back
056: * to the project(s) are encouraged when you make modifications.
057: * Please send them to support@jcorporate.com. For more information
058: * on Jcorporate Ltd. and its products, please see
059: * <http://www.jcorporate.com/>.
060: *
061: * Portions of this software are based upon other open source
062: * products and are subject to their respective licenses.
063: */
064:
065: package com.jcorporate.expresso.ext.controller;
066:
067: import com.jcorporate.expresso.core.controller.ControllerException;
068: import com.jcorporate.expresso.core.controller.ControllerRequest;
069: import com.jcorporate.expresso.core.controller.ControllerResponse;
070: import com.jcorporate.expresso.core.controller.DBController;
071: import com.jcorporate.expresso.core.controller.Input;
072: import com.jcorporate.expresso.core.controller.NonHandleableException;
073: import com.jcorporate.expresso.core.controller.Output;
074: import com.jcorporate.expresso.core.controller.State;
075: import com.jcorporate.expresso.core.controller.Transition;
076: import com.jcorporate.expresso.core.db.DBException;
077: import com.jcorporate.expresso.core.dbobj.DBObject;
078: import com.jcorporate.expresso.core.dbobj.Schema;
079: import com.jcorporate.expresso.core.dbobj.SchemaFactory;
080: import com.jcorporate.expresso.core.dbobj.SecuredDBObject;
081: import com.jcorporate.expresso.core.dbobj.ValidValue;
082: import com.jcorporate.expresso.core.misc.ConfigManager;
083: import com.jcorporate.expresso.core.misc.ConfigurationException;
084: import com.jcorporate.expresso.core.misc.StringUtil;
085: import com.jcorporate.expresso.services.dbobj.SchemaList;
086: import org.apache.log4j.Logger;
087:
088: import java.util.Enumeration;
089: import java.util.Iterator;
090: import java.util.Vector;
091:
092: /**
093: * DataTransfer is a controller used to move data from one
094: * db/context to another, with various options
095: *
096: * @author Michael Nash
097: */
098: public class DataTransfer extends DBController {
099: private static Logger log = Logger.getLogger(DataTransfer.class);
100:
101: /**
102: * Default constructor
103: */
104: public DataTransfer() {
105: super ();
106: State selSchema = new State("selSchema", "Prompt for Schema");
107: addState(selSchema);
108: setInitialState("selSchema");
109:
110: State prompt = new State("prompt",
111: "Prompt for Tranfer Parameters");
112: addState(prompt);
113: prompt.addRequiredParameter("SchemaClass");
114:
115: State transfer = new State("transfer", "Run Transfers");
116: transfer.addRequiredParameter("fromContext");
117: transfer.addRequiredParameter("toContext");
118: addState(transfer);
119: this
120: .setSchema(com.jcorporate.expresso.core.ExpressoSchema.class);
121: } /* DataTransfer() */
122:
123: protected void runSelSchemaState(ControllerRequest req,
124: ControllerResponse res) throws ControllerException {
125: try {
126: Input chooseSchema = new Input();
127: chooseSchema.setLabel("Choose Schema");
128: chooseSchema.setName("SchemaClass");
129:
130: Vector v2 = new Vector(2);
131: v2.addElement(new ValidValue("com.jcorporate.expresso."
132: + "core.ExpressoSchema", "General"));
133:
134: SchemaList sl = new SchemaList(
135: SecuredDBObject.SYSTEM_ACCOUNT);
136: sl.setDataContext(req.getDataContext());
137:
138: SchemaList oneSchema = null;
139:
140: for (Iterator e = sl.searchAndRetrieveList("Descrip")
141: .iterator(); e.hasNext();) {
142: oneSchema = (SchemaList) e.next();
143: v2.addElement(new ValidValue(oneSchema
144: .getField("SchemaClass"), oneSchema
145: .getField("Descrip")));
146: }
147:
148: chooseSchema.setValidValues(v2);
149: res.addInput(chooseSchema);
150: res.addTransition(new Transition("prompt", this ));
151: } catch (DBException de) {
152: throw new ControllerException(de.getMessage());
153: }
154: } /* runSelSchemaState */
155:
156: protected void runPromptState(ControllerRequest req,
157: ControllerResponse res) throws ControllerException,
158: NonHandleableException {
159: Input chooseDBobj = new Input();
160: chooseDBobj.setLabel("Choose Database Object");
161: chooseDBobj.setName("dbobj");
162:
163: Vector v2 = new Vector();
164: v2.addElement(new ValidValue("All", "All Objects in Schema"));
165:
166: DBObject oneDBObject = null;
167: Schema mySchema = SchemaFactory.getInstance().getSchema(
168: req.getParameter("SchemaClass"));
169:
170: if (mySchema == null) {
171: throw new ControllerException(
172: "Unable to instantiate schema: "
173: + req.getParameter("SchemaClass"));
174: }
175:
176: for (Enumeration e = mySchema.getMembers(); e.hasMoreElements();) {
177: oneDBObject = (DBObject) e.nextElement();
178: v2.addElement(new ValidValue(oneDBObject.getClass()
179: .getName(), oneDBObject.getMetaData()
180: .getDescription()));
181: }
182:
183: chooseDBobj.setValidValues(v2);
184: res.addInput(chooseDBobj);
185:
186: Input fromContext = new Input("fromContext");
187: fromContext.setDefaultValue(req.getDataContext());
188: fromContext.setLabel("From " + getString("Context/Database_"));
189:
190: Input toContext = new Input("toContext");
191: toContext.setDefaultValue(req.getDataContext());
192: toContext.setLabel("To " + getString("Context/Database_"));
193:
194: String oneConfigKey = null;
195: String oneDescrip = null;
196: Vector v = new Vector();
197:
198: for (Enumeration ie = ConfigManager.getAllConfigKeys(); ie
199: .hasMoreElements();) {
200: oneConfigKey = (String) ie.nextElement();
201: oneDescrip = "";
202:
203: try {
204: oneDescrip = StringUtil.notNull(ConfigManager
205: .getContext(oneConfigKey).getDescription());
206:
207: if (oneDescrip.equals("")) {
208: oneDescrip = oneConfigKey;
209: }
210: /* If it's not an expresso context, you can't log in to it */
211: if (ConfigManager.getContext(oneConfigKey)
212: .hasSetupTables()) {
213: v.addElement(new ValidValue(oneConfigKey,
214: oneDescrip));
215: }
216: } catch (ConfigurationException ce) {
217: throw new ControllerException(ce);
218: }
219: }
220:
221: fromContext.setValidValues(v);
222: res.addInput(fromContext);
223: toContext.setValidValues(v);
224: res.addInput(toContext);
225:
226: Input handleDups = new Input("handleDups",
227: "Duplicate Key Handling");
228: Vector hdv = new Vector();
229: hdv.addElement(new ValidValue("S", "Skip Duplicate Records"));
230: hdv
231: .addElement(new ValidValue("R",
232: "Replace Duplicate Records"));
233: hdv.addElement(new ValidValue("A", "Add New Records"));
234: hdv.addElement(new ValidValue("I", "Insert Records"));
235: handleDups.setValidValues(hdv);
236: res.addInput(handleDups);
237:
238: Input clearDestination = new Input("clearDestination",
239: "Clear Destination Table before Copy");
240: res.addInput(clearDestination);
241:
242: Input customWhere = new Input("customWhere",
243: "Where clause for source");
244: res.addInput(customWhere);
245:
246: Transition doTransfer = new Transition("transfer", this );
247: doTransfer.addParam("SchemaClass", req
248: .getParameter("SchemaClass"));
249: res.addTransition(doTransfer);
250: } /* runPromptState */
251:
252: protected void runTransferState(ControllerRequest req,
253: ControllerResponse res) throws ControllerException {
254: String dbobj = req.getParameter("dbobj");
255: Vector transferList = new Vector();
256:
257: if (dbobj.equals("All")) {
258: DBObject oneDBObject = null;
259: Schema mySchema = SchemaFactory.getInstance().getSchema(
260: req.getParameter("SchemaClass"));
261:
262: if (mySchema == null) {
263: throw new ControllerException(
264: "Error instantiating schema: "
265: + req.getParameter("SchemaClass"));
266: }
267:
268: for (Enumeration e = mySchema.getMembers(); e
269: .hasMoreElements();) {
270: oneDBObject = (DBObject) e.nextElement();
271: transferList.addElement(oneDBObject.getClass()
272: .getName());
273: }
274: } else {
275: transferList.addElement(dbobj);
276: }
277: try {
278: String oneObj = null;
279:
280: for (Enumeration e = transferList.elements(); e
281: .hasMoreElements();) {
282: oneObj = (String) e.nextElement();
283: transferObject(res, req.getParameter("fromContext"),
284: req.getParameter("toContext"), oneObj, req
285: .getParameter("handleDups"), req
286: .getParameter("clearDestination"), req
287: .getParameter("customWhere"));
288: }
289: } catch (DBException de) {
290: throw new ControllerException(de);
291: }
292: } /* runTranferState */
293:
294: private void transferObject(ControllerResponse res,
295: String fromContext, String toContext, String objectClass,
296: String handleDups, String clearDestination,
297: String customWhere) throws DBException, ControllerException {
298: if (objectClass
299: .equals("com.jcorporate.expresso.ext.dbobj.SingleDBUserInfo")) {
300: return;
301: }
302: if (clearDestination.equalsIgnoreCase("Y")) {
303: DBObject clearObj = createDBObj(objectClass, toContext);
304: clearObj.deleteAll();
305: }
306:
307: DBObject fromList = createDBObj(objectClass, fromContext);
308:
309: if (!customWhere.equals("")) {
310: fromList.setCustomWhereClause(customWhere);
311: }
312:
313: int exceptionCount = 0;
314: int addedCount = 0;
315: int updatedCount = 0;
316: DBObject fromObj = createDBObj(objectClass, fromContext);
317:
318: for (Iterator i = fromList.searchAndRetrieveList().iterator(); i
319: .hasNext();) {
320: try {
321: fromObj = (DBObject) i.next();
322:
323: if (handleDups.equals("S")) {
324: DBObject searchObj = createDBObj(objectClass,
325: toContext);
326:
327: /* set tke keys */
328: copyKeys(fromObj, searchObj);
329:
330: if (!searchObj.find()) {
331: DBObject newObj = createDBObj(objectClass,
332: toContext);
333: copyAll(fromObj, newObj);
334: newObj.add();
335: addedCount++;
336: }
337: } else if (handleDups.equals("R")) {
338: DBObject searchObj = createDBObj(objectClass,
339: toContext);
340:
341: /* set tke keys */
342: copyKeys(fromObj, searchObj);
343:
344: DBObject newObj = createDBObj(objectClass,
345: toContext);
346: copyAll(fromObj, newObj);
347:
348: if (searchObj.find()) {
349: newObj.update();
350: updatedCount++;
351: } else {
352: newObj.add();
353: addedCount++;
354: }
355: } else if (handleDups.equals("A")) {
356: DBObject newObj = createDBObj(objectClass,
357: toContext);
358: copyAll(fromObj, newObj);
359: newObj.add();
360: addedCount++;
361: } else if (handleDups.equals("I")) {
362: DBObject newObj = createDBObj(objectClass,
363: toContext);
364: copyAll(fromObj, newObj);
365: newObj.basicAdd();
366: addedCount++;
367: }
368: } catch (DBException de) {
369: log.error("Exception tranferring records for '"
370: + objectClass + "':", de);
371: exceptionCount++;
372: }
373: } /* for */
374:
375: res.addOutput(new Output("eCount", "Object '" + objectClass
376: + "' There were " + exceptionCount + " exceptions, "
377: + addedCount + " records added, " + updatedCount
378: + " records updated. See log for details"));
379: }
380:
381: private void copyKeys(DBObject fromObj, DBObject toObj)
382: throws DBException {
383: String oneKey = null;
384:
385: for (Iterator i = fromObj.getKeyFieldListIterator(); i
386: .hasNext();) {
387: oneKey = (String) i.next();
388: toObj.setField(oneKey, fromObj.getField(oneKey));
389: }
390: }
391:
392: private void copyAll(DBObject fromObj, DBObject toObj)
393: throws DBException {
394: String oneField = null;
395:
396: for (Iterator i = fromObj.getMetaData().getFieldListArray()
397: .iterator(); i.hasNext();) {
398: oneField = (String) i.next();
399:
400: if (!fromObj.getMetaData().getFieldMetadata(oneField)
401: .isVirtual()) {
402: toObj.setField(oneField, fromObj.getField(oneField));
403: }
404: }
405: }
406:
407: private DBObject createDBObj(String className, String dbContext)
408: throws DBException {
409: DBObject myDBObj = null;
410:
411: try {
412: myDBObj = (DBObject) Class.forName(className).newInstance();
413:
414: if (myDBObj == null) {
415: throw new DBException("Null object - "
416: + "instantiate failed for database object "
417: + className);
418: }
419: } catch (Exception eo) {
420: throw new DBException("Exception loading SecuredDBObject",
421: eo);
422: }
423:
424: myDBObj.setDataContext(dbContext);
425:
426: return myDBObj;
427: }
428:
429: /**
430: * @return java.lang.String The Title of the controller
431: */
432: public String getTitle() {
433: return "Data Transfer";
434: }
435: } /* DataTransfer */
|