]> source.dussan.org Git - archiva.git/commitdiff
start to move out maven specific from dav part
authorOlivier Lamy <olamy@apache.org>
Tue, 3 Dec 2013 05:46:41 +0000 (05:46 +0000)
committerOlivier Lamy <olamy@apache.org>
Tue, 3 Dec 2013 05:46:41 +0000 (05:46 +0000)
git-svn-id: https://svn.apache.org/repos/asf/archiva/trunk@1547291 13f79535-47bb-0310-9956-ffa450edef68

archiva-modules/archiva-web/archiva-security/src/test/java/org/apache/archiva/security/mock/MockBeanServices.java
archiva-modules/archiva-web/archiva-webdav/src/main/java/org/apache/archiva/webdav/ArchivaDavResourceFactory.java
archiva-modules/archiva-web/archiva-webdav/src/test/java/org/apache/archiva/webdav/ArchivaDavResourceFactoryTest.java
archiva-modules/metadata/metadata-repository-api/pom.xml
archiva-modules/metadata/metadata-repository-api/src/main/java/org/apache/archiva/metadata/repository/storage/RepositoryStorage.java
archiva-modules/plugins/maven2-repository/src/main/java/org/apache/archiva/metadata/repository/storage/maven2/Maven2RepositoryStorage.java

index f3d0054cc7adbc061467f94a63914eaa4473cc9a..cb39ca87389841f84dc349d04db4400c64be20fd 100644 (file)
@@ -18,6 +18,7 @@ package org.apache.archiva.security.mock;
  * under the License.
  */
 
+import org.apache.archiva.admin.model.beans.ManagedRepository;
 import org.apache.archiva.metadata.model.ArtifactMetadata;
 import org.apache.archiva.metadata.model.ProjectMetadata;
 import org.apache.archiva.metadata.model.ProjectVersionMetadata;
@@ -142,4 +143,10 @@ public class MockBeanServices
     {
         return false;
     }
+
+    @Override
+    public String getFilePath( String requestPath, ManagedRepository managedRepository )
+    {
+        return null;
+    }
 }
index 9b0f1536701ddcc0a7b26433959836a93048c38c..5e121406e0f2d62298c6256bfc2b1ec32b798080 100644 (file)
@@ -20,7 +20,9 @@ package org.apache.archiva.webdav;
  */
 
 import org.apache.archiva.admin.model.RepositoryAdminException;
+import org.apache.archiva.admin.model.beans.ManagedRepository;
 import org.apache.archiva.admin.model.beans.RemoteRepository;
+import org.apache.archiva.admin.model.managed.ManagedRepositoryAdmin;
 import org.apache.archiva.admin.model.remote.RemoteRepositoryAdmin;
 import org.apache.archiva.audit.AuditEvent;
 import org.apache.archiva.audit.AuditListener;
@@ -111,7 +113,7 @@ import java.util.Set;
 /**
  *
  */
