1   /**
2    * Copyright (c) 2000-2008 Liferay, Inc. All rights reserved.
3    *
4    * Permission is hereby granted, free of charge, to any person obtaining a copy
5    * of this software and associated documentation files (the "Software"), to deal
6    * in the Software without restriction, including without limitation the rights
7    * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
8    * copies of the Software, and to permit persons to whom the Software is
9    * furnished to do so, subject to the following conditions:
10   *
11   * The above copyright notice and this permission notice shall be included in
12   * all copies or substantial portions of the Software.
13   *
14   * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15   * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16   * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
17   * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
18   * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
19   * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
20   * SOFTWARE.
21   */
22  
23  package com.liferay.portlet.documentlibrary.lar;
24  
25  import com.liferay.portal.kernel.lar.PortletDataContext;
26  import com.liferay.portal.kernel.lar.PortletDataException;
27  import com.liferay.portal.kernel.lar.PortletDataHandler;
28  import com.liferay.portal.kernel.lar.PortletDataHandlerBoolean;
29  import com.liferay.portal.kernel.lar.PortletDataHandlerControl;
30  import com.liferay.portal.kernel.lar.PortletDataHandlerKeys;
31  import com.liferay.portal.util.PortalUtil;
32  import com.liferay.portlet.documentlibrary.NoSuchFileEntryException;
33  import com.liferay.portlet.documentlibrary.NoSuchFileShortcutException;
34  import com.liferay.portlet.documentlibrary.NoSuchFolderException;
35  import com.liferay.portlet.documentlibrary.model.DLFileEntry;
36  import com.liferay.portlet.documentlibrary.model.DLFileRank;
37  import com.liferay.portlet.documentlibrary.model.DLFileShortcut;
38  import com.liferay.portlet.documentlibrary.model.DLFolder;
39  import com.liferay.portlet.documentlibrary.model.impl.DLFolderImpl;
40  import com.liferay.portlet.documentlibrary.service.DLFileEntryLocalServiceUtil;
41  import com.liferay.portlet.documentlibrary.service.DLFileRankLocalServiceUtil;
42  import com.liferay.portlet.documentlibrary.service.DLFileShortcutLocalServiceUtil;
43  import com.liferay.portlet.documentlibrary.service.DLFolderLocalServiceUtil;
44  import com.liferay.portlet.documentlibrary.service.persistence.DLFileEntryFinderUtil;
45  import com.liferay.portlet.documentlibrary.service.persistence.DLFileEntryUtil;
46  import com.liferay.portlet.documentlibrary.service.persistence.DLFileRankUtil;
47  import com.liferay.portlet.documentlibrary.service.persistence.DLFileShortcutFinderUtil;
48  import com.liferay.portlet.documentlibrary.service.persistence.DLFileShortcutUtil;
49  import com.liferay.portlet.documentlibrary.service.persistence.DLFolderUtil;
50  import com.liferay.util.CollectionFactory;
51  import com.liferay.util.FileUtil;
52  import com.liferay.util.MapUtil;
53  
54  import com.thoughtworks.xstream.XStream;
55  
56  import java.io.InputStream;
57  
58  import java.util.ArrayList;
59  import java.util.Iterator;
60  import java.util.List;
61  import java.util.Map;
62  
63  import javax.portlet.PortletPreferences;
64  
65  import org.apache.commons.logging.Log;
66  import org.apache.commons.logging.LogFactory;
67  
68  import org.dom4j.Document;
69  import org.dom4j.DocumentHelper;
70  import org.dom4j.Element;
71  
72  /**
73   * <a href="DLPortletDataHandlerImpl.java.html"><b><i>View Source</i></b></a>
74   *
75   * @author Bruno Farache
76   *
77   */
78  public class DLPortletDataHandlerImpl implements PortletDataHandler {
79  
80      public PortletPreferences deleteData(
81              PortletDataContext context, String portletId,
82              PortletPreferences prefs)
83          throws PortletDataException {
84  
85          try {
86  
87              // Folders
88  
89              if (!context.addPrimaryKey(
90                      DLPortletDataHandlerImpl.class, "deleteData")) {
91  
92                  DLFolderLocalServiceUtil.deleteFolders(context.getGroupId());
93              }
94  
95              return null;
96          }
97          catch (Exception e) {
98              throw new PortletDataException(e);
99          }
100     }
101 
102     public String exportData(
103             PortletDataContext context, String portletId,
104             PortletPreferences prefs)
105         throws PortletDataException {
106 
107         try {
108             XStream xStream = new XStream();
109 
110             Document doc = DocumentHelper.createDocument();
111 
112             Element root = doc.addElement("documentlibrary-data");
113 
114             root.addAttribute("group-id", String.valueOf(context.getGroupId()));
115 
116             // Folders
117 
118             List folders = DLFolderUtil.findByGroupId(
119                 context.getGroupId());
120 
121             List entries = new ArrayList();
122 
123             List shortcuts = new ArrayList();
124 
125             Iterator itr = folders.iterator();
126 
127             while (itr.hasNext()) {
128                 DLFolder folder = (DLFolder)itr.next();
129 
130                 if (context.addPrimaryKey(
131                         DLFolder.class, folder.getPrimaryKeyObj())) {
132 
133                     itr.remove();
134                 }
135                 else {
136                     folder.setUserUuid(folder.getUserUuid());
137 
138                     List folderEntries = DLFileEntryUtil.findByFolderId(
139                         folder.getFolderId());
140 
141                     entries.addAll(folderEntries);
142 
143                     if (context.getBooleanParameter(_NAMESPACE, "shortcuts")) {
144                         List folderShortcuts =
145                             DLFileShortcutUtil.findByFolderId(
146                                 folder.getFolderId());
147 
148                         shortcuts.addAll(folderShortcuts);
149                     }
150                 }
151             }
152 
153             String xml = xStream.toXML(folders);
154 
155             Element el = root.addElement("documentlibrary-folders");
156 
157             Document tempDoc = PortalUtil.readDocumentFromXML(xml);
158 
159             el.content().add(tempDoc.getRootElement().createCopy());
160 
161             // Entries
162 
163             List ranks = new ArrayList();
164 
165             itr = entries.iterator();
166 
167             while (itr.hasNext()) {
168                 DLFileEntry entry = (DLFileEntry)itr.next();
169 
170                 if (context.addPrimaryKey(
171                         DLFileEntry.class, entry.getPrimaryKeyObj())) {
172 
173                     itr.remove();
174                 }
175                 else {
176                     entry.setUserUuid(entry.getUserUuid());
177 
178                     if (context.getBooleanParameter(_NAMESPACE, "comments")) {
179                         context.addComments(
180                             DLFileEntry.class, entry.getPrimaryKeyObj());
181                     }
182 
183                     if (context.getBooleanParameter(_NAMESPACE, "ratings")) {
184                         context.addRatingsEntries(
185                             DLFileEntry.class, entry.getPrimaryKeyObj());
186                     }
187 
188                     if (context.getBooleanParameter(_NAMESPACE, "tags")) {
189                         context.addTagsEntries(
190                             DLFileEntry.class, entry.getPrimaryKeyObj());
191                     }
192 
193                     InputStream in =
194                         DLFileEntryLocalServiceUtil.getFileAsStream(
195                             entry.getCompanyId(), entry.getUserId(),
196                             entry.getFolderId(), entry.getName());
197 
198                     context.getZipWriter().addEntry(
199                         _ZIP_FOLDER + entry.getName(), FileUtil.getBytes(in));
200 
201                     if (context.getBooleanParameter(_NAMESPACE, "ranks")) {
202                         List entryRanks = DLFileRankUtil.findByF_N(
203                             entry.getFolderId(), entry.getName());
204 
205                         ranks.addAll(entryRanks);
206                     }
207                 }
208             }
209 
210             xml = xStream.toXML(entries);
211 
212             el = root.addElement("documentlibrary-entries");
213 
214             tempDoc = PortalUtil.readDocumentFromXML(xml);
215 
216             el.content().add(tempDoc.getRootElement().createCopy());
217 
218             // Shortcuts
219 
220             itr = shortcuts.iterator();
221 
222             while (itr.hasNext()) {
223                 DLFileShortcut shortcut = (DLFileShortcut)itr.next();
224 
225                 if (context.addPrimaryKey(
226                         DLFileShortcut.class, shortcut.getPrimaryKeyObj())) {
227 
228                     itr.remove();
229                 }
230                 else {
231                     shortcut.setUserUuid(shortcut.getUserUuid());
232                 }
233             }
234 
235             xml = xStream.toXML(shortcuts);
236 
237             el = root.addElement("documentlibrary-shortcuts");
238 
239             tempDoc = PortalUtil.readDocumentFromXML(xml);
240 
241             el.content().add(tempDoc.getRootElement().createCopy());
242 
243             // Ranks
244 
245             itr = ranks.iterator();
246 
247             while (itr.hasNext()) {
248                 DLFileRank rank = (DLFileRank)itr.next();
249 
250                 if (context.addPrimaryKey(
251                         DLFileRank.class, rank.getPrimaryKeyObj())) {
252 
253                     itr.remove();
254                 }
255                 else {
256                     rank.setUserUuid(rank.getUserUuid());
257                 }
258             }
259 
260             xml = xStream.toXML(ranks);
261 
262             el = root.addElement("documentlibrary-ranks");
263 
264             tempDoc = PortalUtil.readDocumentFromXML(xml);
265 
266             el.content().add(tempDoc.getRootElement().createCopy());
267 
268             return doc.asXML();
269         }
270         catch (Exception e) {
271             throw new PortletDataException(e);
272         }
273     }
274 
275     public PortletDataHandlerControl[] getExportControls()
276         throws PortletDataException {
277 
278         return new PortletDataHandlerControl[] {
279             _foldersAndDocuments, _shortcuts, _ranks, _comments, _ratings, _tags
280         };
281     }
282 
283     public PortletDataHandlerControl[] getImportControls()
284         throws PortletDataException {
285 
286         return new PortletDataHandlerControl[] {
287             _foldersAndDocuments, _shortcuts, _ranks, _comments, _ratings, _tags
288         };
289     }
290 
291     public PortletPreferences importData(
292             PortletDataContext context, String portletId,
293             PortletPreferences prefs, String data)
294         throws PortletDataException {
295 
296         try {
297             XStream xStream = new XStream();
298 
299             Document doc = PortalUtil.readDocumentFromXML(data);
300 
301             Element root = doc.getRootElement();
302 
303             // Folders
304 
305             Element el = root.element(
306                 "documentlibrary-folders").element("list");
307 
308             Document tempDoc = DocumentHelper.createDocument();
309 
310             tempDoc.content().add(el.createCopy());
311 
312             Map folderPKs = CollectionFactory.getHashMap();
313 
314             List folders = (List)xStream.fromXML(tempDoc.asXML());
315 
316             Iterator itr = folders.iterator();
317 
318             while (itr.hasNext()) {
319                 DLFolder folder = (DLFolder)itr.next();
320 
321                 importFolder(context, folderPKs, folder);
322             }
323 
324             // Entries
325 
326             el = root.element("documentlibrary-entries").element("list");
327 
328             tempDoc = DocumentHelper.createDocument();
329 
330             tempDoc.content().add(el.createCopy());
331 
332             Map entryNames = CollectionFactory.getHashMap();
333 
334             List entries = (List)xStream.fromXML(tempDoc.asXML());
335 
336             itr = entries.iterator();
337 
338             while (itr.hasNext()) {
339                 DLFileEntry entry = (DLFileEntry)itr.next();
340 
341                 importEntry(context, folderPKs, entryNames, entry);
342             }
343 
344             // Shortcuts
345 
346             if (context.getBooleanParameter(_NAMESPACE, "shortcuts")) {
347                 el = root.element("documentlibrary-shortcuts").element("list");
348 
349                 tempDoc = DocumentHelper.createDocument();
350 
351                 tempDoc.content().add(el.createCopy());
352 
353                 List shortcuts = (List)xStream.fromXML(tempDoc.asXML());
354 
355                 itr = shortcuts.iterator();
356 
357                 while (itr.hasNext()) {
358                     DLFileShortcut shortcut = (DLFileShortcut)itr.next();
359 
360                     importShortcut(context, folderPKs, entryNames, shortcut);
361                 }
362             }
363 
364             // Ranks
365 
366             if (context.getBooleanParameter(_NAMESPACE, "ranks")) {
367                 el = root.element("documentlibrary-ranks").element("list");
368 
369                 tempDoc = DocumentHelper.createDocument();
370 
371                 tempDoc.content().add(el.createCopy());
372 
373                 List ranks = (List)xStream.fromXML(tempDoc.asXML());
374 
375                 itr = ranks.iterator();
376 
377                 while (itr.hasNext()) {
378                     DLFileRank rank = (DLFileRank)itr.next();
379 
380                     importRank(context, folderPKs, entryNames, rank);
381                 }
382             }
383 
384             return null;
385         }
386         catch (Exception e) {
387             throw new PortletDataException(e);
388         }
389     }
390 
391     protected void importEntry(
392             PortletDataContext context, Map folderPKs, Map entryNames,
393             DLFileEntry entry)
394         throws Exception {
395 
396         long userId = context.getUserId(entry.getUserUuid());
397         long folderId = MapUtil.getLong(
398             folderPKs, entry.getFolderId(), entry.getFolderId());
399 
400         String[] tagsEntries = null;
401 
402         if (context.getBooleanParameter(_NAMESPACE, "tags")) {
403             tagsEntries = context.getTagsEntries(
404                 DLFileEntry.class, entry.getPrimaryKeyObj());
405         }
406 
407         boolean addCommunityPermissions = true;
408         boolean addGuestPermissions = true;
409 
410         byte[] byteArray = context.getZipReader().getEntryAsByteArray(
411             _ZIP_FOLDER + entry.getName());
412 
413         DLFileEntry existingEntry = null;
414 
415         try {
416             DLFolderUtil.findByPrimaryKey(folderId);
417 
418             if (context.getDataStrategy().equals(
419                     PortletDataHandlerKeys.DATA_STRATEGY_MIRROR)) {
420 
421                 try {
422                     existingEntry = DLFileEntryFinderUtil.findByUuid_G(
423                         entry.getUuid(), context.getGroupId());
424 
425                     existingEntry = DLFileEntryLocalServiceUtil.updateFileEntry(
426                         userId, existingEntry.getFolderId(), folderId,
427                         existingEntry.getName(), entry.getName(),
428                         entry.getTitle(), entry.getDescription(), tagsEntries,
429                         entry.getExtraSettings(), byteArray);
430                 }
431                 catch (NoSuchFileEntryException nsfee) {
432                     existingEntry = DLFileEntryLocalServiceUtil.addFileEntry(
433                         entry.getUuid(), userId, folderId, entry.getName(),
434                         entry.getTitle(), entry.getDescription(),
435                         tagsEntries, entry.getExtraSettings(), byteArray,
436                         addCommunityPermissions, addGuestPermissions);
437                 }
438             }
439             else {
440                 existingEntry = DLFileEntryLocalServiceUtil.addFileEntry(
441                     userId, folderId, entry.getName(), entry.getTitle(),
442                     entry.getDescription(), tagsEntries,
443                     entry.getExtraSettings(), byteArray,
444                     addCommunityPermissions, addGuestPermissions);
445             }
446 
447             entryNames.put(entry.getName(), existingEntry.getName());
448 
449             if (context.getBooleanParameter(_NAMESPACE, "comments")) {
450                 context.importComments(
451                     DLFileEntry.class, entry.getPrimaryKeyObj(),
452                     existingEntry.getPrimaryKeyObj(), context.getGroupId());
453             }
454 
455             if (context.getBooleanParameter(_NAMESPACE, "ratings")) {
456                 context.importRatingsEntries(
457                     DLFileEntry.class, entry.getPrimaryKeyObj(),
458                     existingEntry.getPrimaryKeyObj());
459             }
460         }
461         catch (NoSuchFolderException nsfe) {
462             _log.error(
463                 "Could not find the parent folder for entry " +
464                     entry.getFileEntryId());
465         }
466     }
467 
468     protected void importFolder(
469             PortletDataContext context, Map folderPKs, DLFolder folder)
470         throws Exception {
471 
472         long userId = context.getUserId(folder.getUserUuid());
473         long plid = context.getPlid();
474         long parentFolderId = MapUtil.getLong(
475             folderPKs, folder.getParentFolderId(), folder.getParentFolderId());
476 
477         boolean addCommunityPermissions = true;
478         boolean addGuestPermissions = true;
479 
480         DLFolder existingFolder = null;
481 
482         try {
483             if (parentFolderId != DLFolderImpl.DEFAULT_PARENT_FOLDER_ID) {
484                 DLFolderUtil.findByPrimaryKey(parentFolderId);
485             }
486 
487             if (context.getDataStrategy().equals(
488                     PortletDataHandlerKeys.DATA_STRATEGY_MIRROR)) {
489 
490                 existingFolder = DLFolderUtil.fetchByUUID_G(
491                     folder.getUuid(), context.getGroupId());
492 
493                 if (existingFolder == null) {
494                     existingFolder = DLFolderLocalServiceUtil.addFolder(
495                         folder.getUuid(), userId, plid, parentFolderId,
496                         folder.getName(), folder.getDescription(),
497                         addCommunityPermissions, addGuestPermissions);
498                 }
499                 else {
500                     existingFolder = DLFolderLocalServiceUtil.updateFolder(
501                         existingFolder.getFolderId(), parentFolderId,
502                         folder.getName(), folder.getDescription());
503                 }
504             }
505             else {
506                 existingFolder = DLFolderLocalServiceUtil.addFolder(
507                     userId, plid, parentFolderId, folder.getName(),
508                     folder.getDescription(), addCommunityPermissions,
509                     addGuestPermissions);
510             }
511 
512             folderPKs.put(
513                 folder.getPrimaryKeyObj(), existingFolder.getPrimaryKeyObj());
514         }
515         catch (NoSuchFolderException nsfe) {
516             _log.error(
517                 "Could not find the parent folder for folder " +
518                     folder.getFolderId());
519         }
520     }
521 
522     protected void importRank(
523             PortletDataContext context, Map folderPKs, Map entryNames,
524             DLFileRank rank)
525         throws Exception {
526 
527         long userId = context.getUserId(rank.getUserUuid());
528         long folderId = MapUtil.getLong(
529             folderPKs, rank.getFolderId(), rank.getFolderId());
530 
531         String name = (String)folderPKs.get(rank.getName());
532 
533         if (name == null) {
534             name = rank.getName();
535         }
536 
537         try {
538             DLFolderUtil.findByPrimaryKey(folderId);
539 
540             DLFileRankLocalServiceUtil.updateFileRank(
541                 context.getGroupId(), context.getCompanyId(), userId, folderId,
542                 name);
543         }
544         catch (NoSuchFolderException nsfe) {
545             _log.error(
546                 "Could not find the folder for rank " + rank.getFileRankId());
547         }
548     }
549 
550     protected void importShortcut(
551             PortletDataContext context, Map folderPKs, Map entryNames,
552             DLFileShortcut shortcut)
553         throws Exception {
554 
555         long userId = context.getUserId(shortcut.getUserUuid());
556         long folderId = MapUtil.getLong(
557             folderPKs, shortcut.getFolderId(), shortcut.getFolderId());
558         long toFolderId = MapUtil.getLong(
559             folderPKs, shortcut.getToFolderId(), shortcut.getToFolderId());
560         String toName = MapUtil.getString(
561             entryNames, shortcut.getToName(), shortcut.getToName());
562 
563         boolean addCommunityPermissions = true;
564         boolean addGuestPermissions = true;
565 
566         try {
567             DLFolderUtil.findByPrimaryKey(folderId);
568             DLFolderUtil.findByPrimaryKey(toFolderId);
569 
570             if (context.getDataStrategy().equals(
571                     PortletDataHandlerKeys.DATA_STRATEGY_MIRROR)) {
572 
573                 try {
574                     DLFileShortcut existingShortcut =
575                         DLFileShortcutFinderUtil.findByUuid_G(
576                             shortcut.getUuid(), context.getGroupId());
577 
578                     DLFileShortcutLocalServiceUtil.updateFileShortcut(
579                         userId, existingShortcut.getFileShortcutId(), folderId,
580                         toFolderId, toName);
581                 }
582                 catch (NoSuchFileShortcutException nsfse) {
583                     DLFileShortcutLocalServiceUtil.addFileShortcut(
584                         shortcut.getUuid(), userId, folderId, toFolderId,
585                         toName, addCommunityPermissions, addGuestPermissions);
586                 }
587             }
588             else {
589                 DLFileShortcutLocalServiceUtil.addFileShortcut(
590                     userId, folderId, toFolderId, toName,
591                     addCommunityPermissions, addGuestPermissions);
592             }
593         }
594         catch (NoSuchFolderException nsfe) {
595             _log.error(
596                 "Could not find the folder for shortcut " +
597                     shortcut.getFileShortcutId());
598         }
599     }
600 
601     private static final String _NAMESPACE = "document_library";
602 
603     private static final String _ZIP_FOLDER = "document-library/";
604 
605     private static final PortletDataHandlerBoolean _foldersAndDocuments =
606         new PortletDataHandlerBoolean(
607             _NAMESPACE, "folders-and-documents", true, true);
608 
609     private static final PortletDataHandlerBoolean _ranks =
610         new PortletDataHandlerBoolean(_NAMESPACE, "ranks");
611 
612     private static final PortletDataHandlerBoolean _shortcuts=
613         new PortletDataHandlerBoolean(_NAMESPACE, "shortcuts");
614 
615     private static final PortletDataHandlerBoolean _comments =
616         new PortletDataHandlerBoolean(_NAMESPACE, "comments");
617 
618     private static final PortletDataHandlerBoolean _ratings =
619         new PortletDataHandlerBoolean(_NAMESPACE, "ratings");
620 
621     private static final PortletDataHandlerBoolean _tags =
622         new PortletDataHandlerBoolean(_NAMESPACE, "tags");
623 
624     private static Log _log =
625         LogFactory.getLog(DLPortletDataHandlerImpl.class);
626 
627 }