001
014
015 package com.liferay.portal.theme;
016
017 import com.liferay.portal.kernel.log.Log;
018 import com.liferay.portal.kernel.log.LogFactoryUtil;
019 import com.liferay.portal.kernel.util.FileUtil;
020 import com.liferay.portal.kernel.util.GetterUtil;
021 import com.liferay.portal.kernel.util.Validator;
022 import com.liferay.portal.kernel.xml.Document;
023 import com.liferay.portal.kernel.xml.Element;
024 import com.liferay.portal.kernel.xml.UnsecureSAXReaderUtil;
025 import com.liferay.portal.service.ThemeLocalServiceUtil;
026 import com.liferay.portal.util.PropsValues;
027
028 import java.io.File;
029
030 import java.util.HashMap;
031 import java.util.Map;
032
033 import javax.servlet.ServletContext;
034
035
038 public class ThemeLoader {
039
040 public File getFileStorage() {
041 return _fileStorage;
042 }
043
044 public String getServletContextName() {
045 return _servletContextName;
046 }
047
048 public String getThemesPath() {
049 return _themesPath;
050 }
051
052 public synchronized void loadThemes() {
053 if (_log.isInfoEnabled()) {
054 _log.info("Loading themes in " + _fileStorage);
055 }
056
057 File[] files = _fileStorage.listFiles();
058
059 if (files == null) {
060 if (_log.isWarnEnabled()) {
061 _log.warn(
062 "There are no directories to process for " + _fileStorage);
063 }
064
065 return;
066 }
067
068 for (int i = 0; i < files.length; i++) {
069 if (_log.isDebugEnabled()) {
070 _log.debug("Process directory " + files[i]);
071 }
072
073 File liferayLookAndFeelXML = new File(
074 files[i] + "/liferay-look-and-feel.xml");
075
076 if (liferayLookAndFeelXML.exists()) {
077 String lastModifiedKey = liferayLookAndFeelXML.toString();
078
079 Long prevLastModified = _lastModifiedMap.get(lastModifiedKey);
080
081 long lastModified = liferayLookAndFeelXML.lastModified();
082
083 if ((prevLastModified == null) ||
084 (prevLastModified.longValue() < lastModified)) {
085
086 registerTheme(liferayLookAndFeelXML);
087
088 _lastModifiedMap.put(lastModifiedKey, lastModified);
089 }
090 else {
091 if (_log.isDebugEnabled()) {
092 _log.debug(
093 "Do not refresh " + liferayLookAndFeelXML +
094 " because it is has not been modified");
095 }
096 }
097 }
098 else {
099 if (_log.isWarnEnabled()) {
100 _log.warn(liferayLookAndFeelXML + " does not exist");
101 }
102 }
103 }
104 }
105
106 protected ThemeLoader(
107 String servletContextName, ServletContext servletContext,
108 String[] xmls) {
109
110 _servletContextName = servletContextName;
111 _servletContext = servletContext;
112
113 try {
114 Document doc = UnsecureSAXReaderUtil.read(xmls[0], true);
115
116 Element root = doc.getRootElement();
117
118 _themesPath = GetterUtil.getString(
119 root.elementText("themes-path"), "/themes");
120
121 String fileStorageValue = PropsValues.THEME_LOADER_STORAGE_PATH;
122
123 fileStorageValue = GetterUtil.getString(
124 root.elementText("file-storage"), fileStorageValue);
125
126 if (Validator.isNotNull(fileStorageValue)) {
127 _fileStorage = new File(fileStorageValue);
128 _loadFromServletContext = false;
129 }
130 else {
131 _fileStorage = new File(
132 servletContext.getRealPath(_themesPath));
133 _loadFromServletContext = true;
134 }
135
136 if (!_fileStorage.exists()) {
137 if (_log.isWarnEnabled()) {
138 _log.warn(
139 "File storage " + _fileStorage + " does not exist");
140 }
141
142 if (!_fileStorage.mkdirs()) {
143 _log.error(
144 "Unable to create theme loader file storage at " +
145 _fileStorage);
146 }
147 }
148 }
149 catch (Exception e) {
150 _log.error(e, e);
151 }
152
153 loadThemes();
154 }
155
156 protected void destroy() {
157 }
158
159 protected void registerTheme(File liferayLookAndFeelXML) {
160 if (_log.isDebugEnabled()) {
161 _log.debug("Registering " + liferayLookAndFeelXML);
162 }
163
164 try {
165 String content = FileUtil.read(liferayLookAndFeelXML);
166
167 ThemeLocalServiceUtil.init(
168 _servletContextName, _servletContext, _themesPath,
169 _loadFromServletContext, new String[] {content}, null);
170 }
171 catch (Exception e) {
172 _log.error(
173 "Error registering theme " + liferayLookAndFeelXML.toString(),
174 e);
175 }
176 }
177
178 private static Log _log = LogFactoryUtil.getLog(ThemeLoader.class);
179
180 private File _fileStorage;
181 private Map<String, Long> _lastModifiedMap = new HashMap<String, Long>();
182 private boolean _loadFromServletContext = true;
183 private ServletContext _servletContext;
184 private String _servletContextName;
185 private String _themesPath;
186
187 }