-@Service("davResourceFactory#archiva")
+@Service( "davResourceFactory#archiva" )
 public class ArchivaDavResourceFactory
     implements DavResourceFactory, Auditable
 {
@@ -121,63 +123,39 @@ public class ArchivaDavResourceFactory
 
     private Logger log = LoggerFactory.getLogger( ArchivaDavResourceFactory.class );
 
-    /**
-     *
-     */
     @Inject
     private List<AuditListener> auditListeners = new ArrayList<AuditListener>();
 
-    /**
-     *
-     */
     @Inject
     private RepositoryContentFactory repositoryFactory;
 
-    /**
-     *
-     */
     private RepositoryRequest repositoryRequest;
 
-    /**
-     *
-     */
     @Inject
-    @Named(value = "repositoryProxyConnectors#default")
+    @Named( value = "repositoryProxyConnectors#default" )
     private RepositoryProxyConnectors connectors;
 
-    /**
-     *
-     */
     @Inject
     private MetadataTools metadataTools;
 
-    /**
-     *
-     */
     @Inject
     private MimeTypes mimeTypes;
 
-    /**
-     *
-     */
     private ArchivaConfiguration archivaConfiguration;
 
-    /**
-     *
-     */
     @Inject
     private ServletAuthenticator servletAuth;
 
-    /**
-     *
-     */
     @Inject
-    @Named(value = "httpAuthenticator#basic")
+    @Named( value = "httpAuthenticator#basic" )
     private HttpAuthenticator httpAuth;
 
     @Inject
     private RemoteRepositoryAdmin remoteRepositoryAdmin;
 
+    @Inject
+    private ManagedRepositoryAdmin managedRepositoryAdmin;
+
     @Inject
     private IndexMerger indexMerger;
 
@@ -189,26 +167,14 @@ public class ArchivaDavResourceFactory
      */
     private final LockManager lockManager = new SimpleLockManager();
 
-    /**
-     *
-     */
     private ChecksumFile checksum;
 
-    /**
-     *
-     */
     private Digester digestSha1;
 
-    /**
-     *
-     */
     private Digester digestMd5;
 
-    /**
-     *
-     */
     @Inject
-    @Named(value = "archivaTaskScheduler#repository")
+    @Named( value = "archivaTaskScheduler#repository" )
     private RepositoryArchivaTaskScheduler scheduler;
 
     private ApplicationContext applicationContext;
@@ -305,11 +271,11 @@ public class ArchivaDavResourceFactory
                            archivaLocator.getRepositoryId(), e.getMessage() );
             }
 
-            ManagedRepositoryContent managedRepository = null;
+            ManagedRepositoryContent managedRepositoryContent = null;
 
             try
             {
-                managedRepository = repositoryFactory.getManagedRepositoryContent( archivaLocator.getRepositoryId() );
+                managedRepositoryContent = repositoryFactory.getManagedRepositoryContent( archivaLocator.getRepositoryId() );
             }
             catch ( RepositoryNotFoundException e )
             {
@@ -321,13 +287,21 @@ public class ArchivaDavResourceFactory
                 throw new DavException( HttpServletResponse.SC_INTERNAL_SERVER_ERROR, e );
             }
 
-            log.debug( "Managed repository '{}' accessed by '{}'", managedRepository.getId(), activePrincipal );
+            log.debug( "Managed repository '{}' accessed by '{}'", managedRepositoryContent.getId(), activePrincipal );
 
-            resource = processRepository( request, archivaLocator, activePrincipal, managedRepository );
+            try
+            {
+                resource = processRepository( request, archivaLocator, activePrincipal, managedRepositoryContent,
+                                              managedRepositoryAdmin.getManagedRepository( archivaLocator.getRepositoryId() ) );
+            }
+            catch ( RepositoryAdminException e )
+            {
+                throw new DavException( 500, e );
+            }
 
             String logicalResource = RepositoryPathUtil.getLogicalResource( locator.getResourcePath() );
             resourcesInAbsolutePath.add(
-                new File( managedRepository.getRepoRoot(), logicalResource ).getAbsolutePath() );
+                new File( managedRepositoryContent.getRepoRoot(), logicalResource ).getAbsolutePath() );
         }
 
         String requestedResource = request.getRequestURI();
@@ -480,7 +454,8 @@ public class ArchivaDavResourceFactory
                 try
                 {
                     DavResource updatedResource =
-                        processRepository( request, archivaLocator, activePrincipal, managedRepository );
+                        processRepository( request, archivaLocator, activePrincipal, managedRepository,
+                                           managedRepositoryAdmin.getManagedRepository( repositoryId ) );
                     if ( resource == null )
                     {
                         resource = updatedResource;
@@ -498,6 +473,10 @@ public class ArchivaDavResourceFactory
                 {
                     storedExceptions.add( e );
                 }
+                catch ( RepositoryAdminException e )
+                {
+                    storedExceptions.add( new DavException( 500, e ) );
+                }
             }
         }
         if ( resource == null )
