1 13 package info.magnolia.cms.core; 14 15 import info.magnolia.cms.beans.config.Server; 16 import info.magnolia.cms.security.AccessDeniedException; 17 import info.magnolia.cms.security.AccessManager; 18 import info.magnolia.cms.security.Authenticator; 19 import info.magnolia.cms.security.Permission; 20 21 import java.util.ArrayList ; 22 import java.util.Collection ; 23 import java.util.Collections ; 24 import java.util.Comparator ; 25 import java.util.Date ; 26 import java.util.List ; 27 28 import javax.jcr.Item; 29 import javax.jcr.Node; 30 import javax.jcr.NodeIterator; 31 import javax.jcr.PathNotFoundException; 32 import javax.jcr.Property; 33 import javax.jcr.PropertyIterator; 34 import javax.jcr.RepositoryException; 35 import javax.jcr.UnsupportedRepositoryOperationException; 36 import javax.jcr.Value; 37 import javax.jcr.lock.Lock; 38 import javax.jcr.lock.LockException; 39 import javax.jcr.nodetype.NodeType; 40 import javax.jcr.version.Version; 41 import javax.jcr.version.VersionException; 42 import javax.jcr.version.VersionHistory; 43 import javax.jcr.version.VersionIterator; 44 import javax.servlet.http.HttpServletRequest ; 45 46 import org.apache.commons.lang.StringUtils; 47 import org.apache.log4j.Logger; 48 import org.doomdark.uuid.UUIDGenerator; 49 50 51 55 public class Content extends ContentHandler implements Cloneable { 56 57 60 private static Logger log = Logger.getLogger(Content.class); 61 62 65 private static final String PROPERTY_UUID = "mgnl:uuid"; 67 70 protected Node node; 71 72 75 private String path; 76 77 80 private Node rootNode; 81 82 85 private MetaData metaData; 86 87 90 protected Content() { 91 } 92 93 103 public Content(Node rootNode, String path, AccessManager manager) 104 throws PathNotFoundException, 105 RepositoryException, 106 AccessDeniedException { 107 Access.isGranted(manager, Path.getAbsolutePath(rootNode.getPath(), path), Permission.READ); 108 this.setPath(path); 109 this.setRootNode(rootNode); 110 this.setNode(this.rootNode.getNode(this.path)); 111 this.setAccessManager(manager); 112 } 113 114 122 public Content(Item elem, AccessManager manager) throws RepositoryException, AccessDeniedException { 123 Access.isGranted(manager, Path.getAbsolutePath(elem.getPath()), Permission.READ); 124 this.setNode((Node) elem); 125 this.setPath(this.getHandle()); 126 this.setAccessManager(manager); 127 } 128 129 141 public Content(Node rootNode, String path, String contentType, AccessManager manager) 142 throws PathNotFoundException, 143 RepositoryException, 144 AccessDeniedException { 145 Access.isGranted(manager, Path.getAbsolutePath(rootNode.getPath(), path), Permission.WRITE); 146 this.setPath(path); 147 this.setRootNode(rootNode); 148 this.node = this.rootNode.addNode(this.path, contentType); 149 this.addUUID(); 150 this.setAccessManager(manager); 151 this.addMixin(ItemType.MIX_VERSIONABLE); 152 } 153 154 158 public Object clone() { return super.clone(); 161 } 162 163 166 protected void setNode(Node node) { 167 this.node = node; 168 } 169 170 173 protected void setRootNode(Node node) { 174 this.rootNode = node; 175 } 176 177 180 protected void setPath(String path) { 181 this.path = path; 182 } 183 184 194 public Content getContentNode(String path) throws PathNotFoundException, RepositoryException, AccessDeniedException { 195 Content content = new Content(this.node, path, this.accessManager); 196 return content; 197 } 198 199 209 public Content createContentNode(String name) throws PathNotFoundException, RepositoryException, 210 AccessDeniedException { 211 return this.createContent(name, ItemType.CONTENTNODE); 212 } 213 214 223 public Content getContent(String name) throws PathNotFoundException, RepositoryException, AccessDeniedException { 224 return (new Content(this.node, name, this.accessManager)); 225 } 226 227 236 public Content createContent(String name) throws PathNotFoundException, RepositoryException, AccessDeniedException { 237 return this.createContent(name, ItemType.CONTENT); 238 } 239 240 250 public Content createContent(String name, String contentType) throws PathNotFoundException, RepositoryException, 251 AccessDeniedException { 252 Content content = (new Content(this.node, name, contentType, this.accessManager)); 253 MetaData metaData = content.getMetaData(); 254 metaData.setCreationDate(); 255 return content; 256 } 257 258 268 public Content createContent(String name, ItemType contentType) throws PathNotFoundException, RepositoryException, 269 AccessDeniedException { 270 Content content = (new Content(this.node, name, contentType.getSystemName(), this.accessManager)); 271 MetaData metaData = content.getMetaData(); 272 metaData.setCreationDate(); 273 return content; 274 } 275 276 279 public String getTemplate() { 280 return this.getMetaData().getTemplate(); 281 } 282 283 286 public String getTitle() { 287 return this.getNodeData("title").getString(); } 289 290 294 public MetaData getMetaData() { 295 if (this.metaData == null) { 296 this.metaData = new MetaData(this.node, this.accessManager); 297 } 298 return this.metaData; 299 } 300 301 305 public MetaData getMetaData(String context) { 306 return new MetaData(this.node, context, this.accessManager); 307 } 308 309 313 314 public NodeData getNodeData(String name) { 315 return getNodeData(name, false); 316 } 317 318 323 public NodeData getNodeData(String name, boolean create) { 324 try { 325 return (new NodeData(this.node, name, this.accessManager)); 326 } 327 catch (PathNotFoundException e) { 328 if (create) { 329 try { 330 return this.createNodeData(name); 331 } 332 catch (Exception e1) { 333 log.error("can't create property [" + name + "]"); } 335 } 336 if (log.isDebugEnabled()) { 337 String nodepath = null; 338 try { 339 nodepath = this.node.getPath(); 340 } 341 catch (RepositoryException e1) { 342 } 344 if (log.isDebugEnabled()) { 345 log.debug("Path not found for property [" + name + "] in node " + nodepath); } 347 } 348 349 return (new NodeData()); 350 } 351 catch (RepositoryException re) { 352 String nodepath = null; 353 try { 354 nodepath = this.node.getPath(); 355 } 356 catch (RepositoryException e1) { 357 } 359 log.warn("Repository exception while trying to read property [" + name + "] for node " + nodepath, re); return (new NodeData()); 361 } 362 } 363 364 368 public String getName() { 369 try { 370 return this.node.getName(); 371 } 372 catch (RepositoryException e) { 373 log.error(e.getMessage(), e); 374 } 375 return StringUtils.EMPTY; 376 } 377 378 387 public NodeData createNodeData(String name) throws PathNotFoundException, RepositoryException, 388 AccessDeniedException { 389 return (new NodeData(this.node, name, true, this.accessManager)); 390 } 391 392 402 public NodeData createNodeData(String name, Value value) throws PathNotFoundException, RepositoryException, 403 AccessDeniedException { 404 return (new NodeData(this.node, name, value, this.accessManager)); 405 } 406 407 418 public NodeData createNodeData(String name, Value value, int type) throws PathNotFoundException, 419 RepositoryException, AccessDeniedException { 420 return createNodeData(name, value); 421 } 422 423 428 public void deleteNodeData(String name) throws PathNotFoundException, RepositoryException { 429 this.node.getProperty(name).remove(); 430 } 431 432 438 public void updateMetaData(HttpServletRequest request) throws RepositoryException, AccessDeniedException { 439 MetaData md = this.getMetaData(); 440 md.setModificationDate(); 441 md.setAuthorId(Authenticator.getUserId(request)); 442 md = null; 443 } 444 445 449 public Collection getChildren() { 450 String type = null; 451 452 try { 453 type = this.getNodeType().getName(); 454 } 455 catch (RepositoryException re) { 456 log.error(re.getMessage()); 457 log.debug(re); 458 } 459 if ("rep:root".equalsIgnoreCase(type)) { type = ItemType.CONTENT.getSystemName(); 463 } 464 return this.getChildren(StringUtils.defaultString(type)); 466 } 467 468 473 public Collection getChildren(String contentType) { 474 return this.getChildren(contentType, ContentHandler.IGNORE_SORT); 475 } 476 477 482 public Collection getChildren(ItemType contentType) { 483 return this.getChildren(contentType.getSystemName(), ContentHandler.IGNORE_SORT); 484 } 485 486 492 public Collection getChildren(String contentType, String namePattern) { 493 return this.getChildren(contentType, namePattern, ContentHandler.IGNORE_SORT); 494 } 495 496 503 public Collection getChildren(String contentType, int sortCriteria) { 504 return this.getChildren(contentType, "*", sortCriteria); } 506 507 514 public Collection getChildren(ItemType contentType, int sortCriteria) { 515 return this.getChildren(contentType.getSystemName(), sortCriteria); 516 } 517 518 526 public Collection getChildren(String contentType, String namePattern, int sortCriteria) { 527 Collection children = new ArrayList (); 528 try { 529 children = this.getChildContent(contentType, namePattern); 530 children = sort(children, sortCriteria); 531 } 532 catch (RepositoryException e) { 533 log.error(e.getMessage(), e); 534 } 535 return children; 536 } 537 538 543 private Collection sort(Collection collection, int sortCriteria) { 544 if (sortCriteria == ContentHandler.SORT_BY_DATE) { 545 return sortByDate(collection); 546 } 547 else if (sortCriteria == ContentHandler.SORT_BY_SEQUENCE) { 548 return sortBySequence(collection); 549 } 550 return collection; 551 } 552 553 559 private Collection getChildContent(String contentType, String namePattern) throws RepositoryException { 560 Collection children = new ArrayList (); 561 NodeIterator nodeIterator = this.node.getNodes(namePattern); 562 while (nodeIterator.hasNext()) { 563 Node subNode = (Node) nodeIterator.next(); 564 try { 565 if (subNode.isNodeType(contentType)) { 566 children.add(new Content(subNode, this.accessManager)); 567 } 568 } 569 catch (PathNotFoundException e) { 570 log.error(e); 571 } 572 catch (AccessDeniedException e) { 573 } 575 } 576 return children; 577 } 578 579 582 public Collection getNodeDataCollection() { 583 Collection children = new ArrayList (); 584 try { 585 PropertyIterator propertyIterator = this.node.getProperties(); 586 while (propertyIterator.hasNext()) { 587 Property property = (Property) propertyIterator.next(); 588 try { 589 if (!property.getName().startsWith("jcr:") && !property.getName().startsWith("mgnl:")) { children.add(new NodeData(property, this.accessManager)); 591 } 592 } 593 catch (PathNotFoundException e) { 594 log.error(e); 595 } 596 catch (AccessDeniedException e) { 597 } 599 } 600 } 601 catch (RepositoryException re) { 602 log.error(re); 603 } 604 return children; 605 } 606 607 611 public Collection getNodeDataCollection(String namePattern) { 612 Collection children = new ArrayList (); 613 try { 614 PropertyIterator propertyIterator = this.node.getProperties(namePattern); 615 if (propertyIterator == null) { 616 return children; 617 } 618 while (propertyIterator.hasNext()) { 619 Property property = (Property) propertyIterator.next(); 620 try { 621 children.add(new NodeData(property, this.accessManager)); 622 } 623 catch (PathNotFoundException e) { 624 log.error(e); 625 } 626 catch (AccessDeniedException e) { 627 } 629 } 630 } 631 catch (RepositoryException re) { 632 log.error(re); 633 } 634 return children; 635 } 636 637 640 public boolean hasChildren() { 641 return (this.getChildren().size() > 0); 642 } 643 644 648 public boolean hasChildren(String contentType) { 649 return (this.getChildren(contentType).size() > 0); 650 } 651 652 657 public boolean hasContent(String name) throws RepositoryException { 658 return this.node.hasNode(name); 659 } 660 661 666 public boolean hasNodeData(String name) throws RepositoryException { 667 return this.node.hasProperty(name); 668 } 669 670 675 public Collection sortByDate(Collection contentCollection) { 676 try { 677 if (contentCollection == null) { 678 return contentCollection; 679 } 680 Collections.sort((List ) contentCollection, new Comparator () { 681 682 public int compare(Object o1, Object o2) { 683 Date date1 = ((Content) o1).getMetaData().getCreationDate().getTime(); 684 Date date2 = ((Content) o2).getMetaData().getCreationDate().getTime(); 685 return date1.compareTo(date2); 686 } 687 }); 688 } 689 catch (Exception e) { 690 log.error(e.getMessage()); 691 } 692 return contentCollection; 693 } 694 695 700 public Collection sortBySequence(Collection contentCollection) { 701 try { 702 if (contentCollection == null) { 703 return contentCollection; 704 } 705 Collections.sort((List ) contentCollection, new Comparator () { 706 707 public int compare(Object o0, Object o1) { 708 try { 709 long pos0 = (((Content) o0).getMetaData().getSequencePosition()); 710 long pos1 = (((Content) o1).getMetaData().getSequencePosition()); 711 String s0 = "0"; String s1 = "0"; if (pos0 > pos1) { 714 s0 = "1"; } 716 else if (pos0 < pos1) { 717 s1 = "1"; } 719 return s0.compareTo(s1); 720 } 721 catch (Exception e) { 722 return 0; 723 } 724 } 725 726 }); 727 } 728 catch (Exception e) { 729 log.error(e.getMessage(), e); 730 } 731 return contentCollection; 732 } 733 734 738 public String getHandle() { 739 try { 740 return this.node.getPath(); 741 } 742 catch (RepositoryException e) { 743 log.error("Failed to get handle: " + e.getMessage(), e); return StringUtils.EMPTY; 745 } 746 } 747 748 753 public String getHandleWithDefaultExtension() throws PathNotFoundException, RepositoryException { 754 return (this.node.getPath() + "." + Server.getDefaultExtension()); } 756 757 765 public Content getParent() throws PathNotFoundException, RepositoryException, AccessDeniedException { 766 return (new Content(this.node.getParent(), this.accessManager)); 767 } 768 769 777 public Content getAncestor(int digree) throws PathNotFoundException, RepositoryException, AccessDeniedException { 778 if (digree > this.getLevel()) { 779 throw new PathNotFoundException(); 780 } 781 return (new Content(this.node.getAncestor(digree), this.accessManager)); 782 } 783 784 789 public Collection getAncestors() throws PathNotFoundException, RepositoryException { 790 List allAncestors = new ArrayList (); 791 int level = this.getLevel(); 792 while (level != 0) { 793 try { 794 allAncestors.add(new Content(this.node.getAncestor(--level), this.accessManager)); 795 } 796 catch (AccessDeniedException e) { 797 } 799 } 800 return allAncestors; 801 } 802 803 809 public int getLevel() throws PathNotFoundException, RepositoryException { 810 return this.node.getPath().split("/").length - 1; } 812 813 819 public void orderBefore(String srcName, String beforeName) throws RepositoryException { 820 this.node.orderBefore(srcName, beforeName); 821 } 822 823 831 public int getIndex() throws RepositoryException { 832 return this.node.getIndex(); 833 } 834 835 839 public Node getJCRNode() { 840 return this.node; 841 } 842 843 846 public boolean isNodeType(String type) { 847 try { 848 return this.node.isNodeType(type); 849 } 850 catch (RepositoryException re) { 851 log.error(re.getMessage()); 852 log.debug(re); 853 } 854 return false; 855 } 856 857 861 public NodeType getNodeType() throws RepositoryException { 862 return this.node.getPrimaryNodeType(); 863 } 864 865 874 public void restore(String versionName, boolean removeExisting) throws VersionException, 875 UnsupportedRepositoryOperationException, RepositoryException { 876 this.node.restore(versionName, removeExisting); 877 } 878 879 887 public void restore(Version version, boolean removeExisting) throws VersionException, 888 UnsupportedRepositoryOperationException, RepositoryException { 889 this.node.restore(version, removeExisting); 890 } 891 892 901 public void restore(Version version, String relPath, boolean removeExisting) throws VersionException, 902 UnsupportedRepositoryOperationException, RepositoryException { 903 this.node.restore(version, relPath, removeExisting); 904 } 905 906 915 public void restoreByLabel(String versionLabel, boolean removeExisting) throws VersionException, 916 UnsupportedRepositoryOperationException, RepositoryException { 917 this.node.restoreByLabel(versionLabel, removeExisting); 918 } 919 920 924 public Version addVersion() throws UnsupportedRepositoryOperationException, RepositoryException { 925 Version version = this.checkIn(); 926 this.checkOut(); 927 return version; 928 } 929 930 934 public Version checkIn() throws UnsupportedRepositoryOperationException, RepositoryException { 935 return this.node.checkin(); 936 } 937 938 942 public void checkOut() throws UnsupportedRepositoryOperationException, RepositoryException { 943 this.node.checkout(); 944 } 945 946 950 public VersionHistory getVersionHistory() throws UnsupportedRepositoryOperationException, RepositoryException { 951 return this.node.getVersionHistory(); 952 } 953 954 958 public VersionIterator getAllVersions() throws UnsupportedRepositoryOperationException, RepositoryException { 959 return this.getVersionHistory().getAllVersions(); 960 } 961 962 966 public void save() throws RepositoryException { 967 this.node.getSession().save(); 968 } 969 970 975 public boolean isGranted(long permissions) { 976 try { 977 Access.isGranted(this.accessManager, Path.getAbsolutePath(node.getPath()), permissions); 978 return true; 979 } 980 catch (RepositoryException re) { 981 log.debug(this.getHandle() + " says: no access"); } 983 return false; 984 } 985 986 990 public void delete() throws RepositoryException { 991 Access.isGranted(this.accessManager, Path.getAbsolutePath(this.node.getPath()), Permission.REMOVE); 992 this.node.remove(); 993 } 994 995 999 public void delete(String path) throws RepositoryException { 1000 Access.isGranted(this.accessManager, Path.getAbsolutePath(this.node.getPath(), path), Permission.REMOVE); 1001 if (this.isNodeData(path)) { 1002 this.node.getProperty(path).remove(); 1003 } 1004 else { 1005 this.node.getNode(path).remove(); 1006 } 1007 } 1008 1009 1018 public boolean isNodeData(String path) throws AccessDeniedException, RepositoryException { 1019 Access.isGranted(this.accessManager, Path.getAbsolutePath(this.node.getPath(), path), Permission.READ); 1020 try { 1021 return this.node.hasProperty(path); 1022 } 1023 catch (RepositoryException e) { 1024 log.debug("isNodeData(): " + e.getMessage()); } 1026 return false; 1027 } 1028 1029 1034 public void refresh(boolean keepChanges) throws RepositoryException { 1035 this.node.refresh(keepChanges); 1036 } 1037 1038 1042 public String getUUID() { 1043 return this.getNodeData(PROPERTY_UUID).getString(); 1044 } 1045 1046 1051 public void addMixin(String type) throws RepositoryException { 1052 Access.isGranted(this.accessManager, Path.getAbsolutePath(this.node.getPath()), Permission.SET); 1053 if (this.node.canAddMixin(type)) { 1054 this.node.addMixin(type); 1055 } 1056 else { 1057 log.error("Node - " + this.node.getPath() + " does not allow mixin type - " + type); } 1059 } 1060 1061 1067 public void removeMixin(String type) throws RepositoryException { 1068 Access.isGranted(this.accessManager, Path.getAbsolutePath(this.node.getPath()), Permission.SET); 1069 this.node.removeMixin(type); 1070 } 1071 1072 1079 public NodeType[] getMixinNodeTypes() throws RepositoryException { 1080 return this.node.getMixinNodeTypes(); 1081 } 1082 1083 1095 public Lock lock(boolean isDeep, boolean isSessionScoped) throws LockException, RepositoryException { 1096 return this.node.lock(isDeep, isSessionScoped); 1097 } 1098 1099 1105 public Lock getLock() throws LockException, RepositoryException { 1106 return this.node.getLock(); 1107 } 1108 1109 1116 public void unlock() throws LockException, RepositoryException { 1117 this.node.unlock(); 1118 } 1119 1120 1126 public boolean holdsLock() throws RepositoryException { 1127 return this.node.holdsLock(); 1128 } 1129 1130 1134 private void addUUID() throws RepositoryException { 1135 this.node.setProperty(PROPERTY_UUID, UUIDGenerator.getInstance().generateTimeBasedUUID().toString()); 1136 } 1137} 1138 | Popular Tags |