1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34 package info.magnolia.commands.impl;
35
36 import info.magnolia.cms.core.version.VersionManager;
37 import info.magnolia.cms.exchange.ActivationManagerFactory;
38 import info.magnolia.cms.exchange.Subscriber;
39 import info.magnolia.cms.i18n.MessagesManager;
40 import info.magnolia.cms.util.ExclusiveWrite;
41 import info.magnolia.cms.util.Rule;
42 import info.magnolia.context.Context;
43 import info.magnolia.jcr.iterator.FilteringNodeIterator;
44 import info.magnolia.jcr.iterator.FilteringPropertyIterator;
45 import info.magnolia.jcr.predicate.JCRMgnlPropertyHidingPredicate;
46 import info.magnolia.jcr.predicate.NodeTypePredicate;
47 import info.magnolia.jcr.util.NodeTypes;
48 import info.magnolia.objectfactory.Components;
49
50 import java.util.Iterator;
51
52 import javax.jcr.Node;
53 import javax.jcr.Property;
54 import javax.jcr.RepositoryException;
55
56 import org.apache.commons.lang.StringUtils;
57
58
59
60
61
62
63
64
65
66
67 public class MarkNodeAsDeletedCommand extends BaseRepositoryCommand {
68
69 public static final String DELETED_NODE_TEMPLATE = "ui-admincentral:deleted";
70
71 public static final String DELETED_NODE_PROP_NAME = "deleteNode";
72
73 private boolean versionManually = true;
74
75 private boolean forcePreDelete;
76
77 private VersionManager versionManager;
78
79 private String[] nodeTypes = new String[]{NodeTypes.Folder.NAME, NodeTypes.Content.NAME};
80
81 @Override
82 public boolean execute(Context context) throws Exception {
83 versionManager = Components.getComponent(VersionManager.class);
84
85 final Node parentNode = getJCRNode(context);
86 final Node node = parentNode.getNode((String) context.get(DELETED_NODE_PROP_NAME));
87 boolean hasActiveSubscriber = false;
88 for (Subscriber subscriber : ActivationManagerFactory.getActivationManager().getSubscribers()) {
89 if (subscriber.isActive()) {
90 hasActiveSubscriber = true;
91 break;
92 }
93 }
94 if (hasActiveSubscriber || isForcePreDelete()) {
95 preDeleteNode(node, context);
96 } else {
97 node.remove();
98 parentNode.getSession().save();
99 }
100
101 return true;
102 }
103
104 protected void preDeleteNode(Node node, Context context) throws RepositoryException {
105
106
107 version(node, context);
108 synchronized (ExclusiveWrite.getInstance()) {
109 markAsDeleted(node);
110 purgeContent(node);
111 storeDeletionInfo(node, context);
112
113 node.getSession().save();
114 }
115
116
117 for (String nodeType : nodeTypes) {
118 for (Iterator<Node> iter = new FilteringNodeIterator(node.getNodes(), new NodeTypePredicate(nodeType, true)); iter.hasNext();) {
119 preDeleteNode(iter.next(), context);
120 }
121 }
122 }
123
124 protected void storeDeletionInfo(Node node, Context context) throws RepositoryException {
125 String comment = (String) context.get("comment");
126 if (comment == null) {
127 comment = MessagesManager.get("versions.comment.restore");
128 }
129 NodeTypes.Deleted.set(node, comment);
130 }
131
132 protected void version(Node node, Context context) throws RepositoryException {
133 if (isVersionManually()) {
134 synchronized (ExclusiveWrite.getInstance()) {
135 String comment = (String) context.get("comment");
136 if (comment == null) {
137 comment = MessagesManager.get("versions.comment.deleted");
138 }
139 node.setProperty(NodeTypes.Deleted.COMMENT, comment);
140 node.getSession().save();
141 }
142 versionManager.addVersion(node, getRule(node));
143 }
144 }
145
146 protected Rule getRule(Node node) throws RepositoryException {
147 return new Rule(StringUtils.join(nodeTypes, ","), ",");
148 }
149
150 protected void markAsDeleted(Node node) throws RepositoryException {
151
152 node.addMixin(NodeTypes.Deleted.NAME);
153
154 NodeTypes.Renderable.set(node, DELETED_NODE_TEMPLATE);
155 }
156
157 protected void purgeContent(Node node) throws RepositoryException {
158
159 for (Iterator<Node> iter = new FilteringNodeIterator(node.getNodes(), new NodeTypePredicate(NodeTypes.ContentNode.NAME)); iter.hasNext();) {
160 iter.next().remove();
161 }
162
163 for (Iterator<Property> iter = new FilteringPropertyIterator(node.getProperties(), new JCRMgnlPropertyHidingPredicate()); iter.hasNext();) {
164 Property property = iter.next();
165 property.remove();
166 }
167 }
168
169 public boolean isVersionManually() {
170 return versionManually;
171 }
172
173 public void setVersionManually(boolean versionManually) {
174 this.versionManually = versionManually;
175 }
176
177 public boolean isForcePreDelete() {
178 return forcePreDelete;
179 }
180
181 public void setForcePreDelete(boolean forcePreDelete) {
182 this.forcePreDelete = forcePreDelete;
183 }
184 }