/* * Copyright (c) 2009, James Leigh All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions are met: * * - Redistributions of source code must retain the above copyright notice, this * list of conditions and the following disclaimer. * - Redistributions in binary form must reproduce the above copyright notice, * this list of conditions and the following disclaimer in the documentation * and/or other materials provided with the distribution. * - Neither the name of the openrdf.org nor the names of its contributors may * be used to endorse or promote products derived from this software without * specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE * POSSIBILITY OF SUCH DAMAGE. * */ package org.openrdf.repository.object.config; import java.lang.reflect.Method; import java.net.URL; import java.net.URLClassLoader; import java.util.ArrayList; import java.util.List; import java.util.Map; import org.openrdf.model.URI; import org.openrdf.model.ValueFactory; import org.openrdf.model.impl.ValueFactoryImpl; import org.openrdf.model.vocabulary.RDFS; import org.openrdf.repository.Repository; import org.openrdf.repository.RepositoryException; import org.openrdf.repository.config.RepositoryConfigException; import org.openrdf.repository.config.RepositoryFactory; import org.openrdf.repository.config.RepositoryImplConfig; import org.openrdf.repository.contextaware.config.ContextAwareFactory; import org.openrdf.repository.object.ObjectRepository; import org.openrdf.repository.object.ObjectServiceImpl; import org.openrdf.repository.object.behaviours.RDFObjectImpl; import org.openrdf.repository.object.exceptions.ObjectStoreConfigException; import org.openrdf.repository.object.managers.LiteralManager; import org.openrdf.repository.object.managers.RoleMapper; import org.openrdf.repository.object.managers.helpers.RoleClassLoader; /** * Creates {@link ObjectRepository} from any {@link Repository}. * * @author James Leigh * */ public class ObjectRepositoryFactory extends ContextAwareFactory { /** * The type of repositories that are created by this factory. * * @see RepositoryFactory#getRepositoryType() */ public static final String REPOSITORY_TYPE = "openrdf:ObjectRepository"; @Override public String getRepositoryType() { return REPOSITORY_TYPE; } /** * Creates a new ObjectRepositoryConfig instance. */ @Override public ObjectRepositoryConfig getConfig() { return new ObjectRepositoryConfig(); } /** * Wrap a previously initialised repository in an ObjectRepository. */ public ObjectRepository createRepository(ObjectRepositoryConfig config, Repository delegate) throws RepositoryConfigException, RepositoryException { ObjectRepository repo = getRepository(config, delegate.getValueFactory()); repo.setDelegate(delegate); return repo; } /** * Wrap a previously initialised repository in an ObjectRepository. */ public ObjectRepository createRepository(Repository delegate) throws RepositoryConfigException, RepositoryException { return createRepository(getConfig(), delegate); } /** * Create an uninitialised ObjectRepository without a delegate. */ @Override public ObjectRepository getRepository(RepositoryImplConfig configuration) throws RepositoryConfigException { if (!(configuration instanceof ObjectRepositoryConfig)) throw new RepositoryConfigException("Invalid configuration class: " + configuration.getClass()); ObjectRepositoryConfig config = (ObjectRepositoryConfig) configuration; return getRepository(config, ValueFactoryImpl.getInstance()); } protected LiteralManager createLiteralManager(ValueFactory uf, ValueFactory lf) { return new LiteralManager(uf, lf); } protected RoleMapper createRoleMapper(ValueFactory vf) throws ObjectStoreConfigException { return new RoleMapper(vf); } protected ObjectRepository createObjectRepository(RoleMapper mapper, LiteralManager literals, ClassLoader cl) throws ObjectStoreConfigException { return new ObjectRepository(new ObjectServiceImpl(mapper, literals, cl)); } private ObjectRepository getRepository(ObjectRepositoryConfig config, ValueFactory vf) throws ObjectStoreConfigException { ObjectRepository repo = getObjectRepository(config, vf); repo.setIncludeInferred(config.isIncludeInferred()); repo.setMaxQueryTime(config.getMaxQueryTime()); repo.setQueryLanguage(config.getQueryLanguage()); repo.setReadContexts(config.getReadContexts()); repo.setAddContexts(config.getAddContexts()); repo.setInsertContext(config.getInsertContext()); repo.setRemoveContexts(config.getRemoveContexts()); repo.setArchiveContexts(config.getArchiveContexts()); // repo.setQueryResultLimit(config.getQueryResultLimit()); return repo; } private ObjectRepository getObjectRepository(ObjectRepositoryConfig module, ValueFactory vf) throws ObjectStoreConfigException { ClassLoader cl = getClassLoader(module); RoleMapper mapper = getRoleMapper(cl, vf, module); LiteralManager literals = getLiteralManager(cl, vf, module); ObjectRepository repo = createObjectRepository(mapper, literals, cl); repo.setBlobStoreUrl(module.getBlobStore()); repo.setBlobStoreParameters(module.getBlobStoreParameters()); return repo; } private ClassLoader getClassLoader(ObjectRepositoryConfig module) { ClassLoader cl = module.getClassLoader(); List<URL> jars = new ArrayList<URL>(); jars.addAll(module.getConceptJars()); jars.addAll(module.getBehaviourJars()); if (jars.isEmpty()) return cl; URL[] array = jars.toArray(new URL[jars.size()]); return new URLClassLoader(array, cl); } private RoleMapper getRoleMapper(ClassLoader cl, ValueFactory uf, ObjectRepositoryConfig module) throws ObjectStoreConfigException { RoleMapper mapper = createRoleMapper(uf); mapper.addBehaviour(RDFObjectImpl.class, RDFS.RESOURCE); RoleClassLoader loader = new RoleClassLoader(mapper); loader.loadRoles(cl); if (module.getConceptJars() != null) { for (URL url : module.getConceptJars()) { loader.scan(url, cl); } } if (module.getBehaviourJars() != null) { for (URL url : module.getBehaviourJars()) { loader.scan(url, cl); } } for (Map.Entry<Method, List<URI>> e : module.getAnnotations().entrySet()) { if (e.getValue() == null) { mapper.addAnnotation(e.getKey()); } else { for (URI value : e.getValue()) { mapper.addAnnotation(e.getKey(), value); } } } for (Map.Entry<Class<?>, List<URI>> e : module.getConcepts().entrySet()) { if (e.getValue() == null) { mapper.addConcept(e.getKey()); } else { for (URI value : e.getValue()) { mapper.addConcept(e.getKey(), value); } } } for (Map.Entry<Class<?>, List<URI>> e : module.getBehaviours().entrySet()) { if (e.getValue() == null) { mapper.addBehaviour(e.getKey()); } else { for (URI value : e.getValue()) { mapper.addBehaviour(e.getKey(), value); } } } return mapper; } private LiteralManager getLiteralManager(ClassLoader cl, ValueFactory vf, ObjectRepositoryConfig module) { LiteralManager literalManager = createLiteralManager(vf, vf); literalManager.setClassLoader(cl); for (Map.Entry<Class<?>, List<URI>> e : module.getDatatypes().entrySet()) { for (URI value : e.getValue()) { literalManager.addDatatype(e.getKey(), value); } } return literalManager; } }