@@ -524,22 +503,27 @@ public class ArchivaDavResourceFactory
     }
 
     private DavResource processRepository( final DavServletRequest request, ArchivaDavResourceLocator archivaLocator,
-                                           String activePrincipal, ManagedRepositoryContent managedRepository )
+                                           String activePrincipal, ManagedRepositoryContent managedRepositoryContent,
+                                           ManagedRepository managedRepository )
         throws DavException
     {
         DavResource resource = null;
-        if ( isAuthorized( request, managedRepository.getId() ) )
+        if ( isAuthorized( request, managedRepositoryContent.getId() ) )
         {
-            String path = RepositoryPathUtil.getLogicalResource( archivaLocator.getResourcePath() );
+            RepositoryStorage repositoryStorage =
+                this.applicationContext.getBean( "repositoryStorage#" + managedRepository.getLayout(),
+                                                 RepositoryStorage.class );
+            String path = repositoryStorage.getFilePath( archivaLocator.getResourcePath(), managedRepository );
             if ( path.startsWith( "/" ) )
             {
                 path = path.substring( 1 );
             }
             LogicalResource logicalResource = new LogicalResource( path );
-            File resourceFile = new File( managedRepository.getRepoRoot(), path );
-            resource = new ArchivaDavResource( resourceFile.getAbsolutePath(), path, managedRepository.getRepository(),
-                                               request.getRemoteAddr(), activePrincipal, request.getDavSession(),
-                                               archivaLocator, this, mimeTypes, auditListeners, scheduler );
+            File resourceFile = new File( managedRepositoryContent.getRepoRoot(), path );
+            resource =
+                new ArchivaDavResource( resourceFile.getAbsolutePath(), path, managedRepositoryContent.getRepository(),
+                                        request.getRemoteAddr(), activePrincipal, request.getDavSession(),
+                                        archivaLocator, this, mimeTypes, auditListeners, scheduler );
 
             if ( WebdavMethodUtil.isReadMethod( request.getMethod() ) )
             {
@@ -555,7 +539,8 @@ public class ArchivaDavResourceFactory
                         boolean previouslyExisted = resourceFile.exists();
 
                         // Attempt to fetch the resource from any defined proxy.
-                        boolean fromProxy = fetchContentFromProxies( managedRepository, request, logicalResource );
+                        boolean fromProxy =
+                            fetchContentFromProxies( managedRepositoryContent, request, logicalResource );
 
                         // At this point the incoming request can either be in default or
                         // legacy layout format.
@@ -564,13 +549,14 @@ public class ArchivaDavResourceFactory
                             // Perform an adjustment of the resource to the managed
                             // repository expected path.
                             String localResourcePath =
-                                repositoryRequest.toNativePath( logicalResource.getPath(), managedRepository );
-                            resourceFile = new File( managedRepository.getRepoRoot(), localResourcePath );
+                                repositoryRequest.toNativePath( logicalResource.getPath(), managedRepositoryContent );
+                            resourceFile = new File( managedRepositoryContent.getRepoRoot(), localResourcePath );
                             resource =
                                 new ArchivaDavResource( resourceFile.getAbsolutePath(), logicalResource.getPath(),
-                                                        managedRepository.getRepository(), request.getRemoteAddr(),
-                                                        activePrincipal, request.getDavSession(), archivaLocator, this,
-                                                        mimeTypes, auditListeners, scheduler );
+                                                        managedRepositoryContent.getRepository(),
+                                                        request.getRemoteAddr(), activePrincipal,
+                                                        request.getDavSession(), archivaLocator, this, mimeTypes,
+                                                        auditListeners, scheduler );
                         }
                         catch ( LayoutException e )
                         {
@@ -586,7 +572,7 @@ public class ArchivaDavResourceFactory
                                 + PROXIED_SUFFIX;
 
                             log.debug( "Proxied artifact '{}' in repository '{}' (current user '{}')",
-                                       resourceFile.getName(), managedRepository.getId(), activePrincipal );
+                                       resourceFile.getName(), managedRepositoryContent.getId(), activePrincipal );
 
                             triggerAuditEvent( request.getRemoteAddr(), archivaLocator.getRepositoryId(),
                                                logicalResource.getPath(), event, activePrincipal );
@@ -606,22 +592,22 @@ public class ArchivaDavResourceFactory
 
                 // check if target repo is enabled for releases
                 // we suppose that release-artifacts can be deployed only to repos enabled for releases
-                if ( managedRepository.getRepository().isReleases() && !repositoryRequest.isMetadata( resourcePath )
-                    && !repositoryRequest.isSupportFile( resourcePath ) )
+                if ( managedRepositoryContent.getRepository().isReleases() && !repositoryRequest.isMetadata(
+                    resourcePath ) && !repositoryRequest.isSupportFile( resourcePath ) )
                 {
                     ArtifactReference artifact = null;
                     try
                     {
-                        artifact = managedRepository.toArtifactReference( resourcePath );
+                        artifact = managedRepositoryContent.toArtifactReference( resourcePath );
 
                         if ( !VersionUtil.isSnapshot( artifact.getVersion() ) )
                         {
                             // check if artifact already exists and if artifact re-deployment to the repository is allowed
-                            if ( managedRepository.hasContent( artifact )
-                                && managedRepository.getRepository().isBlockRedeployments() )
+                            if ( managedRepositoryContent.hasContent( artifact )
+                                && managedRepositoryContent.getRepository().isBlockRedeployments() )
                             {
                                 log.warn( "Overwriting released artifacts in repository '{}' is not allowed.",
-                                          managedRepository.getId() );
+                                          managedRepositoryContent.getId() );
                                 throw new DavException( HttpServletResponse.SC_CONFLICT,
                                                         "Overwriting released artifacts is not allowed." );
                             }
@@ -629,7 +615,7 @@ public class ArchivaDavResourceFactory
                     }
                     catch ( LayoutException e )
                     {
-                        log.warn( "Artifact path '{}' is invalid." ,resourcePath );
+                        log.warn( "Artifact path '{}' is invalid."resourcePath );
                     }
                 }
 
@@ -640,7 +626,7 @@ public class ArchivaDavResourceFactory
                  * create the collections themselves.
                  */
 
-                File rootDirectory = new File( managedRepository.getRepoRoot() );
+                File rootDirectory = new File( managedRepositoryContent.getRepoRoot() );
                 File destDir = new File( rootDirectory, logicalResource.getPath() ).getParentFile();
 
                 if ( !destDir.exists() )
@@ -651,12 +637,11 @@ public class ArchivaDavResourceFactory
                     log.debug( "Creating destination directory '{}' (current user '{}')", destDir.getName(),
                                activePrincipal );
 
-                    triggerAuditEvent( request.getRemoteAddr(), managedRepository.getId(), relPath,
+                    triggerAuditEvent( request.getRemoteAddr(), managedRepositoryContent.getId(), relPath,
                                        AuditEvent.CREATE_DIR, activePrincipal );
                 }
             }
-        }
-        return resource;
+        } return resource;
     }
 
     public DavResource createResource( final DavResourceLocator locator, final DavSession davSession )
@@ -1202,7 +1187,8 @@ public class ArchivaDavResourceFactory
 
             if ( tmp != null && tmp.getDirectory() != null && tmp.getDirectory().exists() )
             {
-                if ( System.currentTimeMillis() - tmp.getCreationTime() > ( repositoryGroupConfiguration.getMergedIndexTtl() * 60 * 1000 ) )
+                if ( System.currentTimeMillis() - tmp.getCreationTime() > (
+                    repositoryGroupConfiguration.getMergedIndexTtl() * 60 * 1000 ) )
                 {
                     log.debug( MarkerFactory.getMarker( "group.merged.index" ),
                                "tmp group index '{}' is too old so delete it", repositoryGroupConfiguration.getId() );
@@ -1240,11 +1226,13 @@ public class ArchivaDavResourceFactory
                       repositoryGroupConfiguration.getId(), authzRepos );
             IndexingContext indexingContext = indexMerger.buildMergedIndex(
                 new IndexMergerRequest( authzRepos, true, repositoryGroupConfiguration.getId(),
-                                        repositoryGroupConfiguration.getMergedIndexPath(), repositoryGroupConfiguration.getMergedIndexTtl() ) );
+                                        repositoryGroupConfiguration.getMergedIndexPath(),
+                                        repositoryGroupConfiguration.getMergedIndexTtl() ) );
             File mergedRepoDir = indexingContext.getIndexDirectoryFile();
