Issue #1448 - Reduce unncessary URL creation
This commit is contained in:
parent
c285d6f8bb
commit
f53776628f
|
@ -34,8 +34,6 @@ import java.util.List;
|
|||
import java.util.Map;
|
||||
import java.util.Objects;
|
||||
|
||||
import javax.servlet.ServletContainerInitializer;
|
||||
|
||||
import org.eclipse.jetty.util.annotation.Name;
|
||||
import org.eclipse.jetty.util.log.Log;
|
||||
import org.eclipse.jetty.util.log.Logger;
|
||||
|
@ -723,7 +721,7 @@ public class TypeUtil
|
|||
{
|
||||
try
|
||||
{
|
||||
return Resource.newResource(URIUtil.getJarSource(url.toString()));
|
||||
return Resource.newResource(URIUtil.getJarSource(url.toURI()));
|
||||
}
|
||||
catch(Exception e)
|
||||
{
|
||||
|
|
|
@ -0,0 +1,78 @@
|
|||
//
|
||||
// ========================================================================
|
||||
// Copyright (c) 1995-2017 Mort Bay Consulting Pty. Ltd.
|
||||
// ------------------------------------------------------------------------
|
||||
// All rights reserved. This program and the accompanying materials
|
||||
// are made available under the terms of the Eclipse Public License v1.0
|
||||
// and Apache License v2.0 which accompanies this distribution.
|
||||
//
|
||||
// The Eclipse Public License is available at
|
||||
// http://www.eclipse.org/legal/epl-v10.html
|
||||
//
|
||||
// The Apache License v2.0 is available at
|
||||
// http://www.opensource.org/licenses/apache2.0.php
|
||||
//
|
||||
// You may elect to redistribute this code under either of these licenses.
|
||||
// ========================================================================
|
||||
//
|
||||
|
||||
package org.eclipse.jetty.webapp;
|
||||
|
||||
import java.lang.reflect.Field;
|
||||
import java.lang.reflect.Modifier;
|
||||
import java.net.URL;
|
||||
import java.net.URLStreamHandlerFactory;
|
||||
import java.util.Arrays;
|
||||
import java.util.Optional;
|
||||
|
||||
public final class URLStreamHandlerUtil
|
||||
{
|
||||
public static void setFactory(URLStreamHandlerFactory factory)
|
||||
{
|
||||
try
|
||||
{
|
||||
// First, reset the factory field
|
||||
Field factoryField = getURLStreamHandlerFactoryField();
|
||||
factoryField.setAccessible(true);
|
||||
factoryField.set(null, null);
|
||||
|
||||
if(factory != null)
|
||||
{
|
||||
// Next, set the factory
|
||||
URL.setURLStreamHandlerFactory(factory);
|
||||
}
|
||||
}
|
||||
catch(Throwable ignore)
|
||||
{
|
||||
ignore.printStackTrace(System.err);
|
||||
}
|
||||
}
|
||||
|
||||
public static URLStreamHandlerFactory getFactory()
|
||||
{
|
||||
try
|
||||
{
|
||||
// First, reset the factory field
|
||||
Field factoryField = getURLStreamHandlerFactoryField();
|
||||
factoryField.setAccessible(true);
|
||||
return (URLStreamHandlerFactory) factoryField.get(null);
|
||||
}
|
||||
catch(Throwable ignore)
|
||||
{
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
private static Field getURLStreamHandlerFactoryField()
|
||||
{
|
||||
Optional<Field> optFactoryField = Arrays.stream(URL.class.getDeclaredFields())
|
||||
.filter((f) -> Modifier.isStatic(f.getModifiers()) &&
|
||||
f.getType().equals(URLStreamHandlerFactory.class))
|
||||
.findFirst();
|
||||
|
||||
if(optFactoryField.isPresent())
|
||||
return optFactoryField.get();
|
||||
|
||||
throw new RuntimeException( "Cannot find URLStreamHandlerFactory field in " + URL.class.getName() );
|
||||
}
|
||||
}
|
|
@ -18,15 +18,18 @@
|
|||
|
||||
package org.eclipse.jetty.webapp;
|
||||
|
||||
import static org.eclipse.jetty.toolchain.test.ExtraMatchers.*;
|
||||
import static org.hamcrest.Matchers.*;
|
||||
import static org.junit.Assert.*;
|
||||
import static org.eclipse.jetty.toolchain.test.ExtraMatchers.ordered;
|
||||
import static org.hamcrest.Matchers.contains;
|
||||
import static org.hamcrest.Matchers.notNullValue;
|
||||
import static org.hamcrest.Matchers.nullValue;
|
||||
import static org.junit.Assert.assertThat;
|
||||
import static org.junit.Assert.assertTrue;
|
||||
import static org.junit.Assume.assumeThat;
|
||||
|
||||
import java.lang.instrument.ClassFileTransformer;
|
||||
import java.lang.instrument.IllegalClassFormatException;
|
||||
import java.net.URI;
|
||||
import java.net.URL;
|
||||
import java.net.URLClassLoader;
|
||||
import java.nio.file.Path;
|
||||
import java.security.ProtectionDomain;
|
||||
import java.util.ArrayList;
|
||||
|
@ -48,7 +51,7 @@ public class WebAppClassLoaderTest
|
|||
|
||||
private Path testWebappDir;
|
||||
private WebAppContext _context;
|
||||
private WebAppClassLoader _loader;
|
||||
protected WebAppClassLoader _loader;
|
||||
|
||||
@Before
|
||||
public void init() throws Exception
|
||||
|
@ -241,6 +244,9 @@ public class WebAppClassLoaderTest
|
|||
@Test
|
||||
public void testResources() throws Exception
|
||||
{
|
||||
// The existence of a URLStreamHandler changes the behavior
|
||||
assumeThat("No URLStreamHandler in place", URLStreamHandlerUtil.getFactory(), nullValue());
|
||||
|
||||
List<URL> expected = new ArrayList<>();
|
||||
List<URL> resources;
|
||||
|
||||
|
|
|
@ -0,0 +1,113 @@
|
|||
//
|
||||
// ========================================================================
|
||||
// Copyright (c) 1995-2017 Mort Bay Consulting Pty. Ltd.
|
||||
// ------------------------------------------------------------------------
|
||||
// All rights reserved. This program and the accompanying materials
|
||||
// are made available under the terms of the Eclipse Public License v1.0
|
||||
// and Apache License v2.0 which accompanies this distribution.
|
||||
//
|
||||
// The Eclipse Public License is available at
|
||||
// http://www.eclipse.org/legal/epl-v10.html
|
||||
//
|
||||
// The Apache License v2.0 is available at
|
||||
// http://www.opensource.org/licenses/apache2.0.php
|
||||
//
|
||||
// You may elect to redistribute this code under either of these licenses.
|
||||
// ========================================================================
|
||||
//
|
||||
|
||||
package org.eclipse.jetty.webapp;
|
||||
|
||||
import java.net.URLStreamHandler;
|
||||
import java.net.URLStreamHandlerFactory;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
import org.junit.After;
|
||||
import org.junit.Before;
|
||||
|
||||
public class WebAppClassLoaderUrlStreamTest extends WebAppClassLoaderTest
|
||||
{
|
||||
public static class URLHandlers implements URLStreamHandlerFactory
|
||||
{
|
||||
private static final String[] STREAM_HANDLER_PREFIXES;
|
||||
|
||||
static
|
||||
{
|
||||
STREAM_HANDLER_PREFIXES = new String[]{
|
||||
"sun.net.www.protocol",
|
||||
"org.apache.harmony.luni.internal.net.www.protocol",
|
||||
"javax.net.ssl"
|
||||
};
|
||||
}
|
||||
|
||||
private Map<String, URLStreamHandler> handlers = new HashMap<>();
|
||||
private ClassLoader loader;
|
||||
|
||||
public URLHandlers(ClassLoader loader)
|
||||
{
|
||||
this.loader = loader;
|
||||
}
|
||||
|
||||
private URLStreamHandler getBuiltInHandler(String protocol, ClassLoader classLoader)
|
||||
{
|
||||
URLStreamHandler handler = handlers.get(protocol);
|
||||
|
||||
if (handler == null)
|
||||
{
|
||||
for (String prefix : STREAM_HANDLER_PREFIXES)
|
||||
{
|
||||
String className = prefix + '.' + protocol + ".Handler";
|
||||
try
|
||||
{
|
||||
Class<?> clazz = Class.forName(className, false, classLoader);
|
||||
handler = (URLStreamHandler) clazz.newInstance();
|
||||
break;
|
||||
}
|
||||
catch (Exception ignore)
|
||||
{
|
||||
ignore.printStackTrace(System.err);
|
||||
}
|
||||
}
|
||||
|
||||
if (handler != null)
|
||||
{
|
||||
handlers.put(protocol, handler);
|
||||
}
|
||||
}
|
||||
|
||||
if (handler == null)
|
||||
{
|
||||
throw new RuntimeException("Unable to find handler for protocol [" + protocol + "]");
|
||||
}
|
||||
|
||||
return handler;
|
||||
}
|
||||
|
||||
@Override
|
||||
public URLStreamHandler createURLStreamHandler(String protocol)
|
||||
{
|
||||
try
|
||||
{
|
||||
return getBuiltInHandler(protocol, loader);
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
throw new RuntimeException("Unable to create URLStreamHandler for protocol [" + protocol + "]");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@After
|
||||
public void cleanupURLStreamHandlerFactory()
|
||||
{
|
||||
URLStreamHandlerUtil.setFactory(null);
|
||||
}
|
||||
|
||||
@Before
|
||||
public void init() throws Exception
|
||||
{
|
||||
super.init();
|
||||
URLStreamHandlerUtil.setFactory(new URLHandlers(_loader));
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue