View Javadoc

1   /*
2    * ModeShape (http://www.modeshape.org)
3    * See the COPYRIGHT.txt file distributed with this work for information
4    * regarding copyright ownership.  Some portions may be licensed
5    * to Red Hat, Inc. under one or more contributor license agreements.
6    * See the AUTHORS.txt file in the distribution for a full listing of 
7    * individual contributors.
8    *
9    * ModeShape is free software. Unless otherwise indicated, all code in ModeShape
10   * is licensed to you under the terms of the GNU Lesser General Public License as
11   * published by the Free Software Foundation; either version 2.1 of
12   * the License, or (at your option) any later version.
13   *
14   * ModeShape is distributed in the hope that it will be useful,
15   * but WITHOUT ANY WARRANTY; without even the implied warranty of
16   * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
17   * Lesser General Public License for more details.
18   *
19   * You should have received a copy of the GNU Lesser General Public
20   * License along with this software; if not, write to the Free
21   * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
22   * 02110-1301 USA, or see the FSF site: http://www.fsf.org.
23   */
24  package org.modeshape.web.jcr.webdav;
25  
26  import java.io.File;
27  import java.io.IOException;
28  import javax.servlet.ServletException;
29  import javax.servlet.http.HttpServletRequest;
30  import javax.servlet.http.HttpServletResponse;
31  import net.sf.webdav.IWebdavStore;
32  import net.sf.webdav.WebdavServlet;
33  import org.modeshape.common.util.Logger;
34  
35  /**
36   * Custom servlet implementation that provides WebDAV access to a JCR repository. Nodes in the repository with a specified primary
37   * type (nt:file, by default) are treated as WebDAV resources (files) while nodes with any other primary type are treated as
38   * WebDAV folders.
39   */
40  public class ModeShapeWebdavServlet extends WebdavServlet {
41  
42      private static final long serialVersionUID = 1L;
43  
44      public static final String INIT_REQUEST_RESOLVER_CLASS_NAME = "org.modeshape.web.jcr.webdav.REQUEST_RESOLVER_CLASS_NAME";
45  
46      public static final String INIT_CONTENT_PRIMARY_TYPE_NAMES = "org.modeshape.web.jcr.webdav.CONTENT_PRIMARY_TYPE_NAMES";
47      public static final String INIT_RESOURCE_PRIMARY_TYPES_NAMES = "org.modeshape.web.jcr.webdav.RESOURCE_PRIMARY_TYPE_NAMES";
48      public static final String INIT_NEW_FOLDER_PRIMARY_TYPE_NAME = "org.modeshape.web.jcr.webdav.NEW_FOLDER_PRIMARY_TYPE_NAME";
49      public static final String INIT_NEW_RESOURCE_PRIMARY_TYPE_NAME = "org.modeshape.web.jcr.webdav.NEW_RESOURCE_PRIMARY_TYPE_NAME";
50      public static final String INIT_NEW_CONTENT_PRIMARY_TYPE_NAME = "org.modeshape.web.jcr.webdav.NEW_CONTENT_PRIMARY_TYPE_NAME";
51  
52      private RequestResolver requestResolver;
53  
54      /**
55       * {@inheritDoc}
56       */
57      @Override
58      protected IWebdavStore constructStore( String clazzName,
59                                             File root ) {
60          return new ModeShapeWebdavStore(getParam(INIT_CONTENT_PRIMARY_TYPE_NAMES), getParam(INIT_RESOURCE_PRIMARY_TYPES_NAMES),
61                                          getParam(INIT_NEW_FOLDER_PRIMARY_TYPE_NAME),
62                                          getParam(INIT_NEW_RESOURCE_PRIMARY_TYPE_NAME),
63                                          getParam(INIT_NEW_CONTENT_PRIMARY_TYPE_NAME), requestResolver);
64      }
65  
66      protected String getParam( String name ) {
67          return getServletContext().getInitParameter(name);
68      }
69  
70      /**
71       * Loads and initializes the {@link #requestResolver}
72       */
73      private void constructRequestResolver() {
74          // Initialize the request resolver
75          String requestResolverClassName = getParam(INIT_REQUEST_RESOLVER_CLASS_NAME);
76          Logger.getLogger(getClass()).debug("WebDAV Servlet resolver class name = " + requestResolverClassName);
77          if (requestResolverClassName == null) {
78              this.requestResolver = new MultiRepositoryRequestResolver();
79          } else {
80              try {
81                  Class<? extends RequestResolver> clazz = Class.forName(requestResolverClassName)
82                                                                .asSubclass(RequestResolver.class);
83                  this.requestResolver = clazz.newInstance();
84              } catch (Exception ex) {
85                  throw new IllegalStateException(ex);
86              }
87          }
88          Logger.getLogger(getClass()).debug("WebDAV Servlet using resolver class = " + requestResolver.getClass().getName());
89          this.requestResolver.initialize(getServletContext());
90      }
91  
92      @Override
93      public void init() throws ServletException {
94          constructRequestResolver();
95  
96          super.init();
97      }
98  
99      /**
100      * {@inheritDoc}
101      * <p>
102      * This method also sets and clears a thread-local reference to the incoming {@link HttpServletRequest request}.
103      * </p>
104      */
105     @Override
106     protected void service( HttpServletRequest req,
107                             HttpServletResponse resp ) throws ServletException, IOException {
108         ModeShapeWebdavStore.setRequest(req);
109         try {
110             super.service(req, resp);
111         } finally {
112             ModeShapeWebdavStore.setRequest(null);
113         }
114     }
115 }