001
014
015 package com.liferay.portal.model.impl;
016
017 import com.liferay.portal.kernel.log.Log;
018 import com.liferay.portal.kernel.log.LogFactoryUtil;
019 import com.liferay.portal.kernel.servlet.PortalWebResourceConstants;
020 import com.liferay.portal.kernel.servlet.PortalWebResourcesUtil;
021 import com.liferay.portal.kernel.servlet.ServletContextPool;
022 import com.liferay.portal.kernel.template.TemplateConstants;
023 import com.liferay.portal.kernel.util.ListUtil;
024 import com.liferay.portal.kernel.util.StringPool;
025 import com.liferay.portal.kernel.util.StringUtil;
026 import com.liferay.portal.kernel.util.ThemeHelper;
027 import com.liferay.portal.kernel.util.Validator;
028 import com.liferay.portal.model.ColorScheme;
029 import com.liferay.portal.model.Plugin;
030 import com.liferay.portal.model.PortletDecorator;
031 import com.liferay.portal.model.SpriteImage;
032 import com.liferay.portal.model.Theme;
033 import com.liferay.portal.model.ThemeSetting;
034 import com.liferay.portal.theme.ThemeCompanyId;
035 import com.liferay.portal.theme.ThemeCompanyLimit;
036 import com.liferay.portal.theme.ThemeGroupLimit;
037 import com.liferay.portal.util.PortalUtil;
038 import com.liferay.portal.util.PropsValues;
039
040 import java.util.HashMap;
041 import java.util.LinkedHashMap;
042 import java.util.List;
043 import java.util.Map;
044 import java.util.Properties;
045 import java.util.concurrent.ConcurrentHashMap;
046
047 import javax.servlet.ServletContext;
048
049
054 public class ThemeImpl extends PluginBaseImpl implements Theme {
055
056 public ThemeImpl() {
057 this(null);
058 }
059
060 public ThemeImpl(String themeId) {
061 this(themeId, null);
062 }
063
064 public ThemeImpl(String themeId, String name) {
065 _themeId = themeId;
066 _name = name;
067 }
068
069 @Override
070 public void addSetting(
071 String key, String value, boolean configurable, String type,
072 String[] options, String script) {
073
074 ThemeSetting themeSetting = new ThemeSettingImpl(
075 configurable, options, script, type, value);
076
077 _themeSettingsMap.put(key, themeSetting);
078 }
079
080 @Override
081 public int compareTo(Theme theme) {
082 return getName().compareTo(theme.getName());
083 }
084
085 @Override
086 public boolean equals(Object obj) {
087 if (this == obj) {
088 return true;
089 }
090
091 if (!(obj instanceof Theme)) {
092 return false;
093 }
094
095 Theme theme = (Theme)obj;
096
097 String themeId = theme.getThemeId();
098
099 if (getThemeId().equals(themeId)) {
100 return true;
101 }
102 else {
103 return false;
104 }
105 }
106
107 @Override
108 public List<ColorScheme> getColorSchemes() {
109 List<ColorScheme> colorSchemes = ListUtil.fromMapValues(
110 _colorSchemesMap);
111
112 return ListUtil.sort(colorSchemes);
113 }
114
115 @Override
116 public Map<String, ColorScheme> getColorSchemesMap() {
117 return _colorSchemesMap;
118 }
119
120 @Override
121 public Map<String, ThemeSetting> getConfigurableSettings() {
122 Map<String, ThemeSetting> configurableSettings = new LinkedHashMap<>();
123
124 for (Map.Entry<String, ThemeSetting> entry :
125 _themeSettingsMap.entrySet()) {
126
127 ThemeSetting themeSetting = entry.getValue();
128
129 if (themeSetting.isConfigurable()) {
130 configurableSettings.put(entry.getKey(), entry.getValue());
131 }
132 }
133
134 return configurableSettings;
135 }
136
137 @Override
138 public String getContextPath() {
139 if (!isWARFile()) {
140 return PortalUtil.getPathContext();
141 }
142
143 String servletContextName = getServletContextName();
144
145 if (ServletContextPool.containsKey(servletContextName)) {
146 ServletContext servletContext = ServletContextPool.get(
147 servletContextName);
148
149 return servletContext.getContextPath();
150 }
151
152 return StringPool.SLASH.concat(servletContextName);
153 }
154
155 @Override
156 public String getCssPath() {
157 return _cssPath;
158 }
159
160 @Override
161 public String getDevice() {
162 if (isWapTheme()) {
163 return "wap";
164 }
165 else {
166 return "regular";
167 }
168 }
169
170 @Override
171 public String getFreeMarkerTemplateLoader() {
172 if (_loadFromServletContext) {
173 return TemplateConstants.SERVLET_SEPARATOR;
174 }
175 else {
176 return TemplateConstants.THEME_LOADER_SEPARATOR;
177 }
178 }
179
180 @Override
181 public String getImagesPath() {
182 return _imagesPath;
183 }
184
185 @Override
186 public String getJavaScriptPath() {
187 return _javaScriptPath;
188 }
189
190 @Override
191 public boolean getLoadFromServletContext() {
192 return _loadFromServletContext;
193 }
194
195 @Override
196 public String getName() {
197 return _name;
198 }
199
200 @Override
201 public String getPluginId() {
202 return getThemeId();
203 }
204
205 @Override
206 public String getPluginType() {
207 return Plugin.TYPE_THEME;
208 }
209
210 @Override
211 public List<PortletDecorator> getPortletDecorators() {
212 List<PortletDecorator> portletDecorators = ListUtil.fromMapValues(
213 _portletDecoratorsMap);
214
215 return ListUtil.sort(portletDecorators);
216 }
217
218 @Override
219 public Map<String, PortletDecorator> getPortletDecoratorsMap() {
220 return _portletDecoratorsMap;
221 }
222
223 @Override
224 public String getResourcePath(
225 ServletContext servletContext, String portletId, String path) {
226
227 if (!PropsValues.LAYOUT_TEMPLATE_CACHE_ENABLED) {
228 return ThemeHelper.getResourcePath(
229 servletContext, this, portletId, path);
230 }
231
232 String key = path;
233
234 if (Validator.isNotNull(portletId)) {
235 key = path.concat(StringPool.POUND).concat(portletId);
236 }
237
238 String resourcePath = _resourcePathsMap.get(key);
239
240 if (resourcePath != null) {
241 return resourcePath;
242 }
243
244 resourcePath = ThemeHelper.getResourcePath(
245 servletContext, this, portletId, path);
246
247 _resourcePathsMap.put(key, resourcePath);
248
249 return resourcePath;
250 }
251
252 @Override
253 public String getRootPath() {
254 return _rootPath;
255 }
256
257 @Override
258 public String getServletContextName() {
259 return _servletContextName;
260 }
261
262 @Override
263 public String getSetting(String key) {
264 String value = null;
265
266 ThemeSetting themeSetting = _themeSettingsMap.get(key);
267
268 if (themeSetting != null) {
269 value = themeSetting.getValue();
270 }
271
272 return value;
273 }
274
275 @Override
276 public String[] getSettingOptions(String key) {
277 String[] options = null;
278
279 ThemeSetting themeSetting = _themeSettingsMap.get(key);
280
281 if (themeSetting != null) {
282 options = themeSetting.getOptions();
283 }
284
285 return options;
286 }
287
288 @Override
289 public Map<String, ThemeSetting> getSettings() {
290 return _themeSettingsMap;
291 }
292
293 @Override
294 public Properties getSettingsProperties() {
295 Properties properties = new Properties();
296
297 for (String key : _themeSettingsMap.keySet()) {
298 ThemeSetting setting = _themeSettingsMap.get(key);
299
300 if (setting != null) {
301 properties.setProperty(key, setting.getValue());
302 }
303 }
304
305 return properties;
306 }
307
308 @Override
309 public SpriteImage getSpriteImage(String fileName) {
310 return _spriteImagesMap.get(fileName);
311 }
312
313 @Override
314 public String getStaticResourcePath() {
315 String proxyPath = PortalUtil.getPathProxy();
316
317 String virtualPath = getVirtualPath();
318
319 if (Validator.isNotNull(virtualPath)) {
320 return proxyPath.concat(virtualPath);
321 }
322
323 if (isWARFile()) {
324 return getContextPath();
325 }
326
327 String contextPath = null;
328
329 if (_themeId.equals("admin")) {
330 contextPath = PortalWebResourcesUtil.getContextPath(
331 PortalWebResourceConstants.RESOURCE_TYPE_THEME_ADMIN);
332 }
333 else if (_themeId.equals("classic")) {
334 contextPath = PortalWebResourcesUtil.getContextPath(
335 PortalWebResourceConstants.RESOURCE_TYPE_THEME_CLASSIC);
336 }
337
338 if (Validator.isNull(contextPath)) {
339 return proxyPath;
340 }
341
342 return proxyPath.concat(contextPath);
343 }
344
345 @Override
346 public String getTemplateExtension() {
347 return _templateExtension;
348 }
349
350 @Override
351 public String getTemplatesPath() {
352 return _templatesPath;
353 }
354
355 @Override
356 public ThemeCompanyLimit getThemeCompanyLimit() {
357 return _themeCompanyLimit;
358 }
359
360 @Override
361 public ThemeGroupLimit getThemeGroupLimit() {
362 return _themeGroupLimit;
363 }
364
365 @Override
366 public String getThemeId() {
367 return _themeId;
368 }
369
370 @Override
371 public long getTimestamp() {
372 return _timestamp;
373 }
374
375 @Override
376 public String getVelocityResourceListener() {
377 if (_loadFromServletContext) {
378 return TemplateConstants.SERVLET_SEPARATOR;
379 }
380 else {
381 return TemplateConstants.THEME_LOADER_SEPARATOR;
382 }
383 }
384
385 @Override
386 public String getVirtualPath() {
387 return _virtualPath;
388 }
389
390 @Override
391 public boolean getWapTheme() {
392 return _wapTheme;
393 }
394
395 @Override
396 public boolean getWARFile() {
397 return _warFile;
398 }
399
400 @Override
401 public boolean hasColorSchemes() {
402 if (!_colorSchemesMap.isEmpty()) {
403 return true;
404 }
405 else {
406 return false;
407 }
408 }
409
410 @Override
411 public int hashCode() {
412 return _themeId.hashCode();
413 }
414
415 @Override
416 public boolean isCompanyAvailable(long companyId) {
417 return isAvailable(getThemeCompanyLimit(), companyId);
418 }
419
420 @Override
421 public boolean isControlPanelTheme() {
422 return _controlPanelTheme;
423 }
424
425 @Override
426 public boolean isGroupAvailable(long groupId) {
427 return isAvailable(getThemeGroupLimit(), groupId);
428 }
429
430 @Override
431 public boolean isLoadFromServletContext() {
432 return _loadFromServletContext;
433 }
434
435 @Override
436 public boolean isPageTheme() {
437 return _pageTheme;
438 }
439
440 @Override
441 public boolean isWapTheme() {
442 return _wapTheme;
443 }
444
445 @Override
446 public boolean isWARFile() {
447 return _warFile;
448 }
449
450 @Override
451 public boolean resourceExists(
452 ServletContext servletContext, String portletId, String path)
453 throws Exception {
454
455 if (!PropsValues.LAYOUT_TEMPLATE_CACHE_ENABLED) {
456 return ThemeHelper.resourceExists(
457 servletContext, this, portletId, path);
458 }
459
460 if (Validator.isNull(path)) {
461 return false;
462 }
463
464 String key = path;
465
466 if (Validator.isNotNull(portletId)) {
467 key = path.concat(StringPool.POUND).concat(portletId);
468 }
469
470 Boolean resourceExists = _resourceExistsMap.get(key);
471
472 if (resourceExists != null) {
473 return resourceExists;
474 }
475
476 resourceExists = ThemeHelper.resourceExists(
477 servletContext, this, portletId, path);
478
479 _resourceExistsMap.put(key, resourceExists);
480
481 return resourceExists;
482 }
483
484 @Override
485 public void setControlPanelTheme(boolean controlPanelTheme) {
486 _controlPanelTheme = controlPanelTheme;
487 }
488
489 @Override
490 public void setCssPath(String cssPath) {
491 _cssPath = cssPath;
492 }
493
494 @Override
495 public void setImagesPath(String imagesPath) {
496 _imagesPath = imagesPath;
497 }
498
499 @Override
500 public void setJavaScriptPath(String javaScriptPath) {
501 _javaScriptPath = javaScriptPath;
502 }
503
504 @Override
505 public void setLoadFromServletContext(boolean loadFromServletContext) {
506 _loadFromServletContext = loadFromServletContext;
507 }
508
509 @Override
510 public void setName(String name) {
511 _name = name;
512 }
513
514 @Override
515 public void setPageTheme(boolean pageTheme) {
516 _pageTheme = pageTheme;
517 }
518
519 @Override
520 public void setRootPath(String rootPath) {
521 _rootPath = rootPath;
522 }
523
524 @Override
525 public void setServletContextName(String servletContextName) {
526 _servletContextName = servletContextName;
527
528 if (Validator.isNotNull(_servletContextName)) {
529 _warFile = true;
530 }
531 else {
532 _warFile = false;
533 }
534 }
535
536 @Override
537 public void setSetting(String key, String value) {
538 ThemeSetting themeSetting = _themeSettingsMap.get(key);
539
540 if (themeSetting != null) {
541 themeSetting.setValue(value);
542 }
543 else {
544 addSetting(key, value, false, null, null, null);
545 }
546 }
547
548 @Override
549 public void setSpriteImages(
550 String spriteFileName, Properties spriteProperties) {
551
552 for (Map.Entry<Object, Object> entry : spriteProperties.entrySet()) {
553 String key = (String)entry.getKey();
554 String value = (String)entry.getValue();
555
556 int[] values = StringUtil.split(value, 0);
557
558 int offset = values[0];
559 int height = values[1];
560 int width = values[2];
561
562 SpriteImage spriteImage = new SpriteImage(
563 spriteFileName, key, offset, height, width);
564
565 _spriteImagesMap.put(key, spriteImage);
566 }
567 }
568
569 @Override
570 public void setTemplateExtension(String templateExtension) {
571 _templateExtension = templateExtension;
572 }
573
574 @Override
575 public void setTemplatesPath(String templatesPath) {
576 _templatesPath = templatesPath;
577 }
578
579 @Override
580 public void setThemeCompanyLimit(ThemeCompanyLimit themeCompanyLimit) {
581 _themeCompanyLimit = themeCompanyLimit;
582 }
583
584 @Override
585 public void setThemeGroupLimit(ThemeGroupLimit themeGroupLimit) {
586 _themeGroupLimit = themeGroupLimit;
587 }
588
589 @Override
590 public void setTimestamp(long timestamp) {
591 _timestamp = timestamp;
592 }
593
594 @Override
595 public void setVirtualPath(String virtualPath) {
596 if (_warFile && Validator.isNull(virtualPath)) {
597 virtualPath = PropsValues.THEME_VIRTUAL_PATH;
598 }
599
600 _virtualPath = virtualPath;
601 }
602
603 @Override
604 public void setWapTheme(boolean wapTheme) {
605 _wapTheme = wapTheme;
606 }
607
608 protected boolean isAvailable(ThemeCompanyLimit limit, long id) {
609 boolean available = true;
610
611 if (_log.isDebugEnabled()) {
612 _log.debug(
613 "Check if theme " + getThemeId() + " is available for " + id);
614 }
615
616 if (limit != null) {
617 List<ThemeCompanyId> includes = limit.getIncludes();
618 List<ThemeCompanyId> excludes = limit.getExcludes();
619
620 if (!includes.isEmpty() && !excludes.isEmpty()) {
621
622
623
624
625 if (_log.isDebugEnabled()) {
626 _log.debug("Check includes and excludes");
627 }
628
629 available = limit.isIncluded(id);
630
631 if (available) {
632 available = !limit.isExcluded(id);
633 }
634 }
635 else if (includes.isEmpty() && !excludes.isEmpty()) {
636
637
638
639
640 if (_log.isDebugEnabled()) {
641 _log.debug("Check excludes");
642 }
643
644 available = !limit.isExcluded(id);
645 }
646 else if (!includes.isEmpty() && excludes.isEmpty()) {
647
648
649
650
651 if (_log.isDebugEnabled()) {
652 _log.debug("Check includes");
653 }
654
655 available = limit.isIncluded(id);
656 }
657 else {
658
659
660
661
662 if (_log.isDebugEnabled()) {
663 _log.debug("No includes or excludes set");
664 }
665
666 available = true;
667 }
668 }
669
670 if (_log.isDebugEnabled()) {
671 _log.debug(
672 "Theme " + getThemeId() + " is " +
673 (!available ? "NOT " : "") + "available for " + id);
674 }
675
676 return available;
677 }
678
679 private static final Log _log = LogFactoryUtil.getLog(ThemeImpl.class);
680
681 private final Map<String, ColorScheme> _colorSchemesMap = new HashMap<>();
682 private boolean _controlPanelTheme;
683 private String _cssPath = "${root-path}/css";
684 private String _imagesPath = "${root-path}/images";
685 private String _javaScriptPath = "${root-path}/js";
686 private boolean _loadFromServletContext;
687 private String _name;
688 private boolean _pageTheme;
689 private final Map<String, PortletDecorator> _portletDecoratorsMap =
690 new HashMap<>();
691 private final Map<String, Boolean> _resourceExistsMap =
692 new ConcurrentHashMap<>();
693 private final Map<String, String> _resourcePathsMap =
694 new ConcurrentHashMap<>();
695 private String _rootPath = "/";
696 private String _servletContextName = StringPool.BLANK;
697 private final Map<String, SpriteImage> _spriteImagesMap = new HashMap<>();
698 private String _templateExtension = "ftl";
699 private String _templatesPath = "${root-path}/templates";
700 private ThemeCompanyLimit _themeCompanyLimit;
701 private ThemeGroupLimit _themeGroupLimit;
702 private final String _themeId;
703 private final Map<String, ThemeSetting> _themeSettingsMap =
704 new LinkedHashMap<>();
705 private long _timestamp;
706 private String _virtualPath = StringPool.BLANK;
707 private boolean _wapTheme;
708 private boolean _warFile;
709
710 }