View Javadoc
1   /**
2    * This file Copyright (c) 2003-2018 Magnolia International
3    * Ltd.  (http://www.magnolia-cms.com). All rights reserved.
4    *
5    *
6    * This file is dual-licensed under both the Magnolia
7    * Network Agreement and the GNU General Public License.
8    * You may elect to use one or the other of these licenses.
9    *
10   * This file is distributed in the hope that it will be
11   * useful, but AS-IS and WITHOUT ANY WARRANTY; without even the
12   * implied warranty of MERCHANTABILITY or FITNESS FOR A
13   * PARTICULAR PURPOSE, TITLE, or NONINFRINGEMENT.
14   * Redistribution, except as permitted by whichever of the GPL
15   * or MNA you select, is prohibited.
16   *
17   * 1. For the GPL license (GPL), you can redistribute and/or
18   * modify this file under the terms of the GNU General
19   * Public License, Version 3, as published by the Free Software
20   * Foundation.  You should have received a copy of the GNU
21   * General Public License, Version 3 along with this program;
22   * if not, write to the Free Software Foundation, Inc., 51
23   * Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
24   *
25   * 2. For the Magnolia Network Agreement (MNA), this file
26   * and the accompanying materials are made available under the
27   * terms of the MNA which accompanies this distribution, and
28   * is available at http://www.magnolia-cms.com/mna.html
29   *
30   * Any modifications to this file must keep this entire header
31   * intact.
32   *
33   */
34  package info.magnolia.module.delta;
35  
36  import info.magnolia.jcr.util.PropertyUtil;
37  import info.magnolia.module.InstallContext;
38  
39  import java.text.MessageFormat;
40  import java.util.Arrays;
41  import java.util.Collection;
42  
43  import javax.jcr.Node;
44  import javax.jcr.Property;
45  import javax.jcr.RepositoryException;
46  
47  import org.apache.commons.lang3.StringUtils;
48  
49  /**
50   * A tasks that offers helper methods to check on certain properties.
51   */
52  public abstract class PropertyValuesTask extends AbstractTask {
53  
54      public PropertyValuesTask(String name, String description) {
55          super(name, description);
56      }
57  
58      /**
59       * Checks that the given String property has the expected value. Changes it if so, logs otherwise.
60       */
61      protected void checkAndModifyPropertyValue(InstallContext ctx, Node node, String propertyName, String expectedCurrentValue, String newValue) throws RepositoryException {
62          checkAndModifyPropertyValue(ctx, node, propertyName, Arrays.asList(expectedCurrentValue), newValue);
63      }
64  
65      /**
66       * Checks that the given String property has one of the expected values. Changes it if so, logs otherwise.
67       */
68      protected void checkAndModifyPropertyValue(InstallContext ctx, Node node, String propertyName, Collection<String> expectedCurrentValues, String newValue) throws RepositoryException {
69          if (node.hasProperty(propertyName)) {
70              final Property prop = node.getProperty(propertyName);
71              final String currentValue = prop.getString();
72  
73              if(StringUtils.equals(currentValue, newValue)){
74                  return;
75              }
76  
77              if (expectedCurrentValues.contains(currentValue)) {
78                  prop.setValue(newValue);
79              } else {
80                  String msg;
81                  if (expectedCurrentValues.size() == 1) {
82                      msg = format("Property \"{0}\" was expected to exist at {1} with value \"{2}\" but has the value \"{3}\" instead.",
83                              propertyName, node.getPath(), expectedCurrentValues.iterator().next(), currentValue);
84                  } else {
85                      msg = format("Property \"{0}\" was expected to exist at {1} with one of values {2} but has the value \"{3}\" instead.",
86                              propertyName, node.getPath(), expectedCurrentValues.toString(), currentValue);
87                  }
88                  ctx.warn(msg);
89              }
90          } else {
91              String msg;
92              if (expectedCurrentValues.size() == 1) {
93                  msg = format("Property \"{0}\" was expected to exist at {1} with value \"{2}\" but does not exist.",
94                          propertyName, node.getPath(), expectedCurrentValues.iterator().next());
95              } else {
96                  msg = format("Property \"{0}\" was expected to exist at {1} with one of values {2} but does not exist.",
97                          propertyName, node.getPath(), expectedCurrentValues.toString());
98              }
99              ctx.warn(msg);
100         }
101     }
102 
103     /**
104      * Checks if property contains concrete string. If contains then change this part of string, logs otherwise.
105      */
106     protected void checkAndModifyPartOfPropertyValue(InstallContext ctx, Node node, String propertyName, String expectedValue, String newValue) throws RepositoryException {
107         if (node.hasProperty(propertyName)) {
108             final Property prop = node.getProperty(propertyName);
109             final String currentvalue = prop.getString();
110             if (currentvalue.contains(expectedValue)) {
111                 prop.setValue(StringUtils.replace(currentvalue, expectedValue, newValue));
112             } else {
113                 final String msg = format("Property \"{0}\" was expected to exist at {1} with part string \"{2}\" but does not contain this string.",
114                         propertyName, node.getPath(), expectedValue);
115                 ctx.warn(msg);
116             }
117         } else {
118             final String msg = format("Property \"{0}\" was expected to exist at {1} with part string \"{2}\" but does not exist.",
119                     propertyName, node.getPath(), expectedValue);
120             ctx.warn(msg);
121         }
122     }
123 
124     protected void checkOrCreateProperty(InstallContext ctx, Node node, String propertyName, String expectedValue) throws RepositoryException {
125 
126         if (node.hasProperty(propertyName)) {
127             final Property prop = node.getProperty(propertyName);
128             final String currentvalue = prop.getString();
129 
130             if (!currentvalue.equals(expectedValue)) {
131                 final String msg = format("Property \"{0}\" was expected to exist at {1} with value \"{2}\" but {3,choice,0#does not exist|1#has the value \"{4}\" instead}.",
132                         propertyName, node.getPath(), expectedValue, 1, currentvalue);
133                 ctx.warn(msg);
134             }
135         } else {
136             node.setProperty(propertyName, expectedValue);
137         }
138     }
139 
140     /**
141      * Checks that the given property does not exist and creates it with the given value, logs otherwise.
142      */
143     protected void newProperty(InstallContext ctx, Node node, String propertyName, Object value) throws RepositoryException {
144         if (!node.hasProperty(propertyName)) {
145             PropertyUtil.setProperty(node, propertyName, value);
146         } else {
147             final String msg = format("Property \"{0}\" was expected not to exist at {1}, but exists with value \"{2}\" and was going to be created with value \"{3}\".",
148                     propertyName, node.getPath(), node.getProperty(propertyName).getValue().getString(), value);
149             ctx.warn(msg);
150         }
151     }
152 
153     // TODO move this to the InstallContext interface ?
154     protected String format(String pattern, Object arg0, Object arg1, Object arg2, Object arg3, Object arg4) {
155         return MessageFormat.format(pattern, arg0, arg1, arg2, arg3, arg4);
156     }
157 
158     protected String format(String pattern, Object arg0, Object arg1, Object arg2, Object arg3) {
159         return format(pattern, arg0, arg1, arg2, arg3, null);
160     }
161 
162     protected String format(String pattern, Object arg0, Object arg1, Object arg2) {
163         return format(pattern, arg0, arg1, arg2, null);
164     }
165 }