KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > jahia > services > containers > ContentContainerList


1 //
2
// ____.
3
// __/\ ______| |__/\. _______
4
// __ .____| | \ | +----+ \
5
// _______| /--| | | - \ _ | : - \_________
6
// \\______: :---| : : | : | \________>
7
// |__\---\_____________:______: :____|____:_____\
8
// /_____|
9
//
10
// . . . i n j a h i a w e t r u s t . . .
11
//
12

13 package org.jahia.services.containers;
14
15 import org.apache.log4j.Logger;
16 import org.jahia.content.*;
17 import org.jahia.data.containers.JahiaContainerList;
18 import org.jahia.data.fields.LoadFlags;
19 import org.jahia.exceptions.JahiaException;
20 import org.jahia.params.ParamBean;
21 import org.jahia.registries.ServicesRegistry;
22 import org.jahia.services.containers.JahiaContainerUtilsDB;
23 import org.jahia.services.pages.ContentPage;
24 import org.jahia.services.usermanager.JahiaUser;
25 import org.jahia.services.version.*;
26 import org.jahia.utils.LanguageCodeConverters;
27
28 import java.util.*;
29
30 /**
31  * <p>Title: </p>
32  * <p>Description: </p>
33  * <p>Copyright: Copyright (c) 2002</p>
34  * <p>Company: </p>
35  *
36  * @author Serge Huber
37  * @version 1.0
38  */

