Merge branch 'jetty-9.3.x' into jetty-9.4.x

This commit is contained in:
Joakim Erdfelt 2016-10-26 16:42:42 -07:00
commit 55c6514a2e
5 changed files with 224 additions and 93 deletions

View File

@ -31,6 +31,18 @@
</configuration>
</plugin>
<plugin>
<execution>
<id>nolog-jar</id>
<goals>
<goal>jar</goal>
</goals>
<configuration>
<classifier>nolog</classifier>
<excludes>
<exclude>META-INF/services/org.apache.juli.logging.Log</exclude>
</excludes>
</configuration>
</execution>
<groupId>org.jacoco</groupId>
<artifactId>jacoco-maven-plugin</artifactId>
<configuration>

View File

@ -21,6 +21,7 @@ package org.eclipse.jetty.quickstart;
import java.io.File;
import java.io.IOException;
import java.net.URI;
import java.net.URISyntaxException;
import java.net.URL;
import java.nio.file.FileSystems;
import java.nio.file.Files;
@ -53,20 +54,21 @@ public class AttributeNormalizer
{
private static final Logger LOG = Log.getLogger(AttributeNormalizer.class);
private static final Pattern __propertyPattern = Pattern.compile("(?<=[^$]|^)\\$\\{([^}]*)\\}");
private static class PathAttribute
{
public final Path path;
public final String key;
private boolean isUriBased = false;
private int weight = -1;
public PathAttribute(String key, Path path) throws IOException
{
this.key = key;
this.path = toCanonicalPath(path);
// TODO: Don't allow non-directory paths? (but what if the path doesn't exist?)
}
public PathAttribute(String key, String systemPropertyKey) throws IOException
{
this(key, toCanonicalPath(System.getProperty(systemPropertyKey)));
@ -93,7 +95,41 @@ public class AttributeNormalizer
}
return path.toAbsolutePath();
}
public String toUri()
{
if (isUriBased)
{
// Return "{KEY}" -> "<uri>" (including scheme)
return path.toUri().toASCIIString();
}
else
{
// Return "{KEY}" -> "<path>" (excluding scheme)
return path.toUri().getSchemeSpecificPart();
}
}
public String getNormalizedScheme()
{
if (isUriBased)
{
// If we are treating the {KEY} -> "<uri>" (scheme is expanded)
return "";
}
else
{
// If we are treating the {KEY} -> "<path>" (scheme is not part of KEY)
return "file:";
}
}
public PathAttribute treatAsUri()
{
this.isUriBased = true;
return this;
}
public PathAttribute weight(int newweight)
{
this.weight = newweight;
@ -195,7 +231,7 @@ public class AttributeNormalizer
attributes.add(new PathAttribute("user.dir", "user.dir").weight(6));
if(warURI != null && warURI.getScheme().equals("file"))
{
attributes.add(new PathAttribute("WAR", new File(warURI).toPath().toAbsolutePath()).weight(10));
attributes.add(new PathAttribute("WAR", new File(warURI).toPath().toAbsolutePath()).treatAsUri().weight(10));
}
Collections.sort(attributes, new PathAttributeComparator());
@ -215,6 +251,12 @@ public class AttributeNormalizer
}
}
/**
* Normalize a URI, URL, or File reference by replacing known attributes with ${key} attributes.
*
* @param o the object to normalize into a string
* @return the string representation of the object, with expansion keys.
*/
public String normalize(Object o)
{
try
@ -230,9 +272,23 @@ public class AttributeNormalizer
else
{
String s = o.toString();
uri = new URI(s);
if (uri.getScheme() == null)
try
{
uri = new URI(s);
if (uri.getScheme() == null)
{
// Unknown scheme? not relevant to normalize
return s;
}
}
catch(URISyntaxException e)
{
// This path occurs for many reasons, but most common is when this
// is executed on MS Windows, on a string like "D:\jetty"
// and the new URI() fails for
// java.net.URISyntaxException: Illegal character in opaque part at index 2: D:\jetty
return s;
}
}
if ("jar".equalsIgnoreCase(uri.getScheme()))
@ -245,7 +301,7 @@ public class AttributeNormalizer
}
else if ("file".equalsIgnoreCase(uri.getScheme()))
{
return "file:" + normalizePath(new File(uri.getRawSchemeSpecificPart()).toPath());
return normalizePath(new File(uri.getRawSchemeSpecificPart()).toPath());
}
else
{
@ -275,6 +331,8 @@ public class AttributeNormalizer
public String normalizePath(Path path)
{
String uriPath = path.toUri().getSchemeSpecificPart();
for (PathAttribute attr : attributes)
{
if (attr.path == null)
@ -284,7 +342,7 @@ public class AttributeNormalizer
{
if (path.startsWith(attr.path) || path.equals(attr.path) || Files.isSameFile(path,attr.path))
{
return uriSeparators(URIUtil.addPaths("${" + attr.key + "}",attr.path.relativize(path).toString()));
return attr.getNormalizedScheme() + uriSeparators(URIUtil.addPaths("${" + attr.key + "}", attr.path.relativize(path).toString()));
}
}
catch (IOException ignore)
@ -380,18 +438,12 @@ public class AttributeNormalizer
return null;
}
// Use war path (if known)
if("WAR".equalsIgnoreCase(property))
{
return warURI.toASCIIString();
}
// Use known path attributes
for (PathAttribute attr : attributes)
{
if (attr.key.equalsIgnoreCase(property))
{
return uriSeparators(attr.path.toString());
return attr.toUri();
}
}

View File

@ -18,17 +18,21 @@
package org.eclipse.jetty.quickstart;
import static org.hamcrest.Matchers.is;
import static org.junit.Assert.assertThat;
import java.io.File;
import java.io.IOException;
import java.net.MalformedURLException;
import java.net.URI;
import java.net.URISyntaxException;
import java.net.URL;
import java.nio.file.FileSystems;
import java.nio.file.Files;
import java.nio.file.Path;
import java.util.Arrays;
import java.util.List;
import org.eclipse.jetty.toolchain.test.FS;
import org.eclipse.jetty.toolchain.test.MavenTestingUtils;
import org.eclipse.jetty.util.resource.Resource;
import org.junit.AfterClass;
import org.junit.BeforeClass;
@ -37,65 +41,33 @@ import org.junit.runner.RunWith;
import org.junit.runners.Parameterized;
import org.junit.runners.Parameterized.Parameters;
import static org.hamcrest.Matchers.is;
import static org.junit.Assert.assertThat;
@RunWith(Parameterized.class)
public class AttributeNormalizerPathTest
{
@Parameters(name="{0} = {1}")
public static List<String[]> data()
{
String[][] tests = {
// Can't test 'WAR' property, as its not a Path (which this testcase works with)
// { "WAR", toSystemPath("http://localhost/resources/webapps/root") },
{ "jetty.home", toSystemPath("/opt/jetty-distro") },
{ "jetty.base", toSystemPath("/opt/jetty-distro/demo.base") },
{ "user.home", toSystemPath("/home/user") },
{ "user.dir", toSystemPath("/etc/init.d") },
String[][] tests = {
{ "jetty.home", EnvUtils.toSystemPath("/opt/jetty-distro") },
{ "jetty.base", EnvUtils.toSystemPath("/opt/jetty-distro/demo.base") },
{ "user.home", EnvUtils.toSystemPath("/home/user") },
{ "user.dir", EnvUtils.toSystemPath("/etc/init.d") },
};
return Arrays.asList(tests);
}
/**
* As the declared paths in this testcase might be actual paths on the system
* running these tests, the expected paths should be cleaned up to represent
* the actual system paths.
* <p>
* Eg: on fedora /etc/init.d is a symlink to /etc/rc.d/init.d
*/
public static String toSystemPath(String rawpath)
{
Path path = FileSystems.getDefault().getPath(rawpath);
if (Files.exists(path))
{
// It exists, resolve it to the real path
try
{
path = path.toRealPath();
}
catch (IOException e)
{
// something prevented us from resolving to real path, fallback to
// absolute path resolution (not as accurate)
path = path.toAbsolutePath();
e.printStackTrace();
}
}
else
{
// File doesn't exist, resolve to absolute path
// We can't rely on File.toCanonicalPath() here
path = path.toAbsolutePath();
}
return path.toString();
}
private static Path testRoot;
private static String origJettyBase;
private static String origJettyHome;
private static String origUserHome;
private static String origUserDir;
static
{
testRoot = MavenTestingUtils.getTargetTestingPath(AttributeNormalizerPathTest.class.getSimpleName());
FS.ensureEmpty(testRoot);
}
@BeforeClass
public static void initProperties()
@ -125,19 +97,31 @@ public class AttributeNormalizerPathTest
private AttributeNormalizer normalizer;
public AttributeNormalizerPathTest(String key, String path) throws MalformedURLException, IOException
public AttributeNormalizerPathTest(String key, String path) throws IOException
{
this.key = key;
this.path = AttributeNormalizer.uriSeparators(path);
this.normalizer = new AttributeNormalizer(Resource.newResource("/opt/jetty-distro/demo.base/webapps/root"));
this.normalizer = new AttributeNormalizer(Resource.newResource(testRoot.toFile()));
}
private void assertExpand(String line, String expected)
{
assertThat("normalizer.expand(\"" + line + "\")", normalizer.expand(line), is(expected));
}
@Test
public void testEqual()
{
assertThat(normalizer.normalize("file:" + path), is("file:${" + key + "}"));
}
@Test
public void testExpandEqual()
{
String expectedPath = new File(path).toPath().toUri().getRawSchemeSpecificPart();
assertExpand("file:${" + key + "}", "file:" + expectedPath);
}
@Test
public void testEqualsSlash()
{
@ -203,6 +187,13 @@ public class AttributeNormalizerPathTest
{
assertThat(normalizer.normalize("jar:file:" + path + "/file!/file"), is("jar:file:${" + key + "}/file!/file"));
}
@Test
public void testExpandJarFileEquals_FileBangFile()
{
String expectedPath = new File(path).toPath().toUri().getRawSchemeSpecificPart();
assertExpand("jar:file:${" + key + "}/file!/file", "jar:file:" + expectedPath + "/file!/file");
}
@Test
public void testJarFileEquals_URIBangFile() throws URISyntaxException

View File

@ -29,6 +29,7 @@ import java.io.IOException;
import java.net.MalformedURLException;
import java.net.URI;
import org.eclipse.jetty.toolchain.test.MavenTestingUtils;
import org.eclipse.jetty.util.resource.Resource;
import org.junit.Test;
@ -42,9 +43,9 @@ public class AttributeNormalizerTest
try
{
String testJettyHome = AttributeNormalizerPathTest.toSystemPath("/opt/jetty-distro");
String testJettyBase = AttributeNormalizerPathTest.toSystemPath("/opt/jetty-distro/demo.base");
String testWar = AttributeNormalizerPathTest.toSystemPath("/opt/jetty-distro/demo.base/webapps/FOO");
String testJettyHome = EnvUtils.toSystemPath("/opt/jetty-distro");
String testJettyBase = EnvUtils.toSystemPath("/opt/jetty-distro/demo.base");
String testWar = EnvUtils.toSystemPath("/opt/jetty-distro/demo.base/webapps/FOO");
System.setProperty("jetty.home", testJettyHome);
System.setProperty("jetty.base", testJettyBase);
@ -61,12 +62,12 @@ public class AttributeNormalizerTest
// Normalize as URI
result = normalizer.normalize(testWarURI);
assertThat(result, is("file:${WAR}"));
assertThat(result, is("${WAR}"));
// Normalize deep path as File
File testWarDeep = new File(new File(testWar), "deep/ref").getAbsoluteFile();
result = normalizer.normalize(testWarDeep);
assertThat(result, is("file:${WAR}/deep/ref"));
assertThat(result, is("${WAR}/deep/ref"));
// Normalize deep path as String
result = normalizer.normalize(testWarDeep.toString());
@ -74,40 +75,39 @@ public class AttributeNormalizerTest
// Normalize deep path as URI
result = normalizer.normalize(testWarDeep.toURI());
assertThat(result, is("file:${WAR}/deep/ref"));
assertThat(result, is("${WAR}/deep/ref"));
}
finally
{
restoreSystemProperty("jetty.home", oldJettyHome);
restoreSystemProperty("jetty.base", oldJettyBase);
}
}
private void restoreSystemProperty(String key, String value)
{
if (value == null)
{
System.clearProperty(key);
}
else
{
System.setProperty(key, value);
EnvUtils.restoreSystemProperty("jetty.home", oldJettyHome);
EnvUtils.restoreSystemProperty("jetty.base", oldJettyBase);
}
}
@Test
public void testNormalizeWAR() throws MalformedURLException, IOException
public void testNormalizeExpandWAR() throws IOException
{
String webref = "http://localhost/resource/webapps/root";
String webref = MavenTestingUtils.getTargetDir().getAbsolutePath() + "/bogus.war";
Resource webresource = Resource.newResource(webref);
AttributeNormalizer normalizer = new AttributeNormalizer(webresource);
String result = null;
result = normalizer.normalize(URI.create(webref));
assertThat(result, is("${WAR}"));
File webrefFile = new File(webref);
URI uri = webrefFile.toURI();
// As normal URI ref
result = normalizer.normalize(uri);
assertThat("normalize(" + uri + ")", result, is("${WAR}"));
result = normalizer.normalize(URI.create(webref + "/deep/ref"));
assertThat(result, is("${WAR}/deep/ref"));
// as jar internal resource reference
uri = URI.create("jar:" + webrefFile.toURI().toASCIIString() + "!/deep/ref");
result = normalizer.normalize(uri);
assertThat("normalize(" + uri + ")", result, is("jar:${WAR}!/deep/ref"));
// as jar internal resource reference
String line = "jar:${WAR}!/other/file";
result = normalizer.expand(line);
uri = URI.create("jar:" + webrefFile.toPath().toUri().toASCIIString() + "!/other/file");
assertThat("expand(\"" + line + "\")", URI.create(result), is(uri));
}
@Test
@ -120,7 +120,7 @@ public class AttributeNormalizerTest
// Setup example from windows
String javaUserHome = System.getProperty("user.home");
String realUserHome = AttributeNormalizerPathTest.toSystemPath(javaUserHome);
String realUserHome = EnvUtils.toSystemPath(javaUserHome);
String userHome = AttributeNormalizer.uriSeparators(realUserHome);
String path = "jar:file:" + userHome + "/.m2/repository/something/somejar.jar!/META-INF/some.tld";

View File

@ -0,0 +1,76 @@
//
// ========================================================================
// Copyright (c) 1995-2016 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.quickstart;
import java.io.IOException;
import java.nio.file.FileSystems;
import java.nio.file.Files;
import java.nio.file.Path;
/**
* Common utility methods for quickstart tests
*/
public class EnvUtils
{
/**
* As the declared paths in this testcase might be actual paths on the system
* running these tests, the expected paths should be cleaned up to represent
* the actual system paths.
* <p>
* Eg: on fedora /etc/init.d is a symlink to /etc/rc.d/init.d
*/
public static String toSystemPath(String rawpath)
{
Path path = FileSystems.getDefault().getPath(rawpath);
if (Files.exists(path))
{
// It exists, resolve it to the real path
try
{
path = path.toRealPath();
}
catch (IOException e)
{
// something prevented us from resolving to real path, fallback to
// absolute path resolution (not as accurate)
path = path.toAbsolutePath();
e.printStackTrace();
}
}
else
{
// File doesn't exist, resolve to absolute path
// We can't rely on File.toCanonicalPath() here
path = path.toAbsolutePath();
}
return path.toString();
}
public static void restoreSystemProperty(String key, String value)
{
if (value == null)
{
System.clearProperty(key);
}
else
{
System.setProperty(key, value);
}
}
}