This project has retired. For details please refer to its Attic page.
PathManager xref

1   /*
2    * Licensed to the Apache Software Foundation (ASF) under one
3    * or more contributor license agreements.  See the NOTICE file
4    * distributed with this work for additional information
5    * regarding copyright ownership.  The ASF licenses this file
6    * to you under the Apache License, Version 2.0 (the
7    * "License"); you may not use this file except in compliance
8    * with the License.  You may obtain a copy of the License at
9    *
10   *   http://www.apache.org/licenses/LICENSE-2.0
11   *
12   * Unless required by applicable law or agreed to in writing,
13   * software distributed under the License is distributed on an
14   * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15   * KIND, either express or implied.  See the License for the
16   * specific language governing permissions and limitations
17   * under the License.
18   */
19  
20  package org.apache.chemistry.opencmis.jcr;
21  
22  import org.apache.chemistry.opencmis.commons.exceptions.CmisInvalidArgumentException;
23  import org.apache.chemistry.opencmis.commons.exceptions.CmisRuntimeException;
24  import org.apache.commons.logging.Log;
25  import org.apache.commons.logging.LogFactory;
26  
27  import javax.jcr.Node;
28  import javax.jcr.RepositoryException;
29  
30  /**
31   * Utility class for mapping JCR paths to CMIS paths
32   */
33  public class PathManager {
34      private static final Log log = LogFactory.getLog(PathManager.class);
35  
36      /**
37       * Identifier of the root folder
38       */
39      public static final String CMIS_ROOT_ID = "[root]";
40  
41      /**
42       * Root path
43       */
44      public static final String CMIS_ROOT_PATH = "/";
45  
46      private final String jcrRootPath;
47  
48      /**
49       * Create a new <code>PathManager</code> instance for the given JCR root path.
50       * @param jcrRootPath
51       */
52      public PathManager(String jcrRootPath) {
53          this.jcrRootPath = normalize(jcrRootPath);
54      }
55  
56      /**
57       * @return  the JCR root path
58       */
59      public String getJcrRootPath() {
60          return jcrRootPath;
61      }
62  
63      /**
64       * Determines whether a JCR <code>Node</code> is the root node wrt. to this
65       * <code>PathManager</code> instance. That is, whether the path of the node is
66       * equal to this instance's JCR root path.
67       * 
68       * @param node
69       * @return  <code>true</code> iff <code>node</code> is the root node wrt. to
70       *      this <code>PathManager</code> instance.
71       */
72      public boolean isRoot(Node node) {
73          try {
74              return node.getPath().equals(jcrRootPath);
75          }
76          catch (RepositoryException e) {
77              log.debug(e.getMessage(), e);
78              throw new CmisRuntimeException(e.getMessage(), e);
79          }
80      }
81  
82      /**
83       * Determine the CMIS path given a JCR <code>Node</code>.
84       *
85       * @param node
86       * @return
87       * @throws IllegalArgumentException  when <code>node</code> is not part of the hierarchy
88       */
89      public String getPath(Node node) {
90          try {
91              if (jcrRootPath.length() > node.getPath().length()) {
92                  throw new IllegalArgumentException("Node is not part of the hierarchy: " + node.getPath());
93              }
94  
95              String path = node.getPath().substring(jcrRootPath.length());
96              return path.startsWith("/") ? path : '/' + path;
97          }
98          catch (RepositoryException e) {
99              log.debug(e.getMessage(), e);
100             throw new CmisRuntimeException(e.getMessage(), e);
101         }
102     }
103 
104     /**
105      * @param cmisPath
106      * @return  <code>true</code> iff <code>cmisPath</code> equals {@link PathManager#CMIS_ROOT_PATH}
107      */
108     public static boolean isRoot(String cmisPath) {
109         return CMIS_ROOT_PATH.equals(cmisPath);
110     }
111 
112     /**
113      * @param cmisPath
114      * @return  <code>true</code> iff <code>cmisPath</code>
115      */
116     public static boolean isAbsolute(String cmisPath) {
117         return cmisPath.startsWith(CMIS_ROOT_PATH);
118     }
119 
120     /**
121      * Create a CMIS path from a parent path and a child element
122      * @param cmisPath  parent path
123      * @param child  child element
124      * @return
125      */
126     public static String createCmisPath(String cmisPath, String child) {
127         return cmisPath.length() > 0 && cmisPath.charAt(cmisPath.length() - 1) == '/'
128                 ? cmisPath + child
129                 : cmisPath + '/' + child;
130     }
131 
132     /**
133      * Relativize an CMIS path wrt. to a prefix.  
134      * @param prefix
135      * @param cmisPath
136      * @return  a string <code>r</code> such that <code>prefix</code> + <code>r</code> = <code>cmisPath</code> 
137      * @throws IllegalArgumentException  if <code>prefix</code> is not a prefix of <code>cmisPath</code>
138      */
139     public static String relativize(String prefix, String cmisPath) {
140         if (cmisPath.startsWith(prefix)) {
141             return cmisPath.substring(prefix.length());
142         }
143         else {
144             throw new IllegalArgumentException(prefix + " is not a prefix of " + cmisPath);
145         }
146     }
147 
148     //------------------------------------------< private >---
149 
150     private static String normalize(String path) {
151         if (path == null || path.length() == 0) {
152             return "/";
153         }
154 
155         if (!path.startsWith("/")) {
156             throw new CmisInvalidArgumentException("Root path must be absolute. Got: " + path);
157         }
158 
159         while (path.length() > 1 && path.endsWith("/")) {
160             path = path.substring(0, path.length() - 1);
161         }
162         return path;
163     }
164 }