39
40 public class ContentContainerList extends ContentObject implements PageReferenceableInterface {
41
42     private static Logger logger = Logger.getLogger (ContentContainerList.class);
43
44     private ArrayList activeAndStagedEntryStates;
45     private ArrayList versionedEntryStates = null;
46     private int parentContainerID;
47     private int pageID;
48     private int aclID;
49     private int containerListDefinitionID;
50
51     static {
52         JahiaObject.registerType (ContentContainerListKey.CONTAINERLIST_TYPE,
53                 ContentContainerList.class.getName ());
54     }
55
56     public static ContentObject getChildInstance (String JavaDoc IDInType) {
57         try {
58             return getContainerList (Integer.parseInt (IDInType));
59         } catch (JahiaException je) {
60             logger.debug ("Error retrieving container list instance for id : " + IDInType, je);
61         }
62         return null;
63     }
64
65     protected ContentContainerList (int ID, int aParentContainerID, int aPageID, int ctnDefID,
66                                     int anAclID, ArrayList activeAndStagedEntries) {
67         super (new ContentContainerListKey (ID));
68         this.parentContainerID = aParentContainerID;
69         this.pageID = aPageID;
70         this.aclID = anAclID;
71         this.containerListDefinitionID = ctnDefID;
72         this.activeAndStagedEntryStates = activeAndStagedEntries;
73     }
74
75     /**
76      * Return the pageID
77      *
78      * @param loadRequest
79      *
80      * @return
81      */

82     public int getPageID () {
83         return this.pageID;
84     }
85
86     public int getSiteID() {
87         try {
88             return getParent(null,null,null).getSiteID();
89         } catch (JahiaException e) {
90             e.printStackTrace(); //To change body of catch statement use Options | File Templates.
91
}
92         return -1;
93     }
94
95     //-------------------------------------------------------------------------
96
/**
97      * Returns the ContentPage ancestor.
98      *
99      * @return Return the ContentPage ancestor.
100      */

101     public ContentPage getPage () throws JahiaException {
102         return ContentPage.getPage (this.getPageID ());
103     }
104
105     /**
106      * Returns the identifier of the Content Definition for Content object.
107      *
108      * @param loadRequest
109      *
110      * @return
111      */

112     public int getDefinitionID (EntryLoadRequest loadRequest) {
113         return this.containerListDefinitionID;
114     }
115
116     /**
117      * Returns the Definition Key of the Content Definition for this Content object.
118      * This is a ContainerDefinition
119      *
120      * @param loadRequest
121      *
122      * @return
123      */

124     public ObjectKey getDefinitionKey (EntryLoadRequest loadRequest) {
125         int defID = getDefinitionID (loadRequest);
126         ContainerDefinitionKey ctnDefKey = (ContainerDefinitionKey)
127                 ContainerDefinitionKey.getChildInstance (String.valueOf (defID));
128         return ctnDefKey;
129     }
130
131     public SortedSet getEntryStates ()
132             throws JahiaException {
133         SortedSet resultSet = new TreeSet ();
134         if (versionedEntryStates == null) {
135             versionedEntryStates =
136                     ContentContainerListDB.getInstance ().getVersionedEntryStates (getID (),
137                             false);
138         }
139         resultSet.addAll (activeAndStagedEntryStates);
140         resultSet.addAll (versionedEntryStates);
141         return resultSet;
142     }
143
144     public ArrayList getChilds (JahiaUser user,
145                                 EntryLoadRequest loadRequest)
146             throws JahiaException {
147         /**
148          * @todo FIXME Filters are currently not supported in this method.
149          */

150         ArrayList resultList = new ArrayList ();
151         Vector containerIDs = ServicesRegistry.getInstance ().getJahiaContainersService ()
152                 .getctnidsInList (getID (), loadRequest);
153         Enumeration containerIDEnum = containerIDs.elements ();
154         while (containerIDEnum.hasMoreElements ()) {
155             Integer JavaDoc curContainerID = (Integer JavaDoc) containerIDEnum.nextElement ();
156             ContentContainer curContainer = ContentContainer.getContainer (
157                     curContainerID.intValue ());
158             if (curContainer != null) {
159                 resultList.add (curContainer);
160             }
161         }
162         return resultList;
163     }
164
165     public ContentObject getParent (JahiaUser user,
166                                     EntryLoadRequest loadRequest,
167                                     String JavaDoc operationMode)
168             throws JahiaException {
169         if (parentContainerID > 0) {
170             return ContentContainer.getContainer (parentContainerID);
171         } else {
172             return ContentPage.getPage (pageID);
173         }
174     }
175
176     public static synchronized ContentContainerList getContainerList (int containerListID)
177             throws JahiaException {
178         return ContentContainerListDB.getInstance ().getContainerList (containerListID);
179     }
180
181     public JahiaContainerList getJahiaContainerList (ParamBean jParams,
182                                                      EntryLoadRequest loadRequest)
183             throws JahiaException {
184         return ServicesRegistry.getInstance ().getJahiaContainersService ().loadContainerList (
185                 getID (), LoadFlags.ALL, jParams, loadRequest, new Hashtable (), new Hashtable (), new Hashtable());
186     }
187
188     public int getAclID () {
189         return aclID;
190     }
191
192     public RestoreVersionTestResults isValidForRestore (JahiaUser user,
193                                                         String JavaDoc operationMode,
194                                                         ContentObjectEntryState entryState,
195                                                         boolean removeMoreRecentActive,
196                                                         StateModificationContext stateModificationContext)
197             throws JahiaException {
198         // first let's check if we have entries that correspond for this
199
// container list
200
RestoreVersionTestResults opResult = new RestoreVersionTestResults ();
201         opResult.merge (
202                 super.isValidForRestore (user, operationMode, entryState,
203                         removeMoreRecentActive, stateModificationContext));
204         if (opResult.getStatus () == RestoreVersionTestResults.FAILED_OPERATION_STATUS) {
205             return opResult;
206         }
207
208         // now let's check for the children of this container list. If only
209
// one of them fails, we fail the whole container.
210
ArrayList locales = new ArrayList ();
211         locales.add (
212                 LanguageCodeConverters.languageCodeToLocale (ContentObject.SHARED_LANGUAGE));
213         locales.add (LanguageCodeConverters.languageCodeToLocale (entryState.getLanguageCode ()));
214         EntryLoadRequest loadRequest = new EntryLoadRequest (entryState.getWorkflowState (),
215                 entryState.getVersionID (), locales);
216         ArrayList children = getChilds (user, loadRequest);
217         ListIterator childrenIter = children.listIterator ();
218         while (childrenIter.hasNext ()) {
219             ContentObject curChild = (ContentObject) childrenIter.next ();
220             RestoreVersionTestResults childResult = curChild.isValidForRestore (user,
221                     operationMode, entryState, removeMoreRecentActive,
222                     stateModificationContext);
223             // if a child fails this is ok, we simply indicate this by changing
224
// the status to partial, and keeping the messages
225
if (childResult.getStatus () == RestoreVersionTestResults.FAILED_OPERATION_STATUS) {
226                 childResult.setStatus (RestoreVersionTestResults.PARTIAL_OPERATION_STATUS);
227                 childResult.moveErrorsToWarnings ();
228             }
229             opResult.merge (childResult);
230         }
231         return opResult;
232     }
233
234     private boolean hasEntry (EntryStateable entryState)
235             throws JahiaException {
236         getEntryStates (); // this insures we have the loaded the versioned
237
// entry states
238
ContentObjectEntryState entryStateObject = new ContentObjectEntryState (entryState);
239         if (entryStateObject.getWorkflowState () >= ContentObjectEntryState.WORKFLOW_STATE_ACTIVE) {
240             int objectPos = activeAndStagedEntryStates.indexOf (entryStateObject);
241             if (objectPos != -1) {
242                 return true;
243             }
244         } else {
245             int objectPos = versionedEntryStates.indexOf (entryStateObject);
246             if (objectPos != -1) {
247                 return true;
248             }
249
250         }
251         return false;
252     }
253
254     private void removeEntryFromCaches (EntryStateable entryState)
255             throws JahiaException {
256         getEntryStates (); // this insures we have the loaded the versioned
257
// entry states
258
ContentObjectEntryState entryStateObject = new ContentObjectEntryState (entryState);
259         if (entryStateObject.getWorkflowState () >= ContentObjectEntryState.WORKFLOW_STATE_ACTIVE) {
260             int objectPos = activeAndStagedEntryStates.indexOf (entryStateObject);
261             if (objectPos != -1) {
262                 activeAndStagedEntryStates.remove (objectPos);
263             }
264         } else {
265             int objectPos = versionedEntryStates.indexOf (entryStateObject);
266             if (objectPos != -1) {
267                 versionedEntryStates.remove (objectPos);
268             }
269
270         }
271     }
272
273     /**
274      * This method is called when a entry should be copied into a new entry
275      * it is called when an old version -> active version move occurs
276      * This method should not write/change the DBValue, the service handles that.
277      *
278      * @param fromEntryState the entry state that is currently was in the database
279      * @param toEntryState the entry state that will be written to the database
280      */

281     protected void copyEntry (EntryStateable fromEntryState,
282                               EntryStateable toEntryState)
283             throws JahiaException {
284
285         ContentObjectEntryState fromE = new ContentObjectEntryState (fromEntryState);
286         ContentObjectEntryState toE = new ContentObjectEntryState (toEntryState);
287         if (this.isShared ()) {
288             // swith to Shared lang
289
fromE = new ContentObjectEntryState (fromEntryState.getWorkflowState (),
290                     fromEntryState.getVersionID (), ContentObject.SHARED_LANGUAGE);
291
292             toE = new ContentObjectEntryState (toEntryState.getWorkflowState (),
293                     toEntryState.getVersionID (), ContentObject.SHARED_LANGUAGE);
294         }
295
296         if (hasEntry (toE)) {
297             deleteEntry (toE);
298         }
299
300         ContentContainerListDB.getInstance ().copyEntry (getID (), fromE, toE);
301         if (toE.getWorkflowState () >= ContentObjectEntryState.WORKFLOW_STATE_ACTIVE) {
302             activeAndStagedEntryStates.add (toE);
303         } else {
304             versionedEntryStates.add (toE);
305         }
306     }
307
308
309     /**
310      * This method is called when an entry should be deleted for real.
311      * It is called when a object is deleted, and versioning is disabled, or
312      * when staging values are undone.
313      * For a bigtext content fields for instance, this method should delete
314      * the text file corresponding to the field entry
315      *
316      * @param deleteEntryState the entry state to delete
317      * @param jParams ParamBean needed to destroy page related data such as
318      * fields, sub pages, as well as generated JahiaEvents.
319      */

320     protected void deleteEntry (EntryStateable deleteEntryState)
321             throws JahiaException {
322         removeEntryFromCaches (deleteEntryState);
323         ContentContainerListDB.getInstance ().deleteEntry (getID (), deleteEntryState);
324     }
325
326     /**
327      * Mark a content object's language for deletion. Does nothing if the
328      * language doesn't exist, but if it exists only in staging, the staging
329      * entry is removed.
330      *
331      * @param user the user performing the operation, in order to perform
332      * rights checks
333      * @param languageCode the language to mark for deletion
334      * @param stateModificationContext contains the start object of the
335      * operation, as well as settings such as recursive descending in sub pages,
336      * and content object stack trace.
337      *
338      * @throws JahiaException raised if there was a problem while marking the
339      * content object for deletion (mostly related to communication with the
340      * database)
341      */

342     public void markLanguageForDeletion (JahiaUser user,
343                                          String JavaDoc languageCode,
344                                          StateModificationContext
345             stateModificationContext)
346             throws JahiaException {
347         ServicesRegistry.getInstance ().getJahiaContainersService ()
348                 .markContainerListLanguageForDeletion (getID (), user, languageCode,
349                         stateModificationContext);
350     }
351
352     public RestoreVersionTestResults restoreVersion (JahiaUser user,
353                                                      String JavaDoc operationMode,
354                                                      ContentObjectEntryState entryState,
355                                                      boolean removeMoreRecentActive,
356                                                      RestoreVersionStateModificationContext stateModificationContext)
357             throws JahiaException {
358
359         RestoreVersionTestResults opResult = new RestoreVersionTestResults ();
360
361         /**
362          * This check has no meaning because some field could not exists in the current restore language
363          *
364          opResult.merge(isValidForRestore(user, operationMode, entryState,
365          removeMoreRecentActive,
366          stateModificationContext));
367          if (opResult.getStatus() ==
368          RestoreVersionTestResults.FAILED_OPERATION_STATUS) {
369          return opResult;
370          }
371          */

372
373        // retrieve the exact archive entry state
374
getClosestVersionedEntryState(entryState);
375        
376        ArrayList locales = new ArrayList();
377        locales.add(LanguageCodeConverters.languageCodeToLocale(entryState.getLanguageCode()));
378        EntryLoadRequest loadRequest = null;
379
380        // 1. First restore archive
381
// load archive to restore
382
loadRequest = new EntryLoadRequest(entryState.
383            getWorkflowState(), entryState.getVersionID(), locales);
384        ArrayList children = getChilds(user, loadRequest);
385        ListIterator childrenIter = children.listIterator();
386
387        // For performance issue, we don't want to restore twice objects.
388
ArrayList processedChilds = new ArrayList();
389        while (childrenIter.hasNext()) {
390            ContentObject curChild = (ContentObject) childrenIter.next();
391            opResult.merge(curChild.restoreVersion(user,
392                    operationMode, entryState, removeMoreRecentActive, stateModificationContext));
393            processedChilds.add(curChild.getObjectKey().toString());
394        }
395
396        //2.Second, remove more recent data
397
if ( removeMoreRecentActive ){
398            // load staging or active to perform a restore which will mark them for delete
399
loadRequest =
400                    new EntryLoadRequest(EntryLoadRequest.STAGING_WORKFLOW_STATE,
401                    0, locales);
402            children = getChilds(user, loadRequest);
403            childrenIter = children.listIterator();
404            while (childrenIter.hasNext()) {
405                ContentObject curChild = (ContentObject) childrenIter.next();
406                if ( !processedChilds.contains(curChild.getObjectKey().toString()) ){
407                    opResult.merge(curChild.restoreVersion(user,
408                        operationMode, entryState, removeMoreRecentActive,
409                        stateModificationContext));
410                }
411            }
412        }
413
414        opResult.merge(super.restoreVersion(user, operationMode, entryState,
415                                     removeMoreRecentActive,
416                                     stateModificationContext));
417
418        JahiaContainerUtilsDB.getInstance().invalidateSubCtnListIDsByCtnCache(this.getParentContainerID());
419        JahiaContainerUtilsDB.getInstance().invalidateCtnIdsByCtnListCache(this.getID());
420
421        ServicesRegistry.getInstance ().getJahiaContainersService ()
422            .invalidateContainerListFromCache(this.getID());
423
424        return opResult;
425     }
426
427     public int getParentContainerID () {
428         return parentContainerID;
429     }
430
431     public int getContainerListDefinitionID () {
432         return containerListDefinitionID;
433     }
434
435     /**
436      * This method removes all the data related to the staging mode of this
437      * field, effectively "undoing" all the changes and returning to the
438      * active values.
439      *
440      * @throws JahiaException in the case there are errors accessing the
441      * persistant storage system.
442      */

443     public synchronized void undoStaging (ParamBean jParams)
444             throws JahiaException {
445
446         // first we construct a vector of all the staging versions
447
Vector stagedEntryStates = new Vector ();
448         for (int i = 0; i < activeAndStagedEntryStates.size (); i++) {
449             ContentObjectEntryState entryState = (ContentObjectEntryState) activeAndStagedEntryStates.get (
450                     i);
451             // ok huston, we have a staged version here, let's advise...
452
if (entryState.isStaging ()) {
453                 stagedEntryStates.add (entryState);
454             }
455         }
456
457         // now let's use that vector to destroy all staged versions
458
for (int i = 0; i < stagedEntryStates.size (); i++) {
459             ContentObjectEntryState curEntryState = (ContentObjectEntryState) stagedEntryStates.get (
460                     i);
461
462             // first we call the field to destroy it's related data
463
this.deleteEntry (curEntryState);
464         }
465
466         JahiaContainerUtilsDB.getInstance().invalidateSubCtnListIDsByCtnCache(this.getParentContainerID());
467         JahiaContainerUtilsDB.getInstance().invalidateCtnIdsByCtnListCache(this.getID());
468
469         ServicesRegistry.getInstance ().getJahiaContainersService ()
470             .invalidateContainerListFromCache(this.getID());
471
472     }
473
474     /**
475      * Is this kind of field shared (i.e. not one version for each language, but one version for every language)
476      */

477     public boolean isShared () {
478         return true;
479     }
480 }
481
Popular Tags