Source Code Cross Referenced for DataStore.java in  » J2EE » Sofia » com » salmonllc » sql » Java Source Code / Java DocumentationJava Source Code and Java Documentation

Java Source Code / Java Documentation
1. 6.0 JDK Core
2. 6.0 JDK Modules
3. 6.0 JDK Modules com.sun
4. 6.0 JDK Modules com.sun.java
5. 6.0 JDK Modules sun
6. 6.0 JDK Platform
7. Ajax
8. Apache Harmony Java SE
9. Aspect oriented
10. Authentication Authorization
11. Blogger System
12. Build
13. Byte Code
14. Cache
15. Chart
16. Chat
17. Code Analyzer
18. Collaboration
19. Content Management System
20. Database Client
21. Database DBMS
22. Database JDBC Connection Pool
23. Database ORM
24. Development
25. EJB Server geronimo
26. EJB Server GlassFish
27. EJB Server JBoss 4.2.1
28. EJB Server resin 3.1.5
29. ERP CRM Financial
30. ESB
31. Forum
32. GIS
33. Graphic Library
34. Groupware
35. HTML Parser
36. IDE
37. IDE Eclipse
38. IDE Netbeans
39. Installer
40. Internationalization Localization
41. Inversion of Control
42. Issue Tracking
43. J2EE
44. JBoss
45. JMS
46. JMX
47. Library
48. Mail Clients
49. Net
50. Parser
51. PDF
52. Portal
53. Profiler
54. Project Management
55. Report
56. RSS RDF
57. Rule Engine
58. Science
59. Scripting
60. Search Engine
61. Security
62. Sevlet Container
63. Source Control
64. Swing Library
65. Template Engine
66. Test Coverage
67. Testing
68. UML
69. Web Crawler
70. Web Framework
71. Web Mail
72. Web Server
73. Web Services
74. Web Services apache cxf 2.0.1
75. Web Services AXIS2
76. Wiki Engine
77. Workflow Engines
78. XML
79. XML UI
Java
Java Tutorial
Java Open Source
Jar File Download
Java Articles
Java Products
Java by API
Photoshop Tutorials
Maya Tutorials
Flash Tutorials
3ds-Max Tutorials
Illustrator Tutorials
GIMP Tutorials
C# / C Sharp
C# / CSharp Tutorial
C# / CSharp Open Source
ASP.Net
ASP.NET Tutorial
JavaScript DHTML
JavaScript Tutorial
JavaScript Reference
HTML / CSS
HTML CSS Reference
C / ANSI-C
C Tutorial
C++
C++ Tutorial
Ruby
PHP
Python
Python Tutorial
Python Open Source
SQL Server / T-SQL
SQL Server / T-SQL Tutorial
Oracle PL / SQL
Oracle PL/SQL Tutorial
PostgreSQL
SQL / MySQL
MySQL Tutorial
VB.Net
VB.Net Tutorial
Flash / Flex / ActionScript
VBA / Excel / Access / Word
XML
XML Tutorial
Microsoft Office PowerPoint 2007 Tutorial
Microsoft Office Excel 2007 Tutorial
Microsoft Office Word 2007 Tutorial
Java Source Code / Java Documentation » J2EE » Sofia » com.salmonllc.sql 
Source Cross Referenced  Class Diagram Java Document (Java Doc) 


