
org.opencms.ade.configuration.TestLiveConfig Maven / Gradle / Ivy
Show all versions of opencms-test Show documentation
/*
* This library is part of OpenCms -
* the Open Source Content Management System
*
* Copyright (C) Alkacon Software (http://www.alkacon.com)
*
* 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.
*
* For further information about Alkacon Software, please see the
* company website: http://www.alkacon.com
*
* For further information about OpenCms, please see the
* project website: http://www.opencms.org
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
package org.opencms.ade.configuration;
import org.opencms.ade.detailpage.CmsDetailPageInfo;
import org.opencms.ade.detailpage.I_CmsDetailPageHandler;
import org.opencms.ade.sitemap.CmsSitemapAttributeUpdater;
import org.opencms.file.CmsFile;
import org.opencms.file.CmsObject;
import org.opencms.file.CmsProject;
import org.opencms.file.CmsProperty;
import org.opencms.file.CmsResource;
import org.opencms.file.types.CmsResourceTypeFolder;
import org.opencms.file.types.I_CmsResourceType;
import org.opencms.main.CmsException;
import org.opencms.main.OpenCms;
import org.opencms.relations.CmsCategoryService;
import org.opencms.staticexport.CmsLinkManager;
import org.opencms.test.OpenCmsTestCase;
import org.opencms.test.OpenCmsTestProperties;
import org.opencms.ui.components.CmsExtendedSiteSelector;
import org.opencms.util.CmsFileUtil;
import org.opencms.util.CmsStringUtil;
import org.opencms.util.CmsVfsUtil;
import org.opencms.xml.content.CmsXmlContent;
import org.opencms.xml.content.CmsXmlContentFactory;
import java.nio.charset.StandardCharsets;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Locale;
import java.util.Map;
import java.util.Set;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import java.util.stream.Collectors;
import org.apache.logging.log4j.core.appender.OpenCmsTestLogAppender;
import org.antlr.stringtemplate.StringTemplate;
import com.google.common.collect.Maps;
import com.google.common.collect.Sets;
import junit.framework.Test;
/**
* Tests for the ADE configuration mechanism which read the configuration data from multiple files in the VFS.
*
*/
public class TestLiveConfig extends OpenCmsTestCase {
/** Pattern for matching path segment consisting of two characters from {a, b}. */
private static final Pattern detailPageTestSubsitePattern = Pattern.compile("/([ab][ab])/");
/** The current VFS prefix as added to internal links according to the configuration in opencms-importexport.xml. */
String m_vfsPrefix;
/**
* Test constructor.
*
* @param name the name of the test
*/
public TestLiveConfig(String name) {
super(name);
}
/**
* Generates a sitemap config XML with the given types.
*
* @param types the types to use
* @param masterConfigIds the master configuration ids
*
* @return the XML string
*/
public static String generateSitemapConfigWithTypes(Map types, List masterConfigIds) {
String template = "\n"
+ "\r\n"
+ " \r\n"
+ " $masterConfigs:{masterConfig | "
+ ""
+ " "
+ " $masterConfig$ "
+ " "
+ " }$"
+ " $types.keys:{type |"
+ " \r\n"
+ " \n"
+ " false \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " }$\n"
+ " \r\n"
+ " \r\n";
StringTemplate st = new StringTemplate(template);
st.setAttribute("types", types);
st.setAttribute("masterConfigs", masterConfigIds != null ? masterConfigIds : Collections.emptyList());
return st.toString();
}
/**
* Returns the test suite.
*
* @return the test suite
*/
public static Test suite() {
CmsConfigurationCache.DEBUG = true;
OpenCmsTestProperties.initialize(org.opencms.test.AllTests.TEST_PROPERTIES_PATH);
return generateSetupTestWrapper(TestLiveConfig.class, "ade-config", "/");
}
/**
* Tests programmatic updating of sitemap attributes.
*
* @throws Exception
*/
public void testAttributeUpdates() throws Exception {
CmsObject cms = getCmsObject();
I_CmsResourceType configType = OpenCms.getResourceManager().getResourceType("sitemap_config");
String path = "/savetest1.xml";
cms.createResource("/savetest1.xml", configType);
Map originalAttributes = new HashMap<>();
originalAttributes.put("foo", "1");
originalAttributes.put("bar", "2");
{
CmsXmlContent content = CmsXmlContentFactory.unmarshal(cms, cms.readFile(path));
// make sure we have something else than attributes in the sitemap config
content.addValue(cms, "DiscardTypes", Locale.ENGLISH, 0);
CmsSitemapAttributeUpdater updater = new CmsSitemapAttributeUpdater(cms, content);
updater.replaceAttributes(originalAttributes);
CmsFile file = content.getFile();
file.setContents(content.marshal());
cms.lockResource(file);
cms.writeFile(file);
}
{
CmsXmlContent content = CmsXmlContentFactory.unmarshal(cms, cms.readFile(path));
CmsSitemapAttributeUpdater updater = new CmsSitemapAttributeUpdater(cms, content);
assertEquals(originalAttributes, updater.getAttributesFromContent());
Map updates = new HashMap<>();
updates.put("foo", null);
updates.put("baz", "3");
updater.updateAttributes(updates);
CmsFile file = content.getFile();
file.setContents(content.marshal());
cms.lockResource(file);
cms.writeFile(file);
}
{
CmsXmlContent content = CmsXmlContentFactory.unmarshal(cms, cms.readFile(path));
CmsSitemapAttributeUpdater updater = new CmsSitemapAttributeUpdater(cms, content);
assertEquals(CmsStringUtil.splitAsMap("bar:2|baz:3", "|", ":"), updater.getAttributesFromContent());
}
}
/**
* Tests category-based detail page selection.
* @throws Exception
*/
public void testCategoryDetailPages() throws Exception {
CmsObject cms = getCmsObject();
String base = "/testCategoryDetailPages";
cms.createResource(base, 0);
cms.createResource("/.categories", 0);
cms.createResource("/.categories/foo", 0);
if (!cms.existsResource("/system/categories")) {
cms.createResource("/system/categories", 0);
}
boolean preferDetailPages;
boolean excludeExternalContents;
preferDetailPages = true;
excludeExternalContents = false;
createCategoryDetailPageTestSitemap(base + "/a", preferDetailPages, excludeExternalContents, false);
OpenCms.getADEManager().waitForCacheUpdate(false);
CmsADEConfigData config = OpenCms.getADEManager().lookupConfiguration(
cms,
cms.readResource(base + "/a").getRootPath());
List pages = config.getDetailPagesForType("article1");
List types = pages.stream().map(page -> page.getQualifiedType()).collect(Collectors.toList());
String articlePath = base + "/a/.content/blogentries/article.xml";
String link1 = OpenCms.getLinkManager().substituteLinkForUnknownTarget(cms, articlePath);
assertTrue(link1.contains("/detail/"));
assertFalse(link1.contains("/detail-foo/"));
CmsCategoryService.getInstance().addResourceToCategory(cms, articlePath, "foo");
String link2 = OpenCms.getLinkManager().substituteLinkForUnknownTarget(cms, articlePath);
assertFalse(link2.contains("/detail/"));
assertTrue(link2.contains("/detail-foo/"));
}
/**
* Tests cross-site detail page links.
*
* @throws Exception -
*/
public void testCrossSiteDetailPageLinks1() throws Exception {
// Link from site foo to site bar, where a detail page exists in foo
CmsObject cms = getCmsObject();
cms.getRequestContext().setSiteRoot("/sites/foo");
String rootPath = "/sites/bar/.content/blogentries/be_00001.xml";
CmsResource res = rootCms().readResource(rootPath);
String link = OpenCms.getLinkManager().getOnlineLink(cms, rootPath);
assertEquals("http://foo.org" + getVfsPrefix() + "/main/blog/" + res.getStructureId() + "/", link);
System.out.println(link);
}
/**
* Tests cross-site detail page links.
*
* @throws Exception -
*/
public void testCrossSiteDetailPageLinks1a() throws Exception {
// Link from site foo to site bar, where a detail page exists in foo
// (using a site path that also exists in site foo)
OpenCmsTestLogAppender.setBreakOnError(false);
CmsObject cms = getCmsObject();
cms.getRequestContext().setSiteRoot("/sites/foo");
String rootPath = "/sites/bar/.content/blogentries/be_00002.xml";
CmsResource res = rootCms().readResource(rootPath);
String link = OpenCms.getLinkManager().getOnlineLink(cms, rootPath);
assertEquals("http://foo.org" + getVfsPrefix() + "/main/blog/" + res.getStructureId() + "/", link);
System.out.println(link);
}
/**
* Tests cross-site detail page links.
*
* @throws Exception -
*/
public void testCrossSiteDetailPageLinks2() throws Exception {
// Link from site bar to site foo, where a detail page exists in foo
CmsObject cms = getCmsObject();
cms.getRequestContext().setSiteRoot("/sites/bar");
String rootPath = "/sites/foo/.content/blogentries/be_00001.xml";
CmsResource res = rootCms().readResource(rootPath);
String link = OpenCms.getLinkManager().getOnlineLink(cms, rootPath);
assertEquals("http://foo.org" + getVfsPrefix() + "/main/blog/" + res.getStructureId() + "/", link);
System.out.println(link);
}
/**
* Tests cross-site detail page links.
*
* @throws Exception -
*/
public void testCrossSiteDetailPageLinkUtilityFunctions() throws Exception {
// Link from site foo to site bar, where a detail page exists in foo
CmsObject cms = getCmsObject();
cms.getRequestContext().setSiteRoot("/sites/foo");
String rootPath = "/sites/bar/.content/blogentries/be_00001.xml";
CmsResource res = rootCms().readResource(rootPath);
String link = OpenCms.getLinkManager().getOnlineLink(cms, rootPath);
assertEquals(null, CmsLinkManager.getLinkSubsite(cms , "https://www.dummy.invalid/foo/bar/baz"));
assertEquals("/sites/foo/", CmsLinkManager.getLinkSubsite(cms, link));
assertEquals("/sites/bar/", CmsLinkManager.getLinkSubsite(cms, OpenCms.getLinkManager().getOnlineLink(cms, "/sites/bar/")));
}
/**
* Tests that multiple default detail pages can be returned CmsADEConfigData#getDetailPagesForType().
*
* @throws Exception
*/
public void testDefaultDetailPagesPreserved() throws Exception {
CmsObject cms = getCmsObject();
String base = "/testDefaultDetailPagesPreserved";
cms.createResource(base, 0);
boolean preferDetailPages;
boolean excludeExternalContents;
preferDetailPages = false;
excludeExternalContents = false;
createCategoryDetailPageTestSitemap(base + "/a", preferDetailPages, excludeExternalContents, false);
OpenCms.getADEManager().waitForCacheUpdate(false);
CmsADEConfigData config = OpenCms.getADEManager().lookupConfiguration(
cms,
cms.readResource(base + "/a").getRootPath());
List pages = config.getDetailPagesForType("article1");
List types = pages.stream().map(page -> page.getQualifiedType()).collect(Collectors.toList());
assertEquals(
Arrays.asList("article1", "article1|category:foo", "##DEFAULT##", "##DEFAULT##|category:foo"),
types);
}
/**
* Tests deletion of configuration files.
*
* @throws Exception -
*/
public void testDeleted() throws Exception {
try {
waitForUpdate(false);
delete(getCmsObject().readResource("/.content/.config"));
CmsObject offlineCms = getCmsObject();
waitForUpdate(false);
//checkResourceTypes(offlineCms, "/sites/default/today/events", "foldername", "d2");
checkResourceTypes(offlineCms, "/sites/default/today/events/foo", "foldername", "d2");
checkResourceTypes(offlineCms, "/sites/default/today/news", "foldername", "c3", "e3");
checkResourceTypes(offlineCms, "/sites/default/today/news/foo", "foldername", "c3", "e3");
} finally {
restoreFiles();
}
}
/**
* Tests finding detail pages.
*
* @throws Exception -
*/
public void testDetailPage1() throws Exception {
// root site
waitForUpdate(false);
CmsObject cms = rootCms();
String detailPage = OpenCms.getADEManager().getDetailPageHandler().getDetailPage(
cms,
"/sites/default/.content/a1/blarg.html",
"/sites/default/today/news",
null);
assertEquals("/sites/default/", detailPage);
// default site
cms = getCmsObject();
detailPage = OpenCms.getADEManager().getDetailPageHandler().getDetailPage(
cms,
"/sites/default/.content/a1/blarg.html",
"/today/news",
null);
assertEquals("/sites/default/", detailPage);
}
/**
* Tests whether the 'include in site selector' flag is processed correctly.
*
* @throws Exception -
*/
public void testIncludeInSiteSelector() throws Exception {
try {
OpenCms.getSiteManager().getSiteForRootPath(
getCmsObject().getRequestContext().getSiteRoot()).setSubsiteSelectionEnabled(true);
createDetailPageTestSitemap("/includeInSiteSelector", false, false, true);
createDetailPageTestSitemap("/includeInSiteSelector/alpha", false, false, false);
createDetailPageTestSitemap("/includeInSiteSelector/beta", false, false, true);
createDetailPageTestSitemap("/includeInSiteSelector/alpha/gamma", false, false, true);
OpenCms.getADEManager().waitForCacheUpdate(false);
List subsites = OpenCms.getADEManager().getSubsitesForSiteSelector(false);
Set subsiteSet = new HashSet<>(subsites);
Set expected = new HashSet<>(
list(
"/sites/default/includeInSiteSelector/",
"/sites/default/includeInSiteSelector/alpha/gamma/",
"/sites/default/includeInSiteSelector/beta/"));
assertEquals(expected, subsiteSet);
List options = CmsExtendedSiteSelector.getExplorerSiteSelectorOptions(
getCmsObject(),
true);
Set actual = new HashSet<>();
for (CmsExtendedSiteSelector.SiteSelectorOption option : options) {
if (option.getPath() != null) {
actual.add(option.getPath());
assertTrue(
"Site does not match",
CmsStringUtil.comparePaths(option.getSite(), getCmsObject().getRequestContext().getSiteRoot()));
}
}
expected = new HashSet<>(
list("/includeInSiteSelector", "/includeInSiteSelector/alpha/gamma", "/includeInSiteSelector/beta"));
assertEquals(expected, actual);
} finally {
OpenCms.getSiteManager().getSiteForRootPath(
getCmsObject().getRequestContext().getSiteRoot()).setSubsiteSelectionEnabled(false);
}
}
/**
* Tests the configuration in top-level sitemaps.
* @throws Exception -
*/
public void testLevel1Configuration() throws Exception {
CmsObject offlineCms = getCmsObject();
CmsObject onlineCms = onlineCms();
OpenCms.getADEManager().refresh();
checkResourceTypes(offlineCms, "/sites/default", "foldername", "a1", "b1", "c1", "foo1");
checkResourceTypes(onlineCms, "/sites/default", "foldername", "a1", "b1", "c1", "foo1");
checkResourceTypes(offlineCms, "/sites/default/today", "foldername", "a1", "b1", "c1", "foo1");
checkResourceTypes(onlineCms, "/sites/default/today", "foldername", "a1", "b1", "c1", "foo1");
}
/**
* Tests the configuration in level 2 subsitemaps.
* @throws Exception -
*/
public void testLevel2Configuration() throws Exception {
CmsObject offlineCms = getCmsObject();
CmsObject onlineCms = onlineCms();
OpenCms.getADEManager().refresh();
checkResourceTypes(offlineCms, "/sites/default/today/events", "foldername", "d2", "a1", "c1", "foo1");
checkResourceTypes(offlineCms, "/sites/default/today/events/foo", "foldername", "d2", "a1", "c1", "foo1");
checkResourceTypes(onlineCms, "/sites/default/today/events/", "foldername", "d2", "a1", "c1", "foo1");
checkResourceTypes(onlineCms, "/sites/default/today/events/foo", "foldername", "d2", "a1", "c1", "foo1");
checkResourceTypes(onlineCms, "/sites/default/today/news", "foldername", "c3", "e3", "a1", "b1", "foo1");
checkResourceTypes(onlineCms, "/sites/default/today/news/foo/", "foldername", "c3", "e3", "a1", "b1", "foo1");
checkResourceTypes(offlineCms, "/sites/default/today/news", "foldername", "c3", "e3", "a1", "b1", "foo1");
checkResourceTypes(offlineCms, "/sites/default/today/news/foo", "foldername", "c3", "e3", "a1", "b1", "foo1");
}
/**
* Tests the master configuration feature.
*
* @throws Exception -
*/
public void testMasterConfiguration() throws Exception {
CmsObject cms = getCmsObject();
I_CmsResourceType folderType = OpenCms.getResourceManager().getResourceType("folder");
cms.createResource("/system/mastertest", folderType);
try {
I_CmsResourceType configType = OpenCms.getResourceManager().getResourceType("sitemap_config");
I_CmsResourceType masterConfigType = OpenCms.getResourceManager().getResourceType("sitemap_master_config");
cms.createResource("/system/mastertest/.content", folderType);
cms.createResource("/system/mastertest/subfolder", folderType);
cms.createResource("/system/mastertest/subfolder/.content", folderType);
Map types1 = Maps.newHashMap();
types1.put("aa", "aa1");
types1.put("bb", "bb1");
types1.put("cc", "cc1");
String config1 = generateSitemapConfigWithTypes(types1, null);
cms.createResource(
"/system/mastertest/.content/.config",
configType,
config1.getBytes("UTF-8"),
Collections. emptyList());
Map types2 = Maps.newHashMap();
types2.put("bb", "bb2");
types2.put("cc", "cc2");
String config2 = generateSitemapConfigWithTypes(types2, null);
CmsResource masterConfigResource = cms.createResource(
"/system/.master",
masterConfigType,
config2.getBytes("UTF-8"),
Collections. emptyList());
Map types3 = Maps.newHashMap();
types3.put("cc", "cc3");
String config3 = generateSitemapConfigWithTypes(
types3,
Arrays.asList("" + masterConfigResource.getStructureId()));
cms.createResource(
"/system/mastertest/subfolder/.content/.config",
configType,
config3.getBytes("UTF-8"),
Collections. emptyList());
OpenCms.getADEManager().waitForCacheUpdate(false);
checkResourceTypesSet(cms, "/system/mastertest/subfolder", "foldername", "aa1", "bb2", "cc3");
cms.deleteResource("/system/.master", CmsResource.DELETE_PRESERVE_SIBLINGS);
OpenCms.getADEManager().waitForCacheUpdate(false);
checkResourceTypesSet(cms, "/system/mastertest/subfolder", "foldername", "aa1", "bb1", "cc3");
} finally {
cms.deleteResource("/system/mastertest", CmsResource.DELETE_PRESERVE_SIBLINGS);
}
}
/**
* Tests the master configuration chaining feature.
*
* @throws Exception -
*/
public void testMasterConfigurationChaining() throws Exception {
CmsObject cms = getCmsObject();
I_CmsResourceType folderType = OpenCms.getResourceManager().getResourceType("folder");
cms.createResource("/system/chaintest", folderType);
I_CmsResourceType configType = OpenCms.getResourceManager().getResourceType("sitemap_config");
I_CmsResourceType masterConfigType = OpenCms.getResourceManager().getResourceType("sitemap_master_config");
cms.createResource("/system/chaintest/.content", folderType);
Map types1 = Maps.newHashMap();
String config2 = generateSitemapConfigWithTypes(types1, null);
CmsResource masterConfigResource = cms.createResource(
"/system/.chainmaster",
masterConfigType,
config2.getBytes("UTF-8"),
Collections. emptyList());
String config3 = generateSitemapConfigWithTypes(types1, null);
CmsResource masterConfigResource2 = cms.createResource(
"/system/.chainmaster2",
masterConfigType,
config3.getBytes("UTF-8"),
Collections. emptyList());
String config4 = generateSitemapConfigWithTypes(
types1,
Arrays.asList("" + masterConfigResource.getStructureId(), "" + masterConfigResource2.getStructureId()));
CmsResource masterConfigResource3 = cms.createResource(
"/system/.chainmaster3",
masterConfigType,
config4.getBytes("UTF-8"),
Collections. emptyList());
String config1 = generateSitemapConfigWithTypes(
types1,
Arrays.asList("" + masterConfigResource3.getStructureId()));
cms.createResource(
"/system/chaintest/.content/.config",
configType,
config1.getBytes("UTF-8"),
Collections. emptyList());
OpenCms.getADEManager().waitForCacheUpdate(false);
CmsADEConfigData config = OpenCms.getADEManager().lookupConfiguration(cms, "/system/chaintest");
assertEquals(
Arrays.asList(
"/system/.chainmaster",
"/system/.chainmaster2",
"/system/.chainmaster3",
"/system/chaintest/.content/.config").toString(),
config.getConfigPaths().toString());
}
/**
* Tests the master configuration feature.
*
* @throws Exception -
*/
public void testMasterConfigurationMultiple() throws Exception {
CmsObject cms = getCmsObject();
I_CmsResourceType folderType = OpenCms.getResourceManager().getResourceType("folder");
cms.createResource("/system/mastertest", folderType);
try {
I_CmsResourceType configType = OpenCms.getResourceManager().getResourceType("sitemap_config");
I_CmsResourceType masterConfigType = OpenCms.getResourceManager().getResourceType("sitemap_master_config");
cms.createResource("/system/mastertest/.content", folderType);
cms.createResource("/system/mastertest/subfolder", folderType);
cms.createResource("/system/mastertest/subfolder/.content", folderType);
Map types1 = Maps.newHashMap();
types1.put("aa", "aa1");
types1.put("bb", "bb1");
types1.put("cc", "cc1");
String config1 = generateSitemapConfigWithTypes(types1, null);
cms.createResource(
"/system/mastertest/.content/.config",
configType,
config1.getBytes("UTF-8"),
Collections. emptyList());
Map types2 = Maps.newHashMap();
types2.put("bb", "bb2");
types2.put("cc", "cc2");
types2.put("dd", "dd2");
String config2 = generateSitemapConfigWithTypes(types2, null);
CmsResource masterConfigResource = cms.createResource(
"/system/.master",
masterConfigType,
config2.getBytes("UTF-8"),
Collections. emptyList());
Map types3 = new HashMap<>();
types3.put("bb", "bb3");
types3.put("cc", "cc3");
String config3 = generateSitemapConfigWithTypes(types3, null);
CmsResource masterConfigResource2 = cms.createResource(
"/system/.master2",
masterConfigType,
config3.getBytes("UTF-8"),
Collections. emptyList());
Map types4 = Maps.newHashMap();
types4.put("cc", "cc4");
String config4 = generateSitemapConfigWithTypes(
types4,
Arrays.asList("" + masterConfigResource.getStructureId(), "" + masterConfigResource2.getStructureId()));
cms.createResource(
"/system/mastertest/subfolder/.content/.config",
configType,
config4.getBytes("UTF-8"),
Collections. emptyList());
OpenCms.getADEManager().waitForCacheUpdate(false);
checkResourceTypesSet(cms, "/system/mastertest/subfolder", "foldername", "aa1", "bb3", "cc4", "dd2");
} finally {
cms.deleteResource("/system/mastertest", CmsResource.DELETE_PRESERVE_SIBLINGS);
}
}
/**
* Tests merging of master configurations via the ?template=... parameter.
*
* @throws Exception if something goes wrong
*/
public void testMergedMasterConfigurations() throws Exception {
CmsObject cms = getCmsObject();
String base = "/testMergedMasterConfigurations";
CmsVfsUtil.createFolder(cms, "/sites/default" + base + "/.content");
CmsResource reset = makeMasterConfig(
cms,
base + "/reset.xml",
"\n"
+ "\n"
+ "\n"
+ " \n"
+ " true \n"
+ " true \n"
+ " true \n"
+ " \n"
+ " \n"
+ "");
CmsResource master1a = makeMasterConfig(
cms,
base + "/master1a.xml",
"\n"
+ "\n"
+ "\n"
+ " \n"
+ " true \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ "");
CmsResource master1 = makeMasterConfig(
cms,
base + "/master1.xml",
"\n"
+ "\n"
+ "\n"
+ " \n"
+ " \n"
+ " \n"
+ " "
+ master1a.getStructureId()
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ "");
CmsResource master2 = makeMasterConfig(
cms,
base + "/master2.xml",
"\n"
+ "\n"
+ "\n"
+ " \n"
+ " true \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ "");
CmsResource configRes = makeConfig(
cms,
base + "/.content/.config",
"\n"
+ "\n"
+ "\n"
+ " \n"
+ " \n"
+ " \n"
+ " "
+ reset.getStructureId()
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " "
+ master1.getStructureId()
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " "
+ master2.getStructureId()
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ "");
OpenCms.getADEManager().waitForCacheUpdate(false);
CmsADEConfigData config = OpenCms.getADEManager().lookupConfiguration(cms, "/sites/default" + base);
assertEquals(
new HashSet<>(Arrays.asList("A", "B", "C")),
config.getResourceTypes().stream().map(t -> t.getTypeName()).collect(Collectors.toSet()));
// only in source
assertTrue(config.getTypesByName().get("A").isAvailableInTemplate("source"));
assertFalse(config.getTypesByName().get("A").isAvailableInTemplate("target"));
// only in target
assertTrue(config.getTypesByName().get("C").isAvailableInTemplate("target"));
assertFalse(config.getTypesByName().get("C").isAvailableInTemplate("source"));
// in both source and target
assertTrue(config.getTypesByName().get("B").isAvailableInTemplate("source"));
assertTrue(config.getTypesByName().get("B").isAvailableInTemplate("target"));
assertTrue(config.getTypesByName().get("A").isAvailableInTemplate(null));
assertTrue(config.getTypesByName().get("B").isAvailableInTemplate(null));
assertTrue(config.getTypesByName().get("C").isAvailableInTemplate(null));
}
/**
* Tests that newly created module configurations are reflected in the configuration objects.
*
* @throws Exception -
*/
@SuppressWarnings("deprecation")
public void testModuleConfig1() throws Exception {
CmsObject cms = rootCms();
String filename = "/system/modules/org.opencms.base/.config";
try {
String data = "\r\n"
+ "\r\n"
+ " \r\n"
+ " \r\n"
+ " \r\n"
+ " false \r\n"
+ " \r\n"
+ " \r\n"
+ " \r\n"
+ " \r\n"
+ " \r\n"
+ " \r\n"
+ " \r\n";
cms.createResource(
filename,
OpenCms.getADEManager().getModuleConfigurationType().getTypeId(),
data.getBytes(),
Collections. emptyList());
waitForUpdate(false);
checkResourceTypes(cms, "/sites/default", "foldername", "a1", "b1", "c1", "foo1", "m0");
} finally {
cms.lockResource(filename);
cms.deleteResource(filename, CmsResource.DELETE_PRESERVE_SIBLINGS);
}
}
/**
* Tests that when moving a configuration file, the configuration will be correct.
*
* @throws Exception -
*/
public void testMove1() throws Exception {
try {
CmsObject cms = rootCms();
cms.lockResource("/sites/default/today/events");
cms.moveResource("/sites/default/today/events", "/sites/default/today/news/events");
OpenCms.getADEManager().getOfflineCache().getWaitHandleForUpdateTask().enter(0);
checkResourceTypes(cms, "/sites/default/today/news", "foldername", "c3", "e3", "a1", "b1", "foo1");
checkResourceTypes(cms, "/sites/default/today/news/events/", "foldername", "d2", "c3", "e3", "a1", "foo1");
} finally {
restoreFiles();
}
}
/**
* Tests that when detail pages are moved, the configuration will still return the correct URIs.
*
* @throws Exception -
*/
public void testMoveDetailPages() throws Exception {
CmsObject cms = rootCms();
try {
OpenCms.getADEManager().refresh();
cms.lockResource("/sites/default/modelpage1.html");
String newPath = "/sites/default/.content/blah.html";
cms.moveResource("/sites/default/modelpage1.html", newPath);
CmsADEConfigData configData = OpenCms.getADEManager().lookupConfiguration(cms, "/sites/default/today");
List detailPages = configData.getDetailPagesForType("foo");
CmsDetailPageInfo page = detailPages.get(0);
assertEquals("/sites/default/.content/blah.html", page.getUri());
} finally {
restoreFiles();
}
}
/**
* Tests that the configuration is empty at paths where no configuration is defined.
* @throws Exception -
*/
public void testNoConfiguration() throws Exception {
CmsObject offlineCms = getCmsObject();
OpenCms.getADEManager().refresh();
checkResourceTypes(offlineCms, "/", "foldername");
checkResourceTypes(offlineCms, "/sites", "foldername");
checkResourceTypes(offlineCms, "/system", "foldername");
}
/**
* Tests that publishing a changed configuration file updates the online configuration object.
* @throws Exception -
*/
public void testPublish() throws Exception {
CmsObject cms = rootCms();
CmsObject onlineCms = onlineCms();
try {
waitForUpdate(false);
checkResourceTypes(cms, "/sites/default/today", "foldername", "a1", "b1", "c1", "foo1");
cms.copyResource("/sites/default/today/news/.content", "sites/default/today/.content");
waitForUpdate(true);
waitForUpdate(false);
checkResourceTypes(cms, "/sites/default/today", "foldername", "c3", "e3", "a1", "b1", "foo1");
checkResourceTypes(onlineCms, "/sites/default/today", "foldername", "a1", "b1", "c1", "foo1");
publish();
waitForUpdate(true);
waitForUpdate(false);
checkResourceTypes(onlineCms, "/sites/default/today/", "foldername", "c3", "e3", "a1", "b1", "foo1");
checkResourceTypes(onlineCms, "/sites/default/today/events", "foldername", "d2", "c3", "e3", "a1", "foo1");
} finally {
restoreFiles();
}
}
/**
* Tests that publishing a deleted configuration file changes the online configuration.
*
* @throws Exception -
*/
public void testPublishDeleted() throws Exception {
CmsObject cms = rootCms();
CmsObject onlineCms = onlineCms();
try {
waitForUpdate(false);
waitForUpdate(true);
checkResourceTypes(cms, "/sites/default/today", "foldername", "a1", "b1", "c1", "foo1");
checkResourceTypes(onlineCms, "/sites/default/today", "foldername", "a1", "b1", "c1", "foo1");
cms.lockResource("/sites/default/.content");
cms.deleteResource("/sites/default/.content", CmsResource.DELETE_PRESERVE_SIBLINGS);
waitForUpdate(true);
checkResourceTypes(onlineCms, "/sites/default/today", "foldername", "a1", "b1", "c1", "foo1");
publish();
waitForUpdate(true);
checkResourceTypes(onlineCms, "/sites/default/today/", "foldername");
} finally {
restoreFiles();
}
}
/**
* Tests whether getSubsiteFolder works correctly with the shared folder.
*
* @throws Exception in case resource creation fails
*/
@SuppressWarnings("deprecation")
public void testSharedGetSubSite() throws Exception {
CmsObject cms = rootCms();
String filename = "/shared/.content/.config";
String data = "\r\n"
+ "\r\n"
+ " \r\n"
+ " \r\n"
+ " \r\n";
cms.createResource("/shared/.content", CmsResourceTypeFolder.getStaticTypeId());
cms.createResource(
filename,
OpenCms.getADEManager().getSitemapConfigurationType().getTypeId(),
data.getBytes(),
Collections. emptyList());
OpenCms.getADEManager().waitForCacheUpdate(false);
assertEquals(
"/shared",
CmsFileUtil.removeTrailingSeparator(OpenCms.getADEManager().getSubSiteRoot(cms, "/shared")));
}
/**
* Tests that sitmeap folder types override module folder types.
* @throws Exception -
*/
@SuppressWarnings("deprecation")
public void testSitemapFolderTypesOverrideModuleFolderTypes() throws Exception {
CmsObject cms = rootCms();
String filename = "/system/modules/org.opencms.base/.config";
try {
String data = "\r\n"
+ "\r\n"
+ " \r\n"
+ " \r\n"
+ " \r\n"
+ " false \r\n"
+ " \r\n"
+ " \r\n"
+ " \r\n"
+ " \r\n"
+ " \r\n"
+ " \r\n"
+ " \r\n";
cms.createResource(
filename,
OpenCms.getADEManager().getModuleConfigurationType().getTypeId(),
data.getBytes(),
Collections. emptyList());
waitForUpdate(false);
String parentFolderType = OpenCms.getADEManager().getOfflineCache().getState().getParentFolderType(
"/sites/default/.content/a1/foo");
assertEquals("a", parentFolderType);
} finally {
cms.lockResource(filename);
cms.deleteResource(filename, CmsResource.DELETE_PRESERVE_SIBLINGS);
}
}
/**
* Tests new detail page options.
*
* @throws Exception -
*/
public void testSpecialDetailPageOptions() throws Exception {
CmsObject cms = getCmsObject();
String base = "/testDetailPageOptions";
cms.createResource(base, 0);
boolean preferDetailPages;
boolean excludeExternalContents;
preferDetailPages = true;
excludeExternalContents = true;
createDetailPageTestSitemap(base + "/aa", preferDetailPages, excludeExternalContents, false);
preferDetailPages = true;
excludeExternalContents = false;
createDetailPageTestSitemap(base + "/ab", preferDetailPages, excludeExternalContents, false);
preferDetailPages = false;
excludeExternalContents = true;
createDetailPageTestSitemap(base + "/ba", preferDetailPages, excludeExternalContents, false);
preferDetailPages = false;
excludeExternalContents = false;
createDetailPageTestSitemap(base + "/bb", preferDetailPages, excludeExternalContents, false);
OpenCms.getADEManager().waitForCacheUpdate(false);
String aa = base + "/aa";
String ab = base + "/ab";
String ba = base + "/ba";
String bb = base + "/bb";
String link;
link = createLinkFromTo(bb, ab);
assertTrue(link.contains("detail"));
assertEquals("ab", getABSubsite(link));
link = createLinkFromTo(bb, ba);
assertTrue(link.contains("detail"));
assertEquals("bb", getABSubsite(link));
link = createLinkFromTo(ba, bb);
assertFalse("Link should not be a detail link", link.contains("detail"));
link = createLinkFromTo(bb, aa);
assertTrue(link.contains("detail"));
assertEquals("aa", getABSubsite(link));
link = createLinkFromTo(aa, aa);
assertTrue(link.contains("detail"));
assertEquals("aa", getABSubsite(link));
link = createLinkFromTo(ab, bb);
assertTrue(link.contains("detail"));
assertEquals("ab", getABSubsite(link));
link = createLinkFromTo(bb, bb);
assertTrue(link.contains("detail"));
assertEquals("bb", getABSubsite(link));
CmsResource page;
CmsResource content;
final String articlePath = "/.content/blogentries/article.xml";
I_CmsDetailPageHandler handler = OpenCms.getADEManager().getDetailPageHandler();
page = cms.readResource(bb + "/detail/index.html");
content = cms.readResource(ab + articlePath);
assertFalse("Should not be a valid detail page", handler.isValidDetailPage(cms, page, content));
page = cms.readResource(ab + "/detail/index.html");
content = cms.readResource(bb + articlePath);
assertTrue("Should be a valid detail page", handler.isValidDetailPage(cms, page, content));
page = cms.readResource(ab + "/detail/index.html");
content = cms.readResource(ab + articlePath);
assertTrue("Should be a valid detail page", handler.isValidDetailPage(cms, page, content));
page = cms.readResource(ba + "/detail/index.html");
content = cms.readResource(bb + articlePath);
assertFalse("Should not be a valid detail page", handler.isValidDetailPage(cms, page, content));
page = cms.readResource(ba + "/detail/index.html");
content = cms.readResource(ab + articlePath);
assertFalse("Should not be a valid detail page", handler.isValidDetailPage(cms, page, content));
page = cms.readResource(ba + "/detail/index.html");
content = cms.readResource(bb + articlePath);
assertFalse("Should not be a valid detail page", handler.isValidDetailPage(cms, page, content));
page = cms.readResource(ba + "/detail/index.html");
content = cms.readResource(ba + articlePath);
assertTrue("Should be a valid detail page", handler.isValidDetailPage(cms, page, content));
}
/**
* Tests the parameter for specifying a detail page.
*
* @throws Exception -
*/
public void testSpecifiedTargetDetailPage() throws Exception {
waitForUpdate(false);
CmsObject cms = getCmsObject();
String detailPage = OpenCms.getADEManager().getDetailPageHandler().getDetailPage(
cms,
"/sites/default/.content/a1/blarg.html",
"/today/news",
"/otherpage");
assertEquals("/sites/default/otherpage/", detailPage);
detailPage = OpenCms.getADEManager().getDetailPageHandler().getDetailPage(
cms,
"/sites/default/.content/a1/blarg.html",
"/today/news",
"/sites/default/otherpage/");
assertEquals("/sites/default/otherpage/", detailPage);
}
/**
* Waits until the configuration update task has been run.
*
* @param online true if we should wait for the Online task, false for the Offline task
*/
public void waitForUpdate(boolean online) {
OpenCms.getADEManager().getCache(online).getWaitHandleForUpdateTask().enter(0);
}
/**
* Helper method to compare attributes of configured resource types with a list of expected values.
*
* @param cms the CMS context
* @param path the path used to access the configuration
* @param attr the attribute which should be retrieved from the configured resource types
* @param expected the expected resource type names
*/
protected void checkResourceTypes(CmsObject cms, String path, String attr, String... expected) {
CmsADEManager configManager = OpenCms.getADEManager();
CmsADEConfigData data = configManager.lookupConfiguration(cms, path);
List types = data.getResourceTypes();
List actualValues = new ArrayList();
for (CmsResourceTypeConfig typeConfig : types) {
actualValues.add(getAttribute(typeConfig, attr));
}
assertEquals(Arrays.asList(expected), actualValues);
}
/**
* Helper method to compare attributes of configured resource types with a set of expected values.
*
* @param cms the CMS context
* @param path the path used to access the configuration
* @param attr the attribute which should be retrieved from the configured resource types
* @param expected the expected resource type names
*/
protected void checkResourceTypesSet(CmsObject cms, String path, String attr, String... expected) {
CmsADEManager configManager = OpenCms.getADEManager();
CmsADEConfigData data = configManager.lookupConfiguration(cms, path);
List types = data.getResourceTypes();
List actualValues = new ArrayList();
for (CmsResourceTypeConfig typeConfig : types) {
actualValues.add(getAttribute(typeConfig, attr));
}
assertEquals(Sets.newHashSet(expected), Sets.newHashSet(actualValues));
}
/**
* Helper method for deleting a resource.
*
* @param res the resource to delete
* @throws Exception if something goes wrong
*/
protected void delete(CmsResource res) throws Exception {
CmsObject cms = getCmsObject();
String sitePath = cms.getSitePath(res);
cms.lockResource(sitePath);
getCmsObject().deleteResource(sitePath, CmsResource.DELETE_PRESERVE_SIBLINGS);
try {
cms.unlockResource(sitePath);
} catch (CmsException e) {
// ignore
}
}
/**
* Gets an attribute from a resource type configuration object.
*
* @param typeConfig the type configuration object
* @param attr the attribute name
* @return the attribute from the resource type configuration object
*/
protected String getAttribute(CmsResourceTypeConfig typeConfig, String attr) {
if ("type".equals(attr)) {
return typeConfig.getTypeName();
}
if ("foldername".equals(attr)) {
return typeConfig.getFolderOrName().getFolderName();
}
return null;
}
/**
* Initializes m_vfsPrefix lazily, otherwise it does not work.
* @return the VFS prefix as added to internal links
*/
protected String getVfsPrefix() {
if (null == m_vfsPrefix) {
m_vfsPrefix = OpenCms.getStaticExportManager().getVfsPrefix();
}
return m_vfsPrefix;
}
/**
* Helper method for creating a list of given elements.
*
* @param elems the elements
* @return a list containing the elements
*/
protected List list(@SuppressWarnings("unchecked") X... elems) {
List result = new ArrayList();
for (X x : elems) {
result.add(x);
}
return result;
}
/**
* Helper method for creating a CMS context in the Online Project.
*
* @return the CMS context
* @throws Exception -
*/
protected CmsObject onlineCms() throws Exception {
CmsObject cms = getCmsObject();
CmsProject online = cms.readProject(CmsProject.ONLINE_PROJECT_ID);
cms.getRequestContext().setCurrentProject(online);
return cms;
}
/**
* Helper method for publishing the current project.
* @throws Exception -
*/
protected void publish() throws Exception {
OpenCms.getPublishManager().publishProject(getCmsObject());
OpenCms.getPublishManager().waitWhileRunning();
}
/**
* Helper method to re-create the original test data in the VFS.
* @throws Exception -
*/
protected void restoreFiles() throws Exception {
System.out.println("Restoring test data...");
try {
OpenCmsTestLogAppender.setBreakOnError(false);
CmsObject cms = getCmsObject();
cms.getRequestContext().setSiteRoot("");
cms.lockResource("/sites/default");
cms.deleteResource("/sites/default", CmsResource.DELETE_PRESERVE_SIBLINGS);
OpenCms.getPublishManager().publishProject(cms);
OpenCms.getPublishManager().waitWhileRunning();
importResources(cms, "ade-config", "/");
OpenCms.getPublishManager().publishProject(cms);
OpenCms.getPublishManager().waitWhileRunning();
} finally {
OpenCmsTestLogAppender.setBreakOnError(true);
}
}
/**
* Helper method for getting a CMS object in the root site.
*
* @return a CMS context in the root site
*
* @throws CmsException -
*/
protected CmsObject rootCms() throws CmsException {
CmsObject cms = getCmsObject();
cms.getRequestContext().setSiteRoot("");
return cms;
}
private void createCategoryDetailPageTestSitemap(
String path,
boolean preferDetailPages,
boolean excludeExternalContents,
boolean includeInSiteSelector)
throws Exception {
CmsObject cms = getCmsObject();
cms.createResource(path, 0);
cms.createResource(path + "/.content", 0);
CmsResource detailFolder = cms.createResource(path + "/detail", 0);
CmsResource fooFolder = cms.createResource(path + "/detail-foo", 0);
cms.createResource(path + "/detail/index.html", OpenCms.getResourceManager().getResourceType("containerpage"));
CmsResource special1 = cms.createResource(path + "/default-1", 0);
cms.createResource(
path + "/default-1/index.html",
OpenCms.getResourceManager().getResourceType("containerpage"));
CmsResource special2 = cms.createResource(path + "/default-2", 0);
cms.createResource(
path + "/default-2/index.html",
OpenCms.getResourceManager().getResourceType("containerpage"));
String config = "\n"
+ "\n"
+ "\n"
+ " \n"
+ " true \n"
+ " "
+ preferDetailPages
+ " \n"
+ " "
+ excludeExternalContents
+ " \n"
+ ""
+ includeInSiteSelector
+ " "
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " "
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " "
+ detailFolder.getStructureId()
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " "
+ fooFolder.getStructureId()
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " "
+ special1.getStructureId()
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " "
+ special2.getStructureId()
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ "";
cms.createResource(path + "/.content/.config", OpenCms.getResourceManager().getResourceType("sitemap_config"));
CmsFile file = cms.readFile(path + "/.content/.config");
file.setContents(config.getBytes("UTF-8"));
cms.writeFile(file);
cms.createResource(path + "/.content/blogentries", 0);
cms.createResource(
path + "/.content/blogentries/article.xml",
OpenCms.getResourceManager().getResourceType("article1"));
}
private void createDetailPageTestSitemap(
String path,
boolean preferDetailPages,
boolean excludeExternalContents,
boolean includeInSiteSelector)
throws Exception {
CmsObject cms = getCmsObject();
cms.createResource(path, 0);
cms.createResource(path + "/.content", 0);
CmsResource detailFolder = cms.createResource(path + "/detail", 0);
cms.createResource(path + "/detail/index.html", OpenCms.getResourceManager().getResourceType("containerpage"));
String config = "\n"
+ "\n"
+ "\n"
+ " \n"
+ " true \n"
+ " "
+ preferDetailPages
+ " \n"
+ " "
+ excludeExternalContents
+ " \n"
+ ""
+ includeInSiteSelector
+ " "
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " "
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " "
+ detailFolder.getStructureId()
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ " \n"
+ "";
cms.createResource(path + "/.content/.config", OpenCms.getResourceManager().getResourceType("sitemap_config"));
CmsFile file = cms.readFile(path + "/.content/.config");
file.setContents(config.getBytes("UTF-8"));
cms.writeFile(file);
cms.createResource(path + "/.content/blogentries", 0);
cms.createResource(
path + "/.content/blogentries/article.xml",
OpenCms.getResourceManager().getResourceType("article1"));
}
private String createLinkFromTo(String subsite1, String subsite2) throws Exception {
CmsObject cms = OpenCms.initCmsObject(getCmsObject());
cms.getRequestContext().setUri(subsite1);
return OpenCms.getLinkManager().substituteLinkForUnknownTarget(
cms,
subsite2 + "/.content/blogentries/article.xml");
}
private String getABSubsite(String link) {
Matcher matcher = detailPageTestSubsitePattern.matcher(link);
if (matcher.find()) {
return matcher.group(1);
}
return null;
}
/**
* Creates a sitemap configuration with the specified content.
*
* @param cms
* @param path
* @param content
* @return
* @throws Exception
*/
private CmsResource makeConfig(CmsObject cms, String path, String content) throws Exception {
return cms.createResource(
path,
OpenCms.getResourceManager().getResourceType("sitemap_config"),
content.getBytes(StandardCharsets.UTF_8),
new ArrayList<>());
}
/**
* Creates a master configuration with the specified content.
*
* @param cms
* @param path
* @param content
* @return
* @throws Exception
*/
private CmsResource makeMasterConfig(CmsObject cms, String path, String content) throws Exception {
return cms.createResource(
path,
OpenCms.getResourceManager().getResourceType("sitemap_master_config"),
content.getBytes(StandardCharsets.UTF_8),
new ArrayList<>());
}
}