1
22
23 package com.liferay.portal.theme;
24
25 import com.liferay.portal.kernel.util.FileUtil;
26 import com.liferay.portal.kernel.util.GetterUtil;
27 import com.liferay.portal.kernel.util.Validator;
28 import com.liferay.portal.service.ThemeLocalServiceUtil;
29 import com.liferay.portal.util.DocumentUtil;
30 import com.liferay.portal.util.PropsValues;
31
32 import java.io.File;
33
34 import java.util.HashMap;
35 import java.util.Map;
36
37 import javax.servlet.ServletContext;
38
39 import org.apache.commons.logging.Log;
40 import org.apache.commons.logging.LogFactory;
41
42 import org.dom4j.Document;
43 import org.dom4j.Element;
44
45
51 public class ThemeLoader {
52
53 public String getServletContextName() {
54 return _servletContextName;
55 }
56
57 public String getThemesPath() {
58 return _themesPath;
59 }
60
61 public File getFileStorage() {
62 return _fileStorage;
63 }
64
65 public synchronized void loadThemes() {
66 if (_log.isInfoEnabled()) {
67 _log.info("Loading themes in " + _fileStorage);
68 }
69
70 File[] files = _fileStorage.listFiles();
71
72 if (files == null) {
73 if (_log.isWarnEnabled()) {
74 _log.warn(
75 "There are no directories to process for " + _fileStorage);
76 }
77
78 return;
79 }
80
81 for (int i = 0; i < files.length; i++) {
82 if (_log.isDebugEnabled()) {
83 _log.debug("Process directory " + files[i]);
84 }
85
86 File liferayLookAndFeelXML = new File(
87 files[i] + "/liferay-look-and-feel.xml");
88
89 if (liferayLookAndFeelXML.exists()) {
90 String lastModifiedKey = liferayLookAndFeelXML.toString();
91
92 Long prevLastModified = _lastModifiedMap.get(lastModifiedKey);
93
94 long lastModified = liferayLookAndFeelXML.lastModified();
95
96 if ((prevLastModified == null) ||
97 (prevLastModified.longValue() < lastModified)) {
98
99 registerTheme(liferayLookAndFeelXML);
100
101 _lastModifiedMap.put(lastModifiedKey, lastModified);
102 }
103 else {
104 if (_log.isDebugEnabled()) {
105 _log.debug(
106 "Do not refresh " + liferayLookAndFeelXML +
107 " because it is has not been modified");
108 }
109 }
110 }
111 else {
112 if (_log.isWarnEnabled()) {
113 _log.warn(liferayLookAndFeelXML + " does not exist");
114 }
115 }
116 }
117 }
118
119 protected ThemeLoader(
120 String servletContextName, ServletContext servletContext,
121 String[] xmls) {
122
123 _servletContextName = servletContextName;
124 _servletContext = servletContext;
125
126 try {
127 Document doc = DocumentUtil.readDocumentFromXML(xmls[0], true);
128
129 Element root = doc.getRootElement();
130
131 _themesPath = GetterUtil.getString(
132 root.elementText("themes-path"), "/themes");
133
134 String fileStorageValue = PropsValues.THEME_LOADER_STORAGE_PATH;
135
136 fileStorageValue = GetterUtil.getString(
137 root.elementText("file-storage"), fileStorageValue);
138
139 if (Validator.isNotNull(fileStorageValue)) {
140 _fileStorage = new File(fileStorageValue);
141 _loadFromServletContext = false;
142 }
143 else {
144 _fileStorage = new File(
145 servletContext.getRealPath(_themesPath));
146 _loadFromServletContext = true;
147 }
148
149 if (!_fileStorage.exists()) {
150 if (_log.isWarnEnabled()) {
151 _log.warn(
152 "File storage " + _fileStorage + " does not exist");
153 }
154
155 if (!_fileStorage.mkdirs()) {
156 _log.error(
157 "Unable to create theme loader file storage at " +
158 _fileStorage);
159 }
160 }
161 }
162 catch (Exception e) {
163 _log.error(e, e);
164 }
165
166 loadThemes();
167 }
168
169 protected void destroy() {
170 }
171
172 protected void registerTheme(File liferayLookAndFeelXML) {
173 if (_log.isDebugEnabled()) {
174 _log.debug("Registering " + liferayLookAndFeelXML);
175 }
176
177 try {
178 String content = FileUtil.read(liferayLookAndFeelXML);
179
180 ThemeLocalServiceUtil.init(
181 _servletContextName, _servletContext, _themesPath,
182 _loadFromServletContext, new String[] {content}, null);
183 }
184 catch (Exception e) {
185 _log.error(
186 "Error registering theme " + liferayLookAndFeelXML.toString(),
187 e);
188 }
189 }
190
191 private static Log _log = LogFactory.getLog(ThemeLoader.class);
192
193 private String _servletContextName;
194 private ServletContext _servletContext;
195 private String _themesPath;
196 private File _fileStorage;
197 private boolean _loadFromServletContext = true;
198 private Map<String, Long> _lastModifiedMap = new HashMap<String, Long>();
199
200 }