Author: ieb Date: Thu Oct 19 11:42:07 2017 New Revision: 1812621 URL: http://svn.apache.org/viewvc?rev=1812621&view=rev Log: SLING-7140 Support redirects to URLs provided by the underlying resource provider.
Added: sling/trunk/bundles/api/src/main/java/org/apache/sling/api/resource/ExternalizableInputStream.java sling/trunk/bundles/api/src/main/java/org/apache/sling/api/resource/URIProvider.java sling/trunk/bundles/jcr/resource/src/main/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrExternalizableInputStream.java Modified: sling/trunk/bundles/api/src/main/java/org/apache/sling/api/resource/package-info.java sling/trunk/bundles/jcr/resource/pom.xml sling/trunk/bundles/jcr/resource/src/main/java/org/apache/sling/jcr/resource/internal/HelperData.java sling/trunk/bundles/jcr/resource/src/main/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrNodeResource.java sling/trunk/bundles/jcr/resource/src/main/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrProviderStateFactory.java sling/trunk/bundles/jcr/resource/src/main/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrResourceProvider.java sling/trunk/bundles/jcr/resource/src/test/java/org/apache/sling/jcr/resource/internal/JcrModifiableValueMapTest.java sling/trunk/bundles/jcr/resource/src/test/java/org/apache/sling/jcr/resource/internal/helper/JcrNodeResourceIteratorTest.java sling/trunk/bundles/jcr/resource/src/test/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrItemResourceFactoryTest.java sling/trunk/bundles/jcr/resource/src/test/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrNodeResourceTest.java sling/trunk/bundles/jcr/resource/src/test/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrTestNodeResource.java sling/trunk/bundles/servlets/get/pom.xml sling/trunk/bundles/servlets/get/src/main/java/org/apache/sling/servlets/get/impl/helpers/StreamRendererServlet.java sling/trunk/launchpad/builder/src/main/provisioning/sling.txt Added: sling/trunk/bundles/api/src/main/java/org/apache/sling/api/resource/ExternalizableInputStream.java URL: http://svn.apache.org/viewvc/sling/trunk/bundles/api/src/main/java/org/apache/sling/api/resource/ExternalizableInputStream.java?rev=1812621&view=auto ============================================================================== --- sling/trunk/bundles/api/src/main/java/org/apache/sling/api/resource/ExternalizableInputStream.java (added) +++ sling/trunk/bundles/api/src/main/java/org/apache/sling/api/resource/ExternalizableInputStream.java Thu Oct 19 11:42:07 2017 @@ -0,0 +1,49 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +package org.apache.sling.api.resource; + +import java.net.URI; + +/** + * This interface is normally used to extend an InputStream to indicate that it has a URI form that could + * be used in place of the InputStream if desired. It is used in situations where the internal of a ResourceProvider + * wants to offload IO to channels that do not pass through the JVM. The URI that is returned may have restrictions + * imposed on it requiring it to be used immediately. Do not store the URI for later usage as it will, in most cases, + * have expired. + * + * @since 2.11.0 + */ +public interface ExternalizableInputStream { + + /** + * Get a URI that is specific to the current session, and may be used anywhere. May return null if this + * type of URI is not available. + * @return a URI intended for any network context. + */ + URI getURI(); + + /** + * Get a URI that is specific to the current session and may only be used in a private context. A private network context means + * that the URI may only be resolvable inside a private network. Usign this URL in any context will not always work, and + * may leak information about the private network. + * @return a URI intended for a private network context. + */ + URI getPrivateURI(); +} Added: sling/trunk/bundles/api/src/main/java/org/apache/sling/api/resource/URIProvider.java URL: http://svn.apache.org/viewvc/sling/trunk/bundles/api/src/main/java/org/apache/sling/api/resource/URIProvider.java?rev=1812621&view=auto ============================================================================== --- sling/trunk/bundles/api/src/main/java/org/apache/sling/api/resource/URIProvider.java (added) +++ sling/trunk/bundles/api/src/main/java/org/apache/sling/api/resource/URIProvider.java Thu Oct 19 11:42:07 2017 @@ -0,0 +1,51 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +package org.apache.sling.api.resource; + +import org.osgi.annotation.versioning.ProviderType; + +import java.net.URI; + +/** + * Provides a URI in exchange for a Resource. + * Typically the Resource will represent something where is a URI is valiable and usefull. + * Implementations of this interface must ensure that the any underlying security model is delegated + * securely and not circumvented. Typically resource provider bundles should implement this provider as in most cases + * internal implementation details of the resource will be required to achieve the implementation. Ideally + * implementations should be carefully reviewed by peers. + * + * @since 2.11.0 + */ +@ProviderType +public interface URIProvider { + + /** + * Return a URI appicable to the defined scope. + * @param scope the required scope. + * @param resource the resource to convert from. + * @return a URI if the resoruce has a URI suitable for the requested scope. + */ + URI toURI(URIProvider.Scope scope, Resource resource); + + enum Scope { + PUBLIC, + INTERNAL + } +} \ No newline at end of file Modified: sling/trunk/bundles/api/src/main/java/org/apache/sling/api/resource/package-info.java URL: http://svn.apache.org/viewvc/sling/trunk/bundles/api/src/main/java/org/apache/sling/api/resource/package-info.java?rev=1812621&r1=1812620&r2=1812621&view=diff ============================================================================== --- sling/trunk/bundles/api/src/main/java/org/apache/sling/api/resource/package-info.java (original) +++ sling/trunk/bundles/api/src/main/java/org/apache/sling/api/resource/package-info.java Thu Oct 19 11:42:07 2017 @@ -17,7 +17,7 @@ * under the License. */ -@Version("2.10.1") +@Version("2.11.0") package org.apache.sling.api.resource; import org.osgi.annotation.versioning.Version; Modified: sling/trunk/bundles/jcr/resource/pom.xml URL: http://svn.apache.org/viewvc/sling/trunk/bundles/jcr/resource/pom.xml?rev=1812621&r1=1812620&r2=1812621&view=diff ============================================================================== --- sling/trunk/bundles/jcr/resource/pom.xml (original) +++ sling/trunk/bundles/jcr/resource/pom.xml Thu Oct 19 11:42:07 2017 @@ -230,6 +230,11 @@ <version>1.4</version> <scope>test</scope> </dependency> + <dependency> + <groupId>org.apache.sling</groupId> + <artifactId>org.apache.sling.api</artifactId> + <version>2.16.3-SNAPSHOT</version> + </dependency> </dependencies> </project> Modified: sling/trunk/bundles/jcr/resource/src/main/java/org/apache/sling/jcr/resource/internal/HelperData.java URL: http://svn.apache.org/viewvc/sling/trunk/bundles/jcr/resource/src/main/java/org/apache/sling/jcr/resource/internal/HelperData.java?rev=1812621&r1=1812620&r2=1812621&view=diff ============================================================================== --- sling/trunk/bundles/jcr/resource/src/main/java/org/apache/sling/jcr/resource/internal/HelperData.java (original) +++ sling/trunk/bundles/jcr/resource/src/main/java/org/apache/sling/jcr/resource/internal/HelperData.java Thu Oct 19 11:42:07 2017 @@ -23,6 +23,7 @@ import java.util.concurrent.atomic.Atomi import javax.jcr.RepositoryException; import javax.jcr.Session; +import org.apache.sling.api.resource.URIProvider; import org.apache.sling.commons.classloader.DynamicClassLoaderManager; /** @@ -31,12 +32,16 @@ import org.apache.sling.commons.classloa */ public class HelperData { + private static final URIProvider[] EMPTY_URLPROVIDERS = new URIProvider[0]; + private final AtomicReference<DynamicClassLoaderManager> dynamicClassLoaderManagerReference; + private final AtomicReference<URIProvider[]> uriProviderReference; private volatile String[] namespacePrefixes; - public HelperData(final AtomicReference<DynamicClassLoaderManager> dynamicClassLoaderManagerReference) { + public HelperData(final AtomicReference<DynamicClassLoaderManager> dynamicClassLoaderManagerReference, AtomicReference<URIProvider[]> uriProviderReference) { this.dynamicClassLoaderManagerReference = dynamicClassLoaderManagerReference; + this.uriProviderReference = uriProviderReference; } public String[] getNamespacePrefixes(final Session session) @@ -54,4 +59,12 @@ public class HelperData { } return dclm.getDynamicClassLoader(); } + + public URIProvider[] getURIProviders() { + URIProvider[] ups = this.uriProviderReference.get(); + if ( ups == null) { + ups = EMPTY_URLPROVIDERS; + } + return ups; + } } Added: sling/trunk/bundles/jcr/resource/src/main/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrExternalizableInputStream.java URL: http://svn.apache.org/viewvc/sling/trunk/bundles/jcr/resource/src/main/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrExternalizableInputStream.java?rev=1812621&view=auto ============================================================================== --- sling/trunk/bundles/jcr/resource/src/main/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrExternalizableInputStream.java (added) +++ sling/trunk/bundles/jcr/resource/src/main/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrExternalizableInputStream.java Thu Oct 19 11:42:07 2017 @@ -0,0 +1,84 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package org.apache.sling.jcr.resource.internal.helper.jcr; + + +import org.apache.sling.api.resource.ExternalizableInputStream; + +import javax.jcr.Property; +import javax.jcr.RepositoryException; +import java.io.IOException; +import java.io.InputStream; +import java.net.URI; + +/** + * A lazy initialised input stream wrapping a JCR Property that also has a Public URI representation. The + * InputStream will be initialised when the first byte is read from the input stream so that the URI + * can be used without consuming any local IO resources. + * + * If a non any other form of URI is require, (ie Internal) then the URIProvider should be used directly. This + * class is written intentionally to *only* support public URIs. + */ +public class JcrExternalizableInputStream extends InputStream implements ExternalizableInputStream { + private final Property data; + private final URI uri; + private InputStream inputStream; + + + /** + * Construct the InputStream wrapping this existing stream and + * using a public URI + * @param data the binary JCR property. + * @param uri a public URI. + */ + JcrExternalizableInputStream(Property data, URI uri) { + this.data = data; + this.uri = uri; + } + + @Override + public int read() throws IOException { + return getInputStream().read(); + } + + private InputStream getInputStream() throws IOException { + if ( inputStream == null) { + try { + // perform lazy initialisation so that a consumer of + // this object can use the getURI method without triggering + // local IO operations. A DataSource implementation that + // converts the JCR Property to an InputStream might make a local + // copy. This avoids that IO operation. + inputStream = data.getBinary().getStream(); + } catch (RepositoryException e) { + throw new IOException(e.getMessage(), e); + } + } + return inputStream; + } + + @Override + public URI getURI() { + return uri; + } + + @Override + public URI getPrivateURI() { + return null; + } +} Modified: sling/trunk/bundles/jcr/resource/src/main/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrNodeResource.java URL: http://svn.apache.org/viewvc/sling/trunk/bundles/jcr/resource/src/main/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrNodeResource.java?rev=1812621&r1=1812620&r2=1812621&view=diff ============================================================================== --- sling/trunk/bundles/jcr/resource/src/main/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrNodeResource.java (original) +++ sling/trunk/bundles/jcr/resource/src/main/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrNodeResource.java Thu Oct 19 11:42:07 2017 @@ -22,6 +22,7 @@ import static org.apache.jackrabbit.JcrC import static org.apache.jackrabbit.JcrConstants.NT_LINKEDFILE; import java.io.InputStream; +import java.net.URI; import java.security.AccessControlException; import java.util.Iterator; import java.util.Map; @@ -31,12 +32,15 @@ import javax.jcr.ItemNotFoundException; import javax.jcr.Node; import javax.jcr.Property; import javax.jcr.RepositoryException; +import javax.jcr.Value; import org.apache.sling.adapter.annotations.Adaptable; import org.apache.sling.adapter.annotations.Adapter; +import org.apache.sling.api.resource.ExternalizableInputStream; import org.apache.sling.api.resource.ModifiableValueMap; import org.apache.sling.api.resource.Resource; import org.apache.sling.api.resource.ResourceResolver; +import org.apache.sling.api.resource.URIProvider; import org.apache.sling.api.resource.ValueMap; import org.apache.sling.jcr.resource.api.JcrResourceConstants; import org.apache.sling.jcr.resource.internal.HelperData; @@ -48,7 +52,8 @@ import org.slf4j.LoggerFactory; /** A Resource that wraps a JCR Node */ @Adaptable(adaptableClass=Resource.class, adapters={ @Adapter({Node.class, Map.class, Item.class, ValueMap.class}), - @Adapter(value=InputStream.class, condition="If the resource is a JcrNodeResource and has a jcr:data property or is an nt:file node.") + @Adapter(value=InputStream.class, condition="If the resource is a JcrNodeResource and has a jcr:data property or is an nt:file node."), + @Adapter(value=ExternalizableInputStream.class, condition="If the resource is a JcrNodeResource and has a jcr:data property or is an nt:file node, and can be read using a secure URL.") }) class JcrNodeResource extends JcrItemResource<Node> { // this should be package private, see SLING-1414 @@ -201,7 +206,10 @@ class JcrNodeResource extends JcrItemRes data = null; } } - + URI uri = convertToPublicURI(); + if ( uri != null ) { + return new JcrExternalizableInputStream(data, uri); + } if (data != null) { return data.getBinary().getStream(); } @@ -216,6 +224,22 @@ class JcrNodeResource extends JcrItemRes return null; } + /** + * Ask each URIProvider in turn for a Public URI, and return the first + * public URI provided. + * @return a public URI. + */ + private URI convertToPublicURI() { + for (URIProvider up : helper.getURIProviders()) { + URI u = up.toURI(URIProvider.Scope.PUBLIC, this); + if ( u != null) { + return u; + } + } + return null; + } + + // ---------- Descendable interface ---------------------------------------- @Override Modified: sling/trunk/bundles/jcr/resource/src/main/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrProviderStateFactory.java URL: http://svn.apache.org/viewvc/sling/trunk/bundles/jcr/resource/src/main/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrProviderStateFactory.java?rev=1812621&r1=1812620&r2=1812621&view=diff ============================================================================== --- sling/trunk/bundles/jcr/resource/src/main/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrProviderStateFactory.java (original) +++ sling/trunk/bundles/jcr/resource/src/main/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrProviderStateFactory.java Thu Oct 19 11:42:07 2017 @@ -35,6 +35,7 @@ import javax.jcr.SimpleCredentials; import org.apache.sling.api.resource.LoginException; import org.apache.sling.api.resource.ResourceResolver; import org.apache.sling.api.resource.ResourceResolverFactory; +import org.apache.sling.api.resource.URIProvider; import org.apache.sling.commons.classloader.DynamicClassLoaderManager; import org.apache.sling.jcr.api.SlingRepository; import org.apache.sling.jcr.resource.api.JcrResourceConstants; @@ -55,13 +56,16 @@ public class JcrProviderStateFactory { private final SlingRepository repository; private final AtomicReference<DynamicClassLoaderManager> dynamicClassLoaderManagerReference; + private final AtomicReference<URIProvider[]> uriProviderReference; public JcrProviderStateFactory(final ServiceReference<SlingRepository> repositoryReference, final SlingRepository repository, - final AtomicReference<DynamicClassLoaderManager> dynamicClassLoaderManagerReference) { + final AtomicReference<DynamicClassLoaderManager> dynamicClassLoaderManagerReference, + final AtomicReference<URIProvider[]> uriProviderReference) { this.repository = repository; this.repositoryReference = repositoryReference; this.dynamicClassLoaderManagerReference = dynamicClassLoaderManagerReference; + this.uriProviderReference = uriProviderReference; } /** Get the calling Bundle from auth info, fail if not provided @@ -142,7 +146,7 @@ public class JcrProviderStateFactory { @Nullable final BundleContext ctx ) throws LoginException { final Session session = handleImpersonation(s, authenticationInfo, logoutSession); - final HelperData data = new HelperData(this.dynamicClassLoaderManagerReference); + final HelperData data = new HelperData(this.dynamicClassLoaderManagerReference, this.uriProviderReference); return new JcrProviderState(session, data, logoutSession, ctx, ctx == null ? null : repositoryReference); } Modified: sling/trunk/bundles/jcr/resource/src/main/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrResourceProvider.java URL: http://svn.apache.org/viewvc/sling/trunk/bundles/jcr/resource/src/main/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrResourceProvider.java?rev=1812621&r1=1812620&r2=1812621&view=diff ============================================================================== --- sling/trunk/bundles/jcr/resource/src/main/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrResourceProvider.java (original) +++ sling/trunk/bundles/jcr/resource/src/main/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrResourceProvider.java Thu Oct 19 11:42:07 2017 @@ -27,6 +27,7 @@ import java.util.HashSet; import java.util.Iterator; import java.util.Map; import java.util.Set; +import java.util.concurrent.ConcurrentHashMap; import java.util.concurrent.atomic.AtomicReference; import javax.annotation.CheckForNull; @@ -46,6 +47,7 @@ import org.apache.sling.api.resource.Per import org.apache.sling.api.resource.Resource; import org.apache.sling.api.resource.ResourceResolverFactory; import org.apache.sling.api.resource.ResourceUtil; +import org.apache.sling.api.resource.URIProvider; import org.apache.sling.commons.classloader.DynamicClassLoaderManager; import org.apache.sling.jcr.api.SlingRepository; import org.apache.sling.jcr.resource.api.JcrResourceConstants; @@ -107,12 +109,16 @@ public class JcrResourceProvider extends /** The JCR observation listeners. */ private final Map<ObserverConfiguration, Closeable> listeners = new HashMap<>(); + private final Map<URIProvider, URIProvider> providers = new ConcurrentHashMap<URIProvider, URIProvider>(); + private volatile SlingRepository repository; private volatile JcrProviderStateFactory stateFactory; private final AtomicReference<DynamicClassLoaderManager> classLoaderManagerReference = new AtomicReference<DynamicClassLoaderManager>(); + private AtomicReference<URIProvider[]> uriProviderReference = new AtomicReference<URIProvider[]>(); + @Activate protected void activate(final ComponentContext context) throws RepositoryException { SlingRepository repository = context.locateService(REPOSITORY_REFERNENCE_NAME, @@ -128,7 +134,7 @@ public class JcrResourceProvider extends this.repository = repository; this.stateFactory = new JcrProviderStateFactory(repositoryReference, repository, - classLoaderManagerReference); + classLoaderManagerReference, uriProviderReference); } @Deactivate @@ -147,6 +153,29 @@ public class JcrResourceProvider extends this.classLoaderManagerReference.compareAndSet(dynamicClassLoaderManager, null); } + @Reference( + name = "uriprovider", + service = URIProvider.class, + cardinality = ReferenceCardinality.MULTIPLE, + policy = ReferencePolicy.DYNAMIC, + bind = "bindUriProvider", + unbind = "unbindUriProvider" + ) + private void bindUriProvider(URIProvider uriProvider) { + + providers.put(uriProvider, uriProvider); + updateURIProviders(); + } + private void unbindUriProvider(URIProvider uriProvider) { + providers.remove(uriProvider); + updateURIProviders(); + } + + private void updateURIProviders() { + URIProvider[] ups = providers.values().toArray(new URIProvider[providers.size()]); + this.uriProviderReference.set(ups); + } + @Override public void start(final ProviderContext ctx) { super.start(ctx); Modified: sling/trunk/bundles/jcr/resource/src/test/java/org/apache/sling/jcr/resource/internal/JcrModifiableValueMapTest.java URL: http://svn.apache.org/viewvc/sling/trunk/bundles/jcr/resource/src/test/java/org/apache/sling/jcr/resource/internal/JcrModifiableValueMapTest.java?rev=1812621&r1=1812620&r2=1812621&view=diff ============================================================================== --- sling/trunk/bundles/jcr/resource/src/test/java/org/apache/sling/jcr/resource/internal/JcrModifiableValueMapTest.java (original) +++ sling/trunk/bundles/jcr/resource/src/test/java/org/apache/sling/jcr/resource/internal/JcrModifiableValueMapTest.java Thu Oct 19 11:42:07 2017 @@ -45,6 +45,7 @@ import javax.jcr.nodetype.NodeType; import org.apache.commons.io.IOUtils; import org.apache.jackrabbit.util.Text; import org.apache.sling.api.resource.ModifiableValueMap; +import org.apache.sling.api.resource.URIProvider; import org.apache.sling.api.resource.ValueMap; import org.apache.sling.commons.classloader.DynamicClassLoaderManager; import org.apache.sling.commons.testing.jcr.RepositoryTestBase; @@ -131,7 +132,7 @@ public class JcrModifiableValueMapTest e } private HelperData getHelperData() throws Exception { - return new HelperData(new AtomicReference<DynamicClassLoaderManager>()); + return new HelperData(new AtomicReference<DynamicClassLoaderManager>(), new AtomicReference<URIProvider[]>()); } private Map<String, Object> initialSet() { Modified: sling/trunk/bundles/jcr/resource/src/test/java/org/apache/sling/jcr/resource/internal/helper/JcrNodeResourceIteratorTest.java URL: http://svn.apache.org/viewvc/sling/trunk/bundles/jcr/resource/src/test/java/org/apache/sling/jcr/resource/internal/helper/JcrNodeResourceIteratorTest.java?rev=1812621&r1=1812620&r2=1812621&view=diff ============================================================================== --- sling/trunk/bundles/jcr/resource/src/test/java/org/apache/sling/jcr/resource/internal/helper/JcrNodeResourceIteratorTest.java (original) +++ sling/trunk/bundles/jcr/resource/src/test/java/org/apache/sling/jcr/resource/internal/helper/JcrNodeResourceIteratorTest.java Thu Oct 19 11:42:07 2017 @@ -26,6 +26,7 @@ import javax.jcr.NodeIterator; import javax.jcr.RepositoryException; import org.apache.sling.api.resource.Resource; +import org.apache.sling.api.resource.URIProvider; import org.apache.sling.commons.classloader.DynamicClassLoaderManager; import org.apache.sling.commons.testing.jcr.MockNode; import org.apache.sling.commons.testing.jcr.MockNodeIterator; @@ -37,7 +38,7 @@ import junit.framework.TestCase; public class JcrNodeResourceIteratorTest extends TestCase { private HelperData getHelperData() { - return new HelperData(new AtomicReference<DynamicClassLoaderManager>()); + return new HelperData(new AtomicReference<DynamicClassLoaderManager>(), new AtomicReference<URIProvider[]>()); } public void testEmpty() { Modified: sling/trunk/bundles/jcr/resource/src/test/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrItemResourceFactoryTest.java URL: http://svn.apache.org/viewvc/sling/trunk/bundles/jcr/resource/src/test/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrItemResourceFactoryTest.java?rev=1812621&r1=1812620&r2=1812621&view=diff ============================================================================== --- sling/trunk/bundles/jcr/resource/src/test/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrItemResourceFactoryTest.java (original) +++ sling/trunk/bundles/jcr/resource/src/test/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrItemResourceFactoryTest.java Thu Oct 19 11:42:07 2017 @@ -29,6 +29,7 @@ import javax.jcr.RepositoryException; import javax.jcr.Session; import org.apache.jackrabbit.commons.JcrUtils; +import org.apache.sling.api.resource.URIProvider; import org.apache.sling.commons.classloader.DynamicClassLoaderManager; import org.apache.sling.commons.testing.jcr.RepositoryTestBase; import org.apache.sling.jcr.resource.internal.HelperData; @@ -87,7 +88,7 @@ public class JcrItemResourceFactoryTest } private void compareGetItemOrNull(String path, String expectedPath) throws RepositoryException { - HelperData helper = new HelperData(new AtomicReference<DynamicClassLoaderManager>()); + HelperData helper = new HelperData(new AtomicReference<DynamicClassLoaderManager>(), new AtomicReference<URIProvider[]>()); Item item1 = new JcrItemResourceFactory(session, helper).getItemOrNull(path); Item item2 = new JcrItemResourceFactory(nonJackrabbitSession, helper).getItemOrNull(path); if (expectedPath == null) { Modified: sling/trunk/bundles/jcr/resource/src/test/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrNodeResourceTest.java URL: http://svn.apache.org/viewvc/sling/trunk/bundles/jcr/resource/src/test/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrNodeResourceTest.java?rev=1812621&r1=1812620&r2=1812621&view=diff ============================================================================== --- sling/trunk/bundles/jcr/resource/src/test/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrNodeResourceTest.java (original) +++ sling/trunk/bundles/jcr/resource/src/test/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrNodeResourceTest.java Thu Oct 19 11:42:07 2017 @@ -32,6 +32,7 @@ import javax.jcr.Session; import org.apache.jackrabbit.JcrConstants; import org.apache.sling.api.resource.Resource; import org.apache.sling.api.resource.ResourceMetadata; +import org.apache.sling.api.resource.URIProvider; import org.apache.sling.commons.classloader.DynamicClassLoaderManager; import org.apache.sling.jcr.resource.api.JcrResourceConstants; import org.apache.sling.jcr.resource.internal.HelperData; @@ -39,7 +40,7 @@ import org.apache.sling.jcr.resource.int public class JcrNodeResourceTest extends JcrItemResourceTestBase { private HelperData getHelperData() throws Exception { - return new HelperData(new AtomicReference<DynamicClassLoaderManager>()); + return new HelperData(new AtomicReference<DynamicClassLoaderManager>(), new AtomicReference<URIProvider[]>()); } public void testLinkedFile() throws Exception { Modified: sling/trunk/bundles/jcr/resource/src/test/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrTestNodeResource.java URL: http://svn.apache.org/viewvc/sling/trunk/bundles/jcr/resource/src/test/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrTestNodeResource.java?rev=1812621&r1=1812620&r2=1812621&view=diff ============================================================================== --- sling/trunk/bundles/jcr/resource/src/test/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrTestNodeResource.java (original) +++ sling/trunk/bundles/jcr/resource/src/test/java/org/apache/sling/jcr/resource/internal/helper/jcr/JcrTestNodeResource.java Thu Oct 19 11:42:07 2017 @@ -24,6 +24,7 @@ import javax.jcr.Node; import javax.jcr.RepositoryException; import org.apache.sling.api.resource.ResourceResolver; +import org.apache.sling.api.resource.URIProvider; import org.apache.sling.commons.classloader.DynamicClassLoaderManager; import org.apache.sling.jcr.resource.internal.HelperData; @@ -31,7 +32,7 @@ public class JcrTestNodeResource extends public JcrTestNodeResource(ResourceResolver resourceResolver, Node node, ClassLoader dynamicClassLoader) throws RepositoryException { - super(resourceResolver, node.getPath(), null, node, new HelperData(new AtomicReference<DynamicClassLoaderManager>())); + super(resourceResolver, node.getPath(), null, node, new HelperData(new AtomicReference<DynamicClassLoaderManager>(), new AtomicReference<URIProvider[]>())); } } Modified: sling/trunk/bundles/servlets/get/pom.xml URL: http://svn.apache.org/viewvc/sling/trunk/bundles/servlets/get/pom.xml?rev=1812621&r1=1812620&r2=1812621&view=diff ============================================================================== --- sling/trunk/bundles/servlets/get/pom.xml (original) +++ sling/trunk/bundles/servlets/get/pom.xml Thu Oct 19 11:42:07 2017 @@ -92,7 +92,7 @@ <dependency> <groupId>org.apache.sling</groupId> <artifactId>org.apache.sling.api</artifactId> - <version>2.7.0</version> + <version>2.16.3-SNAPSHOT</version> <scope>provided</scope> </dependency> <dependency> Modified: sling/trunk/bundles/servlets/get/src/main/java/org/apache/sling/servlets/get/impl/helpers/StreamRendererServlet.java URL: http://svn.apache.org/viewvc/sling/trunk/bundles/servlets/get/src/main/java/org/apache/sling/servlets/get/impl/helpers/StreamRendererServlet.java?rev=1812621&r1=1812620&r2=1812621&view=diff ============================================================================== --- sling/trunk/bundles/servlets/get/src/main/java/org/apache/sling/servlets/get/impl/helpers/StreamRendererServlet.java (original) +++ sling/trunk/bundles/servlets/get/src/main/java/org/apache/sling/servlets/get/impl/helpers/StreamRendererServlet.java Thu Oct 19 11:42:07 2017 @@ -42,6 +42,7 @@ import org.apache.sling.api.SlingConstan import org.apache.sling.api.SlingHttpServletRequest; import org.apache.sling.api.SlingHttpServletResponse; import org.apache.sling.api.request.RequestDispatcherOptions; +import org.apache.sling.api.resource.ExternalizableInputStream; import org.apache.sling.api.resource.Resource; import org.apache.sling.api.resource.ResourceMetadata; import org.apache.sling.api.resource.ResourceNotFoundException; @@ -50,6 +51,7 @@ import org.apache.sling.api.resource.Res import org.apache.sling.api.resource.ValueMap; import org.apache.sling.api.servlets.HttpConstants; import org.apache.sling.api.servlets.SlingSafeMethodsServlet; +import org.apache.sling.api.resource.ExternalizableInputStream; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -167,6 +169,10 @@ public class StreamRendererServlet exten } InputStream stream = resource.adaptTo(InputStream.class); if (stream != null) { + if ( stream instanceof ExternalizableInputStream) { + response.sendRedirect(((ExternalizableInputStream)stream).getURI().toString()); + return; + } if (isHeadRequest(request)) { setContentLength(response, resource.getResourceMetadata().getContentLength()); setHeaders(resource, response); Modified: sling/trunk/launchpad/builder/src/main/provisioning/sling.txt URL: http://svn.apache.org/viewvc/sling/trunk/launchpad/builder/src/main/provisioning/sling.txt?rev=1812621&r1=1812620&r2=1812621&view=diff ============================================================================== --- sling/trunk/launchpad/builder/src/main/provisioning/sling.txt (original) +++ sling/trunk/launchpad/builder/src/main/provisioning/sling.txt Thu Oct 19 11:42:07 2017 @@ -35,7 +35,7 @@ org.apache.httpcomponents/httpcore-osgi/4.4.1 org.apache.httpcomponents/httpclient-osgi/4.4.1 org.apache.sling/org.apache.sling.adapter/2.1.10 - org.apache.sling/org.apache.sling.api/2.16.2 + org.apache.sling/org.apache.sling.api/2.16.3-SNAPSHOT org.apache.sling/org.apache.sling.auth.core/1.4.0 org.apache.sling/org.apache.sling.auth.form/1.0.8 org.apache.sling/org.apache.sling.bundleresource.impl/2.2.0 @@ -55,13 +55,13 @@ org.apache.sling/org.apache.sling.installer.console/1.0.2 org.apache.sling/org.apache.sling.installer.provider.jcr/3.1.26 org.apache.sling/org.apache.sling.jcr.contentloader/2.2.4 - org.apache.sling/org.apache.sling.jcr.resource/3.0.4 + org.apache.sling/org.apache.sling.jcr.resource/3.0.5-SNAPSHOT org.apache.sling/org.apache.sling.launchpad.content/2.0.12 org.apache.sling/org.apache.sling.models.api/1.3.4 org.apache.sling/org.apache.sling.models.impl/1.4.2 - org.apache.sling/org.apache.sling.resourceresolver/1.5.30 + org.apache.sling/org.apache.sling.resourceresolver/1.5.31-SNAPSHOT org.apache.sling/org.apache.sling.serviceusermapper/1.3.4 - org.apache.sling/org.apache.sling.servlets.get/2.1.26 + org.apache.sling/org.apache.sling.servlets.get/2.1.27-SNAPSHOT org.apache.sling/org.apache.sling.servlets.post/2.3.22 org.apache.sling/org.apache.sling.servlets.resolver/2.4.14 org.apache.sling/org.apache.sling.xss/2.0.0