001/*
002 * ModeShape (http://www.modeshape.org)
003 *
004 * Licensed under the Apache License, Version 2.0 (the "License");
005 * you may not use this file except in compliance with the License.
006 * You may obtain a copy of the License at
007 *
008 *       http://www.apache.org/licenses/LICENSE-2.0
009 *
010 * Unless required by applicable law or agreed to in writing, software
011 * distributed under the License is distributed on an "AS IS" BASIS,
012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013 * See the License for the specific language governing permissions and
014 * limitations under the License.
015 */
016package org.modeshape.cmis;
017
018import java.math.BigInteger;
019import java.util.HashMap;
020import java.util.Map;
021import java.util.Set;
022import javax.jcr.Repository;
023import org.apache.chemistry.opencmis.commons.impl.server.AbstractServiceFactory;
024import org.apache.chemistry.opencmis.commons.server.CallContext;
025import org.apache.chemistry.opencmis.commons.server.CmisService;
026import org.apache.chemistry.opencmis.jcr.JcrRepository;
027import org.apache.chemistry.opencmis.jcr.JcrTypeManager;
028import org.apache.chemistry.opencmis.jcr.PathManager;
029import org.apache.chemistry.opencmis.jcr.impl.DefaultFolderTypeHandler;
030import org.apache.chemistry.opencmis.jcr.impl.DefaultUnversionedDocumentTypeHandler;
031import org.apache.chemistry.opencmis.jcr.type.JcrTypeHandlerManager;
032import org.apache.chemistry.opencmis.server.support.wrapper.ConformanceCmisServiceWrapper;
033import org.modeshape.common.logging.Logger;
034import org.modeshape.web.jcr.NoSuchRepositoryException;
035import org.modeshape.web.jcr.RepositoryManager;
036
037/**
038 * Implementation overwrites original service factory.
039 * 
040 * @author kulikov
041 */
042@SuppressWarnings( "deprecation" )
043public class JcrServiceFactory extends AbstractServiceFactory {
044
045    private static final Logger log = Logger.getLogger(JcrServiceFactory.class);
046
047    public static final String MOUNT_PATH_CONFIG = "mount-path";
048    public static final BigInteger DEFAULT_MAX_ITEMS_TYPES = BigInteger.valueOf(50);
049    public static final BigInteger DEFAULT_DEPTH_TYPES = BigInteger.valueOf(-1);
050    public static final BigInteger DEFAULT_MAX_ITEMS_OBJECTS = BigInteger.valueOf(200);
051    public static final BigInteger DEFAULT_DEPTH_OBJECTS = BigInteger.valueOf(10);
052    
053    private static final String DEFAULT_MOUNT_PATH = "/";
054
055    protected JcrTypeManager typeManager;
056    protected Map<String, Map<String, String>> jcrConfig;
057    protected String mountPath;
058    
059    private PathManager pathManager;
060    private JcrTypeHandlerManager typeHandlerManager;
061
062    @Override
063    public void init( Map<String, String> parameters ) {
064        readConfiguration(parameters);
065        this.typeManager = new JcrTypeManager();
066        this.pathManager = new PathManager(mountPath);
067        this.typeHandlerManager = createTypeHandlerManager(this.pathManager, typeManager);
068    }
069
070    protected void init() {
071        this.typeManager = new JcrTypeManager();
072        this.pathManager = new PathManager(DEFAULT_MOUNT_PATH);
073        this.typeHandlerManager = createTypeHandlerManager(this.pathManager, typeManager);
074    }
075
076    @Override
077    public void destroy() {
078        this.typeManager = null;
079        this.pathManager = null;
080        this.typeHandlerManager = null;
081        if (this.jcrConfig != null) {
082            this.jcrConfig.clear();
083            this.jcrConfig = null;
084        }
085    }
086
087    @Override
088    public CmisService getService( CallContext context ) {
089        JcrService jcrService = createJcrService(loadRepositories(), context);
090        ConformanceCmisServiceWrapper serviceWrapper = new ConformanceCmisServiceWrapper(jcrService,
091                                                                                         DEFAULT_MAX_ITEMS_TYPES,
092                                                                                         DEFAULT_DEPTH_TYPES,
093                                                                                         DEFAULT_MAX_ITEMS_OBJECTS,
094                                                                                         DEFAULT_DEPTH_OBJECTS);
095
096        serviceWrapper.setCallContext(context);
097        return serviceWrapper;
098    }
099
100    // ------------------------------------------< factories >---
101
102    private Map<String, JcrRepository> loadRepositories() {
103        Map<String, JcrRepository> list = new HashMap<>();
104        Set<String> names = RepositoryManager.getJcrRepositoryNames();
105
106        for (String repositoryId : names) {
107            try {
108                Repository repository = RepositoryManager.getRepository(repositoryId);
109                list.put(repositoryId, new JcrMsRepository(repository, pathManager, typeManager, typeHandlerManager));
110                log.debug("--- loaded repository " + repositoryId);
111            } catch (NoSuchRepositoryException e) {
112                // should never happen;
113            }
114        }
115
116        return list;
117    }
118    
119    /**
120     * Create a <code>JcrService</code> from a <code>JcrRepository</code>JcrRepository> and <code>CallContext</code>.
121     * 
122     * @param jcrRepositories the repositories
123     * @param context the context
124     * @return the new JCR service
125     */
126    protected JcrService createJcrService( Map<String, JcrRepository> jcrRepositories,
127                                           CallContext context ) {
128        return new JcrService(jcrRepositories);
129    }
130
131    protected JcrTypeHandlerManager createTypeHandlerManager( PathManager pathManager,
132                                                              JcrTypeManager typeManager ) {
133        JcrTypeHandlerManager typeHandlerManager = new JcrTypeHandlerManager(pathManager, typeManager);
134        typeHandlerManager.addHandler(new DefaultFolderTypeHandler());
135        typeHandlerManager.addHandler(new MsDocumentTypeHandler());
136        typeHandlerManager.addHandler(new DefaultUnversionedDocumentTypeHandler());
137        return typeHandlerManager;
138    }
139
140    // ------------------------------------------< private >---
141
142    private void readConfiguration( Map<String, String> parameters ) {
143        String mountPath = parameters.get(MOUNT_PATH_CONFIG);
144        this.mountPath = mountPath != null ? mountPath : DEFAULT_MOUNT_PATH;
145        this.jcrConfig = RepositoryConfig.load(parameters);
146    }
147}