0001:        //** Copyright Statement ***************************************************
0002:        //The Salmon Open Framework for Internet Applications (SOFIA)
0003:        // Copyright (C) 1999 - 2002, Salmon LLC
0004:        //
0005:        // This program is free software; you can redistribute it and/or
0006:        // modify it under the terms of the GNU General Public License version 2
0007:        // as published by the Free Software Foundation;
0008:        //
0009:        // This program is distributed in the hope that it will be useful,
0010:        // but WITHOUT ANY WARRANTY; without even the implied warranty of
0011:        // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
0012:        // GNU General Public License for more details.
0013:        //
0014:        // You should have received a copy of the GNU General Public License
0015:        // along with this program; if not, write to the Free Software
0016:        // Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
0017:        //
0018:        // For more information please visit http://www.salmonllc.com
0019:        //** End Copyright Statement ***************************************************
0020:        package com.salmonllc.sql;
0021:
0022:        /////////////////////////
0023:        //$Archive: /SOFIA/SourceCode/com/salmonllc/sql/DataStore.java $
0024:        //$Author: Dan $
0025:        //$Revision: 97 $
0026:        //$Modtime: 11/02/04 9:59a $
0027:        /////////////////////////
0028:
0029:        import java.sql.*;
0030:        import java.util.*;
0031:        import java.io.*;
0032:        import java.text.*;
0033:        import java.lang.reflect.*;
0034:
0035:        import com.salmonllc.util.*;
0036:
0037:        /**
0038:         * This class provides a storage buffer for data in SQL ResultSets that allow
0039:         * for retreves, inserts updates and deletes.
0040:         */
0041:        public class DataStore extends DataStoreBuffer implements  Runnable,
0042:                Serializable, DataStoreInterface {
0043:
0044:            public static final int UPDATEMETHOD_UPDATES = 1;
0045:            public static final int UPDATEMETHOD_DELETEINSERTS = 2;
0046:
0047:            private int _updateMethod = UPDATEMETHOD_UPDATES;
0048:            private Vector _listeners;
0049:
0050:            private transient DBConnection _dbConn;
0051:
0052:            protected String _appName = null;
0053:            private String _dbProfile = null;
0054:            private boolean _releaseConn = false;
0055:            private boolean _checkConcurrency = false;
0056:            private boolean _useBind = false;
0057:            private boolean _enableCancel = false; //Added by FC on 2/21/03. Was added
0058:            // to handle JDBC drivers which have
0059:            // problems with the cancel() method
0060:            // being called. Example Driver:
0061:            // JSQLDriver from NetDirect.
0062:            private int _maxRows = -1;
0063:            private String _connType;
0064:            private DataSourceIn _dsIn, _curDsIn;
0065:            private DataSourceOut _dsOut;
0066:            private AutoRetrieveCriteria _havingCrit;
0067:            private boolean _threaded = false;
0068:            private String _dbName = null;
0069:            private String _dbms = null;
0070:            private boolean _autoValidate = false;
0071:            private boolean _batchInserts = false;
0072:
0073:            public static final String CONNECTION_PARM_CHECK_CONCURRENCY = "CheckConcurrency";
0074:            public static final String CONNECTION_PARM_USE_BIND_FOR_UPDATES = "UseBindForUpdates";
0075:            public static final String CONNECTION_PARM_USE_DELETE_INSERT_FOR_UPDATES = "UseDeleteInsertForUpdates";
0076:            public static final String CONNECTION_PARM_TRIM_STRINGS = "TrimStrings";
0077:            public static final String CONNECTION_PARM_CACHE_DATADICTIONARY = "CacheDataDictionary";
0078:
0079:            public static final String CONNECTION_PARM_REPLACE_NULL_STRINGS = "ReplaceNullStrings";
0080:            public static final String CONNECTION_PARM_REPLACE_NULL_INTS = "ReplaceNullInts";
0081:            public static final String CONNECTION_PARM_REPLACE_NULL_DECIMALS = "ReplaceNullDecimals";
0082:            public static final String CONNECTION_PARM_REPLACE_NULL_DATES = "ReplaceNullDates";
0083:            public static final String CONNECTION_PARM_REPLACE_NULL_TIMES = "ReplaceNullTimes";
0084:            public static final String CONNECTION_PARM_REPLACE_NULL_DATETIMES = "ReplaceNullDateTimes";
0085:
0086:            /**
0087:             * Creates a new empty DataStore object. Any method requiring a database
0088:             * connection (retrieve,update and union) will have to be explicitly passed
0089:             * a DBConnection created outside the datastore.
0090:             */
0091:            public DataStore() {
0092:                super ();
0093:            }
0094:
0095:            /**
0096:             * Creates a new empty DataStore. Any methods requiring a database
0097:             * connection (retrieve, update and union) will be able to use appName to
0098:             * get connection parameters from properties files and so an externally
0099:             * created DBConnection object does not need to be provided.
0100:             * 
0101:             * @param dsIn
0102:             *            The data source used to retrieve data.
0103:             * @param dsOut
0104:             *            The data source used to update data.
0105:             */
0106:            public DataStore(DataSourceIn dsIn, DataSourceOut dsOut) {
0107:                super ();
0108:                _appName = null;
0109:                _dbProfile = null;
0110:                _dsIn = dsIn;
0111:                _dsOut = dsOut;
0112:            }
0113:
0114:            /**
0115:             * Creates a new empty DataStore. Any methods requiring a database
0116:             * connection (retrieve, update and union) will be able to use appName to
0117:             * get connection parameters from properties files and so an externally
0118:             * created DBConnection object does not need to be provided.
0119:             * 
0120:             * @param appName
0121:             *            The application to get the default database connection for.
0122:             */
0123:            public DataStore(String appName) {
0124:                this (appName, null);
0125:            }
0126:
0127:            /**
0128:             * Creates a new empty DataStore. Creates a new empty DataStore. Any methods
0129:             * requiring a database connection (retrieve, update and union) will be able
0130:             * to use appName and dbProfile to get connection parameters from properties
0131:             * files and so an externally created DBConnection object does not need to
0132:             * be provided.
0133:             * 
0134:             * @param appName
0135:             *            The application to get the database connection for.
0136:             * @param dbProfile
0137:             *            The particular database profile to load.
0138:             */
0139:            public DataStore(String appName, String dbProfile) {
0140:                super ();
0141:                boolean loadConnParms = false;
0142:                _appName = appName;
0143:                _dbProfile = dbProfile;
0144:
0145:                /*
0146:                 * srufle : May 17, 2004 7 : 37 : 04 PM Added to allow for a
0147:                 * construction with no appName or dbProfile
0148:                 */
0149:                if (Util.isFilled(_appName)) {
0150:                    loadConnParms = true;
0151:                } else if (Util.isFilled(_dbProfile)) {
0152:                    loadConnParms = true;
0153:                }
0154:
0155:                if (loadConnParms) {
0156:                    loadConnectionParms();
0157:                }
0158:
0159:            }
0160:
0161:            /**
0162:             * This method adds a column to the DataStore using the datastore's default
0163:             * table. The column is not part of the primary key of the table and is not
0164:             * updatable.
0165:             * 
0166:             * @param column
0167:             *            The name of the column to add to the datastore.
0168:             * @param type
0169:             *            The type of the column to add to the datastore. This must be
0170:             *            one of the "TYPE" constants in the class.
0171:             * @see DataStore#setDefaultTable
0172:             */
0173:            public void addColumn(String column, int type) {
0174:                addColumn(column, type, false, false);
0175:            }
0176:
0177:            /**
0178:             * This method adds a column to the DataStore using the datastore's default
0179:             * table.
0180:             * 
0181:             * @param column
0182:             *            The name of the column to add to the datastore.
0183:             * @param type
0184:             *            The type of the column to add to the datastore. This must be
0185:             *            one of the "TYPE" constants in the class.
0186:             * @param primaryKey
0187:             *            True if the column is part of the primary key of the table it
0188:             *            is in.
0189:             * @param updatable
0190:             *            True if this column should be updated when the update method
0191:             *            is called.
0192:             * @see DataStore#setDefaultTable
0193:             */
0194:            public void addColumn(String column, int type, boolean primaryKey,
0195:                    boolean updatable) {
0196:                String table = null;
0197:                int i = column.lastIndexOf(".");
0198:                if (i >= 0) {
0199:                    table = column.substring(0, i);
0200:                    column = column.substring(i + 1);
0201:                }
0202:                _desc.addColumn(table, column, type, primaryKey, updatable,
0203:                        null);
0204:            }
0205:
0206:            /**
0207:             * This method adds a column to the DataStore using the datastore's default
0208:             * table. The column is not part of the primary key of the table and is not
0209:             * updatable.
0210:             * 
0211:             * @param table
0212:             *            The name of the table to add to the datastore.
0213:             * @param column
0214:             *            The name of the column to add to the datastore.
0215:             * @param type
0216:             *            The type of the column to add to the datastore. This must be
0217:             *            one of the "TYPE" constants in the class.
0218:             * @see DataStore#setDefaultTable
0219:             */
0220:            public void addColumn(String table, String column, int type) {
0221:                _desc.addColumn(table, column, type, false, false, null);
0222:            }
0223:
0224:            /**
0225:             * This method adds a column to the DataStore
0226:             * 
0227:             * @param table
0228:             *            The name of the table containing the column.
0229:             * @param column
0230:             *            The name of the column to add to the datastore.
0231:             * @param type
0232:             *            The type of the column to add to the datastore. This must be
0233:             *            one of the "TYPE" constants in the class.
0234:             * @param primaryKey
0235:             *            True if the column is part of the primary key of the table it
0236:             *            is in.
0237:             * @param updateable
0238:             *            True if this column should be updated when the update method
0239:             *            is called.
0240:             */
0241:            public void addColumn(String table, String column, int type,
0242:                    boolean primaryKey, boolean updateable) {
0243:                _desc.addColumn(table, column, type, primaryKey, updateable,
0244:                        null);
0245:            }
0246:
0247:            /**
0248:             * This method adds a column to the DataStore
0249:             * 
0250:             * @param table
0251:             *            The name of the table containing the column.
0252:             * @param column
0253:             *            The name of the column to add to the datastore.
0254:             * @param type
0255:             *            The type of the column to add to the datastore. This must be
0256:             *            one of the "TYPE" constants in the class.
0257:             * @param primaryKey
0258:             *            True if the column is part of the primary key of the table it
0259:             *            is in.
0260:             * @param updateable
0261:             *            True if this column should be updated when the update method
0262:             *            is called.
0263:             * @param internalName
0264:             *            The name to use to get the value of the column later. If not
0265:             *            used, the column can be referenced by tablename.columnname
0266:             */
0267:            public void addColumn(String table, String column, int type,
0268:                    boolean primaryKey, boolean updateable, String internalName) {
0269:                _desc.addColumn(table, column, type, primaryKey, updateable,
0270:                        internalName);
0271:            }
0272:
0273:            /**
0274:             * This method adds a column to the DataStore and passes the format to
0275:             * setFormat
0276:             * 
0277:             * @param table
0278:             *            The name of the table containing the column.
0279:             * @param column
0280:             *            The name of the column to add to the datastore.
0281:             * @param type
0282:             *            The type of the column to add to the datastore. This must be
0283:             *            one of the "TYPE" constants in the class.
0284:             * @param primaryKey
0285:             *            True if the column is part of the primary key of the table it
0286:             *            is in.
0287:             * @param updateable
0288:             *            True if this column should be updated when the update method
0289:             *            is called.
0290:             * @param colFormat
0291:             *            The format to use in parsing or formatting the value.
0292:             * @see DataStoreBuffer#setFormat
0293:             */
0294:
0295:            public void addFormattedColumn(String table, String column,
0296:                    int type, boolean primaryKey, boolean updateable,
0297:                    String colFormat) {
0298:                try {
0299:                    _desc.addColumn(table, column, type, primaryKey,
0300:                            updateable, null);
0301:                    setFormat(table + "." + column, colFormat);
0302:                } catch (DataStoreException e) {
0303:                    MessageLog
0304:                            .writeAssertionMessage(
0305:                                    "addFormattedColumn thru a DataStoreException this should not happen !!",
0306:                                    this );
0307:                }
0308:            }
0309:
0310:            /**
0311:             * This method is used to set the join clause connecting two or more tables
0312:             * used in the DataStore. This is not necessary for single table DataStores.
0313:             * 
0314:             * @param columnList1:
0315:             *            A list of column names seperated by commas on the left side of
0316:             *            the join
0317:             * @param columnList2:
0318:             *            A list of column names seperated by commas on the right side
0319:             *            of the join
0320:             * @param outerJoin:
0321:             *            True if this is an outer join and false for a regular join.
0322:             *            Note: the left side of the join (columnList 1) will always be
0323:             *            the outer member of the join.
0324:             */
0325:            public void addJoin(String columnList1, String columnList2,
0326:                    boolean outerJoin) {
0327:                _desc.addJoin(columnList1, columnList2, outerJoin);
0328:            }
0329:
0330:            //fc 06/11/04: Added this method to specify in One to Many Relationship
0331:            // Model
0332:            /**
0333:             * This method is used to set the join clause connecting two or more tables
0334:             * used in the DataStore. This is not necessary for single table DataStores.
0335:             * 
0336:             * @param columnList1:
0337:             *            A list of column names seperated by commas on the left side of
0338:             *            the join
0339:             * @param columnList2:
0340:             *            A list of column names seperated by commas on the right side
0341:             *            of the join
0342:             * @param outerJoin:
0343:             *            True if this is an outer join and false for a regular join.
0344:             *            Note: the left side of the join (columnList 1) will always be
0345:             *            the outer member of the join.
0346:             * @param relationType:
0347:             *            Specifies the type of relation the join represents.
0348:             *            (RELATION_ONE_TO_ONE, RELATION_ONE_TO_MANY,
0349:             *            RELATION_MANY_TO_ONE)
0350:             */
0351:            public void addJoin(String columnList1, String columnList2,
0352:                    boolean outerJoin, int relationType) {
0353:                if (!_manytoonerelationship
0354:                        && relationType > RELATION_MANY_TO_ONE)
0355:                    _manytoonerelationship = true;
0356:                _desc
0357:                        .addJoin(columnList1, columnList2, outerJoin,
0358:                                relationType);
0359:            }
0360:
0361:            /**
0362:             * Adds a new listerner to this page to handle custom page events events.
0363:             */
0364:            public void addSQLPreviewListener(SQLPreviewListener p) {
0365:                if (_listeners == null)
0366:                    _listeners = new Vector();
0367:
0368:                for (int i = 0; i < _listeners.size(); i++) {
0369:                    if (((SQLPreviewListener) _listeners.elementAt(i)) == p)
0370:                        return;
0371:                }
0372:
0373:                _listeners.addElement(p);
0374:            }
0375:
0376:            /**
0377:             * This method adds a table alias to the datastore. Calls to the addColumn
0378:             * method can then use the alias specified to represent the table name.
0379:             * 
0380:             * @param table
0381:             *            The name of the table to alias.
0382:             * @param alias
0383:             *            The name of the alias.
0384:             */
0385:            public void addTableAlias(String table, String alias) {
0386:                _desc.addAlias(table, alias);
0387:            }
0388:
0389:            /**
0390:             * This method indicates whether all the data in the result set that is to
0391:             * be returned by the last retrieve statement has in fact been retrieved.
0392:             * 
0393:             * @return true if all the data has been retrieved and false if the retrieve
0394:             *         is still in progress.
0395:             */
0396:            public boolean allDataRetrieved() {
0397:                return (!_retrieveInProgress);
0398:            }
0399:
0400:            /**
0401:             * This method is called from JspController when the DataStore needs to be
0402:             * automatically retrieved.
0403:             */
0404:            public void autoRetrieve() {
0405:                try {
0406:                    if (getGroupAutoRetrieveCriteria() != null)
0407:                        setHaving(buildCriteriaString(getGroupAutoRetrieveCriteria()));
0408:
0409:                    if (getAutoRetrieveCriteria() != null)
0410:                        retrieve(buildCriteriaString(getAutoRetrieveCriteria()));
0411:                    else
0412:                        retrieve();
0413:
0414:                    waitForRetrieve();
0415:                    gotoFirst();
0416:                } catch (Exception e) {
0417:                    MessageLog.writeErrorMessage("autoRetrieve()", e, this );
0418:                }
0419:            }
0420:
0421:            /**
0422:             * This method will build a datastore buffer from the columns in the sql
0423:             * statement and retrieves the data. After the initial call to this method
0424:             * (for subsequent retrieves), the execute method can be used and is more
0425:             * efficient.
0426:             * 
0427:             * @param conn
0428:             *            The database connection to use to perform this operation.
0429:             * @param sql
0430:             *            The sql to execute.
0431:             */
0432:            public synchronized void buildBuffer(DBConnection conn, String sql)
0433:                    throws java.sql.SQLException, DataStoreException {
0434:                reset();
0435:                _retrieveInProgress = true;
0436:                retrieve(conn, null, null, null, sql, true);
0437:            }
0438:
0439:            /**
0440:             * This method will build a datastore buffer from the columns in the sql
0441:             * statement and retrieves the data. After the initial call to this method
0442:             * (for subsequent retrieves), the execute method can be used and is more
0443:             * efficient.
0444:             * 
0445:             * @param sql
0446:             *            The sql to execute.
0447:             */
0448:            public synchronized void buildBuffer(String sql)
0449:                    throws java.sql.SQLException, DataStoreException {
0450:                if (_appName == null)
0451:                    throw new DataStoreException(
0452:                            "This version of execute requires an application name and/or dbprofile. You cannot call this method on a DataStore created with the no-args constructor");
0453:
0454:                DBConnection conn;
0455:                if (_dbProfile == null)
0456:                    conn = DBConnection.getConnection(_appName);
0457:                else
0458:                    conn = DBConnection.getConnection(_appName, _dbProfile);
0459:
0460:                _releaseConn = true;
0461:                buildBuffer(conn, sql);
0462:            }
0463:
0464:            private void buildBuffer(ResultSetMetaData m, String sql)
0465:                    throws Exception {
0466:                StringTokenizer work = null;
0467:                String test = sql.toUpperCase().trim();
0468:                if (test.startsWith("SELECT")) {
0469:                    int pos = test.indexOf(" DISTINCT ");
0470:                    if (pos == -1)
0471:                        pos = 7;
0472:                    else
0473:                        pos += 10;
0474:                    int pos2 = test.indexOf(" FROM ");
0475:                    // sr 10-24-2001
0476:                    // pos2 was off by one. I think we were alway clipping the last char
0477:                    // sql.substring(beginindex,endindex)
0478:                    // but nobody was referencing columns by name
0479:                    work = new StringTokenizer(sql.substring(pos, pos2 + 1),
0480:                            ",", false);
0481:
0482:                } else if (test.startsWith("INSERT")
0483:                        || test.startsWith("UPDATE") || test.startsWith("DEL")) {
0484:                    throw new DataStoreException(
0485:                            "The buildBuffer method can only be used with SELECT statements or stored procedure calls");
0486:                }
0487:
0488:                //Rebuild the DataStore buffer before we retrieve
0489:                _desc = new DSDataStoreDescriptor();
0490:
0491:                int cc = m.getColumnCount();
0492:                for (int i = 1; i <= cc; i++) {
0493:                    int type = m.getColumnType(i);
0494:
0495:                    switch (type) {
0496:                    case Types.CHAR:
0497:                    case Types.VARCHAR:
0498:                    case Types.LONGVARCHAR:
0499:                    case Types.NULL:
0500:                        type = DATATYPE_STRING;
0501:                        break;
0502:                    case Types.INTEGER:
0503:                        type = DATATYPE_INT;
0504:                        break;
0505:                    case Types.FLOAT:
0506:                        type = DATATYPE_FLOAT;
0507:                        break;
0508:                    case Types.DOUBLE:
0509:                    case Types.REAL:
0510:                    case Types.NUMERIC:
0511:                    case Types.DECIMAL:
0512:                        type = DATATYPE_DOUBLE;
0513:                        break;
0514:                    case Types.TIMESTAMP:
0515:                        type = DATATYPE_DATETIME;
0516:                        break;
0517:                    case Types.DATE:
0518:                        type = DATATYPE_DATE;
0519:                        break;
0520:                    case Types.BIGINT:
0521:                        type = DATATYPE_LONG;
0522:                        break;
0523:                    case Types.BINARY:
0524:                    case Types.LONGVARBINARY:
0525:                    case Types.VARBINARY:
0526:                    case Types.OTHER:
0527:                        type = DATATYPE_BYTEARRAY;
0528:                        break;
0529:                    case Types.SMALLINT:
0530:                    case Types.TINYINT:
0531:                    case Types.BIT:
0532:                        type = DATATYPE_SHORT;
0533:                        break;
0534:                    case Types.TIME:
0535:                        type = DATATYPE_TIME;
0536:                        break;
0537:                    }
0538:
0539:                    String table = null;
0540:                    String column = null;
0541:                    String name = "*";
0542:                    if (work == null)
0543:                        name = "*";
0544:                    else if (work.hasMoreTokens()) {
0545:                        name = work.nextToken();
0546:                        while ((!parensMatch(name)) && work.hasMoreTokens())
0547:                            name += work.nextToken();
0548:                        name = name.trim();
0549:                    }
0550:
0551:                    if (name.equals("*")) {
0552:                        String label = m.getColumnLabel(i);
0553:                        int ndx = 1;
0554:                        while (getColumnIndex(label) > -1) {
0555:                            label += ndx++;
0556:                        }
0557:                        addColumn(null, m.getColumnName(i), type, false, false,
0558:                                label);
0559:                    } else {
0560:                        int pos = name.indexOf(".");
0561:                        if (pos == -1) {
0562:                            column = m.getColumnLabel(i);
0563:                            name = column;
0564:                        } else {
0565:                            table = name.substring(0, pos);
0566:                            column = name.substring(pos + 1);
0567:                        }
0568:
0569:                        StringBuffer sb = new StringBuffer(name.length());
0570:                        for (int j = 0; j < name.length(); j++) {
0571:                            char c = name.charAt(j);
0572:                            if (c == ')' || c == '(' || c == '*' || c == ','
0573:                                    || c == ' ' || c == '+' || c == '-'
0574:                                    || c == '/')
0575:                                sb.append('_');
0576:                            else
0577:                                sb.append(c);
0578:                        }
0579:                        name = sb.toString();
0580:                        int ndx = 1;
0581:                        while (getColumnIndex(name) > -1) {
0582:                            name += ndx++;
0583:                        }
0584:                        addColumn(table, column, type, false, false, name);
0585:                    }
0586:
0587:                }
0588:            }
0589:
0590:            /**
0591:             * This method builds a sql string from an AutoRetrieveCriteria object
0592:             */
0593:            public static String buildCriteriaString(AutoRetrieveCriteria crit) {
0594:                StringBuffer ret = new StringBuffer();
0595:
0596:                for (int i = 0; i < crit.getCriteriaCount(); i++) {
0597:                    if (crit.getPrefix(i) != null)
0598:                        ret.append(crit.getPrefix(i));
0599:                    ret.append(crit.getColumn(i));
0600:                    ret.append(' ');
0601:                    ret.append(crit.getOperator(i));
0602:                    ret.append(' ');
0603:                    ret.append(crit.getValue(i));
0604:                    if (crit.getSuffix(i) != null)
0605:                        ret.append(crit.getSuffix(i));
0606:                    if (crit.getConnector(i) != null) {
0607:                        ret.append(' ');
0608:                        ret.append(crit.getConnector(i));
0609:                        ret.append(' ');
0610:                    }
0611:                }
0612:
0613:                if (ret.length() == 0)
0614:                    return null;
0615:                else
0616:                    return ret.toString();
0617:            }
0618:
0619:            /**
0620:             * If a retrieve is in progress, this method will cancel it.
0621:             */
0622:            public void cancelRetrieve() {
0623:                _retrieveInProgress = false;
0624:                interruptWaitingRetrieveThreads();
0625:            }
0626:
0627:            /**
0628:             * This method will instantiate the datastore described in the className
0629:             * field. The datastore class must have at least one of three constructors.
0630:             * One that takes two strings (application and dbprofile), One that takes
0631:             * one string (application), or a no args constructor. If the app and
0632:             * profile constructor is found, it will be called first, followed by the
0633:             * app only constructor, followed by the no args constructor.
0634:             */
0635:            public static DataStoreBuffer constructDataStore(String className,
0636:                    String applicationName) {
0637:                return constructDataStore(className, applicationName, null);
0638:            }
0639:
0640:            /**
0641:             * This method will instantiate the datastore described in the className
0642:             * field. The datastore class must have at least one of three constructors.
0643:             * One that takes two strings (application and dbprofile), One that takes
0644:             * one string (application), or a no args constructor. If the app and
0645:             * profile constructor is found, it will be called first, followed by the
0646:             * app only constructor, followed by the no args constructor.
0647:             */
0648:            public static DataStoreBuffer constructDataStore(String className,
0649:                    String applicationName, String profileName) {
0650:                DataStoreBuffer ret = null;
0651:                try {
0652:                    Class stringClass = new String().getClass();
0653:                    Class cl = null;
0654:                    className = className.trim();
0655:                    boolean multiClass = false;
0656:                    if (className.indexOf(",") == -1
0657:                            && className.indexOf(" ") == -1)
0658:                        cl = Class.forName(className, true, Thread
0659:                                .currentThread().getContextClassLoader());
0660:                    else
0661:                        multiClass = true;
0662:
0663:                    if (multiClass
0664:                            || (cl != null && !Util.instanceOf(cl,
0665:                                    DataStoreBuffer.class)))
0666:                        return new BeanDataStore(className, multiClass);
0667:
0668:                    Constructor cs[] = cl.getConstructors();
0669:                    Constructor noArgsCon = null;
0670:                    Constructor appCon = null;
0671:                    Constructor appProfileCon = null;
0672:                    for (int i = 0; i < cs.length; i++) {
0673:                        Class[] args = cs[i].getParameterTypes();
0674:                        if (args.length == 2) {
0675:                            if (args[0] == stringClass
0676:                                    && args[1] == stringClass)
0677:                                appProfileCon = cs[i];
0678:                        } else if (args.length == 1) {
0679:                            if (args[0] == stringClass)
0680:                                appCon = cs[i];
0681:                        } else if (args.length == 0) {
0682:                            noArgsCon = cs[i];
0683:                        }
0684:                    }
0685:
0686:                    if (applicationName == null) {
0687:                        if (noArgsCon != null) {
0688:                            Object[] args = new Object[0];
0689:                            ret = (DataStoreBuffer) noArgsCon.newInstance(args);
0690:                        }
0691:                    } else {
0692:                        if (appProfileCon != null) {
0693:                            Object[] args = new String[2];
0694:                            args[0] = applicationName;
0695:                            args[1] = profileName;
0696:                            ret = (DataStoreBuffer) appProfileCon
0697:                                    .newInstance(args);
0698:                        } else if (appCon != null) {
0699:                            Object[] args = new String[1];
0700:                            args[0] = applicationName;
0701:                            ret = (DataStoreBuffer) appCon.newInstance(args);
0702:                        } else if (noArgsCon != null) {
0703:                            Object[] args = new Object[0];
0704:                            ret = (DataStoreBuffer) noArgsCon.newInstance(args);
0705:                        }
0706:                    }
0707:                } catch (Exception e) {
0708:                    MessageLog.writeErrorMessage(
0709:                            "DataStore.constructDataStore()", e, null);
0710:                }
0711:                return ret;
0712:            }
0713:
0714:            /**
0715:             * This method is not used.
0716:             */
0717:            public void destroy() throws Exception {
0718:            }
0719:
0720:            /**
0721:             * Use this method to get the amount of rows that will be retrieved when a
0722:             * data store retrieve is executed.
0723:             */
0724:            public int estimateRowsRetrieved() throws DataStoreException,
0725:                    SQLException {
0726:                String nullSt = null;
0727:                return estimateRowsRetrieved(nullSt);
0728:            }
0729:
0730:            /**
0731:             * Use this method to get the amount of rows that will be retrieved when a
0732:             * data store retrieve is executed.
0733:             * 
0734:             * @param conn
0735:             *            The database connection to use to perform this operation.
0736:             */
0737:            public int estimateRowsRetrieved(DBConnection conn)
0738:                    throws SQLException {
0739:                String st = null;
0740:                return estimateRowsRetrieved(conn, st);
0741:            }
0742:
0743:            /**
0744:             * Use this method to get the amount of rows that will be retrieved when a
0745:             * data store retrieve is executed.
0746:             * 
0747:             * @param conn
0748:             *            The database connection to use to perform this operation.
0749:             * @param criteria
0750:             *            The selection criteria to use for the select.
0751:             */
0752:            public int estimateRowsRetrieved(DBConnection conn,
0753:                    QBEBuilder criteria) throws SQLException {
0754:                return estimateRowsRetrieved(conn, criteria
0755:                        .generateSQLFilter(this ));
0756:            }
0757:
0758:            /**
0759:             * Use this method to get the amount of rows that will be retrieved when a
0760:             * data store retrieve is executed.
0761:             * 
0762:             * @param criteria
0763:             *            The selection criteria to use for the select.
0764:             */
0765:            public int estimateRowsRetrieved(QBEBuilder criteria)
0766:                    throws DataStoreException, SQLException {
0767:                return estimateRowsRetrieved(criteria.generateSQLFilter(this ));
0768:            }
0769:
0770:            /**
0771:             * Use this method to get the amount of rows that will be retrieved when a
0772:             * data store retrieve is executed.
0773:             * 
0774:             * @param conn
0775:             *            The database connection to use to perform this operation.
0776:             * @param criteria
0777:             *            The selection criteria to use for the select.
0778:             */
0779:            public int estimateRowsRetrieved(DBConnection conn, String criteria)
0780:                    throws SQLException {
0781:
0782:                int count = 0;
0783:                try {
0784:                    Statement st = conn.createStatement();
0785:                    String sql = getCountSelectStatement(conn, criteria);
0786:                    ResultSet r = st.executeQuery(sql);
0787:                    if (r.next())
0788:                        count = r.getInt(1);
0789:                    r.close();
0790:                    st.close();
0791:                } catch (java.sql.SQLException e) {
0792:                    throw e;
0793:                }
0794:                return count;
0795:            }
0796:
0797:            //fc 06/24/04
0798:            /**
0799:             * Use this method to get the amount of rows that will be retrieved when a
0800:             * data store retrieve is executed.
0801:             * 
0802:             * @param conn
0803:             *            The database connection to use to perform this operation.
0804:             * @param criteria
0805:             *            The selection criteria to use for the select in ? format.
0806:             * @param psp
0807:             *            the prepared statement parameters for the criteria.
0808:             */
0809:            public int estimateRowsRetrieved(DBConnection conn,
0810:                    String criteria, PreparedStatementParms psp)
0811:                    throws SQLException {
0812:
0813:                int count = 0;
0814:                try {
0815:                    String sql = getCountSelectStatement(conn, criteria);
0816:                    PreparedStatement pst = conn.prepareStatement(sql);
0817:                    if (psp != null) {
0818:                        DataSourceIn dsi = getDSIn(conn);
0819:
0820:                        if (dsi instanceof  DSDataSourceJDBC) {
0821:                            for (int i = 0; i < psp.getParmCount(); i++)
0822:                                DSDataSourceJDBC.prepareForType(null, pst, psp
0823:                                        .getParm(i), psp.getDataType(i), i + 1);
0824:                        }
0825:                    }
0826:                    ResultSet r = pst.executeQuery();
0827:                    if (r.next())
0828:                        count = r.getInt(1);
0829:                    r.close();
0830:                    pst.close();
0831:                } catch (java.sql.SQLException e) {
0832:                    throw e;
0833:                }
0834:                return count;
0835:            }
0836:
0837:            /**
0838:             * Use this method to get the amount of rows that will be retrieved when a
0839:             * data store retrieve is executed.
0840:             * 
0841:             * @param criteria
0842:             *            The selection criteria to use for the select.
0843:             */
0844:            public int estimateRowsRetrieved(String criteria)
0845:                    throws DataStoreException, SQLException {
0846:                if (_appName == null)
0847:                    throw new DataStoreException(
0848:                            "This version of retrieve requires an application name and/or dbprofile. You cannot call this method on a DataStore created with the no-args constructor");
0849:
0850:                DBConnection conn = null;
0851:                if (_dbProfile == null)
0852:                    conn = DBConnection.getConnection(_appName);
0853:                else
0854:                    conn = DBConnection.getConnection(_appName, _dbProfile);
0855:
0856:                int ret = 0;
0857:                try {
0858:                    ret = estimateRowsRetrieved(conn, criteria);
0859:                } catch (SQLException e) {
0860:                    if (conn != null)
0861:                        conn.freeConnection();
0862:                    throw e;
0863:                }
0864:
0865:                if (conn != null)
0866:                    conn.freeConnection();
0867:
0868:                return ret;
0869:            }
0870:
0871:            //fc 06/24/04
0872:            /**
0873:             * Use this method to get the amount of rows that will be retrieved when a
0874:             * data store retrieve is executed.
0875:             * 
0876:             * @param criteria
0877:             *            The selection criteria to use for the select in ? format.
0878:             * @param psp
0879:             *            the prepared statement parameters for the criteria.
0880:             */
0881:            public int estimateRowsRetrieved(String criteria,
0882:                    PreparedStatementParms psp) throws DataStoreException,
0883:                    SQLException {
0884:                if (_appName == null)
0885:                    throw new DataStoreException(
0886:                            "This version of retrieve requires an application name and/or dbprofile. You cannot call this method on a DataStore created with the no-args constructor");
0887:
0888:                DBConnection conn = null;
0889:                if (_dbProfile == null)
0890:                    conn = DBConnection.getConnection(_appName);
0891:                else
0892:                    conn = DBConnection.getConnection(_appName, _dbProfile);
0893:
0894:                int ret = 0;
0895:                try {
0896:                    ret = estimateRowsRetrieved(conn, criteria, psp);
0897:                } catch (SQLException e) {
0898:                    if (conn != null)
0899:                        conn.freeConnection();
0900:                    throw e;
0901:                }
0902:
0903:                if (conn != null)
0904:                    conn.freeConnection();
0905:
0906:                return ret;
0907:            }
0908:
0909:            /**
0910:             * Executes the supplied sql instead of the generated sql. This method will
0911:             * ues the SQL statement supplied and load the returned data into the
0912:             * DataStore buffer. The column types and column order in the SQL supplied
0913:             * must match the types and columns in the buffer.
0914:             * 
0915:             * @param conn
0916:             *            The database connection to use to perform this operation.
0917:             * @param sql
0918:             *            The sql to execute.
0919:             */
0920:            public synchronized void execute(DBConnection conn, String sql)
0921:                    throws java.sql.SQLException {
0922:                retrieve(conn, null, null, null, sql, false);
0923:            }
0924:
0925:            /**
0926:             * Executes the supplied sql instead of the generated sql. This method will
0927:             * ues the SQL statement supplied and load the returned data into the
0928:             * DataStore buffer. The column types and column order in the SQL supplied
0929:             * must match the types and columns in the buffer.
0930:             * 
0931:             * @param sql
0932:             *            The sql to execute.
0933:             */
0934:            public synchronized void execute(String sql)
0935:                    throws java.sql.SQLException, DataStoreException {
0936:                if (_appName == null)
0937:                    throw new DataStoreException(
0938:                            "This version of execute requires an application name and/or dbprofile. You cannot call this method on a DataStore created with the no-args constructor");
0939:
0940:                DBConnection conn;
0941:                if (_dbProfile == null)
0942:                    conn = DBConnection.getConnection(_appName);
0943:                else
0944:                    conn = DBConnection.getConnection(_appName, _dbProfile);
0945:
0946:                _releaseConn = true;
0947:                execute(conn, sql);
0948:            }
0949:
0950:            /**
0951:             * Executes the stored procuedure with no parameters.
0952:             * 
0953:             * @param conn
0954:             *            The database connection to use to perform this operation.
0955:             * @param proc
0956:             *            The procedure statement to execute.
0957:             */
0958:            public synchronized void executeProc(DBConnection conn, String proc)
0959:                    throws java.sql.SQLException {
0960:                executeProc(conn, proc, null);
0961:            }
0962:
0963:            /**
0964:             * Executes the sql statement and retrieves to data. The datatypes and
0965:             * number of columns in the result set must exactly match the columns in the
0966:             * specified sql statement.
0967:             * 
0968:             * @param conn
0969:             *            The database connection to use to perform this operation.
0970:             * @param proc
0971:             *            The procedure to execute.
0972:             * @param parms
0973:             *            A StoredProcedureParms object containing the parameters to
0974:             *            pass to the proc.
0975:             */
0976:            public synchronized void executeProc(DBConnection conn,
0977:                    String proc, StoredProcedureParms parms)
0978:                    throws java.sql.SQLException {
0979:                retrieve(conn, null, proc, parms, null, false);
0980:            }
0981:
0982:            /**
0983:             * Executes the procuedure and retrieves the data. The datatypes and number
0984:             * of columns in the result set must exactly match the columns in the
0985:             * specified sql statement.
0986:             * 
0987:             * @param proc
0988:             *            The procedure to execute.
0989:             */
0990:
0991:            public void executeProc(String proc) throws java.sql.SQLException,
0992:                    DataStoreException {
0993:                executeProc(proc, null);
0994:            }
0995:
0996:            /**
0997:             * Executes the sql statement and retrieves to data. The datatypes and
0998:             * number of columns in the result set must exactly match the columns in the
0999:             * specified sql statement.
1000:             * 
1001:             * @param proc
1002:             *            The procedure to execute.
1003:             * @param parms
1004:             *            A StoredProcedureParms object containing the parameters to
1005:             *            pass to the proc.
1006:             */
1007:            public synchronized void executeProc(String proc,
1008:                    StoredProcedureParms parms) throws java.sql.SQLException,
1009:                    DataStoreException {
1010:                if (_appName == null)
1011:                    throw new DataStoreException(
1012:                            "This version of execute requires an application name and/or dbprofile. You cannot call this method on a DataStore created with the no-args constructor");
1013:
1014:                DBConnection conn;
1015:                if (_dbProfile == null)
1016:                    conn = DBConnection.getConnection(_appName);
1017:                else
1018:                    conn = DBConnection.getConnection(_appName, _dbProfile);
1019:
1020:                _releaseConn = true;
1021:                executeProc(conn, proc, parms);
1022:            }
1023:
1024:            /**
1025:             * This method will fix quotes in a string constant so it can be used in a
1026:             * SQL Statement. This method will automatically figure out which DBMS is in
1027:             * use and make the changes accordingly. Because of this, this method can
1028:             * only be called for datastores created with a constructor that takes
1029:             * database profile arguments (not the no args constructor). Note: You
1030:             * should only use this method with character data (DATATYPE_STRING) types.
1031:             */
1032:            public String fixQuote(String data) {
1033:                DBConnection conn = null;
1034:
1035:                if (_connType == null) {
1036:                    try {
1037:                        if (_appName != null) {
1038:                            if (_dbProfile != null)
1039:                                conn = DBConnection.getConnection(_appName,
1040:                                        _dbProfile);
1041:                            else
1042:                                conn = DBConnection.getConnection(_appName);
1043:                        }
1044:
1045:                        _connType = conn.getDBMS();
1046:                    } catch (Exception e) {
1047:                        _connType = "";
1048:                    } finally {
1049:                        if (conn != null)
1050:                            conn.freeConnection();
1051:                    }
1052:                }
1053:
1054:                return fixQuote(data, DATATYPE_STRING, _connType);
1055:
1056:            }
1057:
1058:            /**
1059:             * This method will format a Date value so it can be used in an SQL
1060:             * Statement. This method will automatically figure out which DBMS is in use
1061:             * and make the changes accordingly. Because of this, this method can only
1062:             * be called for datastores created with a constructor that takes database
1063:             * profile arguments (not the no args constructor).
1064:             */
1065:            public String formatDateTime(java.util.Date data) {
1066:                DBConnection conn = null;
1067:                // Initialize the connection type if necessary.
1068:                if (_connType == null) {
1069:                    try {
1070:                        if (_appName != null) {
1071:                            if (_dbProfile != null)
1072:                                conn = DBConnection.getConnection(_appName,
1073:                                        _dbProfile);
1074:                            else
1075:                                conn = DBConnection.getConnection(_appName);
1076:                        }
1077:
1078:                        _connType = conn.getDBMS();
1079:                    } catch (Exception e) {
1080:                        _connType = "";
1081:                    } finally {
1082:                        if (conn != null)
1083:                            conn.freeConnection();
1084:                    }
1085:                }
1086:                // Format the data according to connection type.
1087:                SimpleDateFormat df;
1088:                if (_connType.equals(DBConnection.DB2VSE_CONNECTION)
1089:                        || _connType.equals(DBConnection.DB2MVS_CONNECTION))
1090:                    df = _dateTimeFormatVSE;
1091:                else
1092:                    df = _dateTimeFormatSTD;
1093:                return "'" + df.format(data) + "'";
1094:            }
1095:
1096:            /**
1097:             * This method returns the name of one of the aliases used by the datastore.
1098:             * Use the method getAliasCount() to find out how many tables or aliases are
1099:             * used by the datastore.
1100:             * 
1101:             * @return The table name.
1102:             */
1103:            public String getAlias(int tableNo) throws DataStoreException {
1104:                if (tableNo < 0 || tableNo >= _desc.getAliasCount())
1105:                    throw (new DataStoreException("Table Number " + tableNo
1106:                            + " is out of range "));
1107:
1108:                return _desc.getAlias(tableNo).getAlias();
1109:            }
1110:
1111:            /**
1112:             * This method returns the number of aliases used by the datastore.
1113:             */
1114:            public int getAliasCount() {
1115:                return _desc.getAliasCount();
1116:            }
1117:
1118:            /**
1119:             * Use this method to get whether or not the datastore will do a concurrency
1120:             * check when rows are updated and deleted.
1121:             */
1122:            public boolean getCheckConcurrency() {
1123:                return _checkConcurrency;
1124:            }
1125:
1126:            /**
1127:             * This method returns the database name of the column in the data store
1128:             * given its index.
1129:             */
1130:            public String getColumnDatabaseName(int col)
1131:                    throws DataStoreException {
1132:                if (col < 0 || _desc.getColumnCount() == 0)
1133:                    throw new DataStoreException("Specified column (" + col
1134:                            + ") does not exist.");
1135:                DSColumnDescriptor d = _desc.getColumn(col);
1136:                String table = d.getTable();
1137:                if (table == null)
1138:                    table = _desc.getDefaultTable();
1139:
1140:                if (table == null)
1141:                    return d.getColumn();
1142:                else
1143:                    return table + "." + d.getColumn();
1144:            }
1145:
1146:            /**
1147:             * This method returns the name of the database table that the column is
1148:             * for.
1149:             */
1150:            public String getColumnFormat(int col) throws DataStoreException {
1151:                if (col < 0 || _desc.getColumnCount() == 0)
1152:                    throw new DataStoreException("Specified column (" + col
1153:                            + ") does not exist.");
1154:                DSColumnDescriptor d = _desc.getColumn(col);
1155:                if (d.getFormat() == null)
1156:                    return null;
1157:
1158:                return d.getFormat().toString();
1159:            }
1160:
1161:            /**
1162:             * This method returns the name of the database table that the column is
1163:             * for.
1164:             */
1165:            public String getColumnInternalName(int col)
1166:                    throws DataStoreException {
1167:                if (col < 0 || _desc.getColumnCount() == 0)
1168:                    throw new DataStoreException("Specified column (" + col
1169:                            + ") does not exist.");
1170:                DSColumnDescriptor d = _desc.getColumn(col);
1171:                return d.getInternalName();
1172:            }
1173:
1174:            /**
1175:             * This method returns the name of the database table that the column is
1176:             * for.
1177:             */
1178:            public String getColumnTableName(int col) throws DataStoreException {
1179:                if (col < 0 || _desc.getColumnCount() == 0)
1180:                    throw new DataStoreException("Specified column (" + col
1181:                            + ") does not exist.");
1182:                DSColumnDescriptor d = _desc.getColumn(col);
1183:                String table = d.getTable();
1184:                if (table == null)
1185:                    table = _desc.getDefaultTable();
1186:
1187:                return table;
1188:            }
1189:
1190:            /**
1191:             * This method returns the database name of the column not including the
1192:             * table name.
1193:             */
1194:            public String getColumnDBColumnName(int col)
1195:                    throws DataStoreException {
1196:                if (col < 0 || _desc.getColumnCount() == 0)
1197:                    throw new DataStoreException("Specified column (" + col
1198:                            + ") does not exist.");
1199:                DSColumnDescriptor d = _desc.getColumn(col);
1200:                return d.getColumn();
1201:            }
1202:
1203:            /**
1204:             * This method is used to get whether a column should be used in the update,
1205:             * delete concurrency check.
1206:             */
1207:            public boolean getConcurrencyCheckColumn(int col)
1208:                    throws DataStoreException {
1209:                if (col < 0 || _desc.getColumnCount() == 0)
1210:                    throw new DataStoreException("Specified column (" + col
1211:                            + ") does not exist.");
1212:
1213:                DSColumnDescriptor c = _desc.getColumn(col);
1214:                return c.getConcurrency();
1215:            }
1216:
1217:            /**
1218:             * This method is used to get whether a column should be used in the update,
1219:             * delete concurrency check.
1220:             */
1221:            public boolean getConcurrencyCheckColumn(String col)
1222:                    throws DataStoreException {
1223:                int c = getColumnIndex(col);
1224:                return getConcurrencyCheckColumn(c);
1225:            }
1226:
1227:            /**
1228:             * This method was created in VisualAge.
1229:             * 
1230:             * @param conn
1231:             *            com.salmonllc.sql.DBConnection
1232:             * @param criteria
1233:             *            java.lang.String
1234:             */
1235:            private String getCountSelectStatement(DBConnection conn,
1236:                    String criteria) {
1237:                DataSourceIn dsIn = getDSIn(conn);
1238:                if (dsIn instanceof  DSDataSourceJDBC)
1239:                    try {
1240:                        return ((DSDataSourceJDBC) dsIn).generateSelect(this ,
1241:                                criteria, true);
1242:                    } catch (Exception e) {
1243:                        return null;
1244:                    }
1245:                else
1246:                    return null;
1247:            }
1248:
1249:            /**
1250:             * This method is used to get selection criteria filtering for the result
1251:             * set of the datastore.
1252:             */
1253:            public String getCriteria() {
1254:                return _desc.getWhereClause();
1255:            }
1256:
1257:            /**
1258:             * This method returns the default table for the datastore
1259:             */
1260:            public String getDefaultTable() {
1261:                return _desc.getDefaultTable();
1262:            }
1263:
1264:            /**
1265:             * This method will return whether the distinct flag in the data store is
1266:             * set. The flag indicates that the distinct keyword should be placed at the
1267:             * beginning of a select statement.
1268:             */
1269:            public boolean getDistinct() {
1270:                return _desc.getDistinct();
1271:            }
1272:
1273:            /**
1274:             * This method was created in VisualAge.
1275:             * 
1276:             * @return com.salmonllc.sql.DataSourceIn
1277:             * @param conn
1278:             *            com.salmonllc.sql.DBConnection
1279:             */
1280:            private DataSourceIn getDSIn(DBConnection conn) {
1281:                if (_dsIn != null)
1282:                    return _dsIn;
1283:                else {
1284:                    if (conn.getDBMS().equals(DBConnection.DB2_CONNECTION))
1285:                        return new DSDataSourceDB2();
1286:                    else if (conn.getDBMS().equals(
1287:                            DBConnection.DB2VSE_CONNECTION))
1288:                        return new DSDataSourceDB2VSE();
1289:                    else if (conn.getDBMS().equals(
1290:                            DBConnection.DB2MVS_CONNECTION))
1291:                        return new DSDataSourceDB2MVS();
1292:                    else if (conn.getDBMS().equals(
1293:                            DBConnection.ORACLE_CONNECTION))
1294:                        return new DSDataSourceOracle();
1295:                    else if (conn.getDBMS().equals(
1296:                            DBConnection.MYSQL_CONNECTION))
1297:                        return new DSDataSourceMySql();
1298:                    else if (conn.getDBMS().equals(
1299:                            DBConnection.MSSQLSEVER_CONNECTION))
1300:                        return new DSDataSourceMSSQL();
1301:                    else if (conn.getDBMS().equals(
1302:                            DBConnection.DB2400_CONNECTION))
1303:                        return new DSDataSourceDB2400();
1304:                    else if (conn.getDBMS().equals(
1305:                            DBConnection.INGRES_CONNECTION))
1306:                        return new DSDataSourceIngres();
1307:                    else if (conn.getDBMS().equals(
1308:                            DBConnection.FIREBIRDSQL_CONNECTION))
1309:                        return new DSDataSourceFireBird();
1310:                    else if (conn.getDBMS().equals(
1311:                            DBConnection.POSTGRES_CONNECTION))
1312:                        return new DSDataSourcePostGres();
1313:                    else if (conn.getDBMS().equals(
1314:                            DBConnection.ANSISQL92_CONNECTION))
1315:                        return new DSDataSourceANSISQL92();
1316:                    else
1317:                        return new DSDataSourceSybase();
1318:                }
1319:            }
1320:
1321:            /**
1322:             * This method was created in VisualAge.
1323:             * 
1324:             * @return com.salmonllc.sql.DataSourceIn
1325:             * @param conn
1326:             *            com.salmonllc.sql.DBConnection
1327:             */
1328:            private DataSourceOut getDSOut(DBConnection conn) {
1329:                if (_dsOut != null)
1330:                    return _dsOut;
1331:                else {
1332:                    if (conn.getDBMS().equals(DBConnection.DB2_CONNECTION))
1333:                        return new DSDataSourceDB2();
1334:                    else if (conn.getDBMS().equals(
1335:                            DBConnection.DB2VSE_CONNECTION))
1336:                        return new DSDataSourceDB2VSE();
1337:                    else if (conn.getDBMS().equals(
1338:                            DBConnection.DB2MVS_CONNECTION))
1339:                        return new DSDataSourceDB2MVS();
1340:                    else if (conn.getDBMS().equals(
1341:                            DBConnection.ORACLE_CONNECTION))
1342:                        return new DSDataSourceOracle();
1343:                    else if (conn.getDBMS().equals(
1344:                            DBConnection.MYSQL_CONNECTION))
1345:                        return new DSDataSourceMySql();
1346:                    else if (conn.getDBMS().equals(
1347:                            DBConnection.DB2400_CONNECTION))
1348:                        return new DSDataSourceDB2400();
1349:                    else if (conn.getDBMS().equals(
1350:                            DBConnection.MSSQLSEVER_CONNECTION))
1351:                        return new DSDataSourceMSSQL();
1352:                    else if (conn.getDBMS().equals(
1353:                            DBConnection.INGRES_CONNECTION))
1354:                        return new DSDataSourceIngres();
1355:                    else if (conn.getDBMS().equals(
1356:                            DBConnection.FIREBIRDSQL_CONNECTION))
1357:                        return new DSDataSourceFireBird();
1358:                    else if (conn.getDBMS().equals(
1359:                            DBConnection.POSTGRES_CONNECTION))
1360:                        return new DSDataSourcePostGres();
1361:                    else if (conn.getDBMS().equals(
1362:                            DBConnection.ANSISQL92_CONNECTION))
1363:                        return new DSDataSourceANSISQL92();
1364:                    else
1365:                        return new DSDataSourceSybase();
1366:                }
1367:            }
1368:
1369:            /**
1370:             * Use this method to get whether or not the datastore does a retrieve in a
1371:             * separate thread.
1372:             */
1373:            public boolean getEnableThreads() {
1374:                return _threaded;
1375:            }
1376:
1377:            /**
1378:             * This method will return the autoretrieve group criteria used for the
1379:             * datastore.
1380:             */
1381:            public AutoRetrieveCriteria getGroupAutoRetrieveCriteria() {
1382:                return _havingCrit;
1383:            }
1384:
1385:            /**
1386:             * This method returns the column list in the group by clause.
1387:             */
1388:            public String getGroupBy() {
1389:                return _desc.getGroupByClause();
1390:            }
1391:
1392:            /**
1393:             * This method returns the having clause for the datastore.
1394:             */
1395:            public String getHaving() {
1396:                return _desc.getHavingClause();
1397:            }
1398:
1399:            /**
1400:             * This method returns the number of columns in a particular join.
1401:             */
1402:            public int getJoinColumnCount(int joinNo) {
1403:                return _desc.getJoin(joinNo).getLeftCount();
1404:            }
1405:
1406:            /**
1407:             * This method returns the number of joins in the datastore.
1408:             */
1409:            public int getJoinCount() {
1410:                return _desc.getJoinCount();
1411:            }
1412:
1413:            /**
1414:             * This method returns a column on the left side of the join.
1415:             */
1416:            public String getJoinLeftColumn(int joinNo, int colNo) {
1417:                return _desc.getJoin(joinNo).getLeftColumn(colNo);
1418:            }
1419:
1420:            /**
1421:             * This method returns the true if a particular join is outer.
1422:             */
1423:            public boolean getJoinOuter(int joinNo) {
1424:                return _desc.getJoin(joinNo).isOuter();
1425:            }
1426:
1427:            //fc 06/11/04: Implements the newly added method to DataStoreInterface.
1428:            /**
1429:             * This method returns the relation type of the join. (RELATION_ONE_TO_ONE,
1430:             * RELATION_ONE_TO_MANY, RELATION_MANY_TO_ONE)
1431:             */
1432:            public int getJoinRelationType(int joinNo) {
1433:                return _desc.getJoin(joinNo).getRelationType();
1434:            }
1435:
1436:            /**
1437:             * This method returns a column on the right side of the join.
1438:             */
1439:            public String getJoinRightColumn(int joinNo, int colNo) {
1440:                return _desc.getJoin(joinNo).getRightColumn(colNo);
1441:            }
1442:
1443:            /**
1444:             * This method will return the maximum number of rows that the datastore
1445:             * will retrieve. If the max is set to -1, the datastore will retrieve all
1446:             * rows in the result set. Otherwise it will stop retrieving when the max is
1447:             * reached.
1448:             */
1449:            public int getMaxRows() {
1450:                return _maxRows;
1451:            }
1452:
1453:            /**
1454:             * This method returns the order by clause for the datastore.
1455:             */
1456:            public String getOrderBy() {
1457:                return _desc.getOrderByClause();
1458:            }
1459:
1460:            /**
1461:             * This method creates a properties object containing the definition of the
1462:             * data store.
1463:             */
1464:            public Properties getProperties() {
1465:
1466:                Properties p = super .getProperties();
1467:                String desc = "base.";
1468:
1469:                p.put(desc + "updateMethod", getIntProperty(_updateMethod));
1470:                p.put(desc + "checkConcurrency",
1471:                        getBoolProperty(_checkConcurrency));
1472:                p.put(desc + "useBind", getBoolProperty(_useBind));
1473:                p.put(desc + "maxRows", getIntProperty(_maxRows));
1474:                p.put(desc + "remoteID", getStringProperty(getRemoteID()));
1475:                p.put(desc + "DBMS", getStringProperty(getDBMS()));
1476:                return p;
1477:            }
1478:
1479:            String getSelectStatement(DBConnection conn) {
1480:                return getSelectStatement(conn, null);
1481:            }
1482:
1483:            public String getSelectStatement(DBConnection conn, String criteria) {
1484:                DataSourceIn dsIn = getDSIn(conn);
1485:                if (dsIn instanceof  DSDataSourceJDBC) {
1486:                    try {
1487:                        return ((DSDataSourceJDBC) dsIn).generateSelect(this ,
1488:                                criteria, false);
1489:                    } catch (Exception e) {
1490:                        return null;
1491:                    }
1492:                } else
1493:                    return null;
1494:
1495:            }
1496:
1497:            /**
1498:             * This method returns the name of one of the tables used by the datastore.
1499:             * Use the method getAliasCount() to find out how many tables or aliases are
1500:             * used by the datastore.
1501:             * 
1502:             * @return The table name.
1503:             */
1504:            public String getTable(int tableNo) throws DataStoreException {
1505:                if (tableNo < 0 || tableNo >= _desc.getAliasCount())
1506:                    throw (new DataStoreException("Table Number " + tableNo
1507:                            + " is out of range "));
1508:
1509:                return _desc.getAlias(tableNo).getTable();
1510:            }
1511:
1512:            /**
1513:             * This method returns an array of all the tables referenced in the
1514:             * datastore.
1515:             * 
1516:             * @param updateable
1517:             *            True if the table list should only include updateable tables
1518:             *            and false if it should include all.
1519:             */
1520:            public String[] getTableList(boolean updateable) {
1521:
1522:                DSColumnDescriptor col = null;
1523:
1524:                Vector tables = new Vector();
1525:                Vector pkey = new Vector();
1526:
1527:                for (int i = 0; i < _desc.getColumnCount(); i++) {
1528:                    col = _desc.getColumn(i);
1529:                    String tableName = col.getTable();
1530:                    if (tableName == null)
1531:                        tableName = _desc.getDefaultTable();
1532:
1533:                    if ((!updateable) || col.isUpdateable()
1534:                            || col.isAutoIncrement()) {
1535:                        boolean found = false;
1536:                        for (int j = 0; j < tables.size(); j++) {
1537:                            if (tables.elementAt(j).equals(tableName)) {
1538:                                if (col.isPrimaryKey())
1539:                                    pkey.setElementAt(new Boolean(true), j);
1540:                                found = true;
1541:                                break;
1542:                            }
1543:                        }
1544:                        if (!found && tableName != null) {
1545:                            tables.addElement(tableName);
1546:                            pkey.addElement(new Boolean(col.isPrimaryKey()));
1547:                        }
1548:                    }
1549:
1550:                }
1551:
1552:                if (updateable) {
1553:                    for (int i = pkey.size() - 1; i > -1; i--) {
1554:                        if (!((Boolean) pkey.elementAt(i)).booleanValue())
1555:                            tables.removeElementAt(i);
1556:                    }
1557:                } else {
1558:                    for (int i = 0; i < getAliasCount(); i++) {
1559:                        try {
1560:                            String table = getTable(i);
1561:                            boolean found = false;
1562:                            for (int j = 0; j < tables.size(); j++) {
1563:                                if (tables.elementAt(j).equals(table))
1564:                                    found = true;
1565:                            }
1566:                            if (!found && table != null)
1567:                                tables.addElement(table);
1568:                        } catch (Exception e) {
1569:                        }
1570:                    }
1571:                }
1572:
1573:                String retVal[] = new String[tables.size()];
1574:                tables.copyInto(retVal);
1575:
1576:                return retVal;
1577:            }
1578:
1579:            /**
1580:             * Use this method to get whether the DataStore will trim (remove trailing
1581:             * spaces) from columns retrieved from the database;
1582:             */
1583:            public boolean getTrimStrings() {
1584:                return _desc.getTrimStrings();
1585:            }
1586:
1587:            /**
1588:             * Gets the update method for the datastore.
1589:             * 
1590:             * @see DataStore#setUpdateMethod
1591:             */
1592:            public int getUpdateMethod() {
1593:                return _updateMethod;
1594:            }
1595:
1596:            /**
1597:             * This method is used to get whether a column should use bind variables for
1598:             * inserts and updates. Valid values and BIND_TRUE, BIND_FALSE and
1599:             * BIND_DEFAULT (Use default for datastore)
1600:             */
1601:            public int getUseBindColumn(int col) throws DataStoreException {
1602:                if (col < 0 || _desc.getColumnCount() == 0)
1603:                    throw new DataStoreException("Specified column (" + col
1604:                            + ") does not exist.");
1605:
1606:                DSColumnDescriptor c = _desc.getColumn(col);
1607:                return c.getUseBind();
1608:            }
1609:
1610:            /**
1611:             * This method is used to get whether a column should use bind variables for
1612:             * inserts and updates. Valid values and BIND_TRUE, BIND_FALSE and
1613:             * BIND_DEFAULT (Use default for datastore)
1614:             */
1615:            public int getUseBindColumn(String col) throws DataStoreException {
1616:                int c = getColumnIndex(col);
1617:                return getUseBindColumn(c);
1618:            }
1619:
1620:            /**
1621:             * Use this method to get whether or not the datastore will use bind
1622:             * variables as the default for updating or inserting columns.
1623:             */
1624:            public boolean getUseBindForUpdate() {
1625:                return _useBind;
1626:            }
1627:
1628:            //Added by FC on 2/21/03. Was added to handle JDBC drivers which have
1629:            // problems with the cancel() method being called.
1630:            //Example Driver: JSQLDriver from NetDirect.
1631:            /**
1632:             * Use this method to get whether or not the cancel() method of a JDBC
1633:             * Statement is to be called when cancelling a retrieve.
1634:             */
1635:            public boolean getEnableCancel() {
1636:                return _enableCancel;
1637:            }
1638:
1639:            /**
1640:             * This method returns the name of the database table that the column is
1641:             * for.
1642:             */
1643:            public boolean isColumnPrimaryKey(int col)
1644:                    throws DataStoreException {
1645:                if (col < 0 || _desc.getColumnCount() == 0)
1646:                    throw new DataStoreException("Specified column (" + col
1647:                            + ") does not exist.");
1648:                DSColumnDescriptor d = _desc.getColumn(col);
1649:
1650:                return d.isPrimaryKey();
1651:            }
1652:
1653:            /**
1654:             * This method returns whether a column is part of the primary key
1655:             */
1656:            public boolean isPrimaryKey(int col) throws DataStoreException {
1657:                if (col < 0 || _desc.getColumnCount() == 0)
1658:                    throw new DataStoreException("Specified column (" + col
1659:                            + ") does not exist.");
1660:
1661:                DSColumnDescriptor c = _desc.getColumn(col);
1662:                return c.isPrimaryKey();
1663:            }
1664:
1665:            /**
1666:             * This method returns whether a column is part of the primary key
1667:             */
1668:            public boolean isPrimaryKey(String col) throws DataStoreException {
1669:                int c = getColumnIndex(col);
1670:                return isPrimaryKey(c);
1671:            }
1672:
1673:            /**
1674:             * This method returns whether a column is updateable
1675:             */
1676:            public boolean isUpdateable(int col) throws DataStoreException {
1677:                if (col < 0 || _desc.getColumnCount() == 0)
1678:                    throw new DataStoreException("Specified column (" + col
1679:                            + ") does not exist.");
1680:
1681:                DSColumnDescriptor c = _desc.getColumn(col);
1682:                return c.isUpdateable();
1683:            }
1684:
1685:            /**
1686:             * This method returns whether a column is updateable
1687:             */
1688:            public boolean isUpdateable(String col) throws DataStoreException {
1689:                int c = getColumnIndex(col);
1690:                return isUpdateable(c);
1691:            }
1692:
1693:            /**
1694:             * This method returns whether a column is an auto increment primary key
1695:             */
1696:            public boolean isAutoIncrement(int col) throws DataStoreException {
1697:                if (col < 0 || _desc.getColumnCount() == 0)
1698:                    throw new DataStoreException("Specified column (" + col
1699:                            + ") does not exist.");
1700:
1701:                DSColumnDescriptor c = _desc.getColumn(col);
1702:                return c.isAutoIncrement();
1703:            }
1704:
1705:            /**
1706:             * This method returns whether a column is an auto increment primary key
1707:             */
1708:            public boolean isAutoIncrement(String col)
1709:                    throws DataStoreException {
1710:                int c = getColumnIndex(col);
1711:                return isAutoIncrement(c);
1712:            }
1713:
1714:            private void notifyListeners(int buffer, int row, String statement,
1715:                    DBConnection conn) throws SQLException {
1716:                if (_listeners == null)
1717:                    return;
1718:                if (statement == null || statement.length() == 0)
1719:                    return;
1720:
1721:                SQLPreviewEvent e = new SQLPreviewEvent(this , buffer, row,
1722:                        statement, conn);
1723:
1724:                for (int i = 0; i < _listeners.size(); i++) {
1725:                    ((SQLPreviewListener) _listeners.elementAt(i))
1726:                            .SQLPreview(e);
1727:                }
1728:            }
1729:
1730:            /**
1731:             * This method is not used.
1732:             */
1733:            public boolean ping() throws Exception {
1734:                return false;
1735:            }
1736:
1737:            /**
1738:             * This method removes a column to the DataStore. And resets the datastore.
1739:             * 
1740:             * @param column
1741:             *            The name of the column to remove to the datastore.
1742:             */
1743:            public void removeColumn(String column) {
1744:                _desc.removeColumn(column);
1745:                reset();
1746:            }
1747:
1748:            /**
1749:             * This method is used to remove a join clause connecting two or more tables
1750:             * used in the DataStore.
1751:             * 
1752:             * @param left:
1753:             *            A list of column names seperated by commas on the left side of
1754:             *            the join
1755:             * @param right:
1756:             *            A list of column names seperated by commas on the right side
1757:             *            of the join
1758:             */
1759:            public void removeJoin(String left, String right) {
1760:                _desc.removeJoin(left, right);
1761:            }
1762:
1763:            /**
1764:             * This method removes a listener from the list of listeners that will be
1765:             * notified when a page event is fired.
1766:             */
1767:            public void removeSQLPreviewListener(SQLPreviewListener p) {
1768:                if (_listeners == null)
1769:                    return;
1770:
1771:                for (int i = 0; i < _listeners.size(); i++) {
1772:                    if (((SQLPreviewListener) _listeners.elementAt(i)) == p) {
1773:                        _listeners.removeElementAt(i);
1774:                        return;
1775:                    }
1776:                }
1777:            }
1778:
1779:            /**
1780:             * This method removes a table alias from the datastore.
1781:             * 
1782:             * @param table
1783:             *            The name of the table to alias.
1784:             */
1785:            public void removeTableAlias(String table) {
1786:                _desc.removeTableAlias(table);
1787:            }
1788:
1789:            /**
1790:             * This method will clear all rows in the dataStore.
1791:             */
1792:            public synchronized void reset() {
1793:                if (_retrieveInProgress)
1794:                    cancelRetrieve();
1795:
1796:                super .reset();
1797:            }
1798:
1799:            /**
1800:             * Executes the sql statement and retrieves to data. The data is retrieved
1801:             * in a new thread so the beginning of the result set can be accessed before
1802:             * all the data has been retrieved. You do not need to pass a database
1803:             * connection to this version of retrieve, but in order to use it the
1804:             * DataStore must be created with a constructor that passes an application
1805:             * (not the no args constructor).
1806:             */
1807:            public void retrieve() throws java.sql.SQLException,
1808:                    DataStoreException {
1809:                String criteria = null;
1810:                retrieve(criteria);
1811:            }
1812:
1813:            /**
1814:             * Executes the sql statement and retrieves to data. The data is retrieved
1815:             * in a new thread so the beginning of the result set can be accessed before
1816:             * all the data has been retrieved.
1817:             * 
1818:             * @param conn
1819:             *            The database connection to use to perform this operation.
1820:             */
1821:            public void retrieve(DBConnection conn)
1822:                    throws java.sql.SQLException, DataStoreException {
1823:                String st = null;
1824:                retrieve(conn, st);
1825:            }
1826:
1827:            /**
1828:             * Executes the sql statement and retrieves to data. The data is retrieved
1829:             * in a new thread so the beginning of the result set can be accessed before
1830:             * all the data has been retrieved. This method will replace the selection
1831:             * criteria with the supplied argument before the data is retieved.
1832:             * 
1833:             * @param conn
1834:             *            The database connection to use to perform this operation.
1835:             * @param criteria
1836:             *            The selection criteria to use for the select.
1837:             */
1838:            public void retrieve(DBConnection conn, String criteria)
1839:                    throws SQLException {
1840:                retrieve(conn, criteria, null, null, null, false);
1841:            }
1842:
1843:            //fc 06/24/04
1844:            /**
1845:             * Executes the sql statement and retrieves to data. The data is retrieved
1846:             * in a new thread so the beginning of the result set can be accessed before
1847:             * all the data has been retrieved. This method will replace the selection
1848:             * criteria with the supplied argument before the data is retieved.
1849:             * 
1850:             * @param conn
1851:             *            The database connection to use to perform this operation.
1852:             * @param criteria
1853:             *            The selection criteria to use for the select in ? format.
1854:             * @param psp
1855:             *            the prepared statement parameters for the criteria.
1856:             */
1857:            public void retrieve(DBConnection conn, String criteria,
1858:                    PreparedStatementParms psp) throws SQLException {
1859:                retrieve(conn, criteria, null, psp, null, false);
1860:            }
1861:
1862:            /**
1863:             * Executes the sql statement and retrieves to data. The data is retrieved
1864:             * in a new thread so the beginning of the result set can be accessed before
1865:             * all the data has been retrieved. This method will replace the selection
1866:             * criteria with the supplied argument before the data is retieved.
1867:             * 
1868:             * @param conn
1869:             *            The database connection to use to perform this operation.
1870:             * @param criteria
1871:             *            The selection criteria QBEBuilder to use for the select.
1872:             */
1873:            public void retrieve(DBConnection conn, QBEBuilder criteria)
1874:                    throws SQLException {
1875:                retrieve(conn, criteria.generateSQLFilter(this ));
1876:            }
1877:
1878:            /**
1879:             * Executes the sql statement and retrieves to data. The data is retrieved
1880:             * in a new thread so the beginning of the result set can be accessed before
1881:             * all the data has been retrieved. This method will replace the selection
1882:             * criteria with the supplied argument before the data is retieved.
1883:             * 
1884:             * @param conn
1885:             *            The database connection to use to perform this operation.
1886:             * @param criteria
1887:             *            The selection criteria QBEBuilder to use for the select.
1888:             */
1889:            public void retrieve(QBEBuilder criteria) throws SQLException,
1890:                    DataStoreException {
1891:                retrieve(criteria.generateSQLFilter(this ));
1892:            }
1893:
1894:            /**
1895:             * Executes the sql statement and retrieves to data. The data is retrieved
1896:             * in a new thread so the beginning of the result set can be accessed before
1897:             * all the data has been retrieved. This method will replace the selection
1898:             * criteria with the supplied argument before the data is retieved.
1899:             * 
1900:             * @param conn
1901:             *            The database connection to use to perform this operation.
1902:             * @param criteria
1903:             *            The selection criteria to use for the select.
1904:             */
1905:            private synchronized void retrieve(DBConnection conn,
1906:                    String criteria, String proc, StoredProcedureParms parms,
1907:                    String select, boolean buildBuffer) throws SQLException {
1908:                reset();
1909:                waitForCancel(); //just in case there was already a retrieve running
1910:                // wait for it to be cancelled before continuing
1911:                _retrieveInProgress = true;
1912:
1913:                try {
1914:                    try {
1915:                        _curDsIn = getDSIn(conn);
1916:
1917:                        if (_curDsIn instanceof  DSDataSourceJDBC) {
1918:                            if (proc != null)
1919:                                ((DSDataSourceJDBC) _curDsIn).setProc(proc,
1920:                                        parms);
1921:                            else if (select != null)
1922:                                ((DSDataSourceJDBC) _curDsIn).setSelect(select);
1923:                            //fc 06/24/04
1924:                            else if (criteria != null
1925:                                    && parms instanceof  PreparedStatementParms) {
1926:                                ((DSDataSourceJDBC) _curDsIn)
1927:                                        .setSelType(DSDataSourceJDBC.SEL_GEN_PREP_STMT);
1928:                                ((DSDataSourceJDBC) _curDsIn).setParms(parms);
1929:                            }
1930:                        }
1931:
1932:                        _curDsIn.preRetrieve(this , criteria, false, conn);
1933:                        if (_curDsIn instanceof  DSDataSourceJDBC) {
1934:                            notifyListeners(BUFFER_STANDARD, -1,
1935:                                    ((DSDataSourceJDBC) _curDsIn).getSelect(),
1936:                                    conn);
1937:                            if (buildBuffer)
1938:                                buildBuffer(((DSDataSourceJDBC) _curDsIn)
1939:                                        .getMetaData(), select);
1940:                        }
1941:                    } catch (java.sql.SQLException e) {
1942:                        _curDsIn.postRetrieve(this );
1943:                        _retrieveInProgress = false;
1944:                        interruptWaitingRetrieveThreads();
1945:                        if (_releaseConn) {
1946:                            conn.freeConnection();
1947:                            _releaseConn = false;
1948:                        }
1949:                        throw (e);
1950:                    }
1951:                } catch (Exception e) {
1952:                    if (_releaseConn) {
1953:                        conn.freeConnection();
1954:                        _releaseConn = false;
1955:                    }
1956:                    if (e instanceof  java.sql.SQLException)
1957:                        throw ((java.sql.SQLException) e);
1958:                    else
1959:                        MessageLog.writeErrorMessage("Retrieve", e, this );
1960:                }
1961:
1962:                _dbConn = conn;
1963:
1964:                if (conn != null)
1965:                    conn.registerRetrieve(this );
1966:                if (_threaded) {
1967:                    Thread t = new Thread(this );
1968:                    t.start();
1969:                } else {
1970:                    run();
1971:                }
1972:
1973:            }
1974:
1975:            /**
1976:             * Executes the sql statement and retrieves to data. The data is retrieved
1977:             * in a new thread so the beginning of the result set can be accessed before
1978:             * all the data has been retrieved. You do not need to pass a database
1979:             * connection to this version of retrieve, but in order to use it the
1980:             * DataStore must be created with a constructor that passes an application
1981:             * (not the no args constructor).
1982:             */
1983:            public synchronized void retrieve(String criteria)
1984:                    throws java.sql.SQLException, DataStoreException {
1985:                DBConnection conn = null;
1986:                if (_dbConn == null) {
1987:                    if (_appName == null)
1988:                        throw new DataStoreException(
1989:                                "This version of retrieve requires an application name and/or dbprofile. You cannot call this method on a DataStore created with the no-args constructor");
1990:
1991:                    if (_dbProfile == null)
1992:                        conn = DBConnection.getConnection(_appName);
1993:                    else
1994:                        conn = DBConnection.getConnection(_appName, _dbProfile);
1995:
1996:                    _releaseConn = true;
1997:                } else {
1998:                    conn = _dbConn;
1999:                }
2000:
2001:                retrieve(conn, criteria);
2002:            }
2003:
2004:            //fc 06/24/04
2005:            /**
2006:             * Executes the sql statement and retrieves to data. The data is retrieved
2007:             * in a new thread so the beginning of the result set can be accessed before
2008:             * all the data has been retrieved. You do not need to pass a database
2009:             * connection to this version of retrieve, but in order to use it the
2010:             * DataStore must be created with a constructor that passes an application
2011:             * (not the no args constructor).
2012:             * 
2013:             * @param criteria
2014:             *            The selection criteria to use for the select in ? format.
2015:             * @param psp
2016:             *            the prepared statement parameters for the criteria.
2017:             */
2018:            public synchronized void retrieve(String criteria,
2019:                    PreparedStatementParms psp) throws java.sql.SQLException,
2020:                    DataStoreException {
2021:                DBConnection conn = null;
2022:                if (_dbConn == null) {
2023:                    if (_appName == null)
2024:                        throw new DataStoreException(
2025:                                "This version of retrieve requires an application name and/or dbprofile. You cannot call this method on a DataStore created with the no-args constructor");
2026:
2027:                    if (_dbProfile == null)
2028:                        conn = DBConnection.getConnection(_appName);
2029:                    else
2030:                        conn = DBConnection.getConnection(_appName, _dbProfile);
2031:
2032:                    _releaseConn = true;
2033:                } else {
2034:                    conn = _dbConn;
2035:                }
2036:
2037:                retrieve(conn, criteria, psp);
2038:            }
2039:
2040:            /**
2041:             * The run method for the thread that retrieves the data from the database.
2042:             * This method should not be called directly. Instead use the retrieve
2043:             * method.
2044:             */
2045:            public void run() {
2046:                try {
2047:
2048:                    DataStoreRow row = new DataStoreRow(this , new DSDataRow(
2049:                            _desc), _desc);
2050:
2051:                    while (_curDsIn.retrieveRow(this , row)) {
2052:                        _rows.addElement(row.getDSDataRow());
2053:
2054:                        if (!_retrieveInProgress
2055:                                || (_maxRows > -1 && _rows.size() >= _maxRows)) {
2056:                            _cancelInProgress = true;
2057:                            _retrieveInProgress = false;
2058:                            interruptWaitingRetrieveThreads();
2059:                            if (_curDsIn instanceof  DSDataSourceJDBC)
2060:                                ((DSDataSourceJDBC) _curDsIn).cancel();
2061:                            break;
2062:                        }
2063:                        Thread.yield();
2064:
2065:                        row.setDSDataRow(new DSDataRow(_desc));
2066:                    }
2067:                    _curDsIn.postRetrieve(this );
2068:                    notifyListeners(ModelChangedEvent.TYPE_DATA_LOADED);
2069:                } catch (Exception e) {
2070:                    MessageLog.writeErrorMessage("DataStore.run", e, this );
2071:                    _cancelInProgress = false;
2072:                    interruptWaitingCancelThreads();
2073:                }
2074:
2075:                if (_dbConn != null) {
2076:                    _dbConn.unregisterRetrieve(this );
2077:                    if (_releaseConn) {
2078:                        _dbConn.freeConnection();
2079:                        _dbConn = null;
2080:                        _releaseConn = false;
2081:                    }
2082:                }
2083:
2084:                _retrieveInProgress = false;
2085:                interruptWaitingRetrieveThreads();
2086:                _cancelInProgress = false;
2087:                interruptWaitingCancelThreads();
2088:
2089:            }
2090:
2091:            /**
2092:             * This method sets the name of the application that the datastore is
2093:             * running in
2094:             */
2095:            public void setAppName(String appName) {
2096:                _appName = appName;
2097:            }
2098:
2099:            /**
2100:             * This method gets the name of the application that the datastore is
2101:             * running in
2102:             */
2103:            public String getAppName() {
2104:                return _appName;
2105:            }
2106:
2107:            /**
2108:             * Use this method to set whether or not the datastore will do a concurrency
2109:             * check when rows are updated and deleted. defaults to falses
2110:             */
2111:            public void setCheckConcurrency(boolean truefalse) {
2112:                _checkConcurrency = truefalse;
2113:            }
2114:
2115:            /**
2116:             * This method is used to indicate whether a column should be used in the
2117:             * update, delete concurrency check.
2118:             */
2119:            public void setConcurrencyCheckColumn(int col, boolean truefalse)
2120:                    throws DataStoreException {
2121:                if (col < 0 || _desc.getColumnCount() == 0)
2122:                    throw new DataStoreException("Specified column (" + col
2123:                            + ") does not exist.");
2124:
2125:                DSColumnDescriptor c = _desc.getColumn(col);
2126:                c.setConcurrency(truefalse);
2127:            }
2128:
2129:            /**
2130:             * This method is used to indicate whether a column should be used in the
2131:             * update, delete concurrency check.
2132:             */
2133:            public void setConcurrencyCheckColumn(String col, boolean truefalse)
2134:                    throws DataStoreException {
2135:                int c = getColumnIndex(col);
2136:                setConcurrencyCheckColumn(c, truefalse);
2137:            }
2138:
2139:            /**
2140:             * This method sets the database connection that the datastore will use for
2141:             * retrieves.
2142:             */
2143:            public void setConnection(DBConnection conn) {
2144:                _dbConn = conn;
2145:            }
2146:
2147:            /**
2148:             * This method is used to set selection criteria filtering for the result
2149:             * set of the datastore.
2150:             * 
2151:             * @param criteria
2152:             *            The SQL used in the WHERE clause to filter rows in the result
2153:             *            set.
2154:             */
2155:            public void setCriteria(String criteria) {
2156:                _desc.setWhereClause(criteria);
2157:            }
2158:
2159:            /**
2160:             * This method is used to change the data source that the data store will
2161:             * use to retrieve the data
2162:             */
2163:            public void setDataSourceIn(DataSourceIn dsIn) {
2164:                _dsIn = dsIn;
2165:            }
2166:
2167:            /**
2168:             * This method is used to change the data source that the data store will
2169:             * use update data
2170:             */
2171:            public void setDataSourceOut(DataSourceOut dsOut) {
2172:                _dsOut = dsOut;
2173:            }
2174:
2175:            /**
2176:             * This method sets the name of the database profile that datastore will use
2177:             */
2178:            public void setDBProfile(String dbProfile) {
2179:                _dbProfile = dbProfile;
2180:            }
2181:
2182:            /**
2183:             * If this DataStore will retrieve data from a single table, it isn't
2184:             * necessary to pass it each time a column is added to the select statement.
2185:             * Instead this method can be called an AddColumn method that does not
2186:             * include table as a parameter.
2187:             * 
2188:             * @param table
2189:             *            The default table for this DataStore
2190:             */
2191:            public void setDefaultTable(String table) {
2192:                _desc.setDefaultTable(table);
2193:            }
2194:
2195:            /**
2196:             * This method will set the distinct flag in the data store.
2197:             * 
2198:             * @param distinct
2199:             *            if the flag is set to true the generated select statement will
2200:             *            begin with a select distinct.
2201:             */
2202:            public void setDistinct(boolean distinct) {
2203:                _desc.setDistinct(distinct);
2204:            }
2205:
2206:            /**
2207:             * Use this method to set whether or not the datastore will do retrieves in
2208:             * a separate thread
2209:             */
2210:            public void setEnableThreads(boolean truefalse) {
2211:                _threaded = truefalse;
2212:            }
2213:
2214:            /**
2215:             * This method will set the autoretrieve group criteria used for the
2216:             * datastore.
2217:             */
2218:            public void setGroupAutoRetrieveCriteria(AutoRetrieveCriteria crit) {
2219:                _havingCrit = crit;
2220:            }
2221:
2222:            /**
2223:             * This method is used to set a list of columns in the SQL Statement to
2224:             * group together.
2225:             * 
2226:             * @param groupByColumns
2227:             *            a list of columns seperated by commas.
2228:             */
2229:            public void setGroupBy(String groupByColumns) {
2230:                _desc.setGroupByClause(groupByColumns);
2231:            }
2232:
2233:            /**
2234:             * This method is used to set selection criteria that acts upon groups of
2235:             * data in the result set rather than individual rows. It is used in
2236:             * conjusction with the setGroupBy method.
2237:             * 
2238:             * @param havingCriteria
2239:             *            Selection criteria for the group
2240:             * @see DataStore#setGroupBy
2241:             */
2242:            public void setHaving(String havingCriteria) {
2243:                _desc.setHavingClause(havingCriteria);
2244:            }
2245:
2246:            /**
2247:             * This method will set the maximum number of rows that the datastore will
2248:             * retrieve. If the max is set to -1, the datastore will retrieve all rows
2249:             * in the result set. Otherwise it will stop retrieving when the max is
2250:             * reached.
2251:             */
2252:            public void setMaxRows(int max) {
2253:                _maxRows = max;
2254:            }
2255:
2256:            /**
2257:             * Sets the order by clause of the DataStore's SQL Statement
2258:             * 
2259:             * @param orderBy
2260:             *            The columns to use to sort the result set.
2261:             */
2262:            public void setOrderBy(String orderBy) {
2263:                _desc.setOrderByClause(orderBy);
2264:            }
2265:
2266:            /**
2267:             * This method is used to indicate whether a column is part of the primary
2268:             * key
2269:             */
2270:            public void setPrimaryKey(int col, boolean pkey)
2271:                    throws DataStoreException {
2272:                if (col < 0 || _desc.getColumnCount() == 0)
2273:                    throw new DataStoreException("Specified column (" + col
2274:                            + ") does not exist.");
2275:
2276:                DSColumnDescriptor c = _desc.getColumn(col);
2277:                c.setPrimaryKey(pkey);
2278:            }
2279:
2280:            /**
2281:             * This method is used to indicate whether a column is part of the primary
2282:             * key
2283:             */
2284:            public void setPrimaryKey(String col, boolean pkey)
2285:                    throws DataStoreException {
2286:                int c = getColumnIndex(col);
2287:                setPrimaryKey(c, pkey);
2288:            }
2289:
2290:            /**
2291:             * This method builds the datastore from the information in the properties
2292:             * object.
2293:             */
2294:            public void setProperties(Properties p) {
2295:                super .setProperties(p);
2296:                String desc = "base.";
2297:                _updateMethod = setIntProperty(p.getProperty(desc
2298:                        + "updateMethod"));
2299:                _checkConcurrency = setBoolProperty(p.getProperty(desc
2300:                        + "checkConcurrency"));
2301:                _useBind = setBoolProperty(p.getProperty(desc + "useBind"));
2302:                _maxRows = setIntProperty(p.getProperty(desc + "maxRows"));
2303:                setRemoteID(getStringProperty(p.getProperty(desc + "remoteID")));
2304:            }
2305:
2306:            /**
2307:             * Use this method to set whether the DataStore will trim (remove trailing
2308:             * spaces) from columns retrieved from the database;
2309:             */
2310:            public void setTrimStrings(boolean trim) {
2311:                _desc.setTrimStrings(trim);
2312:            }
2313:
2314:            /**
2315:             * This method is used to indicate whether a column is updateable
2316:             */
2317:            public void setUpdateable(int col, boolean updateable)
2318:                    throws DataStoreException {
2319:                if (col < 0 || _desc.getColumnCount() == 0)
2320:                    throw new DataStoreException("Specified column (" + col
2321:                            + ") does not exist.");
2322:
2323:                DSColumnDescriptor c = _desc.getColumn(col);
2324:                c.setUpdateable(updateable);
2325:            }
2326:
2327:            /**
2328:             * This method is used to indicate whether a column is updateable
2329:             */
2330:            public void setUpdateable(String col, boolean updateable)
2331:                    throws DataStoreException {
2332:                int c = getColumnIndex(col);
2333:                setUpdateable(c, updateable);
2334:            }
2335:
2336:            /**
2337:             * This method is used to indicate whether a column is auto increment
2338:             */
2339:            public void setAutoIncrement(int col, boolean auto)
2340:                    throws DataStoreException {
2341:                if (col < 0 || _desc.getColumnCount() == 0)
2342:                    throw new DataStoreException("Specified column (" + col
2343:                            + ") does not exist.");
2344:
2345:                DSColumnDescriptor c = _desc.getColumn(col);
2346:                c.setAutoIncrement(auto);
2347:            }
2348:
2349:            /**
2350:             * This method is used to indicate whether a column is auto increment
2351:             */
2352:            public void setAutoIncrement(String col, boolean auto)
2353:                    throws DataStoreException {
2354:                int c = getColumnIndex(col);
2355:                setAutoIncrement(c, auto);
2356:            }
2357:
2358:            /**
2359:             * Sets the update method for the datastore. This will effect the SQL
2360:             * Generated when a row is modified and the changes is made to the database
2361:             * via the update() method.
2362:             * 
2363:             * @param updateMethod
2364:             *            Valid values are UPDATEMETHOD_UPDATES (will use update
2365:             *            statements to change the values of rows in the database) or
2366:             *            UPDATEMETHOD_DELETEINSERTS (will used delete statements and
2367:             *            then insert statements to modify rows in the database).
2368:             */
2369:            public void setUpdateMethod(int updateMethod) {
2370:                _updateMethod = updateMethod;
2371:            }
2372:
2373:            /**
2374:             * This method is used to indicate whether a column should use bind
2375:             * variables for inserts and updates. Valid values and BIND_TRUE, BIND_FALSE
2376:             * and BIND_DEFAULT (Use default for datastore)
2377:             */
2378:            public void setUseBindColumn(int col, int useBind)
2379:                    throws DataStoreException {
2380:                if (col < 0 || _desc.getColumnCount() == 0)
2381:                    throw new DataStoreException("Specified column (" + col
2382:                            + ") does not exist.");
2383:
2384:                DSColumnDescriptor c = _desc.getColumn(col);
2385:                c.setUseBind(useBind);
2386:            }
2387:
2388:            /**
2389:             * This method is used to indicate whether a column should use bind
2390:             * variables for inserts and updates. Valid values and BIND_TRUE, BIND_FALSE
2391:             * and BIND_DEFAULT (Use default for datastore)
2392:             */
2393:            public void setUseBindColumn(String col, int useBind)
2394:                    throws DataStoreException {
2395:                int c = getColumnIndex(col);
2396:                setUseBindColumn(c, useBind);
2397:            }
2398:
2399:            /**
2400:             * Use this method to set whether or not the datastore will use bind
2401:             * variables as the default for updating or inserting columns. This is the
2402:             * default for every column in the datastore. The behavior for individual
2403:             * columns can be set using the setUseBindColumn method.
2404:             */
2405:            public void setUseBindForUpdate(boolean truefalse) {
2406:                _useBind = truefalse;
2407:            }
2408:
2409:            //Added by FC on 2/21/03. Was added to handle JDBC drivers which have
2410:            // problems with the cancel() method being called.
2411:            //Example Driver: JSQLDriver from NetDirect.
2412:            /**
2413:             * Use this method to set whether or not the cancel() method of a JDBC
2414:             * Statement is to be called when cancelling a retrieve.
2415:             */
2416:            public void setEnableCancel(boolean truefalse) {
2417:                _enableCancel = truefalse;
2418:            }
2419:
2420:            /**
2421:             * This method will take a row from the datastores deleted buffer and move
2422:             * it back to the standard buffer.
2423:             * 
2424:             * @param row
2425:             *            The number of the row to undelete. Note: this is the row
2426:             *            number of the row in the deleted buffer not the standard
2427:             *            buffer.
2428:             * @return The number that the deleted row was moved to in the standard
2429:             *         buffer or -1 if an error occurs.
2430:             */
2431:            public int unDeleteRow(int row) {
2432:                if (row < 0)
2433:                    return -1;
2434:                if (row >= getDeletedCount())
2435:                    return -1;
2436:                DSDataRow d = (DSDataRow) _deletedRows.elementAt(row);
2437:                _deletedRows.removeElementAt(row);
2438:                _rows.addElement(d);
2439:
2440:                return _rows.size() - 1;
2441:            }
2442:
2443:            /**
2444:             * Use this method to retrieve the result sets from multiple data stores
2445:             * into the data buffer of this one. The datastores must all be compatible
2446:             * with this one in that the datatypes and number of columns in each much
2447:             * match exactly. You do not need to pass a database connection to this
2448:             * version of union, but in order to use it the DataStore must be created
2449:             * with a constructor that passes an application (not the no args
2450:             * constructor).
2451:             * 
2452:             * @param dataStores
2453:             *            The array of data stores to union result sets together.
2454:             */
2455:            public void union(DataStore dataStores[])
2456:                    throws java.sql.SQLException, DataStoreException {
2457:                if (_appName == null)
2458:                    throw new DataStoreException(
2459:                            "This version of union requires an dbprofile and/or application name. You cannot call this method on a DataStore created with the no-args constructor");
2460:
2461:                DBConnection conn;
2462:                if (_dbProfile == null)
2463:                    conn = DBConnection.getConnection(_appName);
2464:                else
2465:                    conn = DBConnection.getConnection(_appName, _dbProfile);
2466:
2467:                _releaseConn = true;
2468:
2469:                union(conn, dataStores);
2470:
2471:            }
2472:
2473:            /**
2474:             * Use this method to retrieve the result set from a second data stores into
2475:             * the data buffer of this one. The datastores must all be compatible with
2476:             * this one in that the datatypes and number of columns in each much match
2477:             * exactly. You do not need to pass a database connection to this version of
2478:             * union, but in order to use it the DataStore must be created with a
2479:             * constructor that passes an application (not the no args constructor).
2480:             * 
2481:             * @param dataStore
2482:             *            The datastore to union with this one.
2483:             */
2484:            public void union(DataStore dataStore)
2485:                    throws java.sql.SQLException, DataStoreException {
2486:                DataStore d[] = new DataStore[1];
2487:                d[0] = dataStore;
2488:                union(d);
2489:            }
2490:
2491:            /**
2492:             * Use this method to retrieve the result sets from multiple data stores
2493:             * into the data buffer of this one. The datastores must all be compatible
2494:             * with this one in that the datatypes and number of columns in each much
2495:             * match exactly.
2496:             * 
2497:             * @param conn
2498:             *            The database connection to use to perform this operation.
2499:             * @param dataStores
2500:             *            The array of data stores to union result sets together.
2501:             */
2502:            public void union(DBConnection conn, DataStore dataStores[])
2503:                    throws java.sql.SQLException {
2504:                reset();
2505:
2506:                String sql = getSelectStatement(conn);
2507:                for (int i = 0; i < dataStores.length; i++) {
2508:                    sql += " UNION " + dataStores[i].getSelectStatement(conn);
2509:                }
2510:
2511:                retrieve(conn, null, null, null, sql, false);
2512:            }
2513:
2514:            /**
2515:             * Use this method to retrieve the result set from a second data stores into
2516:             * the data buffer of this one. The datastores must all be compatible with
2517:             * this one in that the datatypes and number of columns in each much match
2518:             * exactly.
2519:             * 
2520:             * @param conn
2521:             *            The database connection to use to perform this operation.
2522:             * @param dataStore
2523:             *            The datastore to union with this one.
2524:             */
2525:            public void union(DBConnection conn, DataStore dataStore)
2526:                    throws java.sql.SQLException, DataStoreException {
2527:                DataStore d[] = new DataStore[1];
2528:                d[0] = dataStore;
2529:                union(conn, d);
2530:            }
2531:
2532:            /**
2533:             * This method will cause the database to reflect the changes made in the
2534:             * data store's buffer. All transaction operations are handled within the
2535:             * datastore. You do not need to pass a database connection to this version
2536:             * of update, but in order to use it the DataStore must be created with a
2537:             * constructor that passes an application (not the no args constructor).
2538:             * 
2539:             * @exception com.salmonllc.sql.DataStoreException
2540:             *                If a SQLError occurs while the datastore is updating.
2541:             */
2542:            public void update() throws DataStoreException,
2543:                    java.sql.SQLException {
2544:                if (_appName == null)
2545:                    throw new DataStoreException(
2546:                            "This version of update requires an application name and/or dbprofile. You cannot call this method on a DataStore created with the no-args constructor");
2547:
2548:                DBConnection conn = null;
2549:
2550:                try {
2551:                    if (_dbConn == null) {
2552:                        if (_dbProfile == null)
2553:                            conn = DBConnection.getConnection(_appName);
2554:                        else
2555:                            conn = DBConnection.getConnection(_appName,
2556:                                    _dbProfile);
2557:                    } else {
2558:                        conn = _dbConn;
2559:                    }
2560:                    update(conn, true);
2561:                } catch (DataStoreException e) {
2562:                    throw (e);
2563:                } catch (java.sql.SQLException e) {
2564:                    throw (e);
2565:                } catch (Exception e) {
2566:                    MessageLog.writeErrorMessage("update", e, this );
2567:                } finally {
2568:                    if (conn != null)
2569:                        conn.freeConnection();
2570:                }
2571:            }
2572:
2573:            /**
2574:             * This method will cause the database to reflect the changes made in the
2575:             * data store's buffer. All transaction operations must be handled outside
2576:             * of the datastore.
2577:             * 
2578:             * @param conn
2579:             *            The database connection to use to perform this operation.
2580:             * @exception com.salmonllc.sql.DataStoreException
2581:             *                If a SQLError occurs while the datastore is updating.
2582:             */
2583:            public void update(DBConnection conn) throws DataStoreException,
2584:                    java.sql.SQLException {
2585:                update(conn, false);
2586:            }
2587:
2588:            /**
2589:             * This method will cause the database to reflect the changes made in the
2590:             * data store's buffer.
2591:             * 
2592:             * @param conn
2593:             *            The database connection to use to perform this operation.
2594:             * @param handleTrans
2595:             *            True if the update should perform it's own transaction
2596:             *            management and false if the transaction management will be
2597:             *            handled outside the datastore.
2598:             * @exception com.salmonllc.sql.DataStoreException
2599:             *                If a SQLError occurs while the datastore is updating.
2600:             */
2601:            public void update(DBConnection conn, boolean handleTrans)
2602:                    throws DataStoreException, java.sql.SQLException {
2603:                waitForRetrieve();
2604:
2605:                if (_autoValidate) {
2606:                    DataStoreException[] valEx = validateRowsToUpdate(conn,
2607:                            true);
2608:                    if (valEx.length > 0)
2609:                        throw (valEx[0]);
2610:                }
2611:
2612:                int rowNo = -1;
2613:                int buffer = BUFFER_STANDARD;
2614:                DataSourceOut out = getDSOut(conn);
2615:                DataStoreRow row = new DataStoreRow(this , null, _desc);
2616:
2617:                try {
2618:                    out.preUpdate(this , conn, handleTrans);
2619:                    //do deletes
2620:                    buffer = BUFFER_DELETED;
2621:                    for (rowNo = 0; rowNo < _deletedRows.size(); rowNo++) {
2622:                        row.setDSDataRow((DSDataRow) _deletedRows
2623:                                .elementAt(rowNo));
2624:                        if (!out.deleteRow(this , row, conn))
2625:                            throw new Exception("$Delete$");
2626:                        if (out instanceof  DSDataSourceJDBC)
2627:                            notifyListeners(BUFFER_DELETED, rowNo,
2628:                                    ((DSDataSourceJDBC) out).getSelect(), conn);
2629:                    }
2630:
2631:                    //do the updates
2632:                    buffer = BUFFER_STANDARD;
2633:                    if (_updateMethod == UPDATEMETHOD_DELETEINSERTS) {
2634:                        for (rowNo = 0; rowNo < _rows.size(); rowNo++) {
2635:                            row
2636:                                    .setDSDataRow((DSDataRow) _rows
2637:                                            .elementAt(rowNo));
2638:                            if (row.getDSDataRow().getRowStatus() == STATUS_MODIFIED) {
2639:                                if (!out.deleteRow(this , row, conn))
2640:                                    throw new Exception("$Update$");
2641:                                if (out instanceof  DSDataSourceJDBC)
2642:                                    notifyListeners(BUFFER_STANDARD, rowNo,
2643:                                            ((DSDataSourceJDBC) out)
2644:                                                    .getSelect(), conn);
2645:                            }
2646:                        }
2647:
2648:                        for (rowNo = 0; rowNo < _rows.size(); rowNo++) {
2649:                            row
2650:                                    .setDSDataRow((DSDataRow) _rows
2651:                                            .elementAt(rowNo));
2652:                            if (row.getDSDataRow().getRowStatus() == STATUS_MODIFIED) {
2653:                                if (!out.insertRow(this , row, conn))
2654:                                    throw new Exception("$Update$");
2655:                                if (out instanceof  DSDataSourceJDBC)
2656:                                    notifyListeners(BUFFER_STANDARD, rowNo,
2657:                                            ((DSDataSourceJDBC) out)
2658:                                                    .getSelect(), conn);
2659:                            }
2660:                        }
2661:                    } else {
2662:                        for (rowNo = 0; rowNo < _rows.size(); rowNo++) {
2663:                            row
2664:                                    .setDSDataRow((DSDataRow) _rows
2665:                                            .elementAt(rowNo));
2666:                            if (row.getDSDataRow().getRowStatus() == STATUS_MODIFIED) {
2667:                                if (!out.updateRow(this , row, conn))
2668:                                    throw new Exception("$Update$");
2669:                                if (out instanceof  DSDataSourceJDBC)
2670:                                    notifyListeners(BUFFER_STANDARD, rowNo,
2671:                                            ((DSDataSourceJDBC) out)
2672:                                                    .getSelect(), conn);
2673:                            }
2674:                        }
2675:                    }
2676:
2677:                    //do the inserts
2678:                    for (rowNo = 0; rowNo < _rows.size(); rowNo++) {
2679:                        row.setDSDataRow((DSDataRow) _rows.elementAt(rowNo));
2680:                        if (row.getDSDataRow().getRowStatus() == STATUS_NEW_MODIFIED) {
2681:                            if (!out.insertRow(this , row, conn))
2682:                                throw new Exception("$Insert$");
2683:                            if (out instanceof  DSDataSourceJDBC)
2684:                                notifyListeners(BUFFER_STANDARD, rowNo,
2685:                                        ((DSDataSourceJDBC) out).getSelect(),
2686:                                        conn);
2687:                        }
2688:                    }
2689:
2690:                    out.postUpdate(this , conn, handleTrans, true);
2691:                    if (handleTrans)
2692:                        resetStatus();
2693:                } catch (DirtyDataException e) {
2694:                    try {
2695:                        out.postUpdate(this , conn, handleTrans, false);
2696:                    } catch (Exception ex) {
2697:                        MessageLog.writeErrorMessage("update() -- postUpdate",
2698:                                ex, this );
2699:                    }
2700:                    e.setRowAndBuffer(rowNo, buffer);
2701:                    throw (e);
2702:                } catch (SQLException e) {
2703:                    try {
2704:                        out.postUpdate(this , conn, handleTrans, false);
2705:                    } catch (Exception ex) {
2706:                        MessageLog.writeErrorMessage("update() -- postUpdate",
2707:                                ex, this );
2708:                    }
2709:                    throw (e);
2710:                } catch (DataStoreException e) {
2711:                    try {
2712:                        out.postUpdate(this , conn, handleTrans, false);
2713:                    } catch (Exception ex) {
2714:                        MessageLog.writeErrorMessage("update() -- postUpdate",
2715:                                ex, this );
2716:                    }
2717:                    throw (e);
2718:
2719:                } catch (Exception e) {
2720:                    try {
2721:                        out.postUpdate(this , conn, handleTrans, false);
2722:                    } catch (Exception ex) {
2723:                        MessageLog.writeErrorMessage("update() -- postUpdate",
2724:                                ex, this );
2725:                    }
2726:
2727:                    String message = e.getMessage();
2728:                    if (message.equals("$Update$")
2729:                            || message.equals("$Insert$")
2730:                            || message.equals("$Delete$")) {
2731:                        throw new DataStoreException(
2732:                                "DataStore updated canceled.");
2733:                    } else
2734:                        throw new DataStoreException(message);
2735:
2736:                }
2737:            }
2738:
2739:            /**
2740:             * This method is used for databases profiles where the DBName attribute is
2741:             * specified. It will take a short table name and return the fully qualified
2742:             * table name, including the database name.
2743:             */
2744:            public String computeTableName(String nameIn) {
2745:                //fc: 07/17/02 Added a null check to if statement to stop
2746:                // a null pointer exception from occuring.
2747:                if (nameIn == null || nameIn.indexOf(".") != -1)
2748:                    return nameIn;
2749:                if (_appName == null)
2750:                    return nameIn;
2751:                for (int i = 0; i < _desc.getAliasCount(); i++) {
2752:                    DSTableAliasDescriptor test = _desc.getAlias(i);
2753:                    if (test.getAlias() != null
2754:                            && test.getAlias().equalsIgnoreCase(nameIn))
2755:                        return nameIn;
2756:                }
2757:                loadDBName();
2758:                if (_dbName == null)
2759:                    return nameIn;
2760:                else if (_dbms.equals(DBConnection.SYBASE_CONNECTION)
2761:                        || _dbms.equals(DBConnection.MSSQLSEVER_CONNECTION))
2762:                    return _dbName + ".dbo." + nameIn;
2763:                else
2764:                    return _dbName + "." + nameIn;
2765:            }
2766:
2767:            /**
2768:             * This method is used for databases profiles where the DBName attribute is
2769:             * specified. It will take a short table name, column name combination and
2770:             * return the fully qualified table name + column name, including the
2771:             * database name.
2772:             */
2773:            public String computeTableAndFieldName(String fieldName) {
2774:                int pos = fieldName.lastIndexOf(".");
2775:                if (pos == -1)
2776:                    return fieldName;
2777:                String tableName = fieldName.substring(0, pos);
2778:                String colName = fieldName.substring(pos);
2779:                return computeTableName(tableName) + colName;
2780:            }
2781:
2782:            private void loadDBName() {
2783:                if (_dbms != null)
2784:                    return;
2785:                if (_appName == null)
2786:                    return;
2787:                DBConnection conn = null;
2788:                try {
2789:                    conn = DBConnection.getConnection(_appName, _dbProfile);
2790:                    String DBName = conn.getDBName();
2791:                    String DBMS = conn.getDBMS();
2792:                    _dbms = DBMS;
2793:                    if (DBName != null)
2794:                        _dbName = DBName;
2795:                } catch (Exception e) {
2796:                    MessageLog.writeErrorMessage("loadDBName", e, this );
2797:                } finally {
2798:                    if (conn != null)
2799:                        conn.freeConnection();
2800:                }
2801:
2802:            }
2803:
2804:            /**
2805:             * This method takes the SQL INSERT statements that would have been
2806:             * generated to add these rows to the database, and, rather than executing
2807:             * them, returns them as a string that can be written to a SQL script file.
2808:             */
2809:
2810:            public String exportAsSQL(DBConnection conn, String sDBType,
2811:                    String separator) throws Exception {
2812:                DSDataSourceJDBC x = (DSDataSourceJDBC) Class.forName(
2813:                        "com.salmonllc.sql.DSDataSource" + sDBType)
2814:                        .newInstance();
2815:                String s = x.exportAsSQL(this , conn, separator);
2816:                return s;
2817:            }
2818:
2819:            /**
2820:             * Returns true if the open and close parens on a string match
2821:             */
2822:            public static boolean parensMatch(String s) {
2823:                int open = 0;
2824:                int close = 0;
2825:                for (int i = 0; i < s.length(); i++) {
2826:                    if (s.charAt(i) == '(')
2827:                        open++;
2828:                    else if (s.charAt(i) == ')')
2829:                        close++;
2830:                }
2831:                return (open == close);
2832:
2833:            }
2834:
2835:            /**
2836:             * @return the database profile this datastore is using
2837:             */
2838:            public String getDbProfile() {
2839:                return _dbProfile;
2840:            }
2841:
2842:            /**
2843:             * Returns true if the datastore will execute any defined validation rules
2844:             * before an update
2845:             */
2846:            public boolean getAutoValidate() {
2847:                return _autoValidate;
2848:            }
2849:
2850:            /**
2851:             * Sets whether the datastore will execute any defined validation rules
2852:             * before an update
2853:             */
2854:            public void setAutoValidate(boolean autoValidate) {
2855:                _autoValidate = autoValidate;
2856:            }
2857:
2858:            /**
2859:             * Executes the prepared statement with no parameters.
2860:             * 
2861:             * @param conn
2862:             *            The database connection to use to perform this operation.
2863:             * @param stmt
2864:             *            The prepared statement to execute.
2865:             */
2866:            public synchronized void executePrepStmt(DBConnection conn,
2867:                    String stmt) throws java.sql.SQLException {
2868:                executePrepStmt(conn, stmt, new PreparedStatementParms());
2869:            }
2870:
2871:            /**
2872:             * Executes the prepared statement and retrieves to data. The datatypes and
2873:             * number of columns in the result set must exactly match the columns in the
2874:             * specified sql statement.
2875:             * 
2876:             * @param conn
2877:             *            The database connection to use to perform this operation.
2878:             * @param stmt
2879:             *            The prepared statement to execute.
2880:             * @param parms
2881:             *            A PreparedStatementParms object containing the parameters to
2882:             *            pass to the prepared statement.
2883:             */
2884:            public synchronized void executePrepStmt(DBConnection conn,
2885:                    String stmt, PreparedStatementParms parms)
2886:                    throws java.sql.SQLException {
2887:                retrieve(conn, null, stmt, parms, null, false);
2888:            }
2889:
2890:            /**
2891:             * Executes the prepared statement and retrieves to data.
2892:             * 
2893:             * @param stmt
2894:             *            The prepared statement to execute.
2895:             */
2896:
2897:            public void executePrepStmt(String stmt)
2898:                    throws java.sql.SQLException, DataStoreException {
2899:                executePrepStmt(stmt, new PreparedStatementParms());
2900:            }
2901:
2902:            /**
2903:             * Executes the prepared statement and retrieves to data. The datatypes and
2904:             * number of columns in the result set must exactly match the columns in the
2905:             * specified sql statement.
2906:             * 
2907:             * @param stmt
2908:             *            The prepared statement to execute.
2909:             * @param parms
2910:             *            A PreparedStatementParms object containing the parameters to
2911:             *            pass to the proc.
2912:             */
2913:            public synchronized void executePrepStmt(String stmt,
2914:                    PreparedStatementParms parms) throws java.sql.SQLException,
2915:                    DataStoreException {
2916:                if (_appName == null)
2917:                    throw new DataStoreException(
2918:                            "This version of execute requires an application name and/or dbprofile. You cannot call this method on a DataStore created with the no-args constructor");
2919:
2920:                DBConnection conn;
2921:                if (_dbProfile == null)
2922:                    conn = DBConnection.getConnection(_appName);
2923:                else
2924:                    conn = DBConnection.getConnection(_appName, _dbProfile);
2925:
2926:                _releaseConn = true;
2927:                executePrepStmt(conn, stmt, parms);
2928:            }
2929:
2930:            /**
2931:             * Loads connection parms from the database connection object into the
2932:             * datastore. This method can only be used with the datastore constructor
2933:             * that takes and application name and/or profile name and will be called
2934:             * automatically from those constructors
2935:             */
2936:            public void loadConnectionParms() {
2937:                DBConnection conn = null;
2938:                try {
2939:                    conn = DBConnection.getConnection(_appName, _dbProfile);
2940:                    loadConnectionParms(conn);
2941:                } catch (Exception ex) {
2942:                } finally {
2943:                    if (conn != null)
2944:                        conn.freeConnection();
2945:                }
2946:            }
2947:
2948:            /**
2949:             * Loads connection parameters for this datastore from the specified
2950:             * connection object
2951:             */
2952:            public void loadConnectionParms(DBConnection conn) {
2953:                String val = conn
2954:                        .getConnectionParm(CONNECTION_PARM_CHECK_CONCURRENCY);
2955:                if (val != null)
2956:                    setCheckConcurrency(val.equalsIgnoreCase("true"));
2957:                val = conn
2958:                        .getConnectionParm(CONNECTION_PARM_USE_BIND_FOR_UPDATES);
2959:                if (val != null)
2960:                    setUseBindForUpdate(val.equalsIgnoreCase("true"));
2961:                val = conn
2962:                        .getConnectionParm(CONNECTION_PARM_USE_DELETE_INSERT_FOR_UPDATES);
2963:                if (val != null)
2964:                    setUpdateMethod(val.equalsIgnoreCase("true") ? UPDATEMETHOD_DELETEINSERTS
2965:                            : UPDATEMETHOD_UPDATES);
2966:                val = conn.getConnectionParm(CONNECTION_PARM_TRIM_STRINGS);
2967:                if (val != null)
2968:                    setTrimStrings(val.equalsIgnoreCase("true"));
2969:
2970:                //Handle Nulls
2971:                val = conn
2972:                        .getConnectionParm(CONNECTION_PARM_REPLACE_NULL_STRINGS);
2973:                if (val != null) {
2974:                    if (val.equalsIgnoreCase("true"))
2975:                        setNullDefault(DATATYPE_STRING, "");
2976:                }
2977:
2978:                val = conn.getConnectionParm(CONNECTION_PARM_REPLACE_NULL_INTS);
2979:                if (val != null) {
2980:                    try {
2981:                        short i = Short.parseShort(val);
2982:                        setNullDefault(DATATYPE_INT, new Integer(i));
2983:                        setNullDefault(DATATYPE_LONG, new Long(i));
2984:                        setNullDefault(DATATYPE_SHORT, new Short(i));
2985:                    } catch (Exception ex) {
2986:                        MessageLog.writeErrorMessage(
2987:                                "Error Parsing Null Integer Default for Datastore ("
2988:                                        + val + ").", ex, this );
2989:                    }
2990:                }
2991:
2992:                val = conn
2993:                        .getConnectionParm(CONNECTION_PARM_REPLACE_NULL_DECIMALS);
2994:                if (val != null) {
2995:                    try {
2996:                        float f = Float.parseFloat(val);
2997:                        setNullDefault(DATATYPE_FLOAT, new Float(f));
2998:                        setNullDefault(DATATYPE_DOUBLE, new Double(f));
2999:                    } catch (Exception ex) {
3000:                        MessageLog.writeErrorMessage(
3001:                                "Error Parsing Null Decimal Default for Datastore ("
3002:                                        + val + ").", ex, this );
3003:                    }
3004:                }
3005:
3006:                val = conn
3007:                        .getConnectionParm(CONNECTION_PARM_REPLACE_NULL_DATES);
3008:                if (val != null) {
3009:                    DateFormat df = new SimpleDateFormat("yyyy-MM-dd");
3010:                    try {
3011:                        java.util.Date d = df.parse(val);
3012:                        setNullDefault(DATATYPE_DATE, new java.sql.Date(d
3013:                                .getTime()));
3014:                    } catch (ParseException ex) {
3015:                        MessageLog
3016:                                .writeErrorMessage(
3017:                                        "Error Parsing Null Date Default For Datastore ("
3018:                                                + val
3019:                                                + "). It must be in the form yyyy-mm-dd",
3020:                                        ex, this );
3021:                    }
3022:                }
3023:
3024:                val = conn
3025:                        .getConnectionParm(CONNECTION_PARM_REPLACE_NULL_DATETIMES);
3026:                if (val != null) {
3027:                    DateFormat df = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
3028:                    try {
3029:                        java.util.Date d = df.parse(val);
3030:                        setNullDefault(DATATYPE_DATETIME,
3031:                                new java.sql.Timestamp(d.getTime()));
3032:                    } catch (ParseException ex) {
3033:                        MessageLog
3034:                                .writeErrorMessage(
3035:                                        "Error Parsing Null DateTime Default For Datastore ("
3036:                                                + val
3037:                                                + "). It must be in the form yyyy-mm-dd hh:mm:ss",
3038:                                        ex, this );
3039:                    }
3040:                }
3041:
3042:                val = conn
3043:                        .getConnectionParm(CONNECTION_PARM_REPLACE_NULL_TIMES);
3044:                if (val != null) {
3045:                    DateFormat df = new SimpleDateFormat("HH:mm:ss");
3046:                    try {
3047:                        java.util.Date d = df.parse(val);
3048:                        setNullDefault(DATATYPE_TIME, new java.sql.Time(d
3049:                                .getTime()));
3050:                    } catch (ParseException ex) {
3051:                        MessageLog.writeErrorMessage(
3052:                                "Error Parsing Null Time Default For Datastore ("
3053:                                        + val
3054:                                        + "). It must be in the form hh:mm:ss",
3055:                                ex, this );
3056:                    }
3057:                }
3058:
3059:            }
3060:
3061:            /**
3062:             * Returns a list of column definitions for a particular table in the
3063:             * database that the datastore is using. Note, the datastore must have an
3064:             * app name for this method to work.
3065:             */
3066:            public ColumnDefinition[] getColumnsForTable(String table) {
3067:                DBConnection conn = null;
3068:                ColumnDefinition ret[] = null;
3069:                try {
3070:                    conn = DBConnection.getConnection(getAppName(),
3071:                            getDbProfile());
3072:                    DataDictionary d = conn.getDataDictionary();
3073:                    Vector v = d.getColumns(table);
3074:                    if (v != null) {
3075:                        ret = new ColumnDefinition[v.size()];
3076:                        v.copyInto(ret);
3077:                    } else
3078:                        ret = new ColumnDefinition[0];
3079:                } catch (SQLException ex) {
3080:                    MessageLog.writeErrorMessage("getColumnsForTable()", ex,
3081:                            this );
3082:                    ret = new ColumnDefinition[0];
3083:                } finally {
3084:                    conn.freeConnection();
3085:                }
3086:                return ret;
3087:
3088:            }
3089:
3090:            /**
3091:             * Returns the name of the database engine being used
3092:             */
3093:            public String getDBMS() {
3094:                loadDBName();
3095:                return _dbms;
3096:            }
3097:
3098:            /**
3099:             * Builds a where clause suitable for retrieving a single row from the
3100:             * specified table where the primary key fields match the values in the
3101:             * specified row.
3102:             */
3103:            public String buildCriteriaStringForRow(int row, String table)
3104:                    throws DataStoreException {
3105:                StringBuffer ret = new StringBuffer(255);
3106:                int colCount = getColumnCount();
3107:                for (int i = 0; i < colCount; i++) {
3108:                    String tabName = getColumnTableName(i);
3109:                    if (tabName == null || tabName != table)
3110:                        continue;
3111:                    if (isColumnPrimaryKey(i)) {
3112:                        if (ret.length() != 0)
3113:                            ret.append(" AND ");
3114:                        ret.append(getColumnDatabaseName(i));
3115:                        Object data = getAny(row, i);
3116:                        if (data == null)
3117:                            ret.append(" IS NULL ");
3118:                        else {
3119:                            ret.append(" = ");
3120:                            int type = getColumnDataType(i);
3121:                            if (type == DataStore.DATATYPE_DATETIME)
3122:                                ret.append(" {ts '"
3123:                                        + DataStore.fixQuote(data.toString(),
3124:                                                type, getDBMS()) + "'}");
3125:                            else if (type == DataStore.DATATYPE_DATE)
3126:                                ret.append(" {d '"
3127:                                        + DataStore.fixQuote(data.toString(),
3128:                                                type, getDBMS()) + "'}");
3129:                            else if (type == DataStore.DATATYPE_TIME)
3130:                                ret.append(" {t '"
3131:                                        + DataStore.fixQuote(data.toString(),
3132:                                                type, getDBMS()) + "'}");
3133:                            else if (type == DataStore.DATATYPE_STRING)
3134:                                ret.append("'"
3135:                                        + DataStore.fixQuote(data.toString(),
3136:                                                type, getDBMS()) + "'");
3137:                            else
3138:                                ret.append(data.toString());
3139:                        }
3140:                    }
3141:                }
3142:                if (ret.length() == 0)
3143:                    return null;
3144:                else
3145:                    return ret.toString();
3146:            }
3147:
3148:            /**
3149:             * Reloads the specified row from the database. Any unsaved changes will be
3150:             * overwritten.
3151:             * 
3152:             * @throws DataStoreException
3153:             * @throws SQLException
3154:             */
3155:            public synchronized void reloadRow() throws DataStoreException,
3156:                    SQLException {
3157:                reloadRow(getRow());
3158:            }
3159:
3160:            /**
3161:             * Reloads the specified row from the database. Any unsaved changes will be
3162:             * overwritten.
3163:             * 
3164:             * @param rowNo
3165:             */
3166:            public synchronized void reloadRow(int rowNo)
3167:                    throws DataStoreException, SQLException {
3168:                DBConnection conn = null;
3169:                if (_appName == null)
3170:                    throw new DataStoreException(
3171:                            "This version of reloadRow requires an application name and/or dbprofile. You cannot call this method on a DataStore created with the no-args constructor");
3172:                try {
3173:                    if (_dbProfile == null)
3174:                        conn = DBConnection.getConnection(_appName);
3175:                    else
3176:                        conn = DBConnection.getConnection(_appName, _dbProfile);
3177:                    reloadRow(conn, rowNo);
3178:                } finally {
3179:                    if (conn != null)
3180:                        conn.freeConnection();
3181:                }
3182:            }
3183:
3184:            /**
3185:             * Reloads the specified row from the database. Any unsaved changes will be
3186:             * overwritten.
3187:             * 
3188:             * @param conn
3189:             *            The database connection to use to load the data
3190:             * @param rowNo
3191:             */
3192:            public synchronized void reloadRow(DBConnection conn, int rowNo)
3193:                    throws DataStoreException, SQLException {
3194:                if (rowNo >= getRowCount() || rowNo < 0)
3195:                    throw new DataStoreException("Row number:" + rowNo
3196:                            + " out of range for reloadRow.");
3197:                int rowStatus = getRowStatus(rowNo);
3198:                if (rowStatus == STATUS_NEW || rowStatus == STATUS_NEW_MODIFIED)
3199:                    return;
3200:                DSDataRow row = getDataRow(rowNo);
3201:                SimpleDateFormat df = new SimpleDateFormat(
3202:                        "yyyy-MM-dd HH:mm:ss");
3203:                DataSourceIn in = getDSIn(conn);
3204:                if (in instanceof  DSDataSourceJDBC)
3205:                    df = ((DSDataSourceJDBC) in).getDateTimeFormat();
3206:
3207:                StringBuffer criteria = new StringBuffer();
3208:                for (int i = 0; i < getColumnCount(); i++) {
3209:                    if (!isPrimaryKey(i))
3210:                        continue;
3211:
3212:                    String databaseName = getColumnDatabaseName(i);
3213:
3214:                    Object data = null;
3215:                    if (rowStatus == STATUS_NOT_MODIFIED)
3216:                        data = row.getData(i);
3217:                    else {
3218:                        if (row.getColumnStatus(i) == STATUS_MODIFIED)
3219:                            data = row.getOrigData(i);
3220:                        else
3221:                            data = row.getData(i);
3222:                    }
3223:
3224:                    Object curData = row.getData(i);
3225:                    String value = null;
3226:
3227:                    int type = getColumnDataType(i);
3228:
3229:                    if (type == DataStore.DATATYPE_DATETIME) {
3230:                        if (data == null)
3231:                            value = " IS NULL";
3232:                        else
3233:                            value = " = {ts '"
3234:                                    + DSDataSourceJDBC.formatDateTime(
3235:                                            (Timestamp) data, df, conn) + "'}";
3236:                    } else if (type == DataStore.DATATYPE_DATE) {
3237:                        if (data == null)
3238:                            value = " IS NULL";
3239:                        else
3240:                            value = " = {d '"
3241:                                    + DataStore.fixQuote(data.toString(), type,
3242:                                            conn.getDBMS()) + "'}";
3243:                    } else if (type == DataStore.DATATYPE_TIME) {
3244:                        if (data == null)
3245:                            value = " IS NULL";
3246:                        else
3247:                            value = " = {t '"
3248:                                    + DataStore.fixQuote(data.toString(), type,
3249:                                            conn.getDBMS()) + "'}";
3250:                    } else if (type == DataStore.DATATYPE_STRING) {
3251:                        if (data == null)
3252:                            value = " IS NULL";
3253:                        else
3254:                            value = " = '"
3255:                                    + DataStore.fixQuote(data.toString(), type,
3256:                                            conn.getDBMS()) + "'";
3257:                    } else {
3258:                        if (data == null)
3259:                            value = " IS NULL";
3260:                        else
3261:                            value = " = " + data.toString();
3262:                    }
3263:                    if (criteria.length() > 0)
3264:                        criteria.append(" AND ");
3265:                    criteria.append(databaseName);
3266:                    criteria.append(value);
3267:                }
3268:                if (criteria.length() == 0)
3269:                    throw new DataStoreException(
3270:                            "Could not reload row. No primary key columns defined");
3271:
3272:                String select = getSelectStatement(conn, criteria.toString());
3273:                notifyListeners(BUFFER_STANDARD, rowNo, select, conn);
3274:                Statement st = conn.createStatement();
3275:                ResultSet res = st.executeQuery(select);
3276:                if (res.next()) {
3277:                    DSDataRow newRow = new DSDataRow(_desc);
3278:                    newRow.populateFromResultSet(_desc, res);
3279:                    _rows.setElementAt(newRow, rowNo);
3280:                    ModelChangedEvent evt = new ModelChangedEvent(
3281:                            ModelChangedEvent.TYPE_DATA_LOADED, this );
3282:                    notifyListeners(evt);
3283:                }
3284:                res.close();
3285:                st.close();
3286:            }
3287:
3288:            /**
3289:             * Populates the datastore from a given resultSet.
3290:             * 
3291:             * @param rs
3292:             *            the resultset.
3293:             * @throws Exception
3294:             */
3295:            public void populateFromResultSet(ResultSet rs) throws Exception {
3296:                while (rs.next()) {
3297:                    getDataStoreRow(insertRow(), DataStore.BUFFER_STANDARD)
3298:                            .populateFromResultSet(rs);
3299:                }
3300:            }
3301:
3302:            /**
3303:             * @return Returns whether or not the datastore will batch insert statements.
3304:             */
3305:            public boolean getBatchInserts() {
3306:                return _batchInserts;
3307:            }
3308:
3309:            /**
3310:             * Set to true to batch insert statements. This can speed things up if you are doing a high volume of inserts
3311:             */
3312:            public void setBatchInserts(boolean batchInserts) {
3313:                _batchInserts = batchInserts;
3314:            }
3315:        }
www.java2java.com | Contact Us
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.