-            TemporaryGroupIndex temporaryGroupIndex = new TemporaryGroupIndex( mergedRepoDir, indexingContext.getId(),
-                    repositoryGroupConfiguration.getId(),repositoryGroupConfiguration.getMergedIndexTtl() )
-                    .setCreationTime(new Date().getTime() );
+            TemporaryGroupIndex temporaryGroupIndex =
+                new TemporaryGroupIndex( mergedRepoDir, indexingContext.getId(), repositoryGroupConfiguration.getId(),
+                                         repositoryGroupConfiguration.getMergedIndexTtl() ).setCreationTime(
+                    new Date().getTime() );
             temporaryGroupIndexMap.put( repositoryGroupConfiguration.getId(), temporaryGroupIndex );
             session.setAttribute( TemporaryGroupIndexSessionCleaner.TEMPORARY_INDEX_SESSION_KEY,
                                   temporaryGroupIndexMap );
@@ -1305,4 +1293,14 @@ public class ArchivaDavResourceFactory
     {
         this.remoteRepositoryAdmin = remoteRepositoryAdmin;
     }
+
+    public ManagedRepositoryAdmin getManagedRepositoryAdmin()
+    {
+        return managedRepositoryAdmin;
+    }
+
+    public void setManagedRepositoryAdmin( ManagedRepositoryAdmin managedRepositoryAdmin )
+    {
+        this.managedRepositoryAdmin = managedRepositoryAdmin;
+    }
 }
index e0ea0753a135600da2d4429bc63fb20605c0ed61..7bd7fc360f074d5c59f888b31a03ffb93c3fa5c7 100644 (file)
@@ -182,6 +182,7 @@ public class ArchivaDavResourceFactoryTest
         resourceFactory.setRepositoryRequest( repoRequest );
         resourceFactory.setConnectors( new OverridingRepositoryProxyConnectors() );
         resourceFactory.setRemoteRepositoryAdmin( remoteRepositoryAdmin );
+        resourceFactory.setManagedRepositoryAdmin( defaultManagedRepositoryAdmin );
     }
 
     private ManagedRepository createManagedRepository( String id, String location, String layout )
