Author: andreas
Date: Fri Feb 1 15:25:23 2008
New Revision: 617705
URL: http://svn.apache.org/viewvc?rev=617705&view=rev
Log:
Adding cache for resolved fallback source URIs (disabled by default).
Added:
lenya/trunk/src/webapp/lenya/config/cocoon-xconf/source-factories/fallback-store.xconf
Modified:
lenya/trunk/src/java/org/apache/lenya/cms/cocoon/source/FallbackSourceFactory.java
Modified: lenya/trunk/src/java/org/apache/lenya/cms/cocoon/source/FallbackSourceFactory.java
URL: http://svn.apache.org/viewvc/lenya/trunk/src/java/org/apache/lenya/cms/cocoon/source/FallbackSourceFactory.java?rev=617705&r1=617704&r2=617705&view=diff
==============================================================================
--- lenya/trunk/src/java/org/apache/lenya/cms/cocoon/source/FallbackSourceFactory.java (original)
+++ lenya/trunk/src/java/org/apache/lenya/cms/cocoon/source/FallbackSourceFactory.java Fri Feb 1 15:25:23 2008
@@ -35,6 +35,7 @@
import org.apache.excalibur.source.SourceResolver;
import org.apache.excalibur.source.SourceUtil;
import org.apache.excalibur.source.URIAbsolutizer;
+import org.apache.excalibur.store.impl.MRUMemoryStore;
import org.apache.lenya.cms.module.ModuleManager;
import org.apache.lenya.cms.publication.DocumentFactory;
import org.apache.lenya.cms.publication.DocumentUtil;
@@ -43,6 +44,9 @@
import org.apache.lenya.cms.publication.templating.ExistingSourceResolver;
import org.apache.lenya.cms.publication.templating.PublicationTemplateManager;
import org.apache.lenya.cms.publication.templating.VisitingSourceResolver;
+import org.apache.lenya.cms.repository.RepositoryUtil;
+import org.apache.lenya.cms.repository.Session;
+import org.apache.lenya.util.ServletHelper;
/**
* <p>
@@ -58,19 +62,86 @@
public class FallbackSourceFactory extends AbstractLogEnabled implements SourceFactory,
Serviceable, Contextualizable, URIAbsolutizer {
- /**
- * Ctor.
- */
- public FallbackSourceFactory() {
- super();
+ private static MRUMemoryStore store;
+ private boolean useCache = false;
+
+ protected static final String STORE_ROLE = FallbackSourceFactory.class.getName() + "Store";
+
+ protected MRUMemoryStore getStore() {
+ if (store == null) {
+ try {
+ store = (MRUMemoryStore) this.manager.lookup(STORE_ROLE);
+ } catch (ServiceException e) {
+ throw new RuntimeException(e);
+ }
+ }
+ return store;
}
-
+
/**
* @see org.apache.excalibur.source.SourceFactory#getSource(java.lang.String, java.util.Map)
*/
public Source getSource(final String location, Map parameters) throws IOException,
MalformedURLException {
+ MRUMemoryStore store = getStore();
+ Source source;
+ final String cacheKey = getCacheKey(location);
+ final String cachedSourceUri = (String) store.get(cacheKey);
+
+ if (!useCache || cachedSourceUri == null) {
+ source = findSource(location, parameters);
+ final String resolvedSourceUri = source.getURI();
+ store.hold(cacheKey, resolvedSourceUri);
+ if (getLogger().isDebugEnabled()) {
+ getLogger().debug("No cached source URI for key " + cacheKey + ", caching URI " + resolvedSourceUri);
+ }
+ } else {
+ SourceResolver resolver = null;
+ try {
+ resolver = (SourceResolver) this.manager.lookup(SourceResolver.ROLE);
+ source = resolver.resolveURI(cachedSourceUri);
+ } catch (ServiceException e) {
+ throw new RuntimeException(e);
+ } finally {
+ if (resolver != null) {
+ this.manager.release(resolver);
+ }
+ }
+ if (getLogger().isDebugEnabled()) {
+ getLogger().debug("Using cached source URI " + cachedSourceUri + " for key " + cacheKey);
+ }
+ }
+ return source;
+ }
+
+ protected String getCacheKey(final String location) {
+ String pubId = getPublicationId();
+ String cacheKey = pubId == null ? location : pubId + ":" + location;
+ return cacheKey;
+ }
+
+ protected String getPublicationId() {
+ Request request = ContextHelper.getRequest(this.context);
+ String webappUri = ServletHelper.getWebappURI(request);
+ URLInformation info = new URLInformation(webappUri);
+ String pubId = null;
+ try {
+ Session session = RepositoryUtil.getSession(this.manager, request);
+ DocumentFactory factory = DocumentUtil.createDocumentFactory(this.manager, session);
+ String pubIdCandidate = info.getPublicationId();
+ if (pubIdCandidate != null && factory.existsPublication(pubIdCandidate)) {
+ pubId = pubIdCandidate;
+ }
+ } catch (Exception e) {
+ throw new RuntimeException(e);
+ }
+ return pubId;
+ }
+
+ protected Source findSource(final String location, Map parameters) throws IOException,
+ MalformedURLException {
+
// Remove the protocol and the first '//'
int pos = location.indexOf("://");
@@ -78,11 +149,11 @@
throw new RuntimeException("The location [" + location
+ "] does not contain the string '://'");
}
-
+
String path = location.substring(pos + 3);
-
+
String publicationId = null;
-
+
// extract publication ID
String prefix = location.substring(0, pos);
StringTokenizer tokens = new StringTokenizer(prefix, ":");
@@ -90,13 +161,13 @@
tokens.nextToken();
publicationId = tokens.nextToken();
}
-
+
// remove query string
int questionMarkIndex = path.indexOf("?");
if (questionMarkIndex > -1) {
path = path.substring(0, questionMarkIndex);
}
-
+
if (path.length() == 0) {
throw new RuntimeException("The path after the protocol must not be empty!");
}
@@ -112,12 +183,14 @@
try {
sourceResolver = (SourceResolver) this.manager.lookup(SourceResolver.ROLE);
- templateManager = (PublicationTemplateManager) this.manager.lookup(PublicationTemplateManager.ROLE);
+ templateManager = (PublicationTemplateManager) this.manager
+ .lookup(PublicationTemplateManager.ROLE);
Request request = ContextHelper.getRequest(this.context);
-
+
if (publicationId == null) {
- String webappUrl = request.getRequestURI().substring(request.getContextPath().length());
+ String webappUrl = request.getRequestURI().substring(
+ request.getContextPath().length());
URLInformation info = new URLInformation(webappUrl);
publicationId = info.getPublicationId();
@@ -138,7 +211,8 @@
moduleMgr = (ModuleManager) this.manager.lookup(ModuleManager.ROLE);
final String moduleShortcut = path.split("/")[2];
String baseUri = moduleMgr.getBaseURI(moduleShortcut);
- final String modulePath = path.substring(("lenya/modules/" + moduleShortcut).length());
+ final String modulePath = path
+ .substring(("lenya/modules/" + moduleShortcut).length());
source = sourceResolver.resolveURI(baseUri + modulePath);
} finally {
if (moduleMgr != null) {
@@ -177,7 +251,7 @@
/** The ServiceManager */
private ServiceManager manager;
-
+
/**
* @see org.apache.avalon.framework.service.Serviceable#service(org.apache.avalon.framework.service.ServiceManager)
*/
@@ -223,4 +297,5 @@
public String absolutize(String baseURI, String location) {
return SourceUtil.absolutize(baseURI, location, true);
}
+
}
Added: lenya/trunk/src/webapp/lenya/config/cocoon-xconf/source-factories/fallback-store.xconf
URL: http://svn.apache.org/viewvc/lenya/trunk/src/webapp/lenya/config/cocoon-xconf/source-factories/fallback-store.xconf?rev=617705&view=auto
==============================================================================
--- lenya/trunk/src/webapp/lenya/config/cocoon-xconf/source-factories/fallback-store.xconf (added)
+++ lenya/trunk/src/webapp/lenya/config/cocoon-xconf/source-factories/fallback-store.xconf Fri Feb 1 15:25:23 2008
@@ -0,0 +1,24 @@
+<?xml version="1.0"?>
+<!--
+ Licensed to the Apache Software Foundation (ASF) under one or more
+ contributor license agreements. See the NOTICE file distributed with
+ this work for additional information regarding copyright ownership.
+ The ASF licenses this file to You under the Apache License, Version 2.0
+ (the "License"); you may not use this file except in compliance with
+ the License. You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+-->
+
+<xconf xpath="/cocoon" unless="/cocoon/component[@role = 'org.apache.lenya.cms.cocoon.source.FallbackSourceFactoryStore']">
+ <component role="org.apache.lenya.cms.cocoon.source.FallbackSourceFactoryStore"
+ class="org.apache.excalibur.store.impl.MRUMemoryStore" logger="lenya.source.fallback.store">
+ <parameter name="maxobjects" value="10000"/>
+ </component>
+</xconf>
lmpx.com only provides a reader for public news (NNTP) servers. It is not
affiliated with the servers or forums shown here and is not responsible for
the content of articles, which is written by their respective authors.