001
014
015 package com.liferay.portal.patcher;
016
017 import com.liferay.portal.kernel.log.Log;
018 import com.liferay.portal.kernel.log.LogFactoryUtil;
019 import com.liferay.portal.kernel.patcher.PatchInconsistencyException;
020 import com.liferay.portal.kernel.patcher.Patcher;
021 import com.liferay.portal.kernel.security.pacl.DoPrivileged;
022 import com.liferay.portal.kernel.util.ArrayUtil;
023 import com.liferay.portal.kernel.util.FileUtil;
024 import com.liferay.portal.kernel.util.StreamUtil;
025 import com.liferay.portal.kernel.util.StringPool;
026 import com.liferay.portal.kernel.util.StringUtil;
027 import com.liferay.portal.kernel.util.Validator;
028
029 import java.io.File;
030 import java.io.IOException;
031 import java.io.InputStream;
032
033 import java.util.Arrays;
034 import java.util.Properties;
035
036
041 @DoPrivileged
042 public class PatcherImpl implements Patcher {
043
044 @Override
045 public boolean applyPatch(File patchFile) {
046 File patchDirectory = getPatchDirectory();
047
048 if (patchDirectory == null) {
049 return false;
050 }
051
052 try {
053 FileUtil.copyFile(
054 patchFile,
055 new File(
056 patchDirectory + StringPool.SLASH + patchFile.getName()));
057
058 return true;
059 }
060 catch (Exception e) {
061 _log.error(
062 "Unable to copy " + patchFile.getAbsolutePath() + " to " +
063 patchDirectory.getAbsolutePath());
064
065 return false;
066 }
067 }
068
069 @Override
070 public String[] getFixedIssues() {
071 if (_fixedIssueKeys != null) {
072 return _fixedIssueKeys;
073 }
074
075 Properties properties = getProperties();
076
077 _fixedIssueKeys = StringUtil.split(
078 properties.getProperty(PROPERTY_FIXED_ISSUES));
079
080 return _fixedIssueKeys;
081 }
082
083 @Override
084 public String[] getInstalledPatches() {
085 if (_installedPatchNames != null) {
086 return _installedPatchNames;
087 }
088
089 return _getInstalledPatches(null);
090 }
091
092 @Override
093 public File getPatchDirectory() {
094 if (_patchDirectory != null) {
095 return _patchDirectory;
096 }
097
098 Properties properties = getProperties();
099
100 String patchDirectoryName = properties.getProperty(
101 PROPERTY_PATCH_DIRECTORY);
102
103 if (Validator.isNotNull(patchDirectoryName)) {
104 _patchDirectory = new File(patchDirectoryName);
105
106 if (!_patchDirectory.exists()) {
107 _log.error("The patch directory does not exist");
108 }
109 }
110 else {
111 _log.error("The patch directory is not specified");
112 }
113
114 return _patchDirectory;
115 }
116
117 @Override
118 public String[] getPatchLevels() {
119 if (_patchLevels != null) {
120 return _patchLevels;
121 }
122
123 Properties properties = getProperties();
124
125 _patchLevels = StringUtil.split(
126 properties.getProperty(PROPERTY_PATCH_LEVELS));
127
128 return _patchLevels;
129 }
130
131 @Override
132 public Properties getProperties() {
133 if (_properties != null) {
134 return _properties;
135 }
136
137 return _getProperties(PATCHER_PROPERTIES);
138 }
139
140 @Override
141 public boolean isConfigured() {
142 return _configured;
143 }
144
145 @Override
146 public boolean hasInconsistentPatchLevels() {
147 return _inconsistentPatchLevels;
148 }
149
150 @Override
151 public void verifyPatchLevels() throws PatchInconsistencyException {
152 Properties portalImplJARProperties = _getProperties(PATCHER_PROPERTIES);
153
154 String[] portalImplJARPatches = _getInstalledPatches(
155 portalImplJARProperties);
156
157 Arrays.sort(portalImplJARPatches);
158
159 Properties portalServiceJARProperties = _getProperties(
160 PATCHER_SERVICE_PROPERTIES);
161
162 String[] serviceJARPatches = _getInstalledPatches(
163 portalServiceJARProperties);
164
165 Arrays.sort(serviceJARPatches);
166
167 if (!Arrays.equals(portalImplJARPatches, serviceJARPatches)) {
168 _log.error("Inconsistent patch level detected");
169
170 if (_log.isWarnEnabled()) {
171 if (ArrayUtil.isEmpty(portalImplJARPatches)) {
172 _log.warn(
173 "There are no patches installed on portal-impl.jar");
174 }
175 else {
176 _log.warn(
177 "Patch level on portal-impl.jar: " +
178 Arrays.toString(portalImplJARPatches));
179 }
180
181 if (ArrayUtil.isEmpty(serviceJARPatches)) {
182 _log.warn(
183 "There are no patches installed on portal-service.jar");
184 }
185 else {
186 _log.warn(
187 "Patch level on portal-service.jar: " +
188 Arrays.toString(serviceJARPatches));
189 }
190 }
191
192 _inconsistentPatchLevels = true;
193
194 throw new PatchInconsistencyException();
195 }
196 }
197
198 private String[] _getInstalledPatches(Properties properties) {
199 if (properties == null) {
200 properties = getProperties();
201 }
202
203 _installedPatchNames = StringUtil.split(
204 properties.getProperty(PROPERTY_INSTALLED_PATCHES));
205
206 return _installedPatchNames;
207 }
208
209 private Properties _getProperties(String fileName) {
210 if (Validator.isNull(fileName)) {
211 fileName = PATCHER_PROPERTIES;
212 }
213
214 Properties properties = new Properties();
215
216 Class<?> clazz = getClass();
217
218 if (Validator.equals(fileName, PATCHER_SERVICE_PROPERTIES)) {
219 clazz = clazz.getInterfaces()[0];
220 }
221
222 ClassLoader classLoader = clazz.getClassLoader();
223
224 InputStream inputStream = classLoader.getResourceAsStream(fileName);
225
226 if (inputStream == null) {
227 if (_log.isDebugEnabled()) {
228 _log.debug("Unable to load " + fileName);
229 }
230 }
231 else {
232 try {
233 properties.load(inputStream);
234
235 _configured = true;
236 }
237 catch (IOException ioe) {
238 _log.error(ioe, ioe);
239 }
240 finally {
241 StreamUtil.cleanUp(inputStream);
242 }
243 }
244
245 _properties = properties;
246
247 return _properties;
248 }
249
250 private static Log _log = LogFactoryUtil.getLog(PatcherImpl.class);
251
252 private static boolean _configured;
253 private static String[] _fixedIssueKeys;
254 private static boolean _inconsistentPatchLevels;
255 private static String[] _installedPatchNames;
256 private static File _patchDirectory;
257 private static String[] _patchLevels;
258 private static Properties _properties;
259
260 }