@@ -227,7 +228,7 @@ public class ArchivaDavResourceFactoryTest
         {
             archivaConfigurationControl.reset();
 
-            expect( archivaConfiguration.getConfiguration() ).andReturn( config );
+            expect( archivaConfiguration.getConfiguration() ).andReturn( config ).times( 3 );
 
             expect( request.getMethod() ).andReturn( "GET" ).times( 2 );
 
@@ -304,7 +305,7 @@ public class ArchivaDavResourceFactoryTest
         {
             archivaConfigurationControl.reset();
 
-            expect( archivaConfiguration.getConfiguration() ).andReturn( config );
+            expect( archivaConfiguration.getConfiguration() ).andReturn( config ).times( 3 );
 
             expect( request.getMethod() ).andReturn( "GET" ).times( 2 );
 
@@ -385,7 +386,7 @@ public class ArchivaDavResourceFactoryTest
         {
             archivaConfigurationControl.reset();
 
-            expect( archivaConfiguration.getConfiguration() ).andReturn( config );
+            expect( archivaConfiguration.getConfiguration() ).andReturn( config ).times( 3 );
 
             expect( request.getMethod() ).andReturn( "GET" ).times( 4 );
 
@@ -460,7 +461,7 @@ public class ArchivaDavResourceFactoryTest
         {
             archivaConfigurationControl.reset();
 
-            expect( archivaConfiguration.getConfiguration() ).andReturn( config );
+            expect( archivaConfiguration.getConfiguration() ).andReturn( config ).times( 2 );
 
             expect( repoFactory.getManagedRepositoryContent( INTERNAL_REPO ) ).andReturn( internalRepo );
 
@@ -519,7 +520,7 @@ public class ArchivaDavResourceFactoryTest
         {
             archivaConfigurationControl.reset();
 
-            expect( archivaConfiguration.getConfiguration() ).andReturn( config );
+            expect( archivaConfiguration.getConfiguration() ).andReturn( config ).times( 2 );
 
             expect( repoFactory.getManagedRepositoryContent( INTERNAL_REPO ) ).andReturn( internalRepo );
 
@@ -568,7 +569,7 @@ public class ArchivaDavResourceFactoryTest
         {
             archivaConfigurationControl.reset();
 
-            expect( archivaConfiguration.getConfiguration() ).andReturn( config );
+            expect( archivaConfiguration.getConfiguration() ).andReturn( config ).times( 2 );
 
             expect( repoFactory.getManagedRepositoryContent( LEGACY_REPO ) ).andReturn( legacyRepo );
 
index 4f0cf7c1f2e34376b7cf793605ef5de9f6748d20..4b8e36834d67e397bf32e539d145971baa717b24 100644 (file)
@@ -90,7 +90,8 @@
               org.slf4j;resolution:=optional,
               org.apache.archiva.model,
               org.apache.archiva.policies,
-              org.apache.archiva.repository
+              org.apache.archiva.repository,
+              org.apache.archiva.admin.model.beans
             </Import-Package>
           </instructions>
         </configuration>
index b4bd8eae4c35b760a75b5572e2270cdc604e74f3..31cfe7c831766643eb934330b2d18c010a18bbf4 100644 (file)
@@ -19,6 +19,7 @@ package org.apache.archiva.metadata.repository.storage;
  * under the License.
  */
 
+import org.apache.archiva.admin.model.beans.ManagedRepository;
 import org.apache.archiva.metadata.model.ArtifactMetadata;
 import org.apache.archiva.metadata.model.ProjectMetadata;
 import org.apache.archiva.metadata.model.ProjectVersionMetadata;
@@ -59,4 +60,11 @@ public interface RepositoryStorage
 
     void applyServerSideRelocation( ManagedRepositoryContent managedRepository, ArtifactReference artifact )
         throws ProxyDownloadException;
+
+    /**
+     * @param requestPath the web uri request
+     * @return the file path
+     * @since 2.0.0
+     */
+    String getFilePath( String requestPath, ManagedRepository managedRepository );
 }
index 48271dbf57e36d8939d33cc9b86034e3e6c62d75..e89d1e1ea60fbd356ba3daa42c27939fa1828aa5 100644 (file)
@@ -51,6 +51,7 @@ import org.apache.archiva.proxy.model.RepositoryProxyConnectors;
 import org.apache.archiva.reports.RepositoryProblemFacet;
 import org.apache.archiva.repository.ManagedRepositoryContent;
 import org.apache.archiva.xml.XMLException;
+import org.apache.commons.lang.ArrayUtils;
 import org.apache.commons.lang.StringUtils;
 import org.apache.maven.model.CiManagement;
 import org.apache.maven.model.Dependency;
@@ -69,6 +70,7 @@ import org.apache.maven.model.building.ModelBuildingException;
 import org.apache.maven.model.building.ModelBuildingRequest;
 import org.apache.maven.model.building.ModelProblem;
 import org.apache.maven.model.io.xpp3.MavenXpp3Reader;
+import org.apache.maven.wagon.PathUtils;
 import org.codehaus.plexus.util.xml.pull.XmlPullParserException;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
@@ -105,14 +107,8 @@ import java.util.Map;
 public class Maven2RepositoryStorage
     implements RepositoryStorage
 {
-    /**
-     *
-     */
     private ModelBuilder builder;
 
-    /**
-     *
-     */
     @Inject
     private RemoteRepositoryAdmin remoteRepositoryAdmin;
 
@@ -125,9 +121,6 @@ public class Maven2RepositoryStorage
     @Inject
     private NetworkProxyAdmin networkProxyAdmin;
 
-    /**
-     *
-     */
     @Inject
     @Named ( value = "repositoryPathTranslator#maven2" )
     private RepositoryPathTranslator pathTranslator;
@@ -150,8 +143,7 @@ public class Maven2RepositoryStorage
     @PostConstruct
     public void initialize()
     {
-        DefaultModelBuilderFactory defaultModelBuilderFactory = new DefaultModelBuilderFactory();
-        builder = defaultModelBuilderFactory.newInstance();
+        builder = new DefaultModelBuilderFactory().newInstance();
 
     }
 
@@ -718,9 +710,81 @@ public class Maven2RepositoryStorage
         }
     }
 
+
+    public String getFilePath( String requestPath, ManagedRepository managedRepository )
+    {
+        // extract artifact reference from url
+        // groupId:artifactId:version:packaging:classifier
+        //org/apache/archiva/archiva-checksum/1.4-M4-SNAPSHOT/archiva-checksum-1.4-M4-SNAPSHOT.jar
+        String logicalResource = null;
+        String requestPathInfo = StringUtils.defaultString( requestPath );
+
+        //remove prefix ie /repository/blah becomes /blah
+        requestPathInfo = removePrefix( requestPathInfo );
+
+        // Remove prefixing slash as the repository id doesn't contain it;
+        if ( requestPathInfo.startsWith( "/" ) )
+        {
+            requestPathInfo = requestPathInfo.substring( 1 );
+        }
+
+        int slash = requestPathInfo.indexOf( '/' );
+        if ( slash > 0 )
+        {
+            logicalResource = requestPathInfo.substring( slash );
+
+            if ( logicalResource.endsWith( "/.." ) )
+            {
+                logicalResource += "/";
+            }
+
+            if ( logicalResource != null && logicalResource.startsWith( "//" ) )
+            {
+                logicalResource = logicalResource.substring( 1 );
+            }
+
+            if ( logicalResource == null )
+            {
+                logicalResource = "/";
+            }
+        }
+        else
+        {
+            logicalResource = "/";
+        }
+        return logicalResource;
+
+    }
+
+
+
     //-----------------------------
     // internal
     //-----------------------------
+
+    /**
+     * FIXME remove
+     * @param href
+     * @return
+     */
+    private static String removePrefix( final String href )
+    {
+        String[] parts = StringUtils.split( href, '/' );
+        parts = (String[]) ArrayUtils.subarray( parts, 1, parts.length );
+        if ( parts == null || parts.length == 0 )
+        {
+            return "/";
+        }
+
+        String joinedString = StringUtils.join( parts, '/' );
+        if ( href.endsWith( "/" ) )
+        {
+            joinedString = joinedString + "/";
+        }
+
+        return joinedString;
+    }
+
     private static void populateArtifactMetadataFromFile( ArtifactMetadata metadata, File file )
     {
         metadata.setWhenGathered( new Date() );
@@ -891,6 +955,8 @@ public class Maven2RepositoryStorage
         }
     }
 
+
+
     private static final class PomFilenameFilter
         implements FilenameFilter
     {
@@ -933,4 +999,6 @@ public class Maven2RepositoryStorage
             return pomFile.equals( name );
         }
     }
+
+
 }