Source Code Cross Referenced for AbstractEditableObject.java in  » Content-Management-System » harmonise » org » openharmonise » rm » resources » 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 » Content Management System » harmonise » org.openharmonise.rm.resources 
Source Cross Referenced  Class Diagram Java Document (Java Doc) 


0001:        /*
0002:         * The contents of this file are subject to the 
0003:         * Mozilla Public License Version 1.1 (the "License"); 
0004:         * you may not use this file except in compliance with the License. 
0005:         * You may obtain a copy of the License at http://www.mozilla.org/MPL/
0006:         *
0007:         * Software distributed under the License is distributed on an "AS IS"
0008:         * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. 
0009:         * See the License for the specific language governing rights and 
0010:         * limitations under the License.
0011:         *
0012:         * The Initial Developer of the Original Code is Simulacra Media Ltd.
0013:         * Portions created by Simulacra Media Ltd are Copyright (C) Simulacra Media Ltd, 2004.
0014:         *
0015:         * All Rights Reserved.
0016:         *
0017:         * Contributor(s):
0018:         */
0019:        package org.openharmonise.rm.resources;
0020:
0021:        import java.sql.*;
0022:        import java.util.*;
0023:        import java.util.logging.*;
0024:
0025:        import org.openharmonise.commons.cache.*;
0026:        import org.openharmonise.commons.dsi.*;
0027:        import org.openharmonise.commons.dsi.dml.*;
0028:        import org.openharmonise.commons.xml.XMLUtils;
0029:        import org.openharmonise.rm.*;
0030:        import org.openharmonise.rm.dsi.*;
0031:        import org.openharmonise.rm.factory.*;
0032:        import org.openharmonise.rm.publishing.*;
0033:        import org.openharmonise.rm.resources.lifecycle.*;
0034:        import org.openharmonise.rm.resources.publishing.Template;
0035:        import org.openharmonise.rm.resources.users.User;
0036:        import org.openharmonise.rm.search.*;
0037:        import org.openharmonise.rm.security.authorization.*;
0038:        import org.w3c.dom.*;
0039:
0040:        import EDU.oswego.cs.dl.util.concurrent.*;
0041:
0042:        /**
0043:         * AbstractEditableObject is the abstract implementation of the <code>Editable</code>
0044:         * interface for objects within Harmonise.
0045:         * 
0046:         * @author Michael Bell
0047:         * @version $Revision: 1.9.2.3 $
0048:         *
0049:         */
0050:        public abstract class AbstractEditableObject extends AbstractObject
0051:                implements  Editable, Publishable, DataStoreObject, Cloneable,
0052:                EditEventListener {
0053:
0054:            //XML constants
0055:            /**
0056:             * Status tag name
0057:             */
0058:            public static final String TAG_STATUS = "Status";
0059:
0060:            /**
0061:             * Display name tag name
0062:             */
0063:            public static final String TAG_DISPLAY_NAME = "DisplayName";
0064:
0065:            /**
0066:             * Version tag name
0067:             */
0068:            public static final String TAG_VERSION = "Version";
0069:
0070:            /**
0071:             * Version comment tag name
0072:             */
0073:            public static final String TAG_VERSION_COMMENT = "VersionComment";
0074:
0075:            /**
0076:             * Version date tag name
0077:             */
0078:            public static final String TAG_VERSION_DATE = "VersionDate";
0079:
0080:            /**
0081:             * History date tag name
0082:             */
0083:            public static final String TAG_HISTORY_DATE = "HistoryDate";
0084:
0085:            /**
0086:             * Live version tag name
0087:             */
0088:            public static final String TAG_LIVE_VERSION = "Live";
0089:
0090:            /**
0091:             * Pending version tag name
0092:             */
0093:            public static final String TAG_PENDING_VERSION = "Pending";
0094:
0095:            /**
0096:             * Historical version tag name
0097:             */
0098:            public static final String TAG_HISTORICAL_VERSION = "Historical";
0099:
0100:            /**
0101:             * Locked tag name
0102:             */
0103:            public static final String TAG_LOCKED = "Locked";
0104:
0105:            /**
0106:             * Is locked attribute name
0107:             */
0108:            public static final String ATTRIB_IS_LOCKED = "isLocked";
0109:
0110:            //DB Constants
0111:            /**
0112:             * Version number column name
0113:             */
0114:            private static final String CLMN_VERSION_NUMBER = "version_number";
0115:
0116:            /**
0117:             * Version date column name
0118:             */
0119:            private static final String CLMN_VERSION_DATE = "version_date";
0120:
0121:            /**
0122:             * Version comment column name
0123:             */
0124:            private static final String CLMN_VERSION_COMMENT = "version_comment";
0125:
0126:            /**
0127:             * Status column name
0128:             */
0129:            private static final String CLMN_STATUS = "status";
0130:
0131:            /**
0132:             * Lock user column name
0133:             */
0134:            private static final String CLMN_LOCK_USER = "lock_user";
0135:
0136:            /**
0137:             * Archive date column name
0138:             */
0139:            private static final String CLMN_HISTORY_DATE = "history_date";
0140:
0141:            /**
0142:             * Live object id column name
0143:             */
0144:            private static final String CLMN_LIVE_ID = "live_id";
0145:
0146:            /**
0147:             * Display name column name
0148:             */
0149:            protected static final String CLMN_DISPLAY_NAME = "display_name";
0150:
0151:            /**
0152:             * Prefix for all id sequence names
0153:             * 
0154:             * Note: Id sequence names will follow pattern - 'PRE_SEQ + getTableName()'
0155:             */
0156:            private static final String PRE_SEQ = "seq_";
0157:
0158:            /**
0159:             * Suffix for all key sequence names
0160:             * 
0161:             * Note: Key sequence names will follow pattern - 'PRE_SEQ + getTableName() + EXT_KEY'
0162:             */
0163:            private static final String EXT_KEY = "_key";
0164:
0165:            /**
0166:             * The version number
0167:             */
0168:            protected int m_nVersionNumber = 0;
0169:
0170:            /**
0171:             * The version comment
0172:             */
0173:            protected String m_sVersionComment = "";
0174:
0175:            /**
0176:             * The display name
0177:             */
0178:            protected String m_sDisplayName = "";
0179:
0180:            /**
0181:             * The version date
0182:             */
0183:            protected java.util.Date m_dtVersionDate = null;
0184:
0185:            /**
0186:             * The current status
0187:             */
0188:            protected Status m_status = Status.UNKNOWN;
0189:
0190:            /**
0191:             * The id of the live version
0192:             */
0193:            protected int m_nLiveId = -1;
0194:
0195:            /**
0196:             * The id of the user that locked this resource
0197:             */
0198:            protected int m_nLockUserId = NOTDBSAVED_ID;
0199:
0200:            /**
0201:             * The archive date
0202:             */
0203:            protected java.util.Date m_dtHistDate = null;
0204:
0205:            /**
0206:             * The list of <code>EditListener</code>s registered with this object
0207:             */
0208:            private List m_editlisteners = new ArrayList();
0209:
0210:            /**
0211:             * A cache pointer to the pending version
0212:             */
0213:            protected CachePointer m_pending = null;
0214:
0215:            /**
0216:             * Read-write lock to enable locking of cache access.
0217:             */
0218:            private ReadWriteLock m_edit_lock = new WriterPreferenceReadWriteLock();
0219:
0220:            /**
0221:             * Logger for this class
0222:             */
0223:            static private Logger m_logger = Logger
0224:                    .getLogger(AbstractEditableObject.class.getName());
0225:
0226:            /**
0227:             * Thread which has acquired the write lock on this object
0228:             */
0229:            private Thread m_lockThread = null;
0230:
0231:            /**
0232:             * Constructs a new or anonymous instance without an interface
0233:             * to the database.
0234:             */
0235:            public AbstractEditableObject() {
0236:                super ();
0237:            }
0238:
0239:            /** 
0240:             * Standard constructor for a new or anonymous resource,
0241:             * registering an <code>AbstractDataStoreInterface</code> to use 
0242:             * with all database communications.
0243:             *
0244:             * @param con the interface to the database
0245:             */
0246:            public AbstractEditableObject(AbstractDataStoreInterface con) {
0247:                super (con);
0248:
0249:            }
0250:
0251:            /** 
0252:             * Standard constructor for an existing resource,
0253:             * registering an <code>AbstractDataStoreInterface</code> to use 
0254:             * with all database communications.
0255:             *
0256:             * @param con the interface to the database
0257:             * @param nId the id of the resource
0258:             */
0259:            public AbstractEditableObject(AbstractDataStoreInterface con,
0260:                    int nId) {
0261:                super (con, nId);
0262:
0263:            }
0264:
0265:            /**
0266:             * Standard constructor for an existing resource which may be historical.
0267:             * 
0268:             * @param con the interface to the database
0269:             * @param nId the id of the resource
0270:             * @param nKey the unique key of the resource
0271:             * @param bIsHist <code>true</code> if the object is historical
0272:             */
0273:            public AbstractEditableObject(AbstractDataStoreInterface con,
0274:                    int nId, int nKey, boolean bIsHist) {
0275:                super (con, nId, nKey, bIsHist);
0276:            }
0277:
0278:            /** 
0279:             * Returns the display name of this resource.
0280:             *
0281:             * @return the display name of this resource
0282:             * @throws DataAccessException if an error occurs populating this object
0283:             */
0284:            public String getDisplayName() throws DataAccessException {
0285:                if ((m_sDisplayName == null || m_sDisplayName.length() == 0)
0286:                        && (m_bIsPopulated == false)) {
0287:                    try {
0288:                        populateFromDatabase();
0289:                    } catch (PopulateException e) {
0290:                        throw new DataAccessException("populate error", e);
0291:                    }
0292:                }
0293:
0294:                return m_sDisplayName;
0295:            }
0296:
0297:            /** 
0298:             * Sets the display name
0299:             *
0300:             * @param sName the display name of this resource
0301:             */
0302:            public void setDisplayName(String sDisplayName) {
0303:                if (m_bIsPopulated) {
0304:                    if (m_sDisplayName.equals(sDisplayName) == false) {
0305:                        m_bIsChanged = true;
0306:                    }
0307:                }
0308:
0309:                m_sDisplayName = sDisplayName;
0310:            }
0311:
0312:            /** 
0313:             * Returns the version comment.
0314:             *
0315:             * @return the version comment
0316:             * @throws DataAccessException if an error occurs while populating this object
0317:             */
0318:            public String getVersionComment() throws DataAccessException {
0319:                if ((m_sVersionComment == null)
0320:                        || (m_sVersionComment.equals(""))
0321:                        && (m_bIsPopulated == false)) {
0322:                    try {
0323:                        populateFromDatabase();
0324:                    } catch (PopulateException e) {
0325:                        throw new DataAccessException(e.getLocalizedMessage());
0326:                    }
0327:                }
0328:
0329:                return m_sVersionComment;
0330:            }
0331:
0332:            /** 
0333:             * Sets the version comment attached to this object.
0334:             *
0335:             * @param sVersionComment the version comment 
0336:             */
0337:            public void setVersionComment(String sVersionComment) {
0338:                if (sVersionComment == null) {
0339:                    sVersionComment = "";
0340:                }
0341:
0342:                if (m_bIsPopulated) {
0343:                    if ((m_sVersionComment == null && sVersionComment != null)
0344:                            || (m_sVersionComment.equals(sVersionComment) == false)) {
0345:                        m_bIsChanged = true;
0346:                    }
0347:                }
0348:
0349:                m_sVersionComment = sVersionComment;
0350:            }
0351:
0352:            /** 
0353:             * Returns the version number of this object.
0354:             *
0355:             * @return the version number of the object
0356:             * @throws DataAccessException if an error occurs while populating this object
0357:             */
0358:            public int getVersionNumber() throws DataAccessException {
0359:                if ((m_nVersionNumber == 0) && (m_bIsPopulated == false)) {
0360:                    try {
0361:                        populateFromDatabase();
0362:                    } catch (PopulateException e) {
0363:                        throw new DataAccessException(e.getLocalizedMessage());
0364:                    }
0365:                }
0366:
0367:                return m_nVersionNumber;
0368:            }
0369:
0370:            /** 
0371:             * Returns the version date of this object.
0372:             *
0373:             * @return the version date of this object
0374:             * @throws DataAccessException if an error occurs while populating this object
0375:             */
0376:            public java.util.Date getVersionDate() throws DataAccessException {
0377:                if ((m_dtVersionDate == null) && (m_bIsPopulated == false)) {
0378:                    try {
0379:                        populateFromDatabase();
0380:                    } catch (PopulateException e) {
0381:                        throw new DataAccessException(e.getLocalizedMessage());
0382:                    }
0383:                }
0384:
0385:                return m_dtVersionDate;
0386:            }
0387:
0388:            /**
0389:             * Returns the date this object was archived if this object is an 
0390:             * archived object, otherwise it will return a null.
0391:             * 
0392:             * @return the date this object was archived
0393:             * @throws DataAccessException if an error occurs while populating this object
0394:             */
0395:            public java.util.Date getHistoryDate() throws DataAccessException {
0396:                if ((m_dtHistDate == null) && (m_bIsPopulated == false)
0397:                        && isHistorical() == true) {
0398:                    try {
0399:                        populateFromDatabase();
0400:                    } catch (PopulateException e) {
0401:                        throw new DataAccessException(e.getLocalizedMessage());
0402:                    }
0403:                }
0404:
0405:                return m_dtHistDate;
0406:            }
0407:
0408:            /* (non-Javadoc)
0409:             * @see org.openharmonise.rm.resources.lifecycle.Editable#getStatus()
0410:             */
0411:            public Status getStatus() throws DataAccessException {
0412:                if ((m_status == Status.UNKNOWN) && (m_bIsPopulated == false)) {
0413:                    try {
0414:                        populateFromDatabase();
0415:                    } catch (PopulateException e) {
0416:                        throw new DataAccessException(e.getLocalizedMessage());
0417:                    }
0418:                }
0419:
0420:                return m_status;
0421:            }
0422:
0423:            /* (non-Javadoc)
0424:             * @see org.openharmonise.rm.resources.lifecycle.Editable#getLiveVersion()
0425:             */
0426:            public Editable getLiveVersion() throws DataAccessException {
0427:                if (m_bIsPopulated == false) {
0428:                    try {
0429:                        populateFromDatabase();
0430:                    } catch (PopulateException e) {
0431:                        throw new DataAccessException(e.getLocalizedMessage(),
0432:                                e);
0433:                    }
0434:                }
0435:
0436:                Editable liveVersion = null;
0437:
0438:                if (this .getStatus() == Status.APPROVED
0439:                        && isHistorical() == false) {
0440:                    liveVersion = this ;
0441:                } else if (m_nLiveId > NOTDBSAVED_ID) {
0442:                    if (isHistorical() == true) {
0443:                        m_nLiveId = m_nId;
0444:                    }
0445:                    try {
0446:                        liveVersion = (Editable) HarmoniseObjectFactory
0447:                                .instantiatePublishableObject(m_dsi, this 
0448:                                        .getClass().getName(), m_nLiveId);
0449:                    } catch (HarmoniseFactoryException e) {
0450:                        throw new DataAccessException(e.getLocalizedMessage());
0451:                    }
0452:
0453:                    //if this is historical there might not be a live version - lets check
0454:                    if (((AbstractEditableObject) liveVersion).exists() == false) {
0455:                        liveVersion = null;
0456:                    }
0457:                }
0458:
0459:                return (Editable) liveVersion;
0460:            }
0461:
0462:            /* (non-Javadoc)
0463:             * @see org.openharmonise.rm.resources.lifecycle.Editable#isLiveVersion()
0464:             */
0465:            public boolean isLiveVersion() throws DataAccessException {
0466:                if (m_bIsPopulated == false) {
0467:                    try {
0468:                        populateFromDatabase();
0469:                    } catch (PopulateException e) {
0470:                        throw new DataAccessException(e);
0471:                    }
0472:                }
0473:
0474:                return (m_status == Status.APPROVED && isHistorical() == false);
0475:            }
0476:
0477:            /**
0478:             * Returns <code>true</code> if this object is a pending version.
0479:             * 
0480:             * @return <code>true</code> if this object is a pending version
0481:             * @throws DataAccessException  if an error occurs while populating this object
0482:             */
0483:            public boolean isPendingVersion() throws DataAccessException {
0484:                return (isLiveVersion() == false && isHistorical() == false);
0485:            }
0486:
0487:            /* (non-Javadoc)
0488:             * @see org.openharmonise.rm.resources.lifecycle.Editable#isLocked()
0489:             */
0490:            public boolean isLocked() throws DataAccessException {
0491:                if ((m_nLockUserId == NOTDBSAVED_ID)
0492:                        && (m_bIsPopulated == false)) {
0493:                    try {
0494:                        populateFromDatabase();
0495:                    } catch (PopulateException e) {
0496:                        throw new DataAccessException(e.getLocalizedMessage(),
0497:                                e);
0498:                    }
0499:                }
0500:
0501:                boolean bIsLocked = false;
0502:
0503:                //as lock status is taken from the live version, if there is one
0504:                //we check the status of the live version
0505:                if (isLiveVersion() == true || getLiveVersion() == null) {
0506:                    bIsLocked = (this .m_nLockUserId != NOTDBSAVED_ID);
0507:
0508:                    try {
0509:                        //if there is a lock on this resource
0510:                        //verify that user still exists
0511:                        //otherwise reset lock info
0512:                        if (bIsLocked == true) {
0513:                            User lockUser = (User) HarmoniseObjectFactory
0514:                                    .instantiateHarmoniseObject(m_dsi,
0515:                                            User.class.getName(), m_nLockUserId);
0516:
0517:                            if (lockUser == null || lockUser.exists() == false) {
0518:
0519:                                UpdateStatement update = new UpdateStatement();
0520:                                update.addColumnValue(getInstanceColumnRef(
0521:                                        CLMN_LOCK_USER, false), null);
0522:                                update.addWhereCondition(getInstanceColumnRef(
0523:                                        ATTRIB_ID, false), "=", m_nId);
0524:
0525:                                m_dsi.executeUpdate(update);
0526:
0527:                                bIsLocked = false;
0528:                                m_nLockUserId = NOTDBSAVED_ID;
0529:                            }
0530:                        }
0531:                    } catch (HarmoniseFactoryException e) {
0532:                        throw new DataAccessException(e);
0533:                    } catch (DataStoreException e) {
0534:                        throw new DataAccessException(e);
0535:                    }
0536:                } else {
0537:                    bIsLocked = getLiveVersion().isLocked();
0538:                }
0539:
0540:                return bIsLocked;
0541:            }
0542:
0543:            /* (non-Javadoc)
0544:             * @see org.openharmonise.rm.resources.lifecycle.Editable#getLockOwner()
0545:             */
0546:            public User getLockOwner() throws DataAccessException {
0547:                User usr = null;
0548:
0549:                if (isLocked() == true) {
0550:
0551:                    if (isLiveVersion() == true || getLiveVersion() == null) {
0552:
0553:                        try {
0554:
0555:                            usr = (User) HarmoniseObjectFactory
0556:                                    .instantiateHarmoniseObject(m_dsi,
0557:                                            User.class.getName(), m_nLockUserId);
0558:                        } catch (HarmoniseFactoryException e) {
0559:                            throw new DataAccessException(e
0560:                                    .getLocalizedMessage());
0561:                        }
0562:                    } else {
0563:                        usr = getLiveVersion().getLockOwner();
0564:                    }
0565:                }
0566:
0567:                return usr;
0568:            }
0569:
0570:            /**
0571:             * Returns the user id for the lock on this object.
0572:             * @return the user id for the lock on this object
0573:             * @throws DataAccessException if an error occurs while populating this object
0574:             */
0575:            public int getLockUserId() throws DataAccessException {
0576:                if ((m_nLockUserId == NOTDBSAVED_ID)
0577:                        && (m_bIsPopulated == false)) {
0578:                    try {
0579:                        populateFromDatabase();
0580:                    } catch (PopulateException e) {
0581:                        throw new DataAccessException(e.getLocalizedMessage());
0582:                    }
0583:                }
0584:
0585:                return m_nLockUserId;
0586:            }
0587:
0588:            /* (non-Javadoc)
0589:             * @see org.openharmonise.rm.resources.lifecycle.Editable#getAllVersions()
0590:             */
0591:            public List getAllVersions() throws DataAccessException {
0592:                List versions = new Vector();
0593:
0594:                SelectStatement select = new SelectStatement();
0595:                ResultSet rs = null;
0596:                ColumnRef id_col = null;
0597:
0598:                AbstractEditableObject liveObj = (AbstractEditableObject) getLiveVersion();
0599:
0600:                if (liveObj != null) {
0601:                    versions.add(liveObj);
0602:                }
0603:
0604:                try {
0605:
0606:                    id_col = getInstanceColumnRef(ATTRIB_ID, true);
0607:
0608:                    // add the id column because we are going to need
0609:                    // it for historical versions of the object
0610:                    select.addSelectColumn(id_col);
0611:
0612:                    this .addColumnsToPopulateQuery(select, true);
0613:
0614:                    select.addWhereCondition(id_col, "=", m_nId);
0615:
0616:                    select.addOrderBy(getInstanceColumnRef(CLMN_VERSION_DATE,
0617:                            true), SelectStatement.ORDER_DESCENDING);
0618:                } catch (DataStoreException ds_e) {
0619:                    throw new DataAccessException(
0620:                            "There was a problem constructing the query", ds_e);
0621:                }
0622:
0623:                try {
0624:
0625:                    rs = m_dsi.execute(select);
0626:
0627:                    AbstractEditableObject nextObj = null;
0628:                    int col_id = -1;
0629:                    while (rs.next()) {
0630:
0631:                        int nIdCol = select.getResultSetIndex(id_col);
0632:
0633:                        col_id = rs.getInt(nIdCol);
0634:
0635:                        nextObj = (AbstractEditableObject) this .getClass()
0636:                                .newInstance();
0637:
0638:                        nextObj.setDataStoreInterface(m_dsi);
0639:                        nextObj.setId(col_id);
0640:                        nextObj.setHistorical(true);
0641:                        // this is an historical object
0642:
0643:                        nextObj.populateFromResultSetRow(rs, select);
0644:
0645:                        versions.add(nextObj);
0646:
0647:                    }
0648:                } catch (SQLException sql_e) {
0649:                    throw new DataAccessException(
0650:                            "There was a problem processing the query", sql_e);
0651:                } catch (DataStoreException ds_e) {
0652:                    throw new DataAccessException(
0653:                            "There was a problem processing the query", ds_e);
0654:                } catch (PopulateException pop_e) {
0655:                    throw new DataAccessException(
0656:                            "There was a problem populating the historical objects",
0657:                            pop_e);
0658:                } catch (IllegalAccessException ia_e) {
0659:                    throw new DataAccessException(
0660:                            "There was a problem constructing the new object",
0661:                            ia_e);
0662:                } catch (InstantiationException ins_e) {
0663:                    throw new DataAccessException(
0664:                            "There was a problem constructing the new object",
0665:                            ins_e);
0666:                } finally {
0667:                    if (rs != null) {
0668:                        try {
0669:
0670:                            rs.close();
0671:                        } catch (SQLException sql_e) {
0672:                            throw new DataAccessException(
0673:                                    "There was a problem closing the resultset",
0674:                                    sql_e);
0675:                        }
0676:                    }
0677:
0678:                    select.clear();
0679:                }
0680:
0681:                return versions;
0682:            }
0683:
0684:            /* (non-Javadoc)
0685:             * @see org.openharmonise.rm.resources.lifecycle.Editable#getHistoricalVersions()
0686:             */
0687:            public List getHistoricalVersions() throws DataAccessException {
0688:                List histories = new Vector();
0689:
0690:                SelectStatement select = new SelectStatement();
0691:                ResultSet rs = null;
0692:                ColumnRef id_col = null;
0693:                ColumnRef key_col = null;
0694:
0695:                try {
0696:
0697:                    id_col = getInstanceColumnRef(ATTRIB_ID, true);
0698:                    key_col = getInstanceColumnRef(ATTRIB_KEY, true);
0699:
0700:                    // add the id column because we are going to need
0701:                    // it for historical versions of the object
0702:                    select.addSelectColumn(id_col);
0703:                    select.addSelectColumn(key_col);
0704:
0705:                    this .addColumnsToPopulateQuery(select, true);
0706:
0707:                    select.addWhereCondition(id_col, "=", m_nId);
0708:
0709:                    if (isHistorical() == true) {
0710:                        select
0711:                                .addWhereCondition(getInstanceColumnRef(
0712:                                        CLMN_VERSION_DATE, true), "<",
0713:                                        getVersionDate());
0714:                    }
0715:
0716:                    select.addOrderBy(getInstanceColumnRef(CLMN_VERSION_DATE,
0717:                            true), SelectStatement.ORDER_DESCENDING);
0718:                } catch (DataStoreException ds_e) {
0719:                    throw new DataAccessException(
0720:                            "There was a problem constructing the query", ds_e);
0721:                }
0722:
0723:                try {
0724:
0725:                    rs = m_dsi.execute(select);
0726:
0727:                    AbstractEditableObject nextObj = null;
0728:                    boolean bAdd = false;
0729:                    int col_id = -1;
0730:                    while (rs.next()) {
0731:
0732:                        int nIdCol = select.getResultSetIndex(id_col);
0733:
0734:                        col_id = rs.getInt(nIdCol);
0735:                        int nKey = rs.getInt(select.getResultSetIndex(key_col));
0736:
0737:                        if (nextObj == null || nextObj.getKey() != nKey) {
0738:                            nextObj = (AbstractEditableObject) this .getClass()
0739:                                    .newInstance();
0740:                            nextObj.setDataStoreInterface(m_dsi);
0741:                            nextObj.setId(col_id);
0742:                            nextObj.setKey(nKey);
0743:                            nextObj.setHistorical(true);
0744:                            bAdd = true;
0745:                        }
0746:
0747:                        // this is an historical object
0748:
0749:                        nextObj.populateFromResultSetRow(rs, select);
0750:
0751:                        if (bAdd == true) {
0752:                            histories.add(nextObj);
0753:                            bAdd = false;
0754:                        }
0755:
0756:                    }
0757:                } catch (SQLException sql_e) {
0758:                    throw new DataAccessException(
0759:                            "There was a problem processing the query", sql_e);
0760:                } catch (DataStoreException ds_e) {
0761:                    throw new DataAccessException(
0762:                            "There was a problem processing the query", ds_e);
0763:                } catch (PopulateException pop_e) {
0764:                    throw new DataAccessException(
0765:                            "There was a problem populating the historical objects",
0766:                            pop_e);
0767:                } catch (IllegalAccessException ia_e) {
0768:                    throw new DataAccessException(
0769:                            "There was a problem constructing the new object",
0770:                            ia_e);
0771:                } catch (InstantiationException ins_e) {
0772:                    throw new DataAccessException(
0773:                            "There was a problem constructing the new object",
0774:                            ins_e);
0775:                } finally {
0776:                    if (rs != null) {
0777:                        try {
0778:
0779:                            rs.close();
0780:                        } catch (SQLException sql_e) {
0781:                            throw new DataAccessException(
0782:                                    "There was a problem closing the resultset:"
0783:                                            + sql_e.getLocalizedMessage());
0784:                        }
0785:                    }
0786:
0787:                    select.clear();
0788:                }
0789:
0790:                return histories;
0791:            }
0792:
0793:            /* (non-Javadoc)
0794:             * @see org.openharmonise.rm.resources.lifecycle.Editable#getPendingVersions()
0795:             */
0796:            public List getPendingVersions() throws DataAccessException {
0797:                List pends = new ArrayList();
0798:
0799:                if (m_pending == null) {
0800:
0801:                    ResultSet rs = null;
0802:                    SelectStatement select = new SelectStatement();
0803:
0804:                    try {
0805:
0806:                        select.addSelectColumn(getInstanceColumnRef(ATTRIB_ID,
0807:                                false));
0808:
0809:                        select.addWhereCondition(getInstanceColumnRef(
0810:                                TAG_LIVE_VERSION, false), "=", m_nId);
0811:
0812:                        select.addOrderBy(getInstanceColumnRef(
0813:                                CLMN_VERSION_DATE, false),
0814:                                SelectStatement.ORDER_DESCENDING);
0815:                    } catch (DataStoreException ds_e) {
0816:                        throw new DataAccessException(
0817:                                "A problem occured building the query", ds_e);
0818:                    }
0819:
0820:                    try {
0821:
0822:                        rs = m_dsi.execute(select);
0823:
0824:                        AbstractEditableObject nextObj = null;
0825:
0826:                        while (rs.next()) {
0827:                            nextObj = (AbstractEditableObject) HarmoniseObjectFactory
0828:                                    .instantiateHarmoniseObject(m_dsi,
0829:                                            getClass().getName(), rs.getInt(1));
0830:
0831:                            m_pending = CacheHandler.getInstance(m_dsi)
0832:                                    .getCachePointer(nextObj);
0833:
0834:                            pends.add(nextObj);
0835:
0836:                            nextObj.addEditEventListener(this );
0837:                        }
0838:                    } catch (SQLException sql_e) {
0839:                        throw new DataAccessException(
0840:                                "A problem occured processing the query", sql_e);
0841:                    } catch (DataStoreException ds_e) {
0842:                        throw new DataAccessException(
0843:                                "A problem occured processing the query", ds_e);
0844:                    } catch (HarmoniseFactoryException fact_e) {
0845:                        throw new DataAccessException(
0846:                                "A problem occured processing the query",
0847:                                fact_e);
0848:                    } catch (CacheException e) {
0849:                        throw new DataAccessException(e.getLocalizedMessage(),
0850:                                e);
0851:                    } finally {
0852:                        if (rs != null) {
0853:                            try {
0854:                                rs.close();
0855:                            } catch (SQLException sql_e) {
0856:                                throw new DataAccessException(
0857:                                        "A problem closing the resultset",
0858:                                        sql_e);
0859:                            }
0860:
0861:                        }
0862:                    }
0863:
0864:                } else {
0865:                    try {
0866:                        pends.add(m_pending.getObject());
0867:                    } catch (CacheException e) {
0868:                        throw new DataAccessException(e.getLocalizedMessage(),
0869:                                e);
0870:                    }
0871:                }
0872:
0873:                return pends;
0874:            }
0875:
0876:            /* (non-Javadoc)
0877:             * @see org.openharmonise.rm.resources.lifecycle.EditEventListener#workflowObjectArchived(org.openharmonise.rm.resources.lifecycle.EditEvent)
0878:             */
0879:            public void workflowObjectArchived(EditEvent event) {
0880:                Object obj = event.getSource();
0881:
0882:                try {
0883:                    if (m_pending != null && obj.equals(m_pending.getObject())) {
0884:                        m_pending = null;
0885:                    }
0886:                } catch (CacheException e) {
0887:                    m_logger.log(Level.WARNING, e.getLocalizedMessage(), e);
0888:                }
0889:            }
0890:
0891:            /* (non-Javadoc)
0892:             * @see org.openharmonise.rm.resources.lifecycle.Editable#changeStatus(org.openharmonise.rm.resources.lifecycle.Status)
0893:             */
0894:            public Editable changeStatus(Status status) throws EditException {
0895:                AbstractEditableObject result = this ;
0896:
0897:                if (m_logger.getLevel() == Level.INFO) {
0898:                    m_logger.logp(Level.INFO, this .getClass().getName(),
0899:                            "changeStatus", "Changing status of object (id - "
0900:                                    + m_nId + ", key - " + m_nObjectKey
0901:                                    + ") to " + status);
0902:
0903:                }
0904:
0905:                if (m_status == status) {
0906:                    //doing nothing if not a change in status
0907:                    return this ;
0908:                }
0909:
0910:                if ((m_status != Status.APPROVED)
0911:                        && (status != Status.APPROVED)) {
0912:                    // just a move through a multi stage approval process
0913:                    m_status = status;
0914:
0915:                    try {
0916:                        updateDBStatus();
0917:                    } catch (PopulateException e) {
0918:                        throw new EditException(
0919:                                "A problem occured updating DB:"
0920:                                        + e.getLocalizedMessage());
0921:                    }
0922:
0923:                } else if (m_status != Status.APPROVED
0924:                        && status == Status.APPROVED) {
0925:
0926:                    // archive the parent
0927:
0928:                    Editable live = null;
0929:
0930:                    try {
0931:                        live = getLiveVersion();
0932:                    } catch (DataAccessException e) {
0933:                        throw new EditException(
0934:                                "Had touble getting live version to archive");
0935:                    }
0936:
0937:                    if (live != null) {
0938:                        live.archive();
0939:                    }
0940:
0941:                    if (m_nLiveId > 0) {
0942:                        //take id from parent
0943:                        m_nId = m_nLiveId;
0944:                        m_nLiveId = -1;
0945:                    }
0946:
0947:                    try {
0948:                        // approving the object
0949:                        m_status = status;
0950:
0951:                        //	save status change
0952:                        updateDBStatus();
0953:
0954:                        HarmoniseIndexer.getInstance().indexObject(result);
0955:
0956:                    } catch (PopulateException pop_e) {
0957:                        throw new EditException(pop_e.getLocalizedMessage(),
0958:                                pop_e);
0959:                    } catch (HarmoniseIndexerException idx_e) {
0960:                        throw new EditException(idx_e.getLocalizedMessage(),
0961:                                idx_e);
0962:                    }
0963:                }
0964:
0965:                //notify listeners
0966:                EditEvent event = new EditEvent(this , result);
0967:
0968:                Iterator iter = m_editlisteners.iterator();
0969:
0970:                while (iter.hasNext()) {
0971:                    EditEventListener listener = (EditEventListener) iter
0972:                            .next();
0973:
0974:                    listener.workflowObjectStatusChanged(event);
0975:                }
0976:
0977:                return result;
0978:            }
0979:
0980:            /* (non-Javadoc)
0981:             * @see org.openharmonise.rm.publishing.Publishable#populate(org.w3c.dom.Element, org.openharmonise.rm.publishing.State)
0982:             */
0983:            public void populate(Element xmlElement, State state)
0984:                    throws PopulateException {
0985:                String sTagName = xmlElement.getTagName();
0986:                Text txt = null;
0987:
0988:                if (sTagName.equals(TAG_VERSION_COMMENT) == true) {
0989:                    txt = (Text) xmlElement.getFirstChild();
0990:                    setVersionComment(txt.getNodeValue());
0991:                } else if (sTagName.equals(TAG_DISPLAY_NAME)) {
0992:                    txt = (Text) xmlElement.getFirstChild();
0993:                    if (txt != null) {
0994:                        setDisplayName(txt.getNodeValue());
0995:                    }
0996:                } else {
0997:                    super .populate(xmlElement, state);
0998:                }
0999:            }
1000:
1001:            /* (non-Javadoc)
1002:             * @see org.openharmonise.rm.publishing.Publishable#publish(org.w3c.dom.Element, org.openharmonise.rm.publishing.HarmoniseOutput, org.openharmonise.rm.publishing.State)
1003:             */
1004:            public Element publish(Element topEl, HarmoniseOutput xmlDoc,
1005:                    State state) throws PublishException {
1006:                String sTagName = topEl.getTagName();
1007:                Element docEl = null;
1008:                Text txt = null;
1009:
1010:                try {
1011:
1012:                    if (sTagName.equals(TAG_VERSION_COMMENT)) {
1013:                        docEl = xmlDoc.createElement(TAG_VERSION_COMMENT);
1014:                        txt = xmlDoc.createTextNode(getVersionComment());
1015:                        docEl.appendChild(txt);
1016:                    } else if (sTagName.equals(TAG_DISPLAY_NAME)) {
1017:                        docEl = xmlDoc.createElement(sTagName);
1018:                        txt = xmlDoc.createTextNode(getDisplayName());
1019:                        docEl.appendChild(txt);
1020:                        xmlDoc.copyChildren(docEl, topEl, new Vector());
1021:                    } else if (sTagName.equals(TAG_VERSION)) {
1022:                        docEl = xmlDoc.createElement(TAG_VERSION);
1023:                        txt = xmlDoc.createTextNode(Integer
1024:                                .toString(getVersionNumber()));
1025:
1026:                        docEl.appendChild(txt);
1027:
1028:                    } else if (sTagName.equals(TAG_VERSION_DATE)) {
1029:                        docEl = xmlDoc.createElement(TAG_VERSION_DATE);
1030:                        txt = xmlDoc
1031:                                .createTextNode(getVersionDate().toString());
1032:
1033:                        docEl.appendChild(txt);
1034:
1035:                    } else if (sTagName.equals(TAG_HISTORY_DATE)) {
1036:                        docEl = xmlDoc.createElement(TAG_HISTORY_DATE);
1037:                        txt = xmlDoc
1038:                                .createTextNode(getHistoryDate().toString());
1039:
1040:                        docEl.appendChild(txt);
1041:
1042:                    } else if (sTagName.equals(TAG_LOCKED)) {
1043:                        docEl = xmlDoc.createElement(TAG_LOCKED);
1044:
1045:                        if (isLocked()) {
1046:                            docEl.setAttribute(ATTRIB_IS_LOCKED, "true");
1047:
1048:                            NodeList childnodes = topEl.getChildNodes();
1049:
1050:                            for (int i = 0; i < childnodes.getLength(); i++) {
1051:                                Node child = childnodes.item(i);
1052:
1053:                                if ((child.getNodeType() == Node.ELEMENT_NODE)
1054:                                        && child.getNodeName().equals(
1055:                                                Template.TAG_TEMPLATE)) {
1056:                                    Template templ = null;
1057:                                    try {
1058:                                        templ = (Template) HarmoniseObjectFactory
1059:                                                .instantiateHarmoniseObject(
1060:                                                        m_dsi,
1061:                                                        Template.class
1062:                                                                .getName(),
1063:                                                        Integer
1064:                                                                .parseInt(((Element) child)
1065:                                                                        .getAttribute(ATTRIB_ID)));
1066:                                    } catch (NumberFormatException e) {
1067:                                        throw new PublishException(e);
1068:                                    } catch (HarmoniseFactoryException e) {
1069:                                        throw new PublishException(e);
1070:                                    }
1071:
1072:                                    Element templRoot = templ
1073:                                            .getTemplateRootElement();
1074:
1075:                                    if (templRoot.getNodeName().equals(
1076:                                            User.TAG_USER) == false) {
1077:                                        throw new InvalidXMLElementException(
1078:                                                "User tag needed");
1079:                                    }
1080:
1081:                                    int lockId = this .getLockUserId();
1082:                                    User lockUser = (User) HarmoniseObjectFactory
1083:                                            .instantiateHarmoniseObject(m_dsi,
1084:                                                    User.class.getName(),
1085:                                                    lockId);
1086:                                    Element tempEl = lockUser.publish(
1087:                                            templRoot, xmlDoc, state);
1088:
1089:                                    if (tempEl != null) {
1090:                                        docEl.appendChild(tempEl);
1091:                                    }
1092:                                }
1093:                            }
1094:                        } else {
1095:                            docEl.setAttribute(ATTRIB_IS_LOCKED, "false");
1096:                        }
1097:                    } else if (sTagName.equals(TAG_STATUS)) {
1098:                        docEl = xmlDoc.createElement(TAG_STATUS);
1099:
1100:                        txt = xmlDoc.createTextNode(m_status.getStringValue());
1101:
1102:                        docEl.appendChild(txt);
1103:                    } else if (sTagName.equals(TAG_LIVE_VERSION)) {
1104:                        docEl = xmlDoc.createElement(TAG_LIVE_VERSION);
1105:
1106:                        AbstractEditableObject eObj = (AbstractEditableObject) getLiveVersion();
1107:
1108:                        if (eObj != null) {
1109:                            List nodes = XMLUtils.getChildrenByName(topEl,
1110:                                    Template.TAG_TEMPLATE);
1111:
1112:                            if (nodes.size() > 0) {
1113:                                Element templateEl = (Element) nodes.get(0);
1114:
1115:                                Template template = (Template) HarmoniseObjectFactory
1116:                                        .instantiateHarmoniseObject(m_dsi,
1117:                                                templateEl, state);
1118:
1119:                                docEl = eObj.publish(template, xmlDoc, state);
1120:
1121:                            } else {
1122:                                Element objEl = xmlDoc
1123:                                        .createElement(getTagName());
1124:                                objEl.setAttribute(ATTRIB_ID, String
1125:                                        .valueOf(eObj.getId()));
1126:                                docEl.appendChild(objEl);
1127:                            }
1128:                        }
1129:
1130:                    } else {
1131:                        docEl = super .publish(topEl, xmlDoc, state);
1132:                    }
1133:
1134:                } catch (PublishException pub_e) {
1135:                    throw pub_e;
1136:                } catch (DataAccessException da_e) {
1137:                    throw new PublishException(da_e);
1138:                } catch (Exception ex) {
1139:                    throw new PublishException(ex);
1140:                }
1141:
1142:                return docEl;
1143:            }
1144:
1145:            /* (non-Javadoc)
1146:             * @see org.openharmonise.rm.resources.lifecycle.Editable#reactivate()
1147:             */
1148:            public Editable reactivate() throws EditException {
1149:                Editable result = null;
1150:
1151:                if (m_logger.isLoggable(Level.INFO)) {
1152:                    m_logger.logp(Level.INFO, this .getClass().getName(),
1153:                            "reactivate", "Reactivating object, id - " + m_nId
1154:                                    + ", key - " + m_nObjectKey);
1155:                }
1156:
1157:                if (!this .isHistorical()) {
1158:                    if (m_logger.isLoggable(Level.INFO)) {
1159:                        m_logger.log(Level.INFO,
1160:                                "Can't reactivate - non-historical version");
1161:                    }
1162:                    throw new EditException(
1163:                            "can't reactivate non-historical version");
1164:                }
1165:
1166:                try {
1167:                    fullPopulate();
1168:                } catch (PopulateException e) {
1169:                    throw new EditException(e);
1170:                }
1171:
1172:                setHistorical(false);
1173:
1174:                //try to find it's live version
1175:                m_nLiveId = m_nId;
1176:                AbstractEditableObject live = null;
1177:
1178:                try {
1179:
1180:                    live = (AbstractEditableObject) CacheHandler.getInstance(
1181:                            m_dsi).getObject(this .getClass().getName(),
1182:                            m_nLiveId);
1183:                } catch (CacheException cache_ex) {
1184:                    throw new EditException(
1185:                            "Problem getting current version from cache",
1186:                            cache_ex);
1187:                }
1188:
1189:                //set to be a new object
1190:                try {
1191:                    markAsNew();
1192:                } catch (PopulateException e) {
1193:                    throw new EditException("PopulateException", e);
1194:                }
1195:
1196:                //ensure other stuff is set appropriately
1197:                if (live != null && live.exists() == true) {
1198:                    try {
1199:
1200:                        m_nVersionNumber = live.getVersionNumber();
1201:                    } catch (DataAccessException da_e) {
1202:                        throw new EditException(
1203:                                "Problem occurred accessing data from current version",
1204:                                da_e);
1205:                    }
1206:                }
1207:
1208:                // save this version
1209:                result = ((Editable) this ).save();
1210:
1211:                //	notify listeners
1212:                EditEvent event = new EditEvent(this , result);
1213:
1214:                Iterator iter = m_editlisteners.iterator();
1215:
1216:                while (iter.hasNext()) {
1217:                    EditEventListener listener = (EditEventListener) iter
1218:                            .next();
1219:
1220:                    listener.workflowObjectReactivated(event);
1221:                }
1222:
1223:                return result;
1224:            }
1225:
1226:            /* (non-Javadoc)
1227:             * @see org.openharmonise.rm.resources.lifecycle.Editable#lock(org.openharmonise.rm.resources.users.User)
1228:             */
1229:            public synchronized void lock(User usr) throws EditException {
1230:                int nUserId = usr.getId();
1231:
1232:                if (m_bIsPopulated == false) {
1233:                    try {
1234:                        populateFromDatabase();
1235:                    } catch (PopulateException e) {
1236:                        throw new EditException(e.getLocalizedMessage());
1237:                    }
1238:                }
1239:
1240:                if (m_logger.isLoggable(Level.INFO)) {
1241:                    m_logger.logp(Level.INFO, this .getClass().getName(),
1242:                            "lock", "User " + nUserId
1243:                                    + " locking object, id - " + m_nId
1244:                                    + ", key - " + m_nObjectKey);
1245:                }
1246:
1247:                if ((m_nLockUserId > 0) && (m_nLockUserId != nUserId)) {
1248:                    if (m_logger.isLoggable(Level.INFO)) {
1249:                        m_logger.log(Level.INFO,
1250:                                "unable to lock object - invalid user");
1251:
1252:                    }
1253:                    throw new InvalidLockOwnerException(
1254:                            "This object is locked by another user");
1255:                } else {
1256:                    try {
1257:
1258:                        m_nLockUserId = nUserId;
1259:
1260:                        // as lock status is taken from the live version, if there is one
1261:                        //we lock the live version
1262:                        if (isLiveVersion() == true
1263:                                || this .getLiveVersion() == null) {
1264:
1265:                            UpdateStatement update = new UpdateStatement();
1266:                            update.addColumnValue(getInstanceColumnRef(
1267:                                    CLMN_LOCK_USER, false), m_nLockUserId);
1268:                            update.addWhereCondition(getInstanceColumnRef(
1269:                                    ATTRIB_ID, false), "=", m_nId);
1270:
1271:                            m_dsi.executeUpdate(update);
1272:
1273:                        } else {
1274:                            Editable live = getLiveVersion();
1275:
1276:                            live.lock(usr);
1277:                        }
1278:
1279:                    } catch (DataStoreException ds_e) {
1280:                        throw new EditException(ds_e.getLocalizedMessage());
1281:                    } catch (DataAccessException da_e) {
1282:                        throw new EditException(da_e.getLocalizedMessage());
1283:                    }
1284:
1285:                    // notify listeners
1286:                    EditEvent event = new EditEvent(this );
1287:
1288:                    Iterator iter = m_editlisteners.iterator();
1289:
1290:                    while (iter.hasNext()) {
1291:                        EditEventListener listener = (EditEventListener) iter
1292:                                .next();
1293:
1294:                        listener.workflowObjectLocked(event);
1295:                    }
1296:                }
1297:            }
1298:
1299:            /* (non-Javadoc)
1300:             * @see org.openharmonise.rm.resources.lifecycle.Editable#unlock(org.openharmonise.rm.resources.users.User)
1301:             */
1302:            public void unlock(User usr) throws EditException {
1303:
1304:                boolean bCanUnlock = true;
1305:                try {
1306:                    bCanUnlock = (getLockOwner().equals(usr) == true || AuthorizationValidator
1307:                            .isSuperUser(usr) == true);
1308:                } catch (DataAccessException e) {
1309:                    throw new EditException(
1310:                            "Error occured accessing lock owner", e);
1311:                } catch (AuthorizationException e) {
1312:                    throw new EditException(
1313:                            "Error occured testing super user status", e);
1314:                }
1315:
1316:                if (bCanUnlock == true) {
1317:                    boolean bIsLocked = false;
1318:
1319:                    if (m_logger.isLoggable(Level.INFO)) {
1320:                        m_logger.logp(Level.INFO, this .getClass().getName(),
1321:                                "unlock", "User " + usr.getId()
1322:                                        + "unlocking object, id - " + m_nId
1323:                                        + ", key - " + m_nObjectKey);
1324:                    }
1325:
1326:                    try {
1327:                        bIsLocked = isLocked();
1328:                    } catch (DataAccessException da_e) {
1329:                        throw new EditException(
1330:                                "Problem occurred accessing lock info", da_e);
1331:                    }
1332:
1333:                    if (bIsLocked == true) {
1334:
1335:                        try {
1336:                            // as lock status is taken from the live version, if there is one
1337:                            //we unlock the live version
1338:                            if (isLiveVersion() == true
1339:                                    || getLiveVersion() == null) {
1340:
1341:                                try {
1342:
1343:                                    UpdateStatement update = new UpdateStatement();
1344:                                    update.addColumnValue(getInstanceColumnRef(
1345:                                            CLMN_LOCK_USER, false), null);
1346:                                    update.addWhereCondition(
1347:                                            getInstanceColumnRef(ATTRIB_ID,
1348:                                                    false), "=", m_nId);
1349:
1350:                                    m_dsi.executeUpdate(update);
1351:                                } catch (DataStoreException ds_e) {
1352:                                    throw new EditException(
1353:                                            "Problem occurred updating lock info",
1354:                                            ds_e);
1355:                                }
1356:                            } else {
1357:                                getLiveVersion().unlock(usr);
1358:                            }
1359:
1360:                            m_nLockUserId = 0;
1361:                        } catch (DataAccessException e) {
1362:                            throw new EditException("DA problem unlocking", e);
1363:                        }
1364:
1365:                        // notify listeners
1366:                        EditEvent event = new EditEvent(this );
1367:
1368:                        Iterator iter = m_editlisteners.iterator();
1369:
1370:                        while (iter.hasNext()) {
1371:                            EditEventListener listener = (EditEventListener) iter
1372:                                    .next();
1373:
1374:                            listener.workflowObjectUnlocked(event);
1375:                        }
1376:                    }
1377:
1378:                } else {
1379:                    if (m_logger.isLoggable(Level.INFO)) {
1380:                        m_logger.log(Level.INFO,
1381:                                "Unable to unlock object - invalid user");
1382:
1383:                    }
1384:                    throw new InvalidLockOwnerException(
1385:                            "User not authorised to unlock");
1386:                }
1387:            }
1388:
1389:            /* (non-Javadoc)
1390:             * @see org.openharmonise.rm.resources.AbstractObject#getColumnRef(java.lang.String, java.lang.String, boolean)
1391:             */
1392:            public static ColumnRef getColumnRef(String sClassname,
1393:                    String sColumn, boolean bHist) throws DataStoreException {
1394:                ColumnRef returnColRef = null;
1395:                String sTable = getTableName(sClassname, bHist);
1396:
1397:                return AbstractEditableObject.getObjectColumnRef(sTable,
1398:                        sColumn);
1399:            }
1400:
1401:            /* (non-Javadoc)
1402:             * @see org.openharmonise.rm.dsi.DataStoreObject#getInstanceColumnRef(java.lang.String, boolean)
1403:             */
1404:            public ColumnRef getInstanceColumnRef(String sColumn,
1405:                    boolean bIsHist) throws DataStoreException {
1406:                String sDBTable = getTableName(bIsHist);
1407:
1408:                return getObjectColumnRef(sDBTable, sColumn);
1409:            }
1410:
1411:            /* (non-Javadoc)
1412:             * @see org.openharmonise.rm.resources.AbstractObject#getObjectColumnRef(java.lang.String, java.lang.String)
1413:             */
1414:            public static ColumnRef getObjectColumnRef(String sTable,
1415:                    String sColumn) throws DataStoreException {
1416:                ColumnRef returnColRef = null;
1417:
1418:                if (sColumn.equals(TAG_VERSION) == true
1419:                        || sColumn.equals(CLMN_VERSION_NUMBER) == true) {
1420:                    returnColRef = new ColumnRef(sTable, CLMN_VERSION_NUMBER,
1421:                            ColumnRef.NUMBER);
1422:                } else if (sColumn.equals(TAG_DISPLAY_NAME) == true
1423:                        || sColumn.equals(CLMN_DISPLAY_NAME) == true) {
1424:                    returnColRef = new ColumnRef(sTable, CLMN_DISPLAY_NAME,
1425:                            ColumnRef.TEXT);
1426:                } else if (sColumn.equals(TAG_VERSION_COMMENT) == true
1427:                        || sColumn.equals(CLMN_VERSION_COMMENT) == true) {
1428:                    returnColRef = new ColumnRef(sTable, CLMN_VERSION_COMMENT,
1429:                            ColumnRef.TEXT);
1430:                } else if (sColumn.equals(TAG_LIVE_VERSION) == true
1431:                        || sColumn.equals(CLMN_LIVE_ID) == true) {
1432:                    returnColRef = new ColumnRef(sTable, CLMN_LIVE_ID,
1433:                            ColumnRef.NUMBER);
1434:                } else if (sColumn.equals(TAG_STATUS) == true
1435:                        || sColumn.equals(CLMN_STATUS) == true) {
1436:                    returnColRef = new ColumnRef(sTable, CLMN_STATUS,
1437:                            ColumnRef.NUMBER);
1438:                } else if (sColumn.equals(TAG_VERSION_DATE) == true
1439:                        || sColumn.equals(CLMN_VERSION_DATE) == true) {
1440:                    returnColRef = new ColumnRef(sTable, CLMN_VERSION_DATE,
1441:                            ColumnRef.DATE);
1442:                } else if (sColumn.equals(CLMN_HISTORY_DATE)) {
1443:                    returnColRef = new ColumnRef(sTable, CLMN_HISTORY_DATE,
1444:                            ColumnRef.DATE);
1445:                } else if (sColumn.equals(CLMN_LOCK_USER)) {
1446:                    returnColRef = new ColumnRef(sTable, CLMN_LOCK_USER,
1447:                            ColumnRef.NUMBER);
1448:                }
1449:
1450:                if (returnColRef != null) {
1451:                    return returnColRef;
1452:                } else {
1453:                    return AbstractObject.getObjectColumnRef(sTable, sColumn);
1454:                }
1455:            }
1456:
1457:            /* (non-Javadoc)
1458:             * @see java.lang.Object#clone()
1459:             */
1460:            public Object clone() {
1461:                AbstractEditableObject other = null;
1462:                try {
1463:
1464:                    if (!m_bIsPopulated) {
1465:                        populateFromDatabase();
1466:                    }
1467:
1468:                    other = (AbstractEditableObject) super .clone();
1469:
1470:                    if (this .getVersionDate() != null) {
1471:                        other.setVersionDate((java.util.Date) getVersionDate()
1472:                                .clone());
1473:                    }
1474:
1475:                } catch (DataAccessException e) {
1476:                    m_logger.log(Level.WARNING, e.getLocalizedMessage(), e);
1477:                } catch (PopulateException e) {
1478:                    m_logger.log(Level.WARNING, e.getLocalizedMessage(), e);
1479:                }
1480:
1481:                return other;
1482:
1483:            }
1484:
1485:            /* (non-Javadoc)
1486:             * @see org.openharmonise.rm.resources.AbstractObject#clear()
1487:             */
1488:            public void clear() {
1489:                m_nVersionNumber = 0;
1490:                m_sVersionComment = "";
1491:                m_sDisplayName = "";
1492:                m_dtVersionDate = null;
1493:                m_status = Status.UNKNOWN;
1494:                m_nLockUserId = NOTDBSAVED_ID;
1495:                m_nLiveId = NOTDBSAVED_ID;
1496:
1497:                super .clear();
1498:            }
1499:
1500:            /* (non-Javadoc)
1501:             * @see org.openharmonise.rm.resources.lifecycle.Editable#archive()
1502:             */
1503:            public Editable archive() throws EditException {
1504:                AbstractEditableObject newObj = null;
1505:
1506:                if (m_logger.isLoggable(Level.INFO)) {
1507:                    m_logger.logp(Level.INFO, this .getClass().getName(),
1508:                            "archive", "Archiving object (id - " + m_nId
1509:                                    + ", key - " + m_nObjectKey + ")");
1510:
1511:                }
1512:
1513:                //clear the cached pending
1514:                m_pending = null;
1515:
1516:                try {
1517:                    fullPopulate();
1518:
1519:                    //if it's a live version we'll archive it
1520:                    //otherwise it'll just be a delete
1521:                    if (isLiveVersion() == true) {
1522:
1523:                        // create a historical version of this Document, then save it
1524:                        newObj = (AbstractEditableObject) clone();
1525:                        try {
1526:                            newObj.markAsNew();
1527:                        } catch (PopulateException e) {
1528:                            throw new EditException(
1529:                                    "Problem occurring marking object as new: ",
1530:                                    e);
1531:                        }
1532:                        newObj.setLiveVersion(this );
1533:                        newObj.setHistorical(true);
1534:                        newObj.save();
1535:                    }
1536:                } catch (PopulateException e) {
1537:                    throw new EditException(e.getLocalizedMessage(), e);
1538:                } catch (DataAccessException e) {
1539:                    throw new EditException(e.getLocalizedMessage(), e);
1540:                }
1541:
1542:                // notify listeners before complete deletion so that listeners
1543:                // that maybe removed during deletion know about the archive event
1544:                EditEvent event = new EditEvent(this );
1545:                event.setResult(newObj);
1546:
1547:                Iterator iter = new ArrayList(m_editlisteners).iterator();
1548:
1549:                while (iter.hasNext()) {
1550:                    EditEventListener listener = (EditEventListener) iter
1551:                            .next();
1552:
1553:                    listener.workflowObjectArchived(event);
1554:                }
1555:
1556:                try {
1557:                    HarmoniseIndexer.getInstance().deleteFromIndex(this );
1558:                    // now delete the original Document (without deleting history!!)
1559:                    delete(false);
1560:                } catch (DataStoreException ds_e) {
1561:                    throw new EditException(
1562:                            "Problem ocurred deleting object from datastore",
1563:                            ds_e);
1564:                } catch (PopulateException pop_e) {
1565:                    throw new EditException(pop_e.getLocalizedMessage(), pop_e);
1566:                } catch (DataAccessException da_e) {
1567:                    throw new EditException(da_e.getLocalizedMessage(), da_e);
1568:                } catch (HarmoniseIndexerException e) {
1569:                    throw new EditException(e);
1570:                }
1571:
1572:                return (Editable) newObj;
1573:            }
1574:
1575:            /**
1576:             * Acquire a lock on child addition and removal
1577:             * 
1578:             * Note: this method provides a mechanism for external
1579:             * classes to implement locking on the management of 
1580:             * children but does NOT guarantee that other threads
1581:             * cannot manipulate the children of the collection
1582:             * 
1583:             * @throws EditException
1584:             */
1585:            public void acquireEditWriteLock() throws EditException {
1586:                try {
1587:                    m_edit_lock.writeLock().acquire();
1588:
1589:                    m_lockThread = Thread.currentThread();
1590:
1591:                } catch (InterruptedException e) {
1592:                    throw new EditException(e);
1593:                }
1594:            }
1595:
1596:            /**
1597:             * Release lock on child additions and removals
1598:             *
1599:             */
1600:            public void releaseEditWriteLock() {
1601:                m_edit_lock.writeLock().release();
1602:                m_lockThread = null;
1603:            }
1604:
1605:            /* (non-Javadoc)
1606:             * @see org.openharmonise.rm.resources.lifecycle.Editable#save()
1607:             */
1608:            public Editable save() throws EditException {
1609:
1610:                if (isLockThread() == false) {
1611:                    throw new EditException(
1612:                            "This object is locked by another thread");
1613:                }
1614:
1615:                Editable result = this ;
1616:                boolean bNotifyListeners = true;
1617:
1618:                // ensure we have a full copy
1619:                if (isPopulated() == false) {
1620:                    try {
1621:
1622:                        this .populateFromDatabase();
1623:                    } catch (PopulateException pop_e) {
1624:                        throw new EditException(
1625:                                "Problem occured populating object for save",
1626:                                pop_e);
1627:                    }
1628:                }
1629:
1630:                if (m_nId == NOTDBSAVED_ID) {
1631:
1632:                    if (m_logger.isLoggable(Level.INFO)) {
1633:                        try {
1634:                            m_logger.logp(Level.INFO,
1635:                                    this .getClass().getName(), "save",
1636:                                    "saving new version of " + getName());
1637:                        } catch (DataAccessException e) {
1638:                            m_logger.log(Level.WARNING,
1639:                                    e.getLocalizedMessage(), e);
1640:                        }
1641:                    }
1642:
1643:                    String sTable = getDBTableName();
1644:                    boolean bIsHist = isHistorical();
1645:
1646:                    try {
1647:
1648:                        InsertStatement insert = new InsertStatement();
1649:
1650:                        // For historical documents, the id is the history_id (as it is unique)
1651:                        // and the parent is stored in the id column, as it is the persistant id
1652:                        if (bIsHist == false) {
1653:                            m_nId = m_dsi
1654:                                    .getSequenceNextValue(PRE_SEQ + sTable);
1655:                            m_nObjectKey = m_dsi.getSequenceNextValue(PRE_SEQ
1656:                                    + sTable + EXT_KEY);
1657:                            // increment version number
1658:                            m_nVersionNumber++;
1659:                        } else {
1660:                            sTable = getHistoricalDBTableName();
1661:                            m_nId = m_nLiveId;
1662:                            m_nLiveId = NOTDBSAVED_ID;
1663:                        }
1664:
1665:                        m_status = Status.UNAPPROVED;
1666:
1667:                        insert.setTable(sTable);
1668:
1669:                        addDataToSave(insert);
1670:
1671:                        m_dsi.execute(insert);
1672:
1673:                        saveCoreData();
1674:
1675:                    } catch (DataStoreException ds_e) {
1676:                        throw new EditException(
1677:                                "A problem occurred saving data to DB", ds_e);
1678:                    } catch (SQLException sql_e) {
1679:                        throw new EditException(
1680:                                "A problem occurred saving data to DB", sql_e);
1681:                    }
1682:
1683:                    m_bIsChanged = false;
1684:                    m_bIsPopulated = true;
1685:                    result = (Editable) this ;
1686:                    // cache new object
1687:                    try {
1688:                        CacheHandler.getInstance(m_dsi).addToCache(this );
1689:                    } catch (CacheException e) {
1690:                        // assume the object hasn't been cached but we don't want
1691:                        // to break execution just cause there's been a problem 
1692:                        // caching the object. do we?
1693:                        m_logger.log(Level.WARNING, e.getLocalizedMessage(), e);
1694:                    }
1695:
1696:                } else {
1697:                    try {
1698:
1699:                        if (isChanged() == true && isLiveVersion() == true) {
1700:                            // create a new object and save it
1701:                            AbstractEditableObject objNew = (AbstractEditableObject) this 
1702:                                    .clone();
1703:                            try {
1704:                                objNew.markAsNew();
1705:                            } catch (PopulateException e) {
1706:                                throw new EditException(
1707:                                        "Problem occurring marking object as new: ",
1708:                                        e);
1709:                            }
1710:
1711:                            objNew.setLiveVersion(this );
1712:                            objNew.save();
1713:
1714:                            // delete any changes made to this object that are for the new object
1715:                            clear();
1716:
1717:                            result = (Editable) objNew;
1718:                        } else if (isChanged() == true
1719:                                && isLiveVersion() == false) {
1720:                            update();
1721:
1722:                        } else {
1723:                            // nothing's changed so nothing to do
1724:                            bNotifyListeners = false;
1725:                        }
1726:                    } catch (EditException ed_e) {
1727:                        throw ed_e;
1728:                    } catch (DataAccessException da_e) {
1729:                        throw new EditException(
1730:                                "Problem accessing data on object", da_e);
1731:                    } catch (DataStoreException ds_e) {
1732:                        throw new EditException("Problem updating object", ds_e);
1733:                    }
1734:                }
1735:
1736:                saveNonCoreData();
1737:
1738:                if (bNotifyListeners == true) {
1739:                    // notify listeners
1740:                    EditEvent event = new EditEvent(this , result);
1741:
1742:                    Iterator iter = m_editlisteners.iterator();
1743:
1744:                    while (iter.hasNext()) {
1745:                        EditEventListener listener = (EditEventListener) iter
1746:                                .next();
1747:
1748:                        listener.workflowObjectSaved(event);
1749:                    }
1750:                }
1751:
1752:                return result;
1753:            }
1754:
1755:            /**
1756:             * Returns <code>true</code> if a write lock has been acquired on
1757:             * this object and the current thread acquired that lock, or there
1758:             * is no write lock currently acquired.
1759:             * 
1760:             * @return <code>true</code> if a write lock has been acquired on
1761:             * this object and the current thread acquired that lock, or there
1762:             * is no write lock currently acquired.
1763:             */
1764:            protected boolean isLockThread() {
1765:                return m_lockThread == null
1766:                        || m_lockThread == Thread.currentThread();
1767:            }
1768:
1769:            /* (non-Javadoc)
1770:             * @see org.openharmonise.rm.resources.lifecycle.Editable#createNewVersion()
1771:             */
1772:            public Editable createNewVersion() throws EditException {
1773:                AbstractEditableObject newVersion = this ;
1774:
1775:                try {
1776:                    if (isLiveVersion() == true) {
1777:                        //check there is no pending versions already
1778:                        if (getPendingVersions().size() > 0) {
1779:                            if (m_logger.isLoggable(Level.WARNING)) {
1780:                                m_logger.logp(Level.WARNING, this .getClass()
1781:                                        .getName(), "createNewVersion",
1782:                                        "Can't create new version as pending exists, id - "
1783:                                                + m_nId + ", key - "
1784:                                                + m_nObjectKey);
1785:
1786:                            }
1787:                            throw new EditException(
1788:                                    "Can't create new version, there is already an existing pending version");
1789:                        }
1790:
1791:                        if (m_logger.isLoggable(Level.INFO)) {
1792:                            m_logger.logp(Level.INFO,
1793:                                    this .getClass().getName(),
1794:                                    "createNewVersion",
1795:                                    "Creating new version, id - " + m_nId
1796:                                            + ", key - " + m_nObjectKey);
1797:
1798:                        }
1799:
1800:                        newVersion = (AbstractEditableObject) this .clone();
1801:
1802:                        newVersion.markAsNew();
1803:
1804:                        newVersion.setLiveVersion(this );
1805:                        newVersion.save();
1806:                    } else {
1807:                        if (m_logger.isLoggable(Level.INFO)) {
1808:                            m_logger
1809:                                    .logp(Level.INFO,
1810:                                            this .getClass().getName(),
1811:                                            "createNewVersion",
1812:                                            "Can't create new version as object is not live, id - "
1813:                                                    + m_nId + ", key - "
1814:                                                    + m_nObjectKey);
1815:
1816:                        }
1817:                    }
1818:                } catch (DataAccessException e) {
1819:                    throw new EditException("Data access error", e);
1820:                } catch (PopulateException e) {
1821:                    throw new EditException("Population error", e);
1822:                }
1823:
1824:                return newVersion;
1825:            }
1826:
1827:            /* (non-Javadoc)
1828:             * @see org.openharmonise.rm.resources.lifecycle.Editable#addEditEventListener(org.openharmonise.rm.resources.lifecycle.EditEventListener)
1829:             */
1830:            public void addEditEventListener(EditEventListener listener) {
1831:                if (m_editlisteners.contains(listener) == false
1832:                        && listener != this ) {
1833:                    m_editlisteners.add(listener);
1834:                }
1835:            }
1836:
1837:            /* (non-Javadoc)
1838:             * @see org.openharmonise.rm.resources.lifecycle.Editable#removeEditEventListener(org.openharmonise.rm.resources.lifecycle.EditEventListener)
1839:             */
1840:            public void removeEditEventListener(EditEventListener listener) {
1841:                m_editlisteners.remove(listener);
1842:            }
1843:
1844:            /*----------------------------------------------------------------------------
1845:            Protected Methods
1846:            -----------------------------------------------------------------------------*/
1847:
1848:            /**
1849:             * Save data external to the main object DB table yet part of 
1850:             * it's core data to the database.
1851:             * 
1852:             * @throws EditException if an error occurs
1853:             */
1854:            protected abstract void saveCoreData() throws EditException;
1855:
1856:            /**
1857:             * Saves data external to the main object DB table and not part of
1858:             * it's core data gets saved to the database.
1859:             * 
1860:             * @throws EditException if an error occurs
1861:             */
1862:            protected abstract void saveNonCoreData() throws EditException;
1863:
1864:            /* (non-Javadoc)
1865:             * @see org.openharmonise.rm.resources.AbstractObject#addColumnsToPopulateQuery(org.openharmonise.commons.dsi.dml.SelectStatement, boolean)
1866:             */
1867:            protected void addColumnsToPopulateQuery(SelectStatement select,
1868:                    boolean bIsHist) throws DataStoreException {
1869:
1870:                try {
1871:                    ColumnRefCache cache = ColumnRefCache.getInstance();
1872:
1873:                    select.addSelectColumn(cache.getColumnRef(this ,
1874:                            TAG_DISPLAY_NAME, bIsHist));
1875:
1876:                    select.addSelectColumn(cache.getColumnRef(this , TAG_STATUS,
1877:                            bIsHist));
1878:                    select.addSelectColumn(cache.getColumnRef(this ,
1879:                            TAG_VERSION, bIsHist));
1880:                    select.addSelectColumn(cache.getColumnRef(this ,
1881:                            TAG_VERSION_COMMENT, bIsHist));
1882:                    select.addSelectColumn(cache.getColumnRef(this ,
1883:                            TAG_VERSION_DATE, bIsHist));
1884:                    select.addSelectColumn(cache.getColumnRef(this ,
1885:                            TAG_LIVE_VERSION, bIsHist));
1886:
1887:                    if (bIsHist == true) {
1888:                        select.addSelectColumn(cache.getColumnRef(this ,
1889:                                CLMN_HISTORY_DATE, bIsHist));
1890:                    } else {
1891:                        select.addSelectColumn(cache.getColumnRef(this ,
1892:                                CLMN_LOCK_USER, bIsHist));
1893:                    }
1894:                } catch (CacheException e) {
1895:                    throw new DataStoreException("cache error", e);
1896:                }
1897:
1898:                super .addColumnsToPopulateQuery(select, bIsHist);
1899:
1900:            }
1901:
1902:            /**
1903:             * Deletes object data from data store. If <code>bDeleteHist</code> is 
1904:             * <code>true</code> then the archived data will also be deleted.
1905:             * 
1906:             * @param bDeleteHist <code>true</code> if the the archived data should be deleted
1907:             * @throws DataStoreException if an error occurs 
1908:             */
1909:            protected void delete(boolean bDeleteHist)
1910:                    throws DataStoreException, DataAccessException,
1911:                    EditException, PopulateException {
1912:
1913:                if (m_nObjectKey <= 0 && isPopulated() == false) {
1914:                    populateFromDatabase();
1915:                }
1916:
1917:                String sTable = getDBTableName();
1918:                boolean bIsHist = isHistorical();
1919:
1920:                if (bIsHist == true) {
1921:                    sTable = getHistoricalDBTableName();
1922:                }
1923:
1924:                DeleteStatement deleteStmt = new DeleteStatement();
1925:
1926:                deleteStmt.setTable(sTable);
1927:                deleteStmt.addWhereCondition(getInstanceColumnRef(ATTRIB_KEY,
1928:                        bIsHist), "=", m_nObjectKey);
1929:
1930:                m_dsi.execute(deleteStmt);
1931:                deleteStmt.clear();
1932:
1933:                int i = 0;
1934:
1935:                if (bDeleteHist == true) {
1936:                    AbstractEditableObject nextObj = null;
1937:                    Iterator iter = null;
1938:
1939:                    List listHistorical = getHistoricalVersions();
1940:
1941:                    iter = listHistorical.iterator();
1942:
1943:                    while (iter.hasNext()) {
1944:                        nextObj = (AbstractEditableObject) iter.next();
1945:
1946:                        // set delete history to false so it doesn't cascade
1947:                        nextObj.delete(false);
1948:                    }
1949:
1950:                    // if this isn't an historical version get rid of everything else
1951:                    if (bIsHist == false) {
1952:                        // unapproved versions
1953:                        List pends = getPendingVersions();
1954:
1955:                        iter = pends.iterator();
1956:
1957:                        while (iter.hasNext()) {
1958:                            nextObj = (AbstractEditableObject) iter.next();
1959:                            nextObj.delete(false);
1960:                        }
1961:
1962:                    }
1963:                }
1964:
1965:                try {
1966:                    //ensure that object is not still in the cache
1967:                    CacheHandler.getInstance(m_dsi).getCache(getClass())
1968:                            .removeObjectFromCache(String.valueOf(m_nId));
1969:                } catch (CacheException e) {
1970:                    throw new EditException(e);
1971:                }
1972:
1973:                // set everything to its default states
1974:                m_nId = NOTDBSAVED_ID;
1975:                m_nObjectKey = NOTDBSAVED_KEY;
1976:            }
1977:
1978:            /* (non-Javadoc)
1979:             * @see org.openharmonise.rm.resources.AbstractObject#populateFromResultSetRow(java.sql.ResultSet, org.openharmonise.commons.dsi.dml.SelectStatement)
1980:             */
1981:            protected void populateFromResultSetRow(ResultSet rs,
1982:                    SelectStatement select) throws PopulateException {
1983:
1984:                if (isPopulated() == false) {
1985:
1986:                    String sTemp = null;
1987:                    int nTemp = -1;
1988:                    java.util.Date dTemp = null;
1989:                    ColumnRef colref = null;
1990:
1991:                    try {
1992:                        ColumnRefCache cache = ColumnRefCache.getInstance();
1993:
1994:                        boolean bIsHist = isHistorical();
1995:
1996:                        ColumnRef dispNameCol = cache.getColumnRef(this ,
1997:                                CLMN_DISPLAY_NAME, bIsHist);
1998:
1999:                        if (select.containsSelectColumn(dispNameCol) == true) {
2000:
2001:                            sTemp = rs.getString(select
2002:                                    .getResultSetIndex(dispNameCol));
2003:
2004:                            if ((sTemp != null) && (sTemp.length() > 0)) {
2005:                                if ((m_sDisplayName == null)
2006:                                        || (m_sDisplayName.length() == 0)) {
2007:                                    m_sDisplayName = sTemp;
2008:                                } else if (m_sDisplayName.equals(sTemp) == false) {
2009:                                    m_bIsChanged = true;
2010:                                }
2011:                            }
2012:                        }
2013:
2014:                        colref = cache.getColumnRef(this , CLMN_STATUS, bIsHist);
2015:
2016:                        if (select.containsSelectColumn(colref) == true) {
2017:
2018:                            nTemp = rs.getInt(select.getResultSetIndex(colref));
2019:
2020:                            if (m_status == Status.UNKNOWN) {
2021:                                m_status = Status.getStatus(nTemp);
2022:                            } else if (m_status.getIntValue() != nTemp) {
2023:                                setIsChanged(true);
2024:                            }
2025:
2026:                        }
2027:
2028:                        colref = cache.getColumnRef(this , CLMN_VERSION_NUMBER,
2029:                                bIsHist);
2030:
2031:                        if (select.containsSelectColumn(colref) == true) {
2032:                            nTemp = rs.getInt(select.getResultSetIndex(colref));
2033:
2034:                            if (nTemp >= 0) {
2035:                                setVersionNumber(nTemp);
2036:                            }
2037:                        }
2038:
2039:                        colref = cache.getColumnRef(this , CLMN_VERSION_COMMENT,
2040:                                bIsHist);
2041:
2042:                        if (select.containsSelectColumn(colref) == true) {
2043:                            sTemp = rs.getString(select
2044:                                    .getResultSetIndex(colref));
2045:
2046:                            if ((sTemp != null) && (sTemp.length() > 0)) {
2047:                                this .setVersionComment(sTemp);
2048:                            }
2049:                        }
2050:
2051:                        colref = cache.getColumnRef(this , CLMN_VERSION_DATE,
2052:                                bIsHist);
2053:
2054:                        if (select.containsSelectColumn(colref) == true) {
2055:                            dTemp = rs.getTimestamp(select
2056:                                    .getResultSetIndex(colref));
2057:
2058:                            if (dTemp != null) {
2059:                                this .setVersionDate(dTemp);
2060:                            }
2061:                        }
2062:
2063:                        if (bIsHist == false) {
2064:
2065:                            colref = cache.getColumnRef(this , TAG_LIVE_VERSION,
2066:                                    bIsHist);
2067:
2068:                            if (select.containsSelectColumn(colref) == true) {
2069:                                nTemp = rs.getInt(select
2070:                                        .getResultSetIndex(colref));
2071:
2072:                                if (nTemp >= 0) {
2073:                                    m_nLiveId = nTemp;
2074:                                }
2075:                            }
2076:                        } else {
2077:                            m_nLiveId = m_nId;
2078:                        }
2079:
2080:                        colref = cache.getColumnRef(this , CLMN_LOCK_USER,
2081:                                bIsHist);
2082:
2083:                        if (select.containsSelectColumn(colref) == true) {
2084:                            nTemp = rs.getInt(select.getResultSetIndex(colref));
2085:
2086:                            if (nTemp > 0) {
2087:                                m_nLockUserId = nTemp;
2088:                            }
2089:                        }
2090:
2091:                        if (bIsHist == true) {
2092:                            colref = cache.getColumnRef(this ,
2093:                                    CLMN_HISTORY_DATE, bIsHist);
2094:
2095:                            if (select.containsSelectColumn(colref) == true) {
2096:                                dTemp = rs.getTimestamp(select
2097:                                        .getResultSetIndex(colref));
2098:
2099:                                if (dTemp != null) {
2100:                                    this .m_dtHistDate = dTemp;
2101:                                }
2102:                            }
2103:                        }
2104:                    } catch (SQLException eSQL) {
2105:                        throw new PopulateException("sql error", eSQL);
2106:                    } catch (CacheException e) {
2107:                        throw new PopulateException("cache error", e);
2108:                    }
2109:
2110:                    super .populateFromResultSetRow(rs, select);
2111:
2112:                }
2113:
2114:            }
2115:
2116:            /**
2117:             * Updates data in database.
2118:             * 
2119:             * @throws DataStoreException if any database errors occur
2120:             * @throws EditException if any errors occur processing the data
2121:             */
2122:            protected void update() throws DataStoreException, EditException {
2123:
2124:                if (m_logger.isLoggable(Level.INFO)) {
2125:                    try {
2126:                        m_logger.logp(Level.INFO, this .getClass().getName(),
2127:                                "update", "updating object " + getKey());
2128:                    } catch (DataAccessException e) {
2129:                        m_logger.log(Level.WARNING, e.getLocalizedMessage(), e);
2130:                    }
2131:                }
2132:
2133:                UpdateStatement update = new UpdateStatement();
2134:
2135:                addDataToSave(update);
2136:
2137:                update.addWhereCondition(getInstanceColumnRef(ATTRIB_KEY,
2138:                        isHistorical()), "=", m_nObjectKey);
2139:
2140:                m_dsi.execute(update);
2141:
2142:                m_bIsChanged = false;
2143:
2144:            }
2145:
2146:            /**
2147:             * 
2148:             * Adds data to insert statement which will be executed in the
2149:             * <code>save()</code> method.
2150:             * 
2151:             * @param insert the insert statement
2152:             * @throws DataStoreException if an error occurs
2153:             */
2154:            protected void addDataToSave(InsertStatement insert)
2155:                    throws DataStoreException {
2156:
2157:                boolean bIsHist = isHistorical();
2158:
2159:                insert.addColumnValue(this .getInstanceColumnRef(ATTRIB_ID,
2160:                        bIsHist), m_nId);
2161:                insert.addColumnValue(this .getInstanceColumnRef(ATTRIB_KEY,
2162:                        bIsHist), m_nObjectKey);
2163:                insert.addColumnValue(this .getInstanceColumnRef(
2164:                        TAG_LIVE_VERSION, bIsHist), m_nLiveId);
2165:
2166:                java.util.Date dtNow = new java.util.Date();
2167:
2168:                if (bIsHist == false) {
2169:                    m_dtVersionDate = (java.util.Date) dtNow.clone();
2170:
2171:                    insert.addColumnValue(getInstanceColumnRef(
2172:                            CLMN_VERSION_DATE, bIsHist), m_dtVersionDate);
2173:                } else {
2174:                    insert.addColumnValue(getInstanceColumnRef(
2175:                            CLMN_VERSION_DATE, bIsHist), m_dtVersionDate);
2176:                    insert.addColumnValue(getInstanceColumnRef(
2177:                            CLMN_HISTORY_DATE, bIsHist), dtNow);
2178:                }
2179:
2180:                insert.addColumnValue(getInstanceColumnRef(CLMN_VERSION_NUMBER,
2181:                        bIsHist), m_nVersionNumber);
2182:
2183:                if (m_sVersionComment != null) {
2184:                    insert.addColumnValue(getInstanceColumnRef(
2185:                            CLMN_VERSION_COMMENT, bIsHist), m_sVersionComment);
2186:                }
2187:
2188:                insert.addColumnValue(
2189:                        getInstanceColumnRef(CLMN_STATUS, bIsHist), m_status
2190:                                .getIntValue());
2191:
2192:                if (m_sName != null) {
2193:                    insert.addColumnValue(this .getInstanceColumnRef(TAG_NAME,
2194:                            bIsHist), m_sName);
2195:                }
2196:
2197:                if (m_sDisplayName != null) {
2198:                    insert.addColumnValue(this .getInstanceColumnRef(
2199:                            TAG_DISPLAY_NAME, bIsHist), m_sDisplayName);
2200:                }
2201:
2202:                if (m_sSummary != null) {
2203:                    insert.addColumnValue(this .getInstanceColumnRef(
2204:                            TAG_SUMMARY, bIsHist), m_sSummary);
2205:                }
2206:
2207:                insert.addColumnValue(this .getInstanceColumnRef(ATTRIB_TYPE,
2208:                        bIsHist), this .m_sType);
2209:            }
2210:
2211:            /**
2212:             * Updates the database with the new status value and any
2213:             * other relavent changes, such as id, key and live id.
2214:             * 
2215:             * @throws PopulateException if an error occurs
2216:             */
2217:            protected void updateDBStatus() throws PopulateException {
2218:
2219:                try {
2220:
2221:                    UpdateStatement update = new UpdateStatement();
2222:
2223:                    update.addColumnValue(this .getInstanceColumnRef(TAG_STATUS,
2224:                            false), m_status.getIntValue());
2225:                    update.addColumnValue(this .getInstanceColumnRef(ATTRIB_ID,
2226:                            false), m_nId);
2227:                    update.addColumnValue(this .getInstanceColumnRef(
2228:                            TAG_LIVE_VERSION, false), m_nLiveId);
2229:                    update.addWhereCondition(this .getInstanceColumnRef(
2230:                            ATTRIB_KEY, false), "=", m_nObjectKey);
2231:
2232:                    this .m_dsi.execute(update);
2233:
2234:                } catch (DataStoreException e) {
2235:                    throw new PopulateException(e.getLocalizedMessage());
2236:                }
2237:            }
2238:
2239:            /*----------------------------------------------------------------------------
2240:            Private Methods
2241:            -----------------------------------------------------------------------------*/
2242:
2243:            /** 
2244:             * Sets the status of this object.
2245:             *
2246:             * @param the status
2247:             */
2248:            private void setStatus(Status status) {
2249:                m_status = status;
2250:            }
2251:
2252:            /** 
2253:             * Sets the version number.
2254:             * 
2255:             * @param nVersionNumber The version number
2256:             */
2257:            private void setVersionNumber(int nVersionNumber) {
2258:                m_nVersionNumber = nVersionNumber;
2259:            }
2260:
2261:            /** 
2262:             * Sets the version date.
2263:             * 
2264:             * @param nVersionNumber the version date
2265:             */
2266:            private void setVersionDate(java.util.Date dtDate) {
2267:                m_dtVersionDate = dtDate;
2268:            }
2269:
2270:            /** 
2271:             * Sets the live version of this resource.
2272:             *  
2273:             * @param liveVersion the live version of this object
2274:             */
2275:            private void setLiveVersion(AbstractEditableObject liveVersion) {
2276:                //ensure live version is indeed the same type
2277:                if ((this .getClass().isInstance(liveVersion)) == false) {
2278:                    throw new IllegalArgumentException();
2279:                }
2280:
2281:                if (m_nId <= NOTDBSAVED_ID) {
2282:                    m_nLiveId = liveVersion.getId();
2283:                }
2284:            }
2285:
2286:            /* (non-Javadoc)
2287:             * @see org.openharmonise.rm.resources.AbstractObject#isKeySupported()
2288:             */
2289:            protected boolean isKeySupported() {
2290:                return true;
2291:            }
2292:
2293:            /* (non-Javadoc)
2294:             * @see org.openharmonise.rm.resources.lifecycle.EditEventListener#workflowObjectLocked(org.openharmonise.rm.resources.lifecycle.EditEvent)
2295:             */
2296:            public void workflowObjectLocked(EditEvent event) {
2297:                // nothing to do
2298:
2299:            }
2300:
2301:            /* (non-Javadoc)
2302:             * @see org.openharmonise.rm.resources.lifecycle.EditEventListener#workflowObjectReactivated(org.openharmonise.rm.resources.lifecycle.EditEvent)
2303:             */
2304:            public void workflowObjectReactivated(EditEvent event) {
2305:                // nothing to do
2306:
2307:            }
2308:
2309:            /* (non-Javadoc)
2310:             * @see org.openharmonise.rm.resources.lifecycle.EditEventListener#workflowObjectSaved(org.openharmonise.rm.resources.lifecycle.EditEvent)
2311:             */
2312:            public void workflowObjectSaved(EditEvent event) {
2313:                // nothing to do
2314:
2315:            }
2316:
2317:            /* (non-Javadoc)
2318:             * @see org.openharmonise.rm.resources.lifecycle.EditEventListener#workflowObjectStatusChanged(org.openharmonise.rm.resources.lifecycle.EditEvent)
2319:             */
2320:            public void workflowObjectStatusChanged(EditEvent event) {
2321:                // nothing to do
2322:
2323:            }
2324:
2325:            /* (non-Javadoc)
2326:             * @see org.openharmonise.rm.resources.lifecycle.EditEventListener#workflowObjectUnlocked(org.openharmonise.rm.resources.lifecycle.EditEvent)
2327:             */
2328:            public void workflowObjectUnlocked(EditEvent event) {
2329:                // nothing to do
2330:
2331:            }
2332:        }
www.java2java.com | Contact Us
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.