View Javadoc
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  package org.eclipse.aether.transport.classpath;
20  
21  import java.net.URI;
22  import java.net.URISyntaxException;
23  import java.net.URL;
24  import java.net.URLConnection;
25  
26  import org.eclipse.aether.RepositorySystemSession;
27  import org.eclipse.aether.repository.RemoteRepository;
28  import org.eclipse.aether.spi.connector.transport.AbstractTransporter;
29  import org.eclipse.aether.spi.connector.transport.GetTask;
30  import org.eclipse.aether.spi.connector.transport.PeekTask;
31  import org.eclipse.aether.spi.connector.transport.PutTask;
32  import org.eclipse.aether.spi.connector.transport.TransportTask;
33  import org.eclipse.aether.transfer.NoTransporterException;
34  import org.eclipse.aether.util.ConfigUtils;
35  
36  /**
37   * A transporter reading from the classpath.
38   */
39  final class ClasspathTransporter extends AbstractTransporter {
40  
41      private final String resourceBase;
42  
43      private final ClassLoader classLoader;
44  
45      ClasspathTransporter(RepositorySystemSession session, RemoteRepository repository) throws NoTransporterException {
46          if (!"classpath".equalsIgnoreCase(repository.getProtocol())) {
47              throw new NoTransporterException(repository);
48          }
49  
50          String base;
51          try {
52              URI uri = new URI(repository.getUrl());
53              String ssp = uri.getSchemeSpecificPart();
54              if (ssp.startsWith("/")) {
55                  base = uri.getPath();
56                  if (base == null) {
57                      base = "";
58                  } else if (base.startsWith("/")) {
59                      base = base.substring(1);
60                  }
61              } else {
62                  base = ssp;
63              }
64              if (base.length() > 0 && !base.endsWith("/")) {
65                  base += '/';
66              }
67          } catch (URISyntaxException e) {
68              throw new NoTransporterException(repository, e);
69          }
70          resourceBase = base;
71  
72          Object cl = ConfigUtils.getObject(session, null, ClasspathTransporterFactory.CONFIG_PROP_CLASS_LOADER);
73          if (cl instanceof ClassLoader) {
74              classLoader = (ClassLoader) cl;
75          } else {
76              classLoader = Thread.currentThread().getContextClassLoader();
77          }
78      }
79  
80      private URL getResource(TransportTask task) throws Exception {
81          String resource = resourceBase + task.getLocation().getPath();
82          URL url = classLoader.getResource(resource);
83          if (url == null) {
84              throw new ResourceNotFoundException("Could not locate " + resource);
85          }
86          return url;
87      }
88  
89      public int classify(Throwable error) {
90          if (error instanceof ResourceNotFoundException) {
91              return ERROR_NOT_FOUND;
92          }
93          return ERROR_OTHER;
94      }
95  
96      @Override
97      protected void implPeek(PeekTask task) throws Exception {
98          getResource(task);
99      }
100 
101     @Override
102     protected void implGet(GetTask task) throws Exception {
103         URL url = getResource(task);
104         URLConnection conn = url.openConnection();
105         utilGet(task, conn.getInputStream(), true, conn.getContentLength(), false);
106     }
107 
108     @Override
109     protected void implPut(PutTask task) throws Exception {
110         throw new UnsupportedOperationException("Uploading to a classpath: repository is not supported");
111     }
112 
113     @Override
114     protected void implClose() {}
115 }