/**
* Copyright (c) 2000-present Liferay, Inc. All rights reserved.
*
* This library is free software; you can redistribute it and/or modify it under
* the terms of the GNU Lesser General Public License as published by the Free
* Software Foundation; either version 2.1 of the License, or (at your option)
* any later version.
*
* This library is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
* FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more
* details.
*/
package com.liferay.portal.service.impl;
import com.liferay.portal.kernel.image.SpriteProcessor;
import com.liferay.portal.kernel.image.SpriteProcessorUtil;
import com.liferay.portal.kernel.log.Log;
import com.liferay.portal.kernel.log.LogFactoryUtil;
import com.liferay.portal.kernel.model.ColorScheme;
import com.liferay.portal.kernel.model.PluginSetting;
import com.liferay.portal.kernel.model.PortletConstants;
import com.liferay.portal.kernel.model.PortletDecorator;
import com.liferay.portal.kernel.model.Theme;
import com.liferay.portal.kernel.plugin.PluginPackage;
import com.liferay.portal.kernel.plugin.Version;
import com.liferay.portal.kernel.servlet.ServletContextUtil;
import com.liferay.portal.kernel.spring.aop.Skip;
import com.liferay.portal.kernel.theme.PortletDecoratorFactoryUtil;
import com.liferay.portal.kernel.theme.ThemeCompanyId;
import com.liferay.portal.kernel.theme.ThemeCompanyLimit;
import com.liferay.portal.kernel.theme.ThemeGroupId;
import com.liferay.portal.kernel.theme.ThemeGroupLimit;
import com.liferay.portal.kernel.util.ColorSchemeFactoryUtil;
import com.liferay.portal.kernel.util.GetterUtil;
import com.liferay.portal.kernel.util.ListUtil;
import com.liferay.portal.kernel.util.PortalUtil;
import com.liferay.portal.kernel.util.ReleaseInfo;
import com.liferay.portal.kernel.util.StringPool;
import com.liferay.portal.kernel.util.StringUtil;
import com.liferay.portal.kernel.util.ThemeFactoryUtil;
import com.liferay.portal.kernel.util.Validator;
import com.liferay.portal.kernel.xml.Document;
import com.liferay.portal.kernel.xml.Element;
import com.liferay.portal.kernel.xml.UnsecureSAXReaderUtil;
import com.liferay.portal.model.impl.ThemeImpl;
import com.liferay.portal.plugin.PluginUtil;
import com.liferay.portal.service.base.ThemeLocalServiceBaseImpl;
import com.liferay.portal.util.PropsValues;
import com.liferay.util.ContextReplace;
import java.net.URL;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.Iterator;
import java.util.LinkedHashSet;
import java.util.List;
import java.util.Map;
import java.util.Properties;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
import javax.servlet.ServletContext;
/**
* @author Brian Wing Shun Chan
* @author Jorge Ferrer
* @author Raymond Augé
*/
@Skip
public class ThemeLocalServiceImpl extends ThemeLocalServiceBaseImpl {
@Override
public ColorScheme fetchColorScheme(
long companyId, String themeId, String colorSchemeId) {
colorSchemeId = GetterUtil.getString(colorSchemeId);
Theme theme = fetchTheme(companyId, themeId);
if (theme == null) {
return null;
}
Map<String, ColorScheme> colorSchemesMap = theme.getColorSchemesMap();
return colorSchemesMap.get(colorSchemeId);
}
@Override
public PortletDecorator fetchPortletDecorator(
long companyId, String themeId, String colorSchemeId) {
colorSchemeId = GetterUtil.getString(colorSchemeId);
Theme theme = fetchTheme(companyId, themeId);
if (theme == null) {
return null;
}
Map<String, PortletDecorator> portletDecoratorsMap =
theme.getPortletDecoratorsMap();
return portletDecoratorsMap.get(colorSchemeId);
}
@Override
public Theme fetchTheme(long companyId, String themeId) {
themeId = GetterUtil.getString(themeId);
Map<String, Theme> themes = _getThemes(companyId);
return themes.get(themeId);
}
@Override
public ColorScheme getColorScheme(
long companyId, String themeId, String colorSchemeId) {
colorSchemeId = GetterUtil.getString(colorSchemeId);
Theme theme = getTheme(companyId, themeId);
Map<String, ColorScheme> colorSchemesMap = theme.getColorSchemesMap();
ColorScheme colorScheme = colorSchemesMap.get(colorSchemeId);
if (colorScheme != null) {
return colorScheme;
}
List<ColorScheme> colorSchemes = theme.getColorSchemes();
if (!colorSchemes.isEmpty()) {
for (int i = colorSchemes.size() - 1; i >= 0; i--) {
colorScheme = colorSchemes.get(i);
if (colorScheme.isDefaultCs()) {
return colorScheme;
}
}
}
if (colorScheme == null) {
colorScheme = ColorSchemeFactoryUtil.getDefaultRegularColorScheme();
}
return colorScheme;
}
@Override
public List<Theme> getControlPanelThemes(long companyId, long userId) {
List<Theme> themes = getThemes(companyId);
themes = PluginUtil.restrictPlugins(themes, companyId, userId);
Iterator<Theme> itr = themes.iterator();
while (itr.hasNext()) {
Theme theme = itr.next();
if (!theme.isControlPanelTheme()) {
itr.remove();
}
}
return themes;
}
@Override
public List<Theme> getPageThemes(
long companyId, long groupId, long userId) {
List<Theme> themes = getThemes(companyId);
themes = PluginUtil.restrictPlugins(themes, companyId, userId);
Iterator<Theme> itr = themes.iterator();
while (itr.hasNext()) {
Theme theme = itr.next();
if (!theme.isPageTheme() || !theme.isGroupAvailable(groupId)) {
itr.remove();
}
}
return themes;
}
@Override
public PortletDecorator getPortletDecorator(
long companyId, String themeId, String portletDecoratorId) {
Theme theme = fetchTheme(companyId, themeId);
Map<String, PortletDecorator> portletDecoratorsMap =
theme.getPortletDecoratorsMap();
portletDecoratorId = GetterUtil.getString(portletDecoratorId);
PortletDecorator portletDecorator = portletDecoratorsMap.get(
portletDecoratorId);
if (portletDecorator != null) {
return portletDecorator;
}
ThemeImpl themeImpl = (ThemeImpl)theme;
return themeImpl.getDefaultPortletDecorator();
}
@Override
public Theme getTheme(long companyId, String themeId) {
themeId = GetterUtil.getString(themeId);
Map<String, Theme> themes = _getThemes(companyId);
Theme theme = themes.get(themeId);
if (theme != null) {
return theme;
}
if (_log.isWarnEnabled()) {
_log.warn(
"No theme found for specified theme id " + themeId +
". Returning the default theme.");
}
themeId = ThemeFactoryUtil.getDefaultRegularThemeId(companyId);
theme = _themes.get(themeId);
if (theme != null) {
return theme;
}
if (_themes.isEmpty()) {
if (_log.isDebugEnabled()) {
_log.debug("No themes are installed");
}
return null;
}
if (!themeId.contains(PortletConstants.WAR_SEPARATOR)) {
_log.error(
"No theme found for default theme id " + themeId +
". Returning a random theme.");
}
for (Map.Entry<String, Theme> entry : _themes.entrySet()) {
theme = entry.getValue();
if ((theme != null) && !theme.isControlPanelTheme()) {
return theme;
}
}
return null;
}
@Override
public List<Theme> getThemes(long companyId) {
Map<String, Theme> themes = _getThemes(companyId);
List<Theme> themesList = ListUtil.fromMapValues(themes);
return ListUtil.sort(themesList);
}
/**
* @deprecated As of 7.0.0, replaced by {@link #getPageThemes}
*/
@Deprecated
@Override
public List<Theme> getThemes(
long companyId, long groupId, long userId, boolean wapTheme) {
return getPageThemes(companyId, groupId, userId);
}
@Override
public List<Theme> getWARThemes() {
List<Theme> themes = ListUtil.fromMapValues(_themes);
Iterator<Theme> itr = themes.iterator();
while (itr.hasNext()) {
Theme theme = itr.next();
if (!theme.isWARFile()) {
itr.remove();
}
}
return themes;
}
@Override
public List<Theme> init(
ServletContext servletContext, String themesPath,
boolean loadFromServletContext, String[] xmls,
PluginPackage pluginPackage) {
return init(
null, servletContext, themesPath, loadFromServletContext, xmls,
pluginPackage);
}
@Override
public List<Theme> init(
String servletContextName, ServletContext servletContext,
String themesPath, boolean loadFromServletContext, String[] xmls,
PluginPackage pluginPackage) {
Set<Theme> themes = new LinkedHashSet<>();
try {
for (String xml : xmls) {
themes.addAll(
_readThemes(
servletContextName, servletContext, themesPath,
loadFromServletContext, xml, pluginPackage));
}
}
catch (Exception e) {
_log.error(e, e);
}
_themesPool.clear();
return new ArrayList<>(themes);
}
@Override
public void uninstallThemes(List<Theme> themes) {
for (Theme theme : themes) {
String themeId = theme.getThemeId();
_themes.remove(themeId);
layoutTemplateLocalService.uninstallLayoutTemplates(themeId);
}
_themesPool.clear();
}
private List<ThemeCompanyId> _getCompanyLimitExcludes(Element element) {
List<ThemeCompanyId> includes = new ArrayList<>();
if (element == null) {
return includes;
}
List<Element> companyIdsElements = element.elements("company-id");
for (int i = 0; i < companyIdsElements.size(); i++) {
Element companyIdElement = companyIdsElements.get(i);
String name = companyIdElement.attributeValue("name");
String pattern = companyIdElement.attributeValue("pattern");
ThemeCompanyId themeCompanyId = null;
if (Validator.isNotNull(name)) {
themeCompanyId = new ThemeCompanyId(name, false);
}
else if (Validator.isNotNull(pattern)) {
themeCompanyId = new ThemeCompanyId(pattern, true);
}
if (themeCompanyId != null) {
includes.add(themeCompanyId);
}
}
return includes;
}
private List<ThemeCompanyId> _getCompanyLimitIncludes(Element element) {
return _getCompanyLimitExcludes(element);
}
private List<ThemeGroupId> _getGroupLimitExcludes(Element element) {
List<ThemeGroupId> includes = new ArrayList<>();
if (element == null) {
return includes;
}
List<Element> groupIdsElements = element.elements("group-id");
for (int i = 0; i < groupIdsElements.size(); i++) {
Element groupIdElement = groupIdsElements.get(i);
String name = groupIdElement.attributeValue("name");
String pattern = groupIdElement.attributeValue("pattern");
ThemeGroupId themeGroupId = null;
if (Validator.isNotNull(name)) {
themeGroupId = new ThemeGroupId(name, false);
}
else if (Validator.isNotNull(pattern)) {
themeGroupId = new ThemeGroupId(pattern, true);
}
if (themeGroupId != null) {
includes.add(themeGroupId);
}
}
return includes;
}
private List<ThemeGroupId> _getGroupLimitIncludes(Element element) {
return _getGroupLimitExcludes(element);
}
private Map<String, Theme> _getThemes(long companyId) {
Map<String, Theme> themes = _themesPool.get(companyId);
if (themes != null) {
return themes;
}
themes = new ConcurrentHashMap<>();
for (Map.Entry<String, Theme> entry : _themes.entrySet()) {
String themeId = entry.getKey();
Theme theme = entry.getValue();
if (theme.isCompanyAvailable(companyId)) {
themes.put(themeId, theme);
}
}
_themesPool.put(companyId, themes);
return themes;
}
private Version _getVersion(String version) {
if (version.equals("${current-version}")) {
version = ReleaseInfo.getVersion();
}
return Version.getInstance(version);
}
private void _readColorSchemes(
Element themeElement, Map<String, ColorScheme> colorSchemes,
ContextReplace themeContextReplace) {
List<Element> colorSchemeElements = themeElement.elements(
"color-scheme");
for (Element colorSchemeElement : colorSchemeElements) {
ContextReplace colorSchemeContextReplace =
(ContextReplace)themeContextReplace.clone();
String id = colorSchemeElement.attributeValue("id");
colorSchemeContextReplace.addValue("color-scheme-id", id);
ColorScheme colorSchemeModel = colorSchemes.get(id);
if (colorSchemeModel == null) {
colorSchemeModel = ColorSchemeFactoryUtil.getColorScheme(id);
}
String name = GetterUtil.getString(
colorSchemeElement.attributeValue("name"),
colorSchemeModel.getName());
name = colorSchemeContextReplace.replace(name);
boolean defaultCs = GetterUtil.getBoolean(
colorSchemeElement.elementText("default-cs"),
colorSchemeModel.isDefaultCs());
String cssClass = GetterUtil.getString(
colorSchemeElement.elementText("css-class"),
colorSchemeModel.getCssClass());
cssClass = colorSchemeContextReplace.replace(cssClass);
colorSchemeContextReplace.addValue("css-class", cssClass);
String colorSchemeImagesPath = GetterUtil.getString(
colorSchemeElement.elementText("color-scheme-images-path"),
colorSchemeModel.getColorSchemeImagesPath());
colorSchemeImagesPath = colorSchemeContextReplace.replace(
colorSchemeImagesPath);
colorSchemeContextReplace.addValue(
"color-scheme-images-path", colorSchemeImagesPath);
colorSchemeModel.setName(name);
colorSchemeModel.setDefaultCs(defaultCs);
colorSchemeModel.setCssClass(cssClass);
colorSchemeModel.setColorSchemeImagesPath(colorSchemeImagesPath);
colorSchemes.put(id, colorSchemeModel);
}
}
private void _readPortletDecorators(
Element themeElement, Map<String, PortletDecorator> portletDecorators,
ContextReplace themeContextReplace) {
List<Element> portletDecoratorElements = themeElement.elements(
"portlet-decorator");
for (Element portletDecoratorElement : portletDecoratorElements) {
ContextReplace portletDecoratorContextReplace =
(ContextReplace)themeContextReplace.clone();
String id = portletDecoratorElement.attributeValue("id");
portletDecoratorContextReplace.addValue("portlet-decorator-id", id);
PortletDecorator portletDecoratorModel = portletDecorators.get(id);
if (portletDecoratorModel == null) {
portletDecoratorModel =
PortletDecoratorFactoryUtil.getPortletDecorator(id);
}
String name = GetterUtil.getString(
portletDecoratorElement.attributeValue("name"),
portletDecoratorModel.getName());
name = portletDecoratorContextReplace.replace(name);
boolean defaultPortletDecorator = GetterUtil.getBoolean(
portletDecoratorElement.elementText(
"default-portlet-decorator"),
portletDecoratorModel.isDefaultPortletDecorator());
String cssClass = GetterUtil.getString(
portletDecoratorElement.elementText(
"portlet-decorator-css-class"),
portletDecoratorModel.getCssClass());
cssClass = portletDecoratorContextReplace.replace(cssClass);
portletDecoratorContextReplace.addValue(
"portlet-decorator-css-class", cssClass);
String portletDecoratorThumbnailPath = GetterUtil.getString(
portletDecoratorElement.elementText(
"portlet-decorator-thumbnail-path"),
portletDecoratorModel.getPortletDecoratorThumbnailPath());
portletDecoratorThumbnailPath =
portletDecoratorContextReplace.replace(
portletDecoratorThumbnailPath);
portletDecoratorContextReplace.addValue(
"portlet-decorator-thumbnail-path",
portletDecoratorThumbnailPath);
portletDecoratorModel.setName(name);
portletDecoratorModel.setDefaultPortletDecorator(
defaultPortletDecorator);
portletDecoratorModel.setCssClass(cssClass);
portletDecoratorModel.setPortletDecoratorThumbnailPath(
portletDecoratorThumbnailPath);
portletDecorators.put(id, portletDecoratorModel);
}
}
private Set<Theme> _readThemes(
String servletContextName, ServletContext servletContext,
String themesPath, boolean loadFromServletContext, String xml,
PluginPackage pluginPackage)
throws Exception {
Set<Theme> themes = new HashSet<>();
if (xml == null) {
return themes;
}
Document document = UnsecureSAXReaderUtil.read(xml, true);
Element rootElement = document.getRootElement();
Version portalVersion = _getVersion(ReleaseInfo.getVersion());
boolean compatible = false;
Element compatibilityElement = rootElement.element("compatibility");
if (compatibilityElement != null) {
List<Element> versionElements = compatibilityElement.elements(
"version");
for (Element versionElement : versionElements) {
Version version = _getVersion(versionElement.getTextTrim());
if (version.includes(portalVersion)) {
compatible = true;
break;
}
}
}
if (!compatible) {
_log.error(
"Themes in this WAR are not compatible with " +
ReleaseInfo.getServerInfo());
return themes;
}
ThemeCompanyLimit companyLimit = null;
Element companyLimitElement = rootElement.element("company-limit");
if (companyLimitElement != null) {
companyLimit = new ThemeCompanyLimit();
Element companyIncludesElement = companyLimitElement.element(
"company-includes");
if (companyIncludesElement != null) {
companyLimit.setIncludes(
_getCompanyLimitIncludes(companyIncludesElement));
}
Element companyExcludesElement = companyLimitElement.element(
"company-excludes");
if (companyExcludesElement != null) {
companyLimit.setExcludes(
_getCompanyLimitExcludes(companyExcludesElement));
}
}
ThemeGroupLimit groupLimit = null;
Element groupLimitElement = rootElement.element("group-limit");
if (groupLimitElement != null) {
groupLimit = new ThemeGroupLimit();
Element groupIncludesElement = groupLimitElement.element(
"group-includes");
if (groupIncludesElement != null) {
groupLimit.setIncludes(
_getGroupLimitIncludes(groupIncludesElement));
}
Element groupExcludesElement = groupLimitElement.element(
"group-excludes");
if (groupExcludesElement != null) {
groupLimit.setExcludes(
_getGroupLimitExcludes(groupExcludesElement));
}
}
long timestamp = ServletContextUtil.getLastModified(servletContext);
List<Element> themeElements = rootElement.elements("theme");
for (Element themeElement : themeElements) {
ContextReplace themeContextReplace = new ContextReplace();
themeContextReplace.addValue("themes-path", themesPath);
String themeId = themeElement.attributeValue("id");
if (servletContextName != null) {
themeId =
themeId + PortletConstants.WAR_SEPARATOR +
servletContextName;
}
themeId = PortalUtil.getJsSafePortletId(themeId);
themeContextReplace.addValue("theme-id", themeId);
Theme theme = _themes.get(themeId);
if (theme == null) {
theme = ThemeFactoryUtil.getTheme(themeId);
}
theme.setTimestamp(timestamp);
PluginSetting pluginSetting =
pluginSettingLocalService.getDefaultPluginSetting();
theme.setPluginPackage(pluginPackage);
theme.setDefaultPluginSetting(pluginSetting);
theme.setThemeCompanyLimit(companyLimit);
theme.setThemeGroupLimit(groupLimit);
if (servletContextName != null) {
theme.setServletContextName(servletContextName);
}
theme.setLoadFromServletContext(loadFromServletContext);
String name = GetterUtil.getString(
themeElement.attributeValue("name"), theme.getName());
String rootPath = GetterUtil.getString(
themeElement.elementText("root-path"), theme.getRootPath());
rootPath = themeContextReplace.replace(rootPath);
themeContextReplace.addValue("root-path", rootPath);
String templatesPath = GetterUtil.getString(
themeElement.elementText("templates-path"),
theme.getTemplatesPath());
templatesPath = themeContextReplace.replace(templatesPath);
templatesPath = StringUtil.safePath(templatesPath);
themeContextReplace.addValue("templates-path", templatesPath);
String cssPath = GetterUtil.getString(
themeElement.elementText("css-path"), theme.getCssPath());
cssPath = themeContextReplace.replace(cssPath);
cssPath = StringUtil.safePath(cssPath);
themeContextReplace.addValue("css-path", cssPath);
String imagesPath = GetterUtil.getString(
themeElement.elementText("images-path"), theme.getImagesPath());
imagesPath = themeContextReplace.replace(imagesPath);
imagesPath = StringUtil.safePath(imagesPath);
themeContextReplace.addValue("images-path", imagesPath);
String javaScriptPath = GetterUtil.getString(
themeElement.elementText("javascript-path"),
theme.getJavaScriptPath());
javaScriptPath = themeContextReplace.replace(javaScriptPath);
javaScriptPath = StringUtil.safePath(javaScriptPath);
themeContextReplace.addValue("javascript-path", javaScriptPath);
String virtualPath = GetterUtil.getString(
themeElement.elementText("virtual-path"),
theme.getVirtualPath());
String templateExtension = GetterUtil.getString(
themeElement.elementText("template-extension"),
theme.getTemplateExtension());
theme.setName(name);
theme.setRootPath(rootPath);
theme.setTemplatesPath(templatesPath);
theme.setCssPath(cssPath);
theme.setImagesPath(imagesPath);
theme.setJavaScriptPath(javaScriptPath);
theme.setVirtualPath(virtualPath);
theme.setTemplateExtension(templateExtension);
Element settingsElement = themeElement.element("settings");
if (settingsElement != null) {
List<Element> settingElements = settingsElement.elements(
"setting");
for (Element settingElement : settingElements) {
boolean configurable = GetterUtil.getBoolean(
settingElement.attributeValue("configurable"));
String key = settingElement.attributeValue("key");
String[] options = StringUtil.split(
settingElement.attributeValue("options"));
String type = settingElement.attributeValue("type", "text");
String value = settingElement.attributeValue(
"value", StringPool.BLANK);
String script = settingElement.getTextTrim();
theme.addSetting(
key, value, configurable, type, options, script);
}
}
theme.setControlPanelTheme(
GetterUtil.getBoolean(
themeElement.elementText("control-panel-theme")));
theme.setPageTheme(
GetterUtil.getBoolean(
themeElement.elementText("page-theme"), true));
Element rolesElement = themeElement.element("roles");
if (rolesElement != null) {
List<Element> roleNameElements = rolesElement.elements(
"role-name");
for (Element roleNameElement : roleNameElements) {
pluginSetting.addRole(roleNameElement.getText());
}
}
_readColorSchemes(
themeElement, theme.getColorSchemesMap(), themeContextReplace);
_readColorSchemes(
themeElement, theme.getColorSchemesMap(), themeContextReplace);
Element layoutTemplatesElement = themeElement.element(
"layout-templates");
if (layoutTemplatesElement != null) {
Element standardElement = layoutTemplatesElement.element(
"standard");
if (standardElement != null) {
layoutTemplateLocalService.readLayoutTemplate(
servletContextName, servletContext, null,
standardElement, true, themeId, pluginPackage);
}
Element customElement = layoutTemplatesElement.element(
"custom");
if (customElement != null) {
layoutTemplateLocalService.readLayoutTemplate(
servletContextName, servletContext, null, customElement,
false, themeId, pluginPackage);
}
}
_setSpriteImages(servletContext, theme, imagesPath);
if (!_themes.containsKey(themeId)) {
_themes.put(themeId, theme);
}
_readPortletDecorators(
themeElement, theme.getPortletDecoratorsMap(),
themeContextReplace);
_readPortletDecorators(
themeElement, theme.getPortletDecoratorsMap(),
themeContextReplace);
themes.add(theme);
}
return themes;
}
private void _setSpriteImages(
ServletContext servletContext, Theme theme, String resourcePath)
throws Exception {
if (!resourcePath.startsWith(StringPool.SLASH)) {
resourcePath = StringPool.SLASH.concat(resourcePath);
}
Set<String> resourcePaths = servletContext.getResourcePaths(
resourcePath);
if ((resourcePaths == null) || resourcePaths.isEmpty()) {
return;
}
List<URL> imageURLs = new ArrayList<>(resourcePaths.size());
for (String curResourcePath : resourcePaths) {
if (curResourcePath.endsWith(StringPool.SLASH)) {
_setSpriteImages(servletContext, theme, curResourcePath);
}
else if (curResourcePath.endsWith(".png")) {
URL imageURL = servletContext.getResource(curResourcePath);
if (imageURL != null) {
imageURLs.add(imageURL);
}
else {
_log.error(
"Resource URL for " + curResourcePath + " is null");
}
}
}
String spriteRootDirName = PropsValues.SPRITE_ROOT_DIR;
String spriteFileName = resourcePath.concat(
PropsValues.SPRITE_FILE_NAME);
String spritePropertiesFileName = resourcePath.concat(
PropsValues.SPRITE_PROPERTIES_FILE_NAME);
String rootPath = ServletContextUtil.getRootPath(servletContext);
Properties spriteProperties = SpriteProcessorUtil.generate(
servletContext, imageURLs, spriteRootDirName, spriteFileName,
spritePropertiesFileName, rootPath, 16, 16, 10240);
if (spriteProperties == null) {
return;
}
String contextPath = servletContext.getContextPath();
spriteFileName = contextPath.concat(SpriteProcessor.PATH).concat(
spriteFileName);
theme.setSpriteImages(spriteFileName, spriteProperties);
}
private static final Log _log = LogFactoryUtil.getLog(
ThemeLocalServiceImpl.class);
private static final Map<String, Theme> _themes = new ConcurrentHashMap<>();
private static final Map<Long, Map<String, Theme>> _themesPool =
new ConcurrentHashMap<>();
}