Junit 5 update, matrix params, path trie

This commit is contained in:
Jörg Prante 2019-07-14 17:44:45 +02:00
parent 1f949104ef
commit bc84cfce4a
23 changed files with 989 additions and 375 deletions

View file

@ -6,20 +6,6 @@ plugins {
id "org.xbib.gradle.plugin.asciidoctor" version "1.5.6.0.1" id "org.xbib.gradle.plugin.asciidoctor" version "1.5.6.0.1"
} }
printf "Host: %s\nOS: %s %s %s\nJVM: %s %s %s %s\nGradle: %s Groovy: %s Java: %s\n" +
"Build: group: ${project.group} name: ${project.name} version: ${project.version}\n",
InetAddress.getLocalHost(),
System.getProperty("os.name"),
System.getProperty("os.arch"),
System.getProperty("os.version"),
System.getProperty("java.version"),
System.getProperty("java.vm.version"),
System.getProperty("java.vm.vendor"),
System.getProperty("java.vm.name"),
gradle.gradleVersion,
GroovySystem.getVersion(),
JavaVersion.current()
subprojects { subprojects {
apply plugin: 'java' apply plugin: 'java'
@ -36,14 +22,15 @@ subprojects {
configurations { configurations {
asciidoclet asciidoclet
wagon
} }
dependencies { dependencies {
testCompile "junit:junit:${project.property('junit.version')}" testImplementation "org.junit.jupiter:junit-jupiter-api:${project.property('junit.version')}"
testCompile "com.fasterxml.jackson.core:jackson-databind:${project.property('jackson.version')}" testImplementation "org.junit.jupiter:junit-jupiter-params:${project.property('junit.version')}"
testImplementation "org.hamcrest:hamcrest-library:${project.property('hamcrest.version')}"
testRuntimeOnly "org.junit.jupiter:junit-jupiter-engine:${project.property('junit.version')}"
testImplementation "com.fasterxml.jackson.core:jackson-databind:${project.property('jackson.version')}"
asciidoclet "org.asciidoctor:asciidoclet:${project.property('asciidoclet.version')}" asciidoclet "org.asciidoctor:asciidoclet:${project.property('asciidoclet.version')}"
wagon "org.apache.maven.wagon:wagon-ssh:${project.property('wagon.version')}"
} }
compileJava { compileJava {
@ -51,8 +38,8 @@ subprojects {
targetCompatibility = JavaVersion.VERSION_1_8 targetCompatibility = JavaVersion.VERSION_1_8
} }
compileTestJava { compileTestJava {
sourceCompatibility = JavaVersion.VERSION_1_8 sourceCompatibility = JavaVersion.VERSION_11
targetCompatibility = JavaVersion.VERSION_1_8 targetCompatibility = JavaVersion.VERSION_11
} }
tasks.withType(JavaCompile) { tasks.withType(JavaCompile) {
options.compilerArgs << "-Xlint:all,-serial" options.compilerArgs << "-Xlint:all,-serial"
@ -69,12 +56,22 @@ subprojects {
} }
test { test {
testLogging { useJUnitPlatform()
showStandardStreams = false
exceptionFormat = 'full'
}
systemProperty 'java.net.preferIPv4Stack', 'false' systemProperty 'java.net.preferIPv4Stack', 'false'
systemProperty 'java.net.preferIPv6Addresses', 'true' systemProperty 'java.net.preferIPv6Addresses', 'true'
failFast = false
testLogging {
events 'PASSED', 'FAILED', 'SKIPPED'
}
afterSuite { desc, result ->
if (!desc.parent) {
println "\nTest result: ${result.resultType}"
println "Test summary: ${result.testCount} tests, " +
"${result.successfulTestCount} succeeded, " +
"${result.failedTestCount} failed, " +
"${result.skippedTestCount} skipped"
}
}
} }
asciidoctor { asciidoctor {
@ -114,12 +111,6 @@ subprojects {
archives sourcesJar, javadocJar archives sourcesJar, javadocJar
} }
if (project.hasProperty('signing.keyId')) {
signing {
sign configurations.archives
}
}
apply from: "${rootProject.projectDir}/gradle/publish.gradle" apply from: "${rootProject.projectDir}/gradle/publish.gradle"
tasks.withType(Checkstyle) { tasks.withType(Checkstyle) {

View file

@ -1,10 +1,11 @@
group = org.xbib group = org.xbib
name = net name = net
version = 1.2.2 version = 1.3.3
# test
jackson.version = 2.8.11 jackson.version = 2.8.11
junit.version = 4.12 junit.version = 5.4.2
wagon.version = 3.0.0 hamcrest.version = 2.1
asciidoclet.version = 1.5.4 asciidoclet.version = 1.5.4
org.gradle.warning.mode = all org.gradle.warning.mode = all

View file

@ -6,7 +6,7 @@ ext {
scmDeveloperConnection = 'scm:git:git://github.com/xbib/net.git' scmDeveloperConnection = 'scm:git:git://github.com/xbib/net.git'
} }
task xbibUpload(type: Upload) { /*task xbibUpload(type: Upload) {
group = 'publish' group = 'publish'
configuration = configurations.archives configuration = configurations.archives
uploadDescriptor = true uploadDescriptor = true
@ -20,7 +20,7 @@ task xbibUpload(type: Upload) {
} }
} }
} }
} }*/
task sonatypeUpload(type: Upload, dependsOn: build) { task sonatypeUpload(type: Upload, dependsOn: build) {
group = 'publish' group = 'publish'

View file

@ -1,5 +1,7 @@
package org.xbib.net; package org.xbib.net;
import java.nio.charset.MalformedInputException;
import java.nio.charset.UnmappableCharacterException;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.List; import java.util.List;
import java.util.stream.Collectors; import java.util.stream.Collectors;
@ -7,8 +9,15 @@ import java.util.stream.Collectors;
/** /**
* Query parameter list, of limited size. Default is 1024 pairs. * Query parameter list, of limited size. Default is 1024 pairs.
*/ */
@SuppressWarnings("serial")
public class QueryParameters extends ArrayList<QueryParameters.Pair<String, String>> { public class QueryParameters extends ArrayList<QueryParameters.Pair<String, String>> {
private static final char AMPERSAND_CHAR = '&';
private static final char EQUAL_CHAR = '=';
private final PercentDecoder percentDecoder;
private final int max; private final int max;
public QueryParameters() { public QueryParameters() {
@ -17,6 +26,7 @@ public class QueryParameters extends ArrayList<QueryParameters.Pair<String, Stri
public QueryParameters(int max) { public QueryParameters(int max) {
this.max = max; this.max = max;
this.percentDecoder = new PercentDecoder();
} }
public List<String> get(String key) { public List<String> get(String key) {
@ -36,6 +46,34 @@ public class QueryParameters extends ArrayList<QueryParameters.Pair<String, Stri
return size() < max && super.add(element); return size() < max && super.add(element);
} }
public QueryParameters addPercentEncodedBody(String body) throws MalformedInputException, UnmappableCharacterException {
String s = body;
while (s != null) {
Pair<String, String> pairs = indexOf(AMPERSAND_CHAR, s);
Pair<String, String> pair = indexOf(EQUAL_CHAR, pairs.getFirst());
if (!isNullOrEmpty(pair.getFirst())) {
add(percentDecoder.decode(pair.getFirst()),
percentDecoder.decode(pair.getSecond()));
}
s = pairs.getSecond();
}
return this;
}
/**
* Returns true if the parameter string is neither null nor empty.
*/
private static boolean isNullOrEmpty(String str) {
return str == null || str.isEmpty();
}
private static Pair<String, String> indexOf(char ch, String input) {
int i = input.indexOf(ch);
String k = i >= 0 ? input.substring(0, i) : input;
String v = i >= 0 ? input.substring(i + 1) : null;
return new Pair<>(k, v);
}
/** /**
* A pair of query parameters. * A pair of query parameters.
* @param <K> the key type parameter * @param <K> the key type parameter
@ -45,7 +83,7 @@ public class QueryParameters extends ArrayList<QueryParameters.Pair<String, Stri
private final K first; private final K first;
private final V second; private final V second;
public Pair(K first, V second) { Pair(K first, V second) {
this.first = first; this.first = first;
this.second = second; this.second = second;
} }

View file

@ -240,12 +240,12 @@ public class URL implements Comparable<URL> {
return new Parser(); return new Parser();
} }
public static Resolver base(URL base) { public static Resolver base(String base) {
return new Resolver(base); return base(URL.create(base));
} }
public static Resolver base(String base) { public static Resolver base(URL base) {
return new Resolver(URL.create(base)); return new Resolver(base);
} }
private static final URL NULL_URL = URL.builder().build(); private static final URL NULL_URL = URL.builder().build();
@ -416,6 +416,10 @@ public class URL implements Comparable<URL> {
return decode(path); return decode(path);
} }
public List<PathSegment> getPathSegments() {
return builder.pathSegments;
}
/** /**
* Get the query ('?q=foo{@literal &}bar') of the {@code URL} if it exists. * Get the query ('?q=foo{@literal &}bar') of the {@code URL} if it exists.
* @return the query * @return the query
@ -457,6 +461,20 @@ public class URL implements Comparable<URL> {
return !isNullOrEmpty(builder.scheme) && !isNullOrEmpty(builder.schemeSpecificPart) && builder.host == null; return !isNullOrEmpty(builder.scheme) && !isNullOrEmpty(builder.schemeSpecificPart) && builder.host == null;
} }
/**
* Whether this is a hierarchical URL or not. That is, a URL that allows multiple path segments.
*
* The term <em>hierarchical</em> comes form the URI standard
* (<a href="https://www.ietf.org/rfc/rfc3986.txt">RFC 3986</a>).
* Other libraries might refer to it as <em>relative</em> or <em>cannot-be-a-base-URL</em>.
* The later is the current WHATWG URL standard
* (see <a href="https://github.com/whatwg/url/issues/89">whatwg/url#89</a> for the rationale).
* @return true if URL is hierarchical
*/
public boolean isHierarchical() {
return !isOpaque();
}
/** /**
* @return true if URL is absolute. * @return true if URL is absolute.
*/ */
@ -645,7 +663,7 @@ public class URL implements Comparable<URL> {
return sb.length() == 0 ? null : sb.toString(); return sb.length() == 0 ? null : sb.toString();
} }
private void appendQuery(StringBuilder sb, boolean encoded, boolean withQuestionMark) { private void appendQuery(StringBuilder sb, boolean withEncoding, boolean withQuestionMark) {
if (!builder.queryParams.isEmpty()) { if (!builder.queryParams.isEmpty()) {
if (withQuestionMark) { if (withQuestionMark) {
sb.append(QUESTION_CHAR); sb.append(QUESTION_CHAR);
@ -654,9 +672,9 @@ public class URL implements Comparable<URL> {
while (it.hasNext()) { while (it.hasNext()) {
QueryParameters.Pair<String, String> queryParam = it.next(); QueryParameters.Pair<String, String> queryParam = it.next();
try { try {
sb.append(encoded ? queryParamEncoder.encode(queryParam.getFirst()) : queryParam.getFirst()); sb.append(withEncoding ? queryParamEncoder.encode(queryParam.getFirst()) : queryParam.getFirst());
if (queryParam.getSecond() != null) { if (queryParam.getSecond() != null) {
sb.append(EQUAL_CHAR).append(encoded ? sb.append(EQUAL_CHAR).append(withEncoding ?
queryParamEncoder.encode(queryParam.getSecond()) : queryParam.getSecond()); queryParamEncoder.encode(queryParam.getSecond()) : queryParam.getSecond());
} }
} catch (CharacterCodingException e) { } catch (CharacterCodingException e) {
@ -670,7 +688,7 @@ public class URL implements Comparable<URL> {
if (withQuestionMark) { if (withQuestionMark) {
sb.append(QUESTION_CHAR); sb.append(QUESTION_CHAR);
} }
if (encoded) { if (withEncoding) {
try { try {
sb.append(queryEncoder.encode(builder.query)); sb.append(queryEncoder.encode(builder.query));
} catch (CharacterCodingException e) { } catch (CharacterCodingException e) {
@ -898,10 +916,11 @@ public class URL implements Comparable<URL> {
} }
public Builder pathSegment(String segment) { public Builder pathSegment(String segment) {
if (pathSegments.isEmpty() && !isNullOrEmpty(host) && !isNullOrEmpty(segment)) { if (pathSegments.isEmpty() && !isNullOrEmpty(host) && isNullOrEmpty(segment)) {
pathSegments.add(EMPTY_SEGMENT); pathSegments.add(EMPTY_SEGMENT);
} } else {
pathSegments.add(new PathSegment(segment)); pathSegments.add(new PathSegment(segment));
}
return this; return this;
} }
@ -1132,8 +1151,9 @@ public class URL implements Comparable<URL> {
} }
} }
private void parsePathWithQueryAndFragment(Builder builder, String input) private void parsePathWithQueryAndFragment(Builder builder, String inputStr)
throws MalformedInputException, UnmappableCharacterException { throws MalformedInputException, UnmappableCharacterException {
String input = inputStr;
if (input == null) { if (input == null) {
return; return;
} }
@ -1221,7 +1241,7 @@ public class URL implements Comparable<URL> {
private final URL base; private final URL base;
public Resolver(URL base) { Resolver(URL base) {
this.base = base; this.base = base;
} }
@ -1357,8 +1377,16 @@ public class URL implements Comparable<URL> {
} }
} }
private static class Pair<K, V> { /**
* A pair for matrix params.
*
* @param <K> key
* @param <V> value
*/
public static class Pair<K, V> {
private final K first; private final K first;
private final V second; private final V second;
Pair(K first, V second) { Pair(K first, V second) {
@ -1366,11 +1394,11 @@ public class URL implements Comparable<URL> {
this.second = second; this.second = second;
} }
K getFirst() { public K getFirst() {
return first; return first;
} }
V getSecond() { public V getSecond() {
return second; return second;
} }
@ -1381,9 +1409,9 @@ public class URL implements Comparable<URL> {
} }
/** /**
* A path segment with any associated matrix params. * A path segment with associated matrix params, if any.
*/ */
private static class PathSegment { public static class PathSegment {
private final String segment; private final String segment;
@ -1394,7 +1422,11 @@ public class URL implements Comparable<URL> {
this.params = new ArrayList<>(); this.params = new ArrayList<>();
} }
List<Pair<String, String>> getMatrixParams() { public String getSegment() {
return segment;
}
public List<Pair<String, String>> getMatrixParams() {
return params; return params;
} }

View file

@ -74,8 +74,8 @@ public class PathMatcher {
} }
public String extractPathWithinPattern(String pattern, String path) { public String extractPathWithinPattern(String pattern, String path) {
List<String> patternParts = tokenize(pattern, this.pathSeparator, this.trimTokens, true); List<String> patternParts = tokenize(pattern, pathSeparator, trimTokens);
List<String> pathParts = tokenize(path, this.pathSeparator, this.trimTokens, true); List<String> pathParts = tokenize(path, pathSeparator, trimTokens);
StringBuilder sb = new StringBuilder(); StringBuilder sb = new StringBuilder();
boolean pathStarted = false; boolean pathStarted = false;
for (int segment = 0; segment < patternParts.size(); segment++) { for (int segment = 0; segment < patternParts.size(); segment++) {
@ -95,13 +95,13 @@ public class PathMatcher {
} }
public String combine(String pattern1, String pattern2) { public String combine(String pattern1, String pattern2) {
if (!hasText(pattern1) && !hasText(pattern2)) { if (hasNotText(pattern1) && hasNotText(pattern2)) {
return ""; return "";
} }
if (!hasText(pattern1)) { if (hasNotText(pattern1)) {
return pattern2; return pattern2;
} }
if (!hasText(pattern2)) { if (hasNotText(pattern2)) {
return pattern1; return pattern1;
} }
boolean pattern1ContainsUriVar = pattern1.indexOf('{') != -1; boolean pattern1ContainsUriVar = pattern1.indexOf('{') != -1;
@ -135,18 +135,18 @@ public class PathMatcher {
return new PathPatternComparator(path); return new PathPatternComparator(path);
} }
private static boolean hasText(CharSequence str) { private static boolean hasNotText(CharSequence str) {
if (str == null || str.length() == 0) { if (str == null || str.length() == 0) {
return false; return true;
} }
int strLen = str.length(); int strLen = str.length();
for (int i = 0; i < strLen; i++) { for (int i = 0; i < strLen; i++) {
if (!Character.isWhitespace(str.charAt(i))) { if (!Character.isWhitespace(str.charAt(i))) {
return true;
}
}
return false; return false;
} }
}
return true;
}
private String concat(String path1, String path2) { private String concat(String path1, String path2) {
boolean path1EndsWithSeparator = path1.endsWith(this.pathSeparator); boolean path1EndsWithSeparator = path1.endsWith(this.pathSeparator);
@ -274,22 +274,22 @@ public class PathMatcher {
return tokenizedPatternCache.computeIfAbsent(pattern, this::tokenizePath); return tokenizedPatternCache.computeIfAbsent(pattern, this::tokenizePath);
} }
private List<String> tokenizePath(String path) { public List<String> tokenizePath(String path) {
return tokenize(path, this.pathSeparator, this.trimTokens, true); return tokenize(path, pathSeparator, trimTokens);
} }
private static List<String> tokenize(String str, String delimiters, boolean trimTokens, boolean ignoreEmptyTokens) { private static List<String> tokenize(String str, String delimiters, boolean trimTokens) {
List<String> tokens = new ArrayList<>();
if (str == null) { if (str == null) {
return null; return tokens;
} }
StringTokenizer st = new StringTokenizer(str, delimiters); StringTokenizer st = new StringTokenizer(str, delimiters);
List<String> tokens = new ArrayList<>();
while (st.hasMoreTokens()) { while (st.hasMoreTokens()) {
String token = st.nextToken(); String token = st.nextToken();
if (trimTokens) { if (trimTokens) {
token = token.trim(); token = token.trim();
} }
if (!ignoreEmptyTokens || token.length() > 0) { if (token.length() > 0) {
tokens.add(token); tokens.add(token);
} }
} }
@ -310,6 +310,7 @@ public class PathMatcher {
* @param <K> the key type parameter * @param <K> the key type parameter
* @param <V> the vale type parameter * @param <V> the vale type parameter
*/ */
@SuppressWarnings("serial")
private static class LRUCache<K, V> extends LinkedHashMap<K, V> { private static class LRUCache<K, V> extends LinkedHashMap<K, V> {
private final int cacheSize; private final int cacheSize;

View file

@ -9,22 +9,25 @@ import java.util.StringTokenizer;
*/ */
public class PathNormalizer { public class PathNormalizer {
private static final char separator = '/'; private static final char SEPARATOR_CHAR = '/';
private static final String SEPARATOR_STRING = "/";
private PathNormalizer() { private PathNormalizer() {
} }
public static String normalize(String path) { public static String normalize(String p) {
if (path == null || "".equals(path) || "/".equals(path)) { String path = p;
return "/"; if (path == null || "".equals(path) || SEPARATOR_STRING.equals(path)) {
return SEPARATOR_STRING;
} }
path = path.replaceAll("/+", "/"); path = path.replaceAll("/+", SEPARATOR_STRING);
int leadingSlashes = 0; int leadingSlashes = 0;
while (leadingSlashes < path.length() && path.charAt(leadingSlashes) == '/') { while (leadingSlashes < path.length() && path.charAt(leadingSlashes) == SEPARATOR_CHAR) {
++leadingSlashes; ++leadingSlashes;
} }
boolean isDir = (path.charAt(path.length() - 1) == '/'); boolean isDir = (path.charAt(path.length() - 1) == SEPARATOR_CHAR);
StringTokenizer st = new StringTokenizer(path, "/"); StringTokenizer st = new StringTokenizer(path, SEPARATOR_STRING);
LinkedList<String> list = new LinkedList<>(); LinkedList<String> list = new LinkedList<>();
while (st.hasMoreTokens()) { while (st.hasMoreTokens()) {
String token = st.nextToken(); String token = st.nextToken();
@ -41,16 +44,16 @@ public class PathNormalizer {
} }
StringBuilder sb = new StringBuilder(); StringBuilder sb = new StringBuilder();
while (leadingSlashes-- > 0) { while (leadingSlashes-- > 0) {
sb.append('/'); sb.append(SEPARATOR_CHAR);
} }
for (Iterator<String> it = list.iterator(); it.hasNext();) { for (Iterator<String> it = list.iterator(); it.hasNext();) {
sb.append(it.next()); sb.append(it.next());
if (it.hasNext()) { if (it.hasNext()) {
sb.append('/'); sb.append(SEPARATOR_CHAR);
} }
} }
if (isDir && sb.length() > 0 && sb.charAt(sb.length() - 1) != '/') { if (isDir && sb.length() > 0 && sb.charAt(sb.length() - 1) != SEPARATOR_CHAR) {
sb.append('/'); sb.append(SEPARATOR_CHAR);
} }
return sb.toString(); return sb.toString();
} }

View file

@ -0,0 +1,249 @@
package org.xbib.net.path;
import org.xbib.net.matcher.CharMatcher;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
import java.util.Objects;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
/**
* A simple trie that maps pairs of HTTP methods and parameterized paths to arbitrary data. Each
* node in the tree is a path segment. For example, given a path "discovery/v1/apis", the data would
* be stored in the node path represented by "discovery" -&gt; "v1" -&gt; "apis". A path is
* considered parameterized if one or more segments is of the form "{name}". When a parameterized
* path is resolved, a map from parameter names to raw String values is returned as part of the
* result. Null values are not acceptable values in this trie. Parameter names can only contain
* alphanumeric characters or underscores, and cannot start with a numeric.
*/
public class PathTrie<T> {
private static final String PARAMETER_PATH_SEGMENT = "{}";
private static final Pattern PARAMETER_NAME_PATTERN = Pattern.compile("[a-zA-Z_][a-zA-Z_\\d]*");
// General delimiters that must be URL encoded, as defined by RFC 3986.
private static final CharMatcher RESERVED_URL_CHARS = CharMatcher.anyOf(":/?#[]{}");
private final Map<String, PathTrie<T>> subTries;
private final Map<String, MethodInfo<T>> httpMethodMap;
private final PathMatcher pathMatcher;
private PathTrie(Builder<T> builder) {
this.httpMethodMap = builder.httpMethodMap;
Map<String, PathTrie<T>> subTriesBuilder = new LinkedHashMap<>();
for (Entry<String, Builder<T>> entry : builder.subBuilders.entrySet()) {
subTriesBuilder.put(entry.getKey(), new PathTrie<>(entry.getValue()));
}
this.subTries = subTriesBuilder;
this.pathMatcher = new PathMatcher();
}
/**
* Attempts to resolve a path. Resolution prefers literal paths over path parameters. The result
* includes the object to which the path mapped, as well a map from parameter names to
* URL-decoded values. If the path cannot be resolved, null is returned.
* @param method method
* @param path path
* @return result of resolving
*/
public Result<T> resolve(String method, String path) {
Objects.requireNonNull(method, "method");
Objects.requireNonNull(path, "path");
return resolve(method, pathMatcher.tokenizePath(path), 0, new ArrayList<>(), new ArrayList<>());
}
private Result<T> resolve(String method, List<String> pathSegments, int index,
List<String> context, List<String> rawParameters) {
if (index < pathSegments.size()) {
String segment = pathSegments.get(index);
PathTrie<T> subTrie = subTries.get(segment);
if (subTrie != null) {
context.add(segment);
Result<T> result = subTrie.resolve(method, pathSegments, index + 1, context, rawParameters);
if (result != null) {
return result;
}
}
subTrie = subTries.get(PARAMETER_PATH_SEGMENT);
if (subTrie != null) {
rawParameters.add(segment);
Result<T> result = subTrie.resolve(method, pathSegments, index + 1, context, rawParameters);
if (result == null) {
rawParameters.remove(rawParameters.size() - 1);
}
return result;
}
return null;
} else if (httpMethodMap.containsKey(method)) {
MethodInfo<T> methodInfo = httpMethodMap.get(method);
List<String> parameterNames = methodInfo.parameterNames;
if (rawParameters.size() != parameterNames.size()) {
throw new IllegalStateException();
}
Map<String, String> rawParameterMap = new LinkedHashMap<>();
for (int i = 0; i < parameterNames.size(); i++) {
rawParameterMap.put(parameterNames.get(i), rawParameters.get(i));
}
return new Result<>(methodInfo.value, context, rawParameterMap);
}
return null;
}
/**
* The resulting information for a successful path resolution, which includes the value to which
* the path maps, as well as the raw (but URL decoded) string values of all path parameters.
*/
public static class Result<T> {
private final T result;
private final List<String> context;
private final Map<String, String> rawParameters;
Result(T result, List<String> context, Map<String, String> rawParameters) {
this.result = result;
this.context = context;
this.rawParameters = rawParameters;
}
public T getResult() {
return result;
}
public List<String> getContext() {
return context;
}
public Map<String, String> getRawParameters() {
return rawParameters;
}
}
/**
* Returns a new, path conflict validating {@link PathTrie.Builder}.
*
* @param <T> the type that the trie will be storing
* @return the trie builder
*/
public static <T> Builder<T> builder() {
return new Builder<>(true);
}
/**
* Returns a new {@link PathTrie.Builder}.
*
* @param throwOnConflict whether or not to throw an exception on path conflicts
* @param <T> the type that the trie will be storing
* @return the trie builder
*/
public static <T> Builder<T> builder(boolean throwOnConflict) {
return new Builder<>(throwOnConflict);
}
/**
* A builder for creating a {@link PathTrie}, which is immutable.
*/
public static class Builder<T> {
private final Map<String, Builder<T>> subBuilders = new LinkedHashMap<>();
private final Map<String, MethodInfo<T>> httpMethodMap =new LinkedHashMap<>();
private final boolean throwOnConflict;
private final PathMatcher pathMatcher;
Builder(boolean throwOnConflict) {
this.throwOnConflict = throwOnConflict;
this.pathMatcher = new PathMatcher();
}
/**
* Adds a path to the trie.
*
* @param method the method
* @param path the path
* @param value the value
* @return the trie builder
* @throws IllegalArgumentException if the path cannot be added to the trie
* @throws NullPointerException if either path or value are null
*/
public Builder<T> add(String method, String path, T value) {
Objects.requireNonNull(method, "method");
Objects.requireNonNull(path, "path");
Objects.requireNonNull(value, "value");
add(method, path, pathMatcher.tokenizePath(path).iterator(), value, new ArrayList<>());
return this;
}
public PathTrie<T> build() {
return new PathTrie<>(this);
}
private void add(String method, String path, Iterator<String> pathSegments, T value,
List<String> parameterNames) {
if (pathSegments.hasNext()) {
String segment = pathSegments.next();
if (segment.startsWith("{")) {
if (segment.endsWith("}")) {
parameterNames.add(getAndCheckParameterName(segment));
getOrCreateSubBuilder(PARAMETER_PATH_SEGMENT)
.add(method, path, pathSegments, value, parameterNames);
} else {
throw new IllegalArgumentException(String.format("'%s' contains invalid parameter syntax: %s",
path, segment));
}
} else {
if (RESERVED_URL_CHARS.matchesAnyOf(segment)) {
throw new IllegalArgumentException(String.format("'%s' contains invalid path segment: %s",
path, segment));
}
getOrCreateSubBuilder(segment).add(method, path, pathSegments, value, parameterNames);
}
} else {
boolean pathExists = httpMethodMap.containsKey(method);
if (pathExists && throwOnConflict) {
throw new IllegalArgumentException(String.format("Path '%s' is already mapped", path));
}
httpMethodMap.put(method, new MethodInfo<>(parameterNames, value));
}
}
private String getAndCheckParameterName(String segment) {
String name = segment.substring(1, segment.length() - 1);
Matcher matcher = PARAMETER_NAME_PATTERN.matcher(name);
if (!matcher.matches()) {
throw new IllegalArgumentException(String.format("'%s' not a valid path parameter name", name));
}
return name;
}
private Builder<T> getOrCreateSubBuilder(String segment) {
Builder<T> subBuilder = subBuilders.get(segment);
if (subBuilder == null) {
subBuilder = builder(throwOnConflict);
subBuilders.put(segment, subBuilder);
}
return subBuilder;
}
}
private static class MethodInfo<T> {
private final List<String> parameterNames;
private final T value;
MethodInfo(List<String> parameterNames, T value) {
this.parameterNames = parameterNames;
this.value = value;
}
}
}

View file

@ -16,7 +16,7 @@ public class Variables {
private final Map<String, VariableValue> vars; private final Map<String, VariableValue> vars;
Variables(Builder builder) { private Variables(Builder builder) {
this.vars = builder.vars; this.vars = builder.vars;
} }
@ -45,7 +45,7 @@ public class Variables {
} }
/** /**
* * A Builder for variables.
*/ */
public static class Builder { public static class Builder {

View file

@ -1,39 +1,35 @@
package org.xbib.net; package org.xbib.net;
import org.junit.Test; import org.junit.jupiter.api.Test;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNotEquals;
import static org.junit.Assert.assertTrue;
import java.text.Normalizer; import java.text.Normalizer;
/** import static org.junit.jupiter.api.Assertions.assertEquals;
* import static org.junit.jupiter.api.Assertions.assertNotEquals;
*/
public class IRITest { class IRITest {
@Test @Test
public void testIpv4() { void testIpv4() {
URL iri = URL.create("http://127.0.0.1"); URL iri = URL.create("http://127.0.0.1");
assertEquals("http://127.0.0.1", iri.toExternalForm()); assertEquals("http://127.0.0.1", iri.toExternalForm());
} }
@Test @Test
public void testIpv6() { void testIpv6() {
URL iri = URL.from("http://[2001:0db8:85a3:08d3:1319:8a2e:0370:7344]"); URL iri = URL.from("http://[2001:0db8:85a3:08d3:1319:8a2e:0370:7344]");
assertEquals(iri.getProtocolVersion(), ProtocolVersion.IPV6); assertEquals(iri.getProtocolVersion(), ProtocolVersion.IPV6);
assertEquals("http://[2001:db8:85a3:8d3:1319:8a2e:370:7344]", iri.toString()); assertEquals("http://[2001:db8:85a3:8d3:1319:8a2e:370:7344]", iri.toString());
} }
@Test @Test
public void testIpv6Invalid() { void testIpv6Invalid() {
URL iri = URL.from("http://[2001:0db8:85a3:08d3:1319:8a2e:0370:734o]"); URL iri = URL.from("http://[2001:0db8:85a3:08d3:1319:8a2e:0370:734o]");
assertEquals(URL.nullUrl(), iri); assertEquals(URL.nullUrl(), iri);
} }
@Test @Test
public void testSimple() { void testSimple() {
URL iri = URL.create("http://validator.w3.org/check?uri=http%3A%2F%2Fr\u00E9sum\u00E9.example.org"); URL iri = URL.create("http://validator.w3.org/check?uri=http%3A%2F%2Fr\u00E9sum\u00E9.example.org");
//assertEquals("http://validator.w3.org/check?uri=http%3A%2F%2Fr\u00E9sum\u00E9.example.org", iri.toString()); //assertEquals("http://validator.w3.org/check?uri=http%3A%2F%2Fr\u00E9sum\u00E9.example.org", iri.toString());
assertEquals("http://validator.w3.org/check?uri=http://r%C3%A9sum%C3%A9.example.org", assertEquals("http://validator.w3.org/check?uri=http://r%C3%A9sum%C3%A9.example.org",
@ -41,7 +37,7 @@ public class IRITest {
} }
@Test @Test
public void testFile() throws Exception { void testFile() throws Exception {
URL iri = URL.create("file:///tmp/test/foo"); URL iri = URL.create("file:///tmp/test/foo");
assertEquals("", iri.getHost()); assertEquals("", iri.getHost());
assertEquals("/tmp/test/foo", iri.getPath()); assertEquals("/tmp/test/foo", iri.getPath());
@ -50,25 +46,25 @@ public class IRITest {
} }
@Test @Test
public void testSimple2() throws Exception { void testSimple2() throws Exception {
URL iri = URL.create("http://www.example.org/red%09ros\u00E9#red"); URL iri = URL.create("http://www.example.org/red%09ros\u00E9#red");
assertEquals("http://www.example.org/red%09ros%C3%A9#red", iri.toExternalForm()); assertEquals("http://www.example.org/red%09ros%C3%A9#red", iri.toExternalForm());
} }
@Test @Test
public void testNotSoSimple() throws Exception { void testNotSoSimple() throws Exception {
URL iri = URL.create("http://example.com/\uD800\uDF00\uD800\uDF01\uD800\uDF02"); URL iri = URL.create("http://example.com/\uD800\uDF00\uD800\uDF01\uD800\uDF02");
assertEquals("http://example.com/%F0%90%8C%80%F0%90%8C%81%F0%90%8C%82", iri.toExternalForm()); assertEquals("http://example.com/%F0%90%8C%80%F0%90%8C%81%F0%90%8C%82", iri.toExternalForm());
} }
@Test @Test
public void testIRItoURI() throws Exception { void testIRItoURI() throws Exception {
URL iri = URL.from("http://\u7D0D\u8C46.example.org/%E2%80%AE"); URL iri = URL.from("http://\u7D0D\u8C46.example.org/%E2%80%AE");
assertEquals("http://xn--99zt52a.example.org/%E2%80%AE", iri.toExternalForm()); assertEquals("http://xn--99zt52a.example.org/%E2%80%AE", iri.toExternalForm());
} }
@Test @Test
public void testComparison() throws Exception { void testComparison() throws Exception {
URL url1 = URL.create("http://www.example.org/"); URL url1 = URL.create("http://www.example.org/");
URL url2 = URL.create("http://www.example.org/.."); URL url2 = URL.create("http://www.example.org/..");
@ -90,7 +86,7 @@ public class IRITest {
} }
@Test @Test
public void testUCN() throws Exception { void testUCN() throws Exception {
URL iri1 = URL.create("http://www.example.org/r\u00E9sum\u00E9.html"); URL iri1 = URL.create("http://www.example.org/r\u00E9sum\u00E9.html");
String s = Normalizer.normalize("http://www.example.org/re\u0301sume\u0301.html", Normalizer.Form.NFC); String s = Normalizer.normalize("http://www.example.org/re\u0301sume\u0301.html", Normalizer.Form.NFC);
URL iri2 = URL.create(s); URL iri2 = URL.create(s);
@ -98,20 +94,20 @@ public class IRITest {
} }
@Test @Test
public void testPercent() { void testPercent() {
URL iri1 = URL.create("http://example.org/%7e%2Fuser?%2f"); URL iri1 = URL.create("http://example.org/%7e%2Fuser?%2f");
URL iri2 = URL.create("http://example.org/%7E%2fuser?/"); URL iri2 = URL.create("http://example.org/%7E%2fuser?/");
assertEquals(iri1.normalize(), iri2.normalize()); assertEquals(iri1.normalize(), iri2.normalize());
} }
@Test @Test
public void testIDN() { void testIDN() {
URL iri1 = URL.from("http://r\u00E9sum\u00E9.example.org"); URL iri1 = URL.from("http://r\u00E9sum\u00E9.example.org");
assertEquals("xn--rsum-bpad.example.org", iri1.getHost()); assertEquals("xn--rsum-bpad.example.org", iri1.getHost());
} }
@Test @Test
public void testResolveRelative() { void testResolveRelative() {
URL base = URL.create("http://example.org/foo/"); URL base = URL.create("http://example.org/foo/");
assertEquals("http://example.org/", base.resolve("/").toString()); assertEquals("http://example.org/", base.resolve("/").toString());
assertEquals("http://example.org/test", base.resolve("/test").toString()); assertEquals("http://example.org/test", base.resolve("/test").toString());
@ -125,7 +121,7 @@ public class IRITest {
} }
@Test @Test
public void testSchemes() { void testSchemes() {
URL iri = URL.create("http://a:b@c.org:80/d/e?f#g"); URL iri = URL.create("http://a:b@c.org:80/d/e?f#g");
assertEquals("http", iri.getScheme()); assertEquals("http", iri.getScheme());

View file

@ -1,10 +1,6 @@
package org.xbib.net; package org.xbib.net;
import org.junit.Before; import org.junit.jupiter.api.Test;
import org.junit.Test;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.fail;
import java.nio.charset.MalformedInputException; import java.nio.charset.MalformedInputException;
import java.nio.charset.StandardCharsets; import java.nio.charset.StandardCharsets;
@ -17,33 +13,29 @@ import java.util.stream.Collectors;
import static java.lang.Character.isHighSurrogate; import static java.lang.Character.isHighSurrogate;
import static java.lang.Character.isLowSurrogate; import static java.lang.Character.isLowSurrogate;
import static java.lang.Integer.toHexString; import static java.lang.Integer.toHexString;
import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.junit.jupiter.api.Assertions.fail;
/** class PercentDecoderTest {
*/
public class PercentDecoderTest {
private static final int CODE_POINT_IN_SUPPLEMENTARY = 2; private static final int CODE_POINT_IN_SUPPLEMENTARY = 2;
private static final int CODE_POINT_IN_BMP = 1; private static final int CODE_POINT_IN_BMP = 1;
private PercentDecoder decoder; private PercentDecoder decoder = new PercentDecoder(StandardCharsets.UTF_8.newDecoder());
@Before
public void setUp() {
decoder = new PercentDecoder(StandardCharsets.UTF_8.newDecoder());
}
@Test @Test
public void testDecodesWithoutPercents() throws Exception { void testDecodesWithoutPercents() throws Exception {
assertEquals("asdf", decoder.decode("asdf")); assertEquals("asdf", decoder.decode("asdf"));
} }
@Test @Test
public void testDecodeSingleByte() throws Exception { void testDecodeSingleByte() throws Exception {
assertEquals("#", decoder.decode("%23")); assertEquals("#", decoder.decode("%23"));
} }
@Test @Test
public void testIncompletePercentPairNoNumbers() throws Exception { void testIncompletePercentPairNoNumbers() throws Exception {
try { try {
decoder.decode("%"); decoder.decode("%");
fail(); fail();
@ -53,7 +45,7 @@ public class PercentDecoderTest {
} }
@Test @Test
public void testIncompletePercentPairOneNumber() throws Exception { void testIncompletePercentPairOneNumber() throws Exception {
try { try {
decoder.decode("%2"); decoder.decode("%2");
fail(); fail();
@ -63,7 +55,7 @@ public class PercentDecoderTest {
} }
@Test @Test
public void testInvalidHex() throws Exception { void testInvalidHex() throws Exception {
try { try {
decoder.decode("%xz"); decoder.decode("%xz");
fail(); fail();
@ -73,7 +65,7 @@ public class PercentDecoderTest {
} }
@Test @Test
public void testRandomStrings() throws MalformedInputException, UnmappableCharacterException { void testRandomStrings() throws MalformedInputException, UnmappableCharacterException {
PercentEncoder encoder = PercentEncoders.getQueryEncoder(StandardCharsets.UTF_8); PercentEncoder encoder = PercentEncoders.getQueryEncoder(StandardCharsets.UTF_8);
Random rand = new Random(); Random rand = new Random();
long seed = rand.nextLong(); long seed = rand.nextLong();
@ -87,10 +79,10 @@ public class PercentDecoderTest {
randString(buf, codePoints, charBuf, rand, 1 + rand.nextInt(1000)); randString(buf, codePoints, charBuf, rand, 1 + rand.nextInt(1000));
byte[] origBytes = buf.toString().getBytes(StandardCharsets.UTF_8); byte[] origBytes = buf.toString().getBytes(StandardCharsets.UTF_8);
byte[] decodedBytes = null; byte[] decodedBytes = null;
String codePointsHex = String.join("", codePoints.stream().map(Integer::toHexString).collect(Collectors.toList())); String codePointsHex = codePoints.stream().map(Integer::toHexString).collect(Collectors.joining(""));
try { try {
decodedBytes = decoder.decode(encoder.encode(buf.toString())).getBytes(StandardCharsets.UTF_8); decodedBytes = decoder.decode(encoder.encode(buf.toString())).getBytes(StandardCharsets.UTF_8);
assertEquals("Seed: $seed Code points: $codePointsHex", toHex(origBytes), toHex(decodedBytes)); assertEquals(toHex(origBytes), toHex(decodedBytes));
} catch (IllegalArgumentException e) { } catch (IllegalArgumentException e) {
List<String> charHex = new ArrayList<>(); List<String> charHex = new ArrayList<>();
for (int j = 0; j < buf.toString().length(); j++) { for (int j = 0; j < buf.toString().length(); j++) {

View file

@ -1,25 +1,22 @@
package org.xbib.net; package org.xbib.net;
import org.junit.Before; import org.junit.jupiter.api.BeforeAll;
import org.junit.Test; import org.junit.jupiter.api.Test;
import static org.junit.Assert.assertEquals;
import java.nio.charset.StandardCharsets; import java.nio.charset.StandardCharsets;
import java.util.BitSet; import java.util.BitSet;
import static java.nio.charset.CodingErrorAction.REPLACE; import static java.nio.charset.CodingErrorAction.REPLACE;
import static org.junit.jupiter.api.Assertions.assertEquals;
/** class PercentEncoderTest {
*
*/
public class PercentEncoderTest {
private PercentEncoder alnum; private static PercentEncoder alnum;
private PercentEncoder alnum16;
@Before private static PercentEncoder alnum16;
public void setUp() {
@BeforeAll
static void setUp() {
BitSet bs = new BitSet(); BitSet bs = new BitSet();
for (int i = 'a'; i <= 'z'; i++) { for (int i = 'a'; i <= 'z'; i++) {
bs.set(i); bs.set(i);
@ -31,14 +28,14 @@ public class PercentEncoderTest {
bs.set(i); bs.set(i);
} }
this.alnum = new PercentEncoder(bs, StandardCharsets.UTF_8.newEncoder().onMalformedInput(REPLACE) alnum = new PercentEncoder(bs, StandardCharsets.UTF_8.newEncoder().onMalformedInput(REPLACE)
.onUnmappableCharacter(REPLACE)); .onUnmappableCharacter(REPLACE));
this.alnum16 = new PercentEncoder(bs, StandardCharsets.UTF_16BE.newEncoder().onMalformedInput(REPLACE) alnum16 = new PercentEncoder(bs, StandardCharsets.UTF_16BE.newEncoder().onMalformedInput(REPLACE)
.onUnmappableCharacter(REPLACE)); .onUnmappableCharacter(REPLACE));
} }
@Test @Test
public void testDoesntEncodeSafe() throws Exception { void testDoesntEncodeSafe() throws Exception {
BitSet set = new BitSet(); BitSet set = new BitSet();
for (int i = 'a'; i <= 'z'; i++) { for (int i = 'a'; i <= 'z'; i++) {
set.set(i); set.set(i);
@ -49,32 +46,32 @@ public class PercentEncoderTest {
} }
@Test @Test
public void testEncodeInBetweenSafe() throws Exception { void testEncodeInBetweenSafe() throws Exception {
assertEquals("abc%20123", alnum.encode("abc 123")); assertEquals("abc%20123", alnum.encode("abc 123"));
} }
@Test @Test
public void testSafeInBetweenEncoded() throws Exception { void testSafeInBetweenEncoded() throws Exception {
assertEquals("%20abc%20", alnum.encode(" abc ")); assertEquals("%20abc%20", alnum.encode(" abc "));
} }
@Test @Test
public void testEncodeUtf8() throws Exception { void testEncodeUtf8() throws Exception {
assertEquals("snowman%E2%98%83", alnum.encode("snowman\u2603")); assertEquals("snowman%E2%98%83", alnum.encode("snowman\u2603"));
} }
@Test @Test
public void testEncodeUtf8SurrogatePair() throws Exception { void testEncodeUtf8SurrogatePair() throws Exception {
assertEquals("clef%F0%9D%84%9E", alnum.encode("clef\ud834\udd1e")); assertEquals("clef%F0%9D%84%9E", alnum.encode("clef\ud834\udd1e"));
} }
@Test @Test
public void testEncodeUtf16() throws Exception { void testEncodeUtf16() throws Exception {
assertEquals("snowman%26%03", alnum16.encode("snowman\u2603")); assertEquals("snowman%26%03", alnum16.encode("snowman\u2603"));
} }
@Test @Test
public void testUrlEncodedUtf16SurrogatePair() throws Exception { void testUrlEncodedUtf16SurrogatePair() throws Exception {
assertEquals("clef%D8%34%DD%1E", alnum16.encode("clef\ud834\udd1e")); assertEquals("clef%D8%34%DD%1E", alnum16.encode("clef\ud834\udd1e"));
} }
} }

View file

@ -1,18 +1,15 @@
package org.xbib.net; package org.xbib.net;
import org.junit.Test; import org.junit.jupiter.api.Test;
import static org.junit.Assert.assertEquals;
import java.net.URI; import java.net.URI;
import static org.junit.jupiter.api.Assertions.assertEquals;
/** class URIComponentTest {
*/
public class URIComponentTest {
@Test @Test
public void testURI() { void testURI() {
URI uri = URI.create("ftp://user:pass@host:1234/path/to/filename.txt"); URI uri = URI.create("ftp://user:pass@host:1234/path/to/filename.txt");
assertEquals("ftp", scheme(uri)); assertEquals("ftp", scheme(uri));
assertEquals("user", user(uri)); assertEquals("user", user(uri));
@ -24,7 +21,7 @@ public class URIComponentTest {
} }
@Test @Test
public void testURI2() { void testURI2() {
URI uri = URI.create("sftp://user:pass@host:1234/filename.txt"); URI uri = URI.create("sftp://user:pass@host:1234/filename.txt");
assertEquals("sftp", scheme(uri)); assertEquals("sftp", scheme(uri));
assertEquals("user", user(uri)); assertEquals("user", user(uri));

View file

@ -1,26 +1,23 @@
package org.xbib.net; package org.xbib.net;
import org.junit.Test; import org.junit.jupiter.api.Test;
import static org.junit.Assert.assertEquals; import static org.junit.jupiter.api.Assertions.assertEquals;
/** class URLBuilderTest {
*
*/
public class URLBuilderTest {
@Test @Test
public void testNoUrlParts() { void testNoUrlParts() {
assertUrl(URL.http().resolveFromHost("foo.com").toUrlString(), "http://foo.com"); assertUrl(URL.http().resolveFromHost("foo.com").toUrlString(), "http://foo.com");
} }
@Test @Test
public void testWithPort() { void testWithPort() {
assertUrl(URL.http().resolveFromHost("foo.com").port(33).toUrlString(), "http://foo.com:33"); assertUrl(URL.http().resolveFromHost("foo.com").port(33).toUrlString(), "http://foo.com:33");
} }
@Test @Test
public void testSimplePath() { void testSimplePath() {
assertUrl(URL.http().resolveFromHost("foo.com") assertUrl(URL.http().resolveFromHost("foo.com")
.pathSegment("seg1") .pathSegment("seg1")
.pathSegment("seg2") .pathSegment("seg2")
@ -29,7 +26,7 @@ public class URLBuilderTest {
} }
@Test @Test
public void testPathWithReserved() { void testPathWithReserved() {
// RFC 1738 S3.3 // RFC 1738 S3.3
assertUrl(URL.http().resolveFromHost("foo.com") assertUrl(URL.http().resolveFromHost("foo.com")
.pathSegment("seg/;?ment") .pathSegment("seg/;?ment")
@ -38,14 +35,14 @@ public class URLBuilderTest {
} }
@Test @Test
public void testPathSegments() { void testPathSegments() {
assertUrl(URL.http().resolveFromHost("foo.com") assertUrl(URL.http().resolveFromHost("foo.com")
.pathSegments("seg1", "seg2", "seg3") .pathSegments("seg1", "seg2", "seg3")
.toUrlString(), "http://foo.com/seg1/seg2/seg3"); .toUrlString(), "http://foo.com/seg1/seg2/seg3");
} }
@Test @Test
public void testMatrixWithReserved() { void testMatrixWithReserved() {
assertUrl(URL.http().resolveFromHost("foo.com") assertUrl(URL.http().resolveFromHost("foo.com")
.pathSegment("foo") .pathSegment("foo")
.matrixParam("foo", "bar") .matrixParam("foo", "bar")
@ -55,28 +52,28 @@ public class URLBuilderTest {
} }
@Test @Test
public void testUrlEncodedPathSegmentUtf8() { void testUrlEncodedPathSegmentUtf8() {
assertUrl(URL.http().resolveFromHost("foo.com") assertUrl(URL.http().resolveFromHost("foo.com")
.pathSegment("snowman").pathSegment("\u2603") .pathSegment("snowman").pathSegment("\u2603")
.toUrlString(), "http://foo.com/snowman/%E2%98%83"); .toUrlString(), "http://foo.com/snowman/%E2%98%83");
} }
@Test @Test
public void testUrlEncodedPathSegmentUtf8SurrogatePair() { void testUrlEncodedPathSegmentUtf8SurrogatePair() {
assertUrl(URL.http().resolveFromHost("foo.com") assertUrl(URL.http().resolveFromHost("foo.com")
.pathSegment("clef").pathSegment("\ud834\udd1e") .pathSegment("clef").pathSegment("\ud834\udd1e")
.toUrlString(), "http://foo.com/clef/%F0%9D%84%9E"); .toUrlString(), "http://foo.com/clef/%F0%9D%84%9E");
} }
@Test @Test
public void testQueryParamNoPath() { void testQueryParamNoPath() {
assertUrl(URL.http().resolveFromHost("foo.com") assertUrl(URL.http().resolveFromHost("foo.com")
.queryParam("foo", "bar") .queryParam("foo", "bar")
.toUrlString(), "http://foo.com?foo=bar"); .toUrlString(), "http://foo.com?foo=bar");
} }
@Test @Test
public void testQueryParamsDuplicated() { void testQueryParamsDuplicated() {
assertUrl(URL.http().resolveFromHost("foo.com") assertUrl(URL.http().resolveFromHost("foo.com")
.queryParam("foo", "bar") .queryParam("foo", "bar")
.queryParam("foo", "bar2") .queryParam("foo", "bar2")
@ -86,7 +83,7 @@ public class URLBuilderTest {
} }
@Test @Test
public void testEncodeQueryParams() { void testEncodeQueryParams() {
assertUrl(URL.http().resolveFromHost("foo.com") assertUrl(URL.http().resolveFromHost("foo.com")
.queryParam("foo", "bar&=#baz") .queryParam("foo", "bar&=#baz")
.queryParam("foo", "bar?/2") .queryParam("foo", "bar?/2")
@ -94,7 +91,7 @@ public class URLBuilderTest {
} }
@Test @Test
public void testEncodeQueryParamWithSpaceAndPlus() { void testEncodeQueryParamWithSpaceAndPlus() {
assertUrl(URL.http().resolveFromHost("foo.com") assertUrl(URL.http().resolveFromHost("foo.com")
.queryParam("foo", "spa ce") .queryParam("foo", "spa ce")
.queryParam("fo+o", "plus+") .queryParam("fo+o", "plus+")
@ -102,7 +99,7 @@ public class URLBuilderTest {
} }
@Test @Test
public void testPlusInVariousParts() { void testPlusInVariousParts() {
assertUrl(URL.http().resolveFromHost("foo.com") assertUrl(URL.http().resolveFromHost("foo.com")
.pathSegment("has+plus") .pathSegment("has+plus")
.matrixParam("plusMtx", "pl+us") .matrixParam("plusMtx", "pl+us")
@ -112,7 +109,7 @@ public class URLBuilderTest {
} }
@Test @Test
public void testFragment() { void testFragment() {
assertUrl(URL.http().resolveFromHost("foo.com") assertUrl(URL.http().resolveFromHost("foo.com")
.queryParam("foo", "bar") .queryParam("foo", "bar")
.fragment("#frag/?") .fragment("#frag/?")
@ -120,7 +117,7 @@ public class URLBuilderTest {
} }
@Test @Test
public void testAllParts() { void testAllParts() {
assertUrl(URL.https().resolveFromHost("foo.bar.com").port(3333) assertUrl(URL.https().resolveFromHost("foo.bar.com").port(3333)
.pathSegment("foo") .pathSegment("foo")
.pathSegment("bar") .pathSegment("bar")
@ -134,24 +131,24 @@ public class URLBuilderTest {
} }
@Test @Test
public void testSlashInHost() { void testSlashInHost() {
URL.http().resolveFromHost("/").toUrlString(); URL.http().resolveFromHost("/").toUrlString();
} }
@Test @Test
public void testGoogle() { void testGoogle() {
URL url = URL.https().resolveFromHost("google.com").build(); URL url = URL.https().resolveFromHost("google.com").build();
assertEquals("https://google.com", url.toString()); assertEquals("https://google.com", url.toString());
} }
@Test @Test
public void testBadIPv4LiteralDoesntChoke() { void testBadIPv4LiteralDoesntChoke() {
assertUrl(URL.http().resolveFromHost("300.100.50.1") assertUrl(URL.http().resolveFromHost("300.100.50.1")
.toUrlString(), "http://300.100.50.1"); .toUrlString(), "http://300.100.50.1");
} }
@Test @Test
public void testIPv4Literal() { void testIPv4Literal() {
if ("false".equals(System.getProperty("java.net.preferIPv6Addresses"))) { if ("false".equals(System.getProperty("java.net.preferIPv6Addresses"))) {
assertUrl(URL.http().resolveFromHost("127.0.0.1") assertUrl(URL.http().resolveFromHost("127.0.0.1")
.toUrlString(), "http://localhost"); .toUrlString(), "http://localhost");
@ -161,7 +158,7 @@ public class URLBuilderTest {
} }
@Test @Test
public void testIPv6LiteralLocalhost() { void testIPv6LiteralLocalhost() {
String s = URL.http().resolveFromHost("[::1]").toUrlString(); String s = URL.http().resolveFromHost("[::1]").toUrlString();
if ("true".equals(System.getProperty("java.net.preferIPv6Addresses"))) { if ("true".equals(System.getProperty("java.net.preferIPv6Addresses"))) {
assertEquals("http://[0:0:0:0:0:0:0:1]", s); assertEquals("http://[0:0:0:0:0:0:0:1]", s);
@ -171,7 +168,7 @@ public class URLBuilderTest {
} }
@Test @Test
public void testIPv6Literal() { void testIPv6Literal() {
if ("true".equals(System.getProperty("java.net.preferIPv6Addresses"))) { if ("true".equals(System.getProperty("java.net.preferIPv6Addresses"))) {
String s = URL.http().resolveFromHost("[2001:db8:85a3::8a2e:370:7334]") String s = URL.http().resolveFromHost("[2001:db8:85a3::8a2e:370:7334]")
.toUrlString(); .toUrlString();
@ -180,21 +177,21 @@ public class URLBuilderTest {
} }
@Test @Test
public void testEncodedRegNameSingleByte() { void testEncodedRegNameSingleByte() {
String s = URL.http().resolveFromHost("host?name;") String s = URL.http().resolveFromHost("host?name;")
.toUrlString(); .toUrlString();
assertEquals("http://host%3Fname;", s); assertEquals("http://host%3Fname;", s);
} }
@Test @Test
public void testEncodedRegNameMultiByte() { void testEncodedRegNameMultiByte() {
String s = URL.http().host("snow\u2603man") String s = URL.http().host("snow\u2603man")
.toUrlString(); .toUrlString();
assertEquals("http://snow%E2%98%83man", s); assertEquals("http://snow%E2%98%83man", s);
} }
@Test @Test
public void testThreePathSegments() { void testThreePathSegments() {
String s = URL.https().resolveFromHost("foo.com") String s = URL.https().resolveFromHost("foo.com")
.pathSegments("a", "b", "c") .pathSegments("a", "b", "c")
.toUrlString(); .toUrlString();
@ -202,7 +199,7 @@ public class URLBuilderTest {
} }
@Test @Test
public void testThreePathSegmentsWithQueryParams() { void testThreePathSegmentsWithQueryParams() {
String s = URL.https().resolveFromHost("foo.com") String s = URL.https().resolveFromHost("foo.com")
.pathSegments("a", "b", "c") .pathSegments("a", "b", "c")
.queryParam("foo", "bar") .queryParam("foo", "bar")
@ -211,7 +208,7 @@ public class URLBuilderTest {
} }
@Test @Test
public void testIntermingledMatrixParamsAndPathSegments() { void testIntermingledMatrixParamsAndPathSegments() {
String s = URL.http().resolveFromHost("foo.com") String s = URL.http().resolveFromHost("foo.com")
.pathSegments("seg1", "seg2") .pathSegments("seg1", "seg2")
.matrixParam("m1", "v1") .matrixParam("m1", "v1")
@ -222,7 +219,7 @@ public class URLBuilderTest {
} }
@Test @Test
public void testUseQueryParamAfterQuery() { void testUseQueryParamAfterQuery() {
String s = URL.http().resolveFromHost("foo.com") String s = URL.http().resolveFromHost("foo.com")
.query("q") .query("q")
.queryParam("foo", "bar") .queryParam("foo", "bar")
@ -231,7 +228,7 @@ public class URLBuilderTest {
} }
@Test @Test
public void testUseQueryAfterQueryParam() { void testUseQueryAfterQueryParam() {
String s = URL.http().resolveFromHost("foo.com") String s = URL.http().resolveFromHost("foo.com")
.queryParam("foo", "bar") .queryParam("foo", "bar")
.query("q") .query("q")
@ -240,7 +237,7 @@ public class URLBuilderTest {
} }
@Test @Test
public void testQueryWithNoSpecialChars() { void testQueryWithNoSpecialChars() {
String s = URL.http().resolveFromHost("foo.com") String s = URL.http().resolveFromHost("foo.com")
.query("q") .query("q")
.toUrlString(); .toUrlString();
@ -248,28 +245,28 @@ public class URLBuilderTest {
} }
@Test @Test
public void testQueryWithOkSpecialChars() { void testQueryWithOkSpecialChars() {
String s = URL.http().resolveFromHost("foo.com") String s = URL.http().resolveFromHost("foo.com")
.query("q?/&=").toUrlString(); .query("q?/&=").toUrlString();
assertEquals("http://foo.com?q?/&=", s); assertEquals("http://foo.com?q?/&=", s);
} }
@Test @Test
public void testQueryWithEscapedSpecialChars() { void testQueryWithEscapedSpecialChars() {
String s = URL.http().resolveFromHost("foo.com") String s = URL.http().resolveFromHost("foo.com")
.query("q#+").toUrlString(); .query("q#+").toUrlString();
assertEquals("http://foo.com?q%23%2B", s); assertEquals("http://foo.com?q%23%2B", s);
} }
@Test @Test
public void testNewBuilder() { void testNewBuilder() {
URL.Builder builder = URL.from("http://google.com:8008/foobar").newBuilder(); URL.Builder builder = URL.from("http://google.com:8008/foobar").newBuilder();
builder.scheme("https"); builder.scheme("https");
assertEquals("https://google.com:8008/foobar", builder.build().toString()); assertEquals("https://google.com:8008/foobar", builder.build().toString());
} }
@Test @Test
public void testUserInfo(){ void testUserInfo(){
String s = URL.http().userInfo("foo:bar").host("foo.com").toUrlString(); String s = URL.http().userInfo("foo:bar").host("foo.com").toUrlString();
assertEquals("http://foo:bar@foo.com", s); assertEquals("http://foo:bar@foo.com", s);
s = URL.http().userInfo("foo:foo:bar").host("foo.com").toUrlString(); s = URL.http().userInfo("foo:foo:bar").host("foo.com").toUrlString();

View file

@ -1,39 +1,39 @@
package org.xbib.net; package org.xbib.net;
import org.junit.Test; import org.junit.jupiter.api.Assertions;
import org.junit.jupiter.api.Test;
import static org.junit.Assert.assertEquals; import java.util.Iterator;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertNull;
/** import static org.junit.jupiter.api.Assertions.assertEquals;
* import static org.junit.jupiter.api.Assertions.assertFalse;
*/ import static org.junit.jupiter.api.Assertions.assertNotNull;
public class URLParserTest { import static org.junit.jupiter.api.Assertions.assertNull;
class URLParserTest {
@Test @Test
public void testNull() { void testNull() {
assertEquals(URL.nullUrl(), URL.from(null)); assertEquals(URL.nullUrl(), URL.from(null));
} }
@Test @Test
public void testEmpty() { void testEmpty() {
assertEquals(URL.nullUrl(), URL.from("")); assertEquals(URL.nullUrl(), URL.from(""));
} }
@Test @Test
public void testNewline() { void testNewline() {
assertEquals(URL.nullUrl(), URL.from("\n")); assertEquals(URL.nullUrl(), URL.from("\n"));
} }
@Test(expected = IllegalArgumentException.class) @Test
public void testInvalidScheme() { void testInvalidScheme() {
URL.from("/:23"); Assertions.assertThrows(IllegalArgumentException.class, () -> URL.from("/:23"));
} }
@Test @Test
public void testScheme() throws Exception { void testScheme() throws Exception {
URL url = URL.from("http://"); URL url = URL.from("http://");
assertEquals("http://", url.toExternalForm()); assertEquals("http://", url.toExternalForm());
assertEquals("http://", url.toString()); assertEquals("http://", url.toString());
@ -41,7 +41,7 @@ public class URLParserTest {
} }
@Test @Test
public void testPath(){ void testPath(){
URL url = URL.from("http"); URL url = URL.from("http");
assertFalse(url.isAbsolute()); assertFalse(url.isAbsolute());
assertNull(url.getScheme()); assertNull(url.getScheme());
@ -52,7 +52,7 @@ public class URLParserTest {
} }
@Test @Test
public void testOpaque() throws Exception { void testOpaque() throws Exception {
URL url = URL.from("a:b"); URL url = URL.from("a:b");
assertEquals("a", url.getScheme()); assertEquals("a", url.getScheme());
assertEquals("b", url.getSchemeSpecificPart()); assertEquals("b", url.getSchemeSpecificPart());
@ -62,13 +62,13 @@ public class URLParserTest {
} }
@Test @Test
public void testGopher() { void testGopher() {
URL url = URL.from("gopher:/example.com/"); URL url = URL.from("gopher:/example.com/");
assertEquals("gopher:/example.com/", url.toExternalForm()); assertEquals("gopher:/example.com/", url.toExternalForm());
} }
@Test @Test
public void testWithoutDoubleSlash() throws Exception { void testWithoutDoubleSlash() throws Exception {
URL url = URL.from("http:foo.com"); URL url = URL.from("http:foo.com");
assertEquals("http:foo.com", url.toExternalForm()); assertEquals("http:foo.com", url.toExternalForm());
assertEquals("http:foo.com", url.toString()); assertEquals("http:foo.com", url.toString());
@ -76,82 +76,82 @@ public class URLParserTest {
} }
@Test @Test
public void testSlashAfterScheme() { void testSlashAfterScheme() {
URL url = URL.from("http:/example.com/"); URL url = URL.from("http:/example.com/");
assertEquals("http:/example.com/", url.toExternalForm()); assertEquals("http:/example.com/", url.toExternalForm());
} }
@Test @Test
public void testSchemeHost() throws Exception { void testSchemeHost() throws Exception {
URL url = URL.from("http://foo.bar"); URL url = URL.from("http://foo.bar");
assertEquals("http://foo.bar", url.toString()); assertEquals("http://foo.bar", url.toString());
assertRoundTrip(url.toExternalForm()); assertRoundTrip(url.toExternalForm());
} }
@Test @Test
public void testSchemeHostPort() throws Exception { void testSchemeHostPort() throws Exception {
URL url = URL.from("http://f:/c"); URL url = URL.from("http://f:/c");
assertEquals("http://f:/c", url.toString()); assertEquals("http://f:/c", url.toString());
assertRoundTrip(url.toExternalForm()); assertRoundTrip(url.toExternalForm());
} }
@Test @Test
public void testNetworkLocation() { void testNetworkLocation() {
URL url = URL.from("//foo.bar"); URL url = URL.from("//foo.bar");
assertEquals("//foo.bar", url.toExternalForm()); assertEquals("//foo.bar", url.toExternalForm());
assertEquals("//foo.bar", url.toString()); assertEquals("//foo.bar", url.toString());
} }
@Test @Test
public void testSchemeHostAuthInfo() throws Exception { void testSchemeHostAuthInfo() throws Exception {
URL url = URL.from("http://auth@foo.bar"); URL url = URL.from("http://auth@foo.bar");
assertEquals("http://auth@foo.bar", url.toString()); assertEquals("http://auth@foo.bar", url.toString());
assertRoundTrip(url.toExternalForm()); assertRoundTrip(url.toExternalForm());
} }
@Test @Test
public void testSchemeHostAuthInfoPort() throws Exception { void testSchemeHostAuthInfoPort() throws Exception {
URL url = URL.from("http://auth@foo.bar:1"); URL url = URL.from("http://auth@foo.bar:1");
assertEquals("http://auth@foo.bar:1", url.toString()); assertEquals("http://auth@foo.bar:1", url.toString());
assertRoundTrip(url.toExternalForm()); assertRoundTrip(url.toExternalForm());
} }
@Test @Test
public void testSchemeHostAuthInfoPortPath() throws Exception { void testSchemeHostAuthInfoPortPath() throws Exception {
URL url = URL.from("http://auth@foo.bar:1/path"); URL url = URL.from("http://auth@foo.bar:1/path");
assertEquals("http://auth@foo.bar:1/path", url.toString()); assertEquals("http://auth@foo.bar:1/path", url.toString());
assertRoundTrip(url.toExternalForm()); assertRoundTrip(url.toExternalForm());
} }
@Test @Test
public void testTrailingSlash() throws Exception { void testTrailingSlash() throws Exception {
URL url = URL.from("http://foo.bar/path/"); URL url = URL.from("http://foo.bar/path/");
assertEquals("http://foo.bar/path/", url.toString()); assertEquals("http://foo.bar/path/", url.toString());
assertRoundTrip(url.toExternalForm()); assertRoundTrip(url.toExternalForm());
} }
@Test @Test
public void testBackslash() { void testBackslash() {
URL url = URL.from("http://foo.com/\\@"); URL url = URL.from("http://foo.com/\\@");
assertEquals("http://foo.com/@", url.toExternalForm()); assertEquals("http://foo.com/@", url.toExternalForm());
} }
@Test @Test
public void testQuery() throws Exception { void testQuery() throws Exception {
URL url = URL.from("http://auth@foo.bar:1/path?query"); URL url = URL.from("http://auth@foo.bar:1/path?query");
assertEquals("http://auth@foo.bar:1/path?query", url.toString()); assertEquals("http://auth@foo.bar:1/path?query", url.toString());
assertRoundTrip(url.toExternalForm()); assertRoundTrip(url.toExternalForm());
} }
@Test @Test
public void testFragment() throws Exception { void testFragment() throws Exception {
URL url = URL.from("http://auth@foo.bar:1/path#fragment"); URL url = URL.from("http://auth@foo.bar:1/path#fragment");
assertEquals("http://auth@foo.bar:1/path#fragment", url.toString()); assertEquals("http://auth@foo.bar:1/path#fragment", url.toString());
assertRoundTrip(url.toExternalForm()); assertRoundTrip(url.toExternalForm());
} }
@Test @Test
public void testReservedChar() throws Exception { void testReservedChar() throws Exception {
URL url = URL.from("http://www.google.com/ig/calculator?q=1USD=?EUR"); URL url = URL.from("http://www.google.com/ig/calculator?q=1USD=?EUR");
if ("false".equals(System.getProperty("java.net.preferIPv6Addresses"))) { if ("false".equals(System.getProperty("java.net.preferIPv6Addresses"))) {
assertEquals("http://www.google.com/ig/calculator?q=1USD%3D?EUR", url.toString()); assertEquals("http://www.google.com/ig/calculator?q=1USD%3D?EUR", url.toString());
@ -160,7 +160,7 @@ public class URLParserTest {
} }
@Test @Test
public void testPassword() throws Exception { void testPassword() throws Exception {
URL url = URL.from("ftp://aaa:b%2B1@www.google.com"); URL url = URL.from("ftp://aaa:b%2B1@www.google.com");
assertEquals("b+1", url.getPassword()); assertEquals("b+1", url.getPassword());
assertRoundTrip(url.toExternalForm()); assertRoundTrip(url.toExternalForm());
@ -170,21 +170,21 @@ public class URLParserTest {
} }
@Test @Test
public void testPlus() throws Exception { void testPlus() throws Exception {
URL url = URL.from("http://foobar:8080/test/print?value=%EA%B0%80+%EB%82%98"); URL url = URL.from("http://foobar:8080/test/print?value=%EA%B0%80+%EB%82%98");
assertEquals("http://foobar:8080/test/print?value=%EA%B0%80%2B%EB%82%98", url.toExternalForm()); assertEquals("http://foobar:8080/test/print?value=%EA%B0%80%2B%EB%82%98", url.toExternalForm());
assertRoundTrip(url.toExternalForm()); assertRoundTrip(url.toExternalForm());
} }
@Test @Test
public void testIPv6() throws Exception { void testIPv6() throws Exception {
URL url = URL.from("http://[2001:db8:85a3::8a2e:370:7334]"); URL url = URL.from("http://[2001:db8:85a3::8a2e:370:7334]");
assertEquals("http://[2001:db8:85a3:0:0:8a2e:370:7334]", url.toString()); assertEquals("http://[2001:db8:85a3:0:0:8a2e:370:7334]", url.toString());
assertRoundTrip(url.toExternalForm()); assertRoundTrip(url.toExternalForm());
} }
@Test @Test
public void testIPv6WithScope() throws Exception { void testIPv6WithScope() throws Exception {
// test scope ID. Must be a valid IPv6 // test scope ID. Must be a valid IPv6
URL url = URL.from("http://[3002:0:0:0:20c:29ff:fe64:614a%2]:8080/resource"); URL url = URL.from("http://[3002:0:0:0:20c:29ff:fe64:614a%2]:8080/resource");
assertEquals("http://[3002:0:0:0:20c:29ff:fe64:614a%2]:8080/resource", url.toString()); assertEquals("http://[3002:0:0:0:20c:29ff:fe64:614a%2]:8080/resource", url.toString());
@ -192,90 +192,90 @@ public class URLParserTest {
} }
@Test @Test
public void testIPv6WithIPv4() throws Exception { void testIPv6WithIPv4() throws Exception {
URL url = URL.from("http://[::192.168.1.1]:8080/resource"); URL url = URL.from("http://[::192.168.1.1]:8080/resource");
assertEquals("http://[0:0:0:0:0:0:c0a8:101]:8080/resource", url.toString()); assertEquals("http://[0:0:0:0:0:0:c0a8:101]:8080/resource", url.toString());
assertRoundTrip(url.toExternalForm()); assertRoundTrip(url.toExternalForm());
} }
@Test @Test
public void testFromUrlWithEverything() throws Exception { void testFromUrlWithEverything() throws Exception {
assertUrlCompatibility("https://foo.bar.com:3333/foo/ba%20r;mtx1=val1;mtx2=val%202/" assertUrlCompatibility("https://foo.bar.com:3333/foo/ba%20r;mtx1=val1;mtx2=val%202/"
+ "seg%203;m2=v2?q1=v1&q2=v%202#zomg%20it's%20a%20fragment"); + "seg%203;m2=v2?q1=v1&q2=v%202#zomg%20it's%20a%20fragment");
} }
@Test @Test
public void testFromUrlWithEmptyPath() throws Exception { void testFromUrlWithEmptyPath() throws Exception {
assertUrlCompatibility("http://foo.com"); assertUrlCompatibility("http://foo.com");
} }
@Test @Test
public void testFromUrlWithPort() throws Exception { void testFromUrlWithPort() throws Exception {
assertUrlCompatibility("http://foo.com:1234"); assertUrlCompatibility("http://foo.com:1234");
} }
@Test @Test
public void testFromUrlWithEncodedHost() throws Exception { void testFromUrlWithEncodedHost() throws Exception {
assertUrlCompatibility("http://f%20oo.com/bar"); assertUrlCompatibility("http://f%20oo.com/bar");
} }
@Test @Test
public void testFromUrlWithEncodedPathSegment() throws Exception { void testFromUrlWithEncodedPathSegment() throws Exception {
assertUrlCompatibility("http://foo.com/foo/b%20ar"); assertUrlCompatibility("http://foo.com/foo/b%20ar");
} }
@Test @Test
public void testFromUrlWithEncodedMatrixParam() throws Exception { void testFromUrlWithEncodedMatrixParam() throws Exception {
assertUrlCompatibility("http://foo.com/foo;m1=v1;m%202=v%202"); assertUrlCompatibility("http://foo.com/foo;m1=v1;m%202=v%202");
} }
@Test @Test
public void testFromUrlWithEncodedQueryParam() throws Exception { void testFromUrlWithEncodedQueryParam() throws Exception {
assertUrlCompatibility("http://foo.com/foo?q%201=v%202&q2=v2"); assertUrlCompatibility("http://foo.com/foo?q%201=v%202&q2=v2");
} }
@Test @Test
public void testFromUrlWithEncodedQueryParamDelimiter() throws Exception { void testFromUrlWithEncodedQueryParamDelimiter() throws Exception {
assertUrlCompatibility("http://foo.com/foo?q1=%3Dv1&%26q2=v2"); assertUrlCompatibility("http://foo.com/foo?q1=%3Dv1&%26q2=v2");
} }
@Test @Test
public void testFromUrlWithEncodedFragment() throws Exception { void testFromUrlWithEncodedFragment() throws Exception {
assertUrlCompatibility("http://foo.com/foo#b%20ar"); assertUrlCompatibility("http://foo.com/foo#b%20ar");
} }
@Test @Test
public void testFromUrlWithEmptyPathSegmentWithMatrixParams() throws Exception { void testFromUrlWithEmptyPathSegmentWithMatrixParams() throws Exception {
assertUrlCompatibility("http://foo.com/foo/;m1=v1"); assertUrlCompatibility("http://foo.com/foo/;m1=v1");
} }
@Test @Test
public void testFromUrlWithEmptyPathWithMatrixParams() throws Exception { void testFromUrlWithEmptyPathWithMatrixParams() throws Exception {
assertUrlCompatibility("http://foo.com/;m1=v1"); assertUrlCompatibility("http://foo.com/;m1=v1");
} }
@Test @Test
public void testFromUrlWithEmptyPathWithMultipleMatrixParams() throws Exception { void testFromUrlWithEmptyPathWithMultipleMatrixParams() throws Exception {
assertUrlCompatibility("http://foo.com/;m1=v1;m2=v2"); assertUrlCompatibility("http://foo.com/;m1=v1;m2=v2");
} }
@Test @Test
public void testFromUrlMalformedQueryParamNoValue() throws Exception { void testFromUrlMalformedQueryParamNoValue() throws Exception {
assertUrlCompatibility("http://foo.com/foo?q1=v1&q2"); assertUrlCompatibility("http://foo.com/foo?q1=v1&q2");
} }
@Test @Test
public void testFromUrlMalformedQueryParamMultiValues() throws Exception { void testFromUrlMalformedQueryParamMultiValues() throws Exception {
assertRoundTrip("http://foo.com/foo?q1=v1=v2"); assertRoundTrip("http://foo.com/foo?q1=v1=v2");
} }
@Test @Test
public void testFromUrlQueryWithEscapedChars() throws Exception { void testFromUrlQueryWithEscapedChars() throws Exception {
assertRoundTrip("http://foo.com/foo?query==&%23"); assertRoundTrip("http://foo.com/foo?query==&%23");
} }
@Test @Test
public void testSimple() throws Exception { void testSimple() throws Exception {
URL url = URL.parser().parse("http://foo.com/seg1/seg2"); URL url = URL.parser().parse("http://foo.com/seg1/seg2");
assertEquals("http", url.getScheme()); assertEquals("http", url.getScheme());
assertEquals("foo.com", url.getHostInfo()); assertEquals("foo.com", url.getHostInfo());
@ -283,7 +283,7 @@ public class URLParserTest {
} }
@Test @Test
public void testReserved() throws Exception { void testReserved() throws Exception {
URL url = URL.parser().parse("http://foo.com/seg%2F%3B%3Fment/seg=&2"); URL url = URL.parser().parse("http://foo.com/seg%2F%3B%3Fment/seg=&2");
assertEquals("http", url.getScheme()); assertEquals("http", url.getScheme());
assertEquals("foo.com", url.getHostInfo()); assertEquals("foo.com", url.getHostInfo());
@ -291,7 +291,7 @@ public class URLParserTest {
} }
@Test @Test
public void testMatrix() throws Exception { void testMatrix() throws Exception {
URL url = URL.parser().parse("http://foo.com/;foo=bar"); URL url = URL.parser().parse("http://foo.com/;foo=bar");
assertEquals("http", url.getScheme()); assertEquals("http", url.getScheme());
assertEquals("foo.com", url.getHostInfo()); assertEquals("foo.com", url.getHostInfo());
@ -299,7 +299,28 @@ public class URLParserTest {
} }
@Test @Test
public void testAnotherQuery() throws Exception { void testMatrix2() throws Exception {
URL url = URL.parser().parse("http://foo.com/some;p1=v1/path;p2=v2?q1=v3");
assertEquals("http", url.getScheme());
assertEquals("foo.com", url.getHostInfo());
assertEquals("/some;p1=v1/path;p2=v2", url.getPath());
Iterator<URL.PathSegment> iterator = url.getPathSegments().iterator();
URL.PathSegment pathSegment = iterator.next();
assertEquals("", pathSegment.getSegment());
assertEquals("[]", pathSegment.getMatrixParams().toString());
pathSegment = iterator.next();
assertEquals("some", pathSegment.getSegment());
assertEquals("p1", pathSegment.getMatrixParams().get(0).getFirst());
assertEquals("v1", pathSegment.getMatrixParams().get(0).getSecond());
pathSegment = iterator.next();
assertEquals("path", pathSegment.getSegment());
assertEquals("p2", pathSegment.getMatrixParams().get(0).getFirst());
assertEquals("v2", pathSegment.getMatrixParams().get(0).getSecond());
assertEquals("v3", url.getQueryParams().get("q1").get(0));
}
@Test
void testAnotherQuery() throws Exception {
URL url = URL.parser().parse("http://foo.com?foo=bar"); URL url = URL.parser().parse("http://foo.com?foo=bar");
assertEquals("http", url.getScheme()); assertEquals("http", url.getScheme());
assertEquals("foo.com", url.getHostInfo()); assertEquals("foo.com", url.getHostInfo());
@ -307,7 +328,7 @@ public class URLParserTest {
} }
@Test @Test
public void testQueryAndFragment() throws Exception { void testQueryAndFragment() throws Exception {
URL url = URL.parser().parse("http://foo.com?foo=bar#fragment"); URL url = URL.parser().parse("http://foo.com?foo=bar#fragment");
assertEquals("http", url.getScheme()); assertEquals("http", url.getScheme());
assertEquals("foo.com", url.getHostInfo()); assertEquals("foo.com", url.getHostInfo());
@ -316,7 +337,7 @@ public class URLParserTest {
} }
@Test @Test
public void testRelative() throws Exception { void testRelative() throws Exception {
URL url = URL.parser().parse("/foo/bar?foo=bar#fragment"); URL url = URL.parser().parse("/foo/bar?foo=bar#fragment");
assertNull(url.getScheme()); assertNull(url.getScheme());
assertEquals("", url.getHostInfo()); assertEquals("", url.getHostInfo());
@ -326,7 +347,7 @@ public class URLParserTest {
} }
@Test @Test
public void testRelativeDecoded() throws Exception { void testRelativeDecoded() throws Exception {
URL url = URL.parser().parse("/foo/bar%2F?foo=b%2Far#frag%2Fment"); URL url = URL.parser().parse("/foo/bar%2F?foo=b%2Far#frag%2Fment");
assertNull(url.getScheme()); assertNull(url.getScheme());
assertEquals("", url.getHostInfo()); assertEquals("", url.getHostInfo());
@ -336,7 +357,7 @@ public class URLParserTest {
} }
@Test @Test
public void testFileSchemeSpecificPart() throws Exception { void testFileSchemeSpecificPart() throws Exception {
URL url = URL.parser().parse("file:foo/bar?foo=bar#fragment"); URL url = URL.parser().parse("file:foo/bar?foo=bar#fragment");
assertEquals("", url.getHostInfo()); assertEquals("", url.getHostInfo());
assertNotNull(url.getSchemeSpecificPart()); assertNotNull(url.getSchemeSpecificPart());
@ -344,7 +365,7 @@ public class URLParserTest {
} }
@Test @Test
public void testRelativeFilePath() throws Exception { void testRelativeFilePath() throws Exception {
URL url = URL.parser().parse("file:/foo/bar?foo=bar#fragment"); URL url = URL.parser().parse("file:/foo/bar?foo=bar#fragment");
assertEquals("file", url.getScheme()); assertEquals("file", url.getScheme());
assertEquals("", url.getHostInfo()); assertEquals("", url.getHostInfo());
@ -354,7 +375,7 @@ public class URLParserTest {
} }
@Test @Test
public void testAbsoluteFilePath() throws Exception { void testAbsoluteFilePath() throws Exception {
URL url = URL.parser().parse("file:///foo/bar?foo=bar#fragment"); URL url = URL.parser().parse("file:///foo/bar?foo=bar#fragment");
assertEquals("file", url.getScheme()); assertEquals("file", url.getScheme());
assertEquals("", url.getHostInfo()); assertEquals("", url.getHostInfo());
@ -364,14 +385,14 @@ public class URLParserTest {
} }
@Test @Test
public void testMoreQuery() throws Exception { void testMoreQuery() throws Exception {
URL url = URL.parser().parse("http://foo.com?foo=bar%26%3D%23baz&foo=bar?/2"); URL url = URL.parser().parse("http://foo.com?foo=bar%26%3D%23baz&foo=bar?/2");
assertEquals("foo=bar%26%3D%23baz&foo=bar?/2", url.getQuery()); assertEquals("foo=bar%26%3D%23baz&foo=bar?/2", url.getQuery());
assertEquals("foo=bar&=#baz&foo=bar?/2", url.getDecodedQuery()); assertEquals("foo=bar&=#baz&foo=bar?/2", url.getDecodedQuery());
} }
@Test @Test
public void testAnotherPlus() throws Exception { void testAnotherPlus() throws Exception {
URL url = URL.parser().parse("http://foo.com/has+plus;plusMtx=pl+us?plusQp=pl%2Bus#plus+frag"); URL url = URL.parser().parse("http://foo.com/has+plus;plusMtx=pl+us?plusQp=pl%2Bus#plus+frag");
assertEquals("/has+plus;plusMtx=pl+us", url.getPath()); assertEquals("/has+plus;plusMtx=pl+us", url.getPath());
assertEquals("plusQp=pl%2Bus", url.getQuery()); assertEquals("plusQp=pl%2Bus", url.getQuery());
@ -379,7 +400,7 @@ public class URLParserTest {
} }
@Test @Test
public void testUserInfo() throws Exception { void testUserInfo() throws Exception {
URL url = URL.parser().parse("http://foo:bar@foo.com/"); URL url = URL.parser().parse("http://foo:bar@foo.com/");
assertEquals("foo:bar", url.getUserInfo()); assertEquals("foo:bar", url.getUserInfo());
url = URL.parser().parse("http://foo:foo:bar@foo.com/"); url = URL.parser().parse("http://foo:foo:bar@foo.com/");

View file

@ -1,19 +1,17 @@
package org.xbib.net; package org.xbib.net;
import org.junit.Test; import org.junit.jupiter.api.Test;
import static org.junit.Assert.assertEquals;
import java.net.URI; import java.net.URI;
import java.nio.charset.MalformedInputException; import java.nio.charset.MalformedInputException;
import java.nio.charset.UnmappableCharacterException; import java.nio.charset.UnmappableCharacterException;
/** import static org.junit.jupiter.api.Assertions.assertEquals;
*/
public class URLResolverTest { class URLResolverTest {
@Test @Test
public void testResolveURI() throws Exception { void testResolveURI() throws Exception {
URI base = URI.create("http://example.org/foo"); URI base = URI.create("http://example.org/foo");
assertEquals("http://example.org/", base.resolve("/").toString()); assertEquals("http://example.org/", base.resolve("/").toString());
assertEquals("http://example.org/foobar", base.resolve("/foobar").toString()); assertEquals("http://example.org/foobar", base.resolve("/foobar").toString());
@ -25,7 +23,7 @@ public class URLResolverTest {
} }
@Test @Test
public void testResolveURL() throws Exception { void testResolveURL() throws Exception {
URL base = URL.create("http://example.org/foo"); URL base = URL.create("http://example.org/foo");
assertEquals("http://example.org/", base.resolve("/").toString()); assertEquals("http://example.org/", base.resolve("/").toString());
assertEquals("http://example.org/foobar", base.resolve("/foobar").toString()); assertEquals("http://example.org/foobar", base.resolve("/foobar").toString());
@ -37,7 +35,7 @@ public class URLResolverTest {
} }
@Test @Test
public void testMultiResolve() throws Exception { void testMultiResolve() throws Exception {
URL base = URL.create("http://example:8080"); URL base = URL.create("http://example:8080");
String pathSpec = "foobar/"; String pathSpec = "foobar/";
String index = "index.html"; String index = "index.html";
@ -47,7 +45,7 @@ public class URLResolverTest {
} }
@Test @Test
public void testFielding() throws Exception { void testFielding() throws Exception {
// http://www.ics.uci.edu/~fielding/url/test1.html // http://www.ics.uci.edu/~fielding/url/test1.html
resolve("http://a/b/c/d;p?q", "g:h", "g:h"); resolve("http://a/b/c/d;p?q", "g:h", "g:h");
resolve("http://a/b/c/d;p?q", "g", "http://a/b/c/g"); resolve("http://a/b/c/d;p?q", "g", "http://a/b/c/g");

View file

@ -4,33 +4,30 @@ import com.fasterxml.jackson.core.JsonParser;
import com.fasterxml.jackson.databind.JsonNode; import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper; import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.ObjectReader; import com.fasterxml.jackson.databind.ObjectReader;
import org.junit.Test; import org.junit.jupiter.api.Test;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertTrue;
import static org.junit.Assert.fail;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.List; import java.util.List;
/** import static org.junit.jupiter.api.Assertions.assertEquals;
*/ import static org.junit.jupiter.api.Assertions.fail;
public class URLTest {
class URLTest {
@Test @Test
public void test() throws Exception { void test() throws Exception {
List<JsonTest> tests = readTests(fromResource("/urltestdata.json")); List<JsonTest> tests = readTests(fromResource("/urltestdata.json"));
for (JsonTest test : tests) { for (JsonTest test : tests) {
String base = test.base; String base = test.base;
String input = test.input; String input = test.input;
System.err.println("testing: " + base + " " + input + " " + test.failure); //System.err.println("testing: " + base + " " + input + " " + test.failure);
if (test.skip) { if (test.skip) {
continue; continue;
} }
if (test.failure) { if (test.failure) {
try { try {
URL url = URL.base(base).resolve(input); URL url = URL.base(base).resolve(input);
System.err.println("resolved: " + url.toString()); //System.err.println("resolved: " + url.toString());
fail(); fail();
} catch (Exception e) { } catch (Exception e) {
// pass // pass
@ -39,7 +36,7 @@ public class URLTest {
if (base != null && input != null) { if (base != null && input != null) {
try { try {
URL url = URL.base(base).resolve(input); URL url = URL.base(base).resolve(input);
System.err.println("resolved: " + url.toString()); //System.err.println("resolved: " + url.toString());
if (test.protocol != null) { if (test.protocol != null) {
assertEquals(test.protocol, url.getScheme() + ":"); assertEquals(test.protocol, url.getScheme() + ":");
} }
@ -58,9 +55,9 @@ public class URLTest {
//if (test.pathname != null && !test.pathname.isEmpty() && url.getPath() != null) { //if (test.pathname != null && !test.pathname.isEmpty() && url.getPath() != null) {
// assertEquals(test.pathname, url.getPath()); // assertEquals(test.pathname, url.getPath());
//} //}
System.err.println("passed: " + base + " " + input); //System.err.println("passed: " + base + " " + input);
} catch (URLSyntaxException e) { } catch (URLSyntaxException e) {
System.err.println("unable to resolve: " + base + " " + input + " reason: " + e.getMessage()); //System.err.println("unable to resolve: " + base + " " + input + " reason: " + e.getMessage());
} }
} }
} }

View file

@ -0,0 +1,38 @@
package org.xbib.net.body;
import org.junit.jupiter.api.Test;
import org.xbib.net.QueryParameters;
import java.nio.charset.MalformedInputException;
import java.nio.charset.UnmappableCharacterException;
import java.util.ArrayList;
import java.util.List;
import static org.junit.jupiter.api.Assertions.assertEquals;
class ParseBodyTest {
@Test
void testSimpleParse() throws MalformedInputException, UnmappableCharacterException {
QueryParameters queryParameters = new QueryParameters();
String body = "a=b&c=d&e=f";
queryParameters.addPercentEncodedBody(body);
assertEquals("b", queryParameters.get("a").get(0));
assertEquals("d", queryParameters.get("c").get(0));
assertEquals("f", queryParameters.get("e").get(0));
}
@Test
void testManyParse() throws MalformedInputException, UnmappableCharacterException {
QueryParameters queryParameters = new QueryParameters(100);
List<String> list = new ArrayList<>();
for (int i = 0; i < 200; i++) {
list.add("a" + i + "=b" + i );
}
String body = String.join("&", list);
queryParameters.addPercentEncodedBody(body);
assertEquals("b0", queryParameters.get("a0").get(0));
assertEquals("b99", queryParameters.get("a99").get(0));
assertEquals("[]", queryParameters.get("a100").toString());
}
}

View file

@ -1,42 +1,40 @@
package org.xbib.net.path; package org.xbib.net.path;
import org.junit.Test; import org.junit.jupiter.api.Test;
import org.xbib.net.URL; import org.xbib.net.URL;
import static org.junit.Assert.assertEquals;
import java.nio.charset.MalformedInputException; import java.nio.charset.MalformedInputException;
import java.nio.charset.StandardCharsets; import java.nio.charset.StandardCharsets;
import java.nio.charset.UnmappableCharacterException; import java.nio.charset.UnmappableCharacterException;
import java.util.logging.Level; import java.util.logging.Level;
import java.util.logging.Logger; import java.util.logging.Logger;
/** import static org.junit.jupiter.api.Assertions.assertEquals;
*/
public class PathDecoderTest { class PathDecoderTest {
@Test @Test
public void testPlusSign() throws Exception { void testPlusSign() throws Exception {
PathDecoder decoder = new PathDecoder("/path?a=b+c", "d=e+f", StandardCharsets.UTF_8); PathDecoder decoder = new PathDecoder("/path?a=b+c", "d=e+f", StandardCharsets.UTF_8);
assertEquals("[b c]", decoder.params().get("a").toString()); assertEquals("[b c]", decoder.params().get("a").toString());
assertEquals("[e f]", decoder.params().get("d").toString()); assertEquals("[e f]", decoder.params().get("d").toString());
} }
@Test @Test
public void testSlash() throws Exception { void testSlash() throws Exception {
PathDecoder decoder = new PathDecoder("path/foo/bar/?a=b+c", "d=e+f", StandardCharsets.UTF_8); PathDecoder decoder = new PathDecoder("path/foo/bar/?a=b+c", "d=e+f", StandardCharsets.UTF_8);
assertEquals("[b c]", decoder.params().get("a").toString()); assertEquals("[b c]", decoder.params().get("a").toString());
assertEquals("[e f]", decoder.params().get("d").toString()); assertEquals("[e f]", decoder.params().get("d").toString());
} }
@Test @Test
public void testDoubleSlashes() throws Exception { void testDoubleSlashes() throws Exception {
PathDecoder decoder = new PathDecoder("//path", "", StandardCharsets.UTF_8); PathDecoder decoder = new PathDecoder("//path", "", StandardCharsets.UTF_8);
assertEquals("/path", decoder.path()); assertEquals("/path", decoder.path());
} }
@Test @Test
public void testSlashes() throws Exception { void testSlashes() throws Exception {
PathDecoder decoder = new PathDecoder("//path?a=b+c", "d=e+f", StandardCharsets.UTF_8); PathDecoder decoder = new PathDecoder("//path?a=b+c", "d=e+f", StandardCharsets.UTF_8);
assertEquals("/path", decoder.path()); assertEquals("/path", decoder.path());
assertEquals("[b c]", decoder.params().get("a").toString()); assertEquals("[b c]", decoder.params().get("a").toString());
@ -44,7 +42,7 @@ public class PathDecoderTest {
} }
@Test @Test
public void testPlusPercent() throws Exception { void testPlusPercent() throws Exception {
PathDecoder decoder = new PathDecoder("//path?a=b%2Bc", "d=e%2Bf", StandardCharsets.UTF_8); PathDecoder decoder = new PathDecoder("//path?a=b%2Bc", "d=e%2Bf", StandardCharsets.UTF_8);
assertEquals("/path", decoder.path()); assertEquals("/path", decoder.path());
assertEquals("[b+c]", decoder.params().get("a").toString()); assertEquals("[b+c]", decoder.params().get("a").toString());
@ -52,7 +50,7 @@ public class PathDecoderTest {
} }
@Test @Test
public void decodeURL() throws MalformedInputException, UnmappableCharacterException { void decodeURL() throws MalformedInputException, UnmappableCharacterException {
String requestURI = "/pdfconverter/index.gtpl?x-fl-key=20190035592&x-fl-source=ftp://DE-465:r09t00k25@herakles.hbz-nrw.de/fl/upload/20190035592/20190035592.pdf&x-fl-target=ftp://DE-1073:haribo%2B1@herakles.hbz-nrw.de/fl/download/20190035592/Fernleihe_Kopienlieferung_null_FB201900373_BLQDMT62_20190035592_20190035592.pdf&x-fl-copy=&x-fl-ack=https://fl.hbz-nrw.de/app/ack/index.gtpl&x-fl-pages=1-"; String requestURI = "/pdfconverter/index.gtpl?x-fl-key=20190035592&x-fl-source=ftp://DE-465:r09t00k25@herakles.hbz-nrw.de/fl/upload/20190035592/20190035592.pdf&x-fl-target=ftp://DE-1073:haribo%2B1@herakles.hbz-nrw.de/fl/download/20190035592/Fernleihe_Kopienlieferung_null_FB201900373_BLQDMT62_20190035592_20190035592.pdf&x-fl-copy=&x-fl-ack=https://fl.hbz-nrw.de/app/ack/index.gtpl&x-fl-pages=1-";
URL url = URL.builder().path(requestURI).build(); URL url = URL.builder().path(requestURI).build();
log.log(Level.INFO, "URL: url=" + url + " path=" + url.getPath() + " query=" + url.getQuery() + log.log(Level.INFO, "URL: url=" + url + " path=" + url.getPath() + " query=" + url.getQuery() +

View file

@ -1,31 +1,27 @@
package org.xbib.net.path; package org.xbib.net.path;
import org.junit.Rule; import org.junit.jupiter.api.Assertions;
import org.junit.Test; import org.junit.jupiter.api.Test;
import org.junit.rules.ExpectedException;
import org.xbib.net.QueryParameters; import org.xbib.net.QueryParameters;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertNull;
import static org.junit.Assert.assertTrue;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.Collections; import java.util.Collections;
import java.util.Comparator; import java.util.Comparator;
import java.util.List; import java.util.List;
import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.junit.jupiter.api.Assertions.assertFalse;
import static org.junit.jupiter.api.Assertions.assertNull;
import static org.junit.jupiter.api.Assertions.assertTrue;
/** /**
*/ */
public class PathMatcherTest { class PathMatcherTest {
private PathMatcher pathMatcher = new PathMatcher(); private PathMatcher pathMatcher = new PathMatcher();
@Rule
public final ExpectedException exception = ExpectedException.none();
@Test @Test
public void match() { void match() {
// test exact matching // test exact matching
assertTrue(pathMatcher.match("test", "test")); assertTrue(pathMatcher.match("test", "test"));
assertTrue(pathMatcher.match("/test", "/test")); assertTrue(pathMatcher.match("/test", "/test"));
@ -110,7 +106,7 @@ public class PathMatcherTest {
} }
@Test @Test
public void withMatchStart() { void withMatchStart() {
// test exact matching // test exact matching
assertTrue(pathMatcher.matchStart("test", "test")); assertTrue(pathMatcher.matchStart("test", "test"));
assertTrue(pathMatcher.matchStart("/test", "/test")); assertTrue(pathMatcher.matchStart("/test", "/test"));
@ -197,7 +193,7 @@ public class PathMatcherTest {
} }
@Test @Test
public void uniqueDeliminator() { void uniqueDeliminator() {
pathMatcher.setPathSeparator("."); pathMatcher.setPathSeparator(".");
// test exact matching // test exact matching
@ -259,7 +255,7 @@ public class PathMatcherTest {
} }
@Test @Test
public void extractPathWithinPattern() throws Exception { void extractPathWithinPattern() throws Exception {
assertEquals("", assertEquals("",
pathMatcher.extractPathWithinPattern("/docs/commit.html", "/docs/commit.html")); pathMatcher.extractPathWithinPattern("/docs/commit.html", "/docs/commit.html"));
@ -303,7 +299,7 @@ public class PathMatcherTest {
} }
@Test @Test
public void extractUriTemplateVariables() throws Exception { void extractUriTemplateVariables() throws Exception {
QueryParameters result = pathMatcher.extractUriTemplateVariables("/hotels/{hotel}", "/hotels/1"); QueryParameters result = pathMatcher.extractUriTemplateVariables("/hotels/{hotel}", "/hotels/1");
assertEquals("[hotel:1]", result.toString()); assertEquals("[hotel:1]", result.toString());
result = pathMatcher.extractUriTemplateVariables("/h?tels/{hotel}", "/hotels/1"); result = pathMatcher.extractUriTemplateVariables("/h?tels/{hotel}", "/hotels/1");
@ -323,7 +319,7 @@ public class PathMatcherTest {
} }
@Test @Test
public void extractUriTemplateVariablesRegex() { void extractUriTemplateVariablesRegex() {
QueryParameters result = pathMatcher QueryParameters result = pathMatcher
.extractUriTemplateVariables("{symbolicName:[\\w\\.]+}-{version:[\\w\\.]+}.jar", .extractUriTemplateVariables("{symbolicName:[\\w\\.]+}-{version:[\\w\\.]+}.jar",
"com.example-1.0.0.jar"); "com.example-1.0.0.jar");
@ -337,7 +333,7 @@ public class PathMatcherTest {
} }
@Test @Test
public void extractUriTemplateVarsRegexQualifiers() { void extractUriTemplateVarsRegexQualifiers() {
QueryParameters result = pathMatcher.extractUriTemplateVariables( QueryParameters result = pathMatcher.extractUriTemplateVariables(
"{symbolicName:[\\p{L}\\.]+}-sources-{version:[\\p{N}\\.]+}.jar", "{symbolicName:[\\p{L}\\.]+}-sources-{version:[\\p{N}\\.]+}.jar",
"com.example-sources-1.0.0.jar"); "com.example-sources-1.0.0.jar");
@ -359,14 +355,14 @@ public class PathMatcherTest {
} }
@Test @Test
public void extractUriTemplateVarsRegexCapturingGroups() { void extractUriTemplateVarsRegexCapturingGroups() {
exception.expect(IllegalArgumentException.class); Assertions.assertThrows(IllegalArgumentException.class, () -> {
//exception.expectMessage(containsString("The number of capturing groups in the pattern"))
pathMatcher.extractUriTemplateVariables("/web/{id:foo(bar)?}", "/web/foobar"); pathMatcher.extractUriTemplateVariables("/web/{id:foo(bar)?}", "/web/foobar");
});
} }
@Test @Test
public void combine() { void combine() {
assertEquals("", pathMatcher.combine(null, null)); assertEquals("", pathMatcher.combine(null, null));
assertEquals("/hotels", pathMatcher.combine("/hotels", null)); assertEquals("/hotels", pathMatcher.combine("/hotels", null));
assertEquals("/hotels", pathMatcher.combine(null, "/hotels")); assertEquals("/hotels", pathMatcher.combine(null, "/hotels"));
@ -397,13 +393,14 @@ public class PathMatcherTest {
} }
@Test @Test
public void combineWithTwoFileExtensionPatterns() { void combineWithTwoFileExtensionPatterns() {
exception.expect(IllegalArgumentException.class); Assertions.assertThrows(IllegalArgumentException.class, () ->{
pathMatcher.combine("/*.html", "/*.txt"); pathMatcher.combine("/*.html", "/*.txt");
});
} }
@Test @Test
public void patternComparator() { void patternComparator() {
Comparator<String> comparator = pathMatcher.getPatternComparator("/hotels/new"); Comparator<String> comparator = pathMatcher.getPatternComparator("/hotels/new");
assertEquals(0, comparator.compare(null, null)); assertEquals(0, comparator.compare(null, null));
@ -451,7 +448,7 @@ public class PathMatcherTest {
} }
@Test @Test
public void patternComparatorSort() { void patternComparatorSort() {
Comparator<String> comparator = pathMatcher.getPatternComparator("/hotels/new"); Comparator<String> comparator = pathMatcher.getPatternComparator("/hotels/new");
List<String> paths = new ArrayList<>(3); List<String> paths = new ArrayList<>(3);
paths.add(null); paths.add(null);
@ -546,7 +543,7 @@ public class PathMatcherTest {
} }
@Test @Test
public void trimTokensOff() { void trimTokensOff() {
pathMatcher.setTrimTokens(false); pathMatcher.setTrimTokens(false);
assertTrue(pathMatcher.match("/group/{groupName}/members", "/group/sales/members")); assertTrue(pathMatcher.match("/group/{groupName}/members", "/group/sales/members"));
assertTrue(pathMatcher.match("/group/{groupName}/members", "/group/ sales/members")); assertTrue(pathMatcher.match("/group/{groupName}/members", "/group/ sales/members"));
@ -554,7 +551,7 @@ public class PathMatcherTest {
} }
@Test @Test
public void caseInsensitive() { void caseInsensitive() {
pathMatcher.setCaseSensitive(false); pathMatcher.setCaseSensitive(false);
assertTrue(pathMatcher.match("/group/{groupName}/members", "/group/sales/members")); assertTrue(pathMatcher.match("/group/{groupName}/members", "/group/sales/members"));
assertTrue(pathMatcher.match("/group/{groupName}/members", "/Group/Sales/Members")); assertTrue(pathMatcher.match("/group/{groupName}/members", "/Group/Sales/Members"));
@ -562,10 +559,9 @@ public class PathMatcherTest {
} }
@Test @Test
public void extensionMappingWithDotPathSeparator() { void extensionMappingWithDotPathSeparator() {
pathMatcher.setPathSeparator("."); pathMatcher.setPathSeparator(".");
assertEquals("Extension mapping should be disabled with \".\" as path separator", assertEquals("/*.html.hotel.*", pathMatcher.combine("/*.html", "hotel.*"));
"/*.html.hotel.*", pathMatcher.combine("/*.html", "hotel.*"));
} }
} }

View file

@ -1,73 +1,69 @@
package org.xbib.net.path; package org.xbib.net.path;
import org.junit.Test; import org.junit.jupiter.api.Test;
import static org.junit.Assert.assertEquals; import static org.junit.jupiter.api.Assertions.assertEquals;
/** class PathNormalizerTest {
*
*/
public class PathNormalizerTest {
@Test @Test
public void normalizeNullPath() { void normalizeNullPath() {
assertEquals("/", PathNormalizer.normalize(null)); assertEquals("/", PathNormalizer.normalize(null));
} }
@Test @Test
public void normalizeEmptyPath() { void normalizeEmptyPath() {
assertEquals("/", PathNormalizer.normalize("")); assertEquals("/", PathNormalizer.normalize(""));
} }
@Test @Test
public void normalizeSlashPath() { void normalizeSlashPath() {
assertEquals("/", PathNormalizer.normalize("/")); assertEquals("/", PathNormalizer.normalize("/"));
} }
@Test @Test
public void normalizeDoubleSlashPath() { void normalizeDoubleSlashPath() {
assertEquals("/", PathNormalizer.normalize("//")); assertEquals("/", PathNormalizer.normalize("//"));
} }
@Test @Test
public void normalizeTripleSlashPath() { void normalizeTripleSlashPath() {
assertEquals("/", PathNormalizer.normalize("///")); assertEquals("/", PathNormalizer.normalize("///"));
} }
@Test @Test
public void normalizePathWithPoint() { void normalizePathWithPoint() {
assertEquals("/", PathNormalizer.normalize("/.")); assertEquals("/", PathNormalizer.normalize("/."));
} }
@Test @Test
public void normalizePathWithPointAndElement() { void normalizePathWithPointAndElement() {
assertEquals("/a", PathNormalizer.normalize("/./a")); assertEquals("/a", PathNormalizer.normalize("/./a"));
} }
@Test @Test
public void normalizePathWithTwoPointsAndElement() { void normalizePathWithTwoPointsAndElement() {
assertEquals("/a", PathNormalizer.normalize("/././a")); assertEquals("/a", PathNormalizer.normalize("/././a"));
} }
@Test @Test
public void normalizePathWithDoublePoint() { void normalizePathWithDoublePoint() {
assertEquals("/", PathNormalizer.normalize("/..")); assertEquals("/", PathNormalizer.normalize("/.."));
assertEquals("/", PathNormalizer.normalize("/../..")); assertEquals("/", PathNormalizer.normalize("/../.."));
assertEquals("/", PathNormalizer.normalize("/../../..")); assertEquals("/", PathNormalizer.normalize("/../../.."));
} }
@Test @Test
public void normalizePathWithFirstElementAndDoublePoint() { void normalizePathWithFirstElementAndDoublePoint() {
assertEquals("/", PathNormalizer.normalize("/a/..")); assertEquals("/", PathNormalizer.normalize("/a/.."));
assertEquals("/", PathNormalizer.normalize("/a/../..")); assertEquals("/", PathNormalizer.normalize("/a/../.."));
assertEquals("/", PathNormalizer.normalize("/a/../../..")); assertEquals("/", PathNormalizer.normalize("/a/../../.."));
} }
@Test @Test
public void normalizePathWithTwoElementsAndDoublePoint() { void normalizePathWithTwoElementsAndDoublePoint() {
assertEquals("/b", PathNormalizer.normalize("/a/../b")); assertEquals("/b", PathNormalizer.normalize("/a/../b"));
assertEquals("/b", PathNormalizer.normalize("/a/../../b")); assertEquals("/b", PathNormalizer.normalize("/a/../../b"));
assertEquals("/b", PathNormalizer.normalize("/a/../../../b")); assertEquals("/b", PathNormalizer.normalize("/a/../../../b"));
} }
} }

View file

@ -0,0 +1,277 @@
package org.xbib.net.path;
import org.junit.jupiter.api.Disabled;
import org.junit.jupiter.api.Test;
import java.util.Collections;
import java.util.Map;
import static org.hamcrest.MatcherAssert.assertThat;
import static org.hamcrest.Matchers.notNullValue;
import static org.hamcrest.Matchers.nullValue;
import static org.hamcrest.Matchers.is;
import static org.junit.jupiter.api.Assertions.fail;
class PathTrieTest {
@Test
void example() {
PathTrie<Integer> trie = PathTrie.<Integer>builder()
.add("GET", "/static/{file}", 1234)
.add("HEAD", "/static/{file}", 1234)
.build();
assertSuccessfulResolution(trie, "GET", "/static/test.txt", 1234, Map.of("file", "test.txt"));
}
@Test
void simple() {
PathTrie<Integer> trie = PathTrie.<Integer>builder()
.add("GET", "explorer", 1234)
.build();
assertSuccessfulGetResolution(trie, "explorer", 1234);
assertFailedGetResolution(trie, "PUT", "explorer");
assertFailedGetResolution(trie, "");
assertFailedGetResolution(trie, "test");
}
@Test
void sharedPrefix() {
PathTrie<Integer> trie = PathTrie.<Integer>builder()
.add("GET", "discovery/v1/rest", 1234)
.add("GET", "discovery/v2/rest", 4321)
.build();
assertSuccessfulGetResolution(trie, "discovery/v1/rest", 1234);
assertSuccessfulGetResolution(trie, "discovery/v2/rest", 4321);
assertFailedGetResolution(trie, "");
assertFailedGetResolution(trie, "discovery");
assertFailedGetResolution(trie, "discovery/v1");
}
@Test
void prefix() {
PathTrie<Integer> trie = PathTrie.<Integer>builder()
.add("GET", "discovery", 1234)
.add("GET", "discovery/v1", 4321)
.build();
assertSuccessfulGetResolution(trie, "discovery", 1234);
assertSuccessfulGetResolution(trie, "discovery/v1", 4321);
assertFailedGetResolution(trie, "");
}
@Test
void parameter() {
PathTrie<Integer> trie = PathTrie.<Integer>builder()
.add("GET", "discovery/{version}/rest", 1234)
.build();
assertSuccessfulGetResolution(
trie, "discovery/v1/rest", 1234, Map.of("version", "v1"));
}
@Test
void multipleParameters() {
PathTrie<Integer> trie = PathTrie.<Integer>builder()
.add("GET", "discovery/{discovery_version}/apis/{api}/{format}", 1234)
.build();
assertSuccessfulGetResolution(trie, "discovery/v1/apis/test/rest", 1234,
Map.of("discovery_version", "v1", "api", "test", "format", "rest"));
}
@Test
void sharedParameterPrefix() {
PathTrie<Integer> trie = PathTrie.<Integer>builder()
.add("GET", "discovery/{version}/rest", 1234)
.add("GET", "discovery/{version}/rpc", 4321)
.build();
assertSuccessfulGetResolution(
trie, "discovery/v1/rest", 1234, Map.of("version", "v1"));
assertSuccessfulGetResolution(
trie, "discovery/v1/rpc", 4321, Map.of("version", "v1"));
}
@Disabled
@Test
void encodedParameter() {
PathTrie<Integer> trie = PathTrie.<Integer>builder()
.add("GET", "{value}", 1234)
.build();
assertSuccessfulGetResolution(
trie, "%E4%B8%AD%E6%96%87", 1234, Map.of("value", "中文"));
}
@Test
void testResolveParameterAfterLiteral() {
PathTrie<Integer> trie = PathTrie.<Integer>builder()
.add("GET", "{one}/three", 1234)
.add("GET", "one/two", 4321)
.build();
assertSuccessfulGetResolution(trie, "one/three", 1234, Map.of("one", "one"));
assertSuccessfulGetResolution(trie, "one/two", 4321);
}
@Test
void testResolveBacktrack() {
PathTrie<Integer> trie = PathTrie.<Integer>builder()
.add("GET", "{one}/{two}/three/{four}", 1234)
.add("GET", "one/two/{three}/four", 4321)
.build();
assertSuccessfulGetResolution(trie, "one/two/three/five", 1234,
Map.of("one", "one", "two", "two", "four", "five"));
assertSuccessfulGetResolution(
trie, "one/two/three/four", 4321, Map.of("three", "three"));
}
@Test
void pathMethodsWithDifferentParameterNames() {
PathTrie<Integer> trie = PathTrie.<Integer>builder()
.add("GET", "test/{one}", 1234)
.add("PUT", "test/{two}", 4321)
.build();
assertSuccessfulResolution(
trie, "GET", "test/foo", 1234, Map.of("one", "foo"));
assertSuccessfulResolution(
trie, "PUT", "test/foo", 4321, Map.of("two", "foo"));
}
@Test
void duplicatePath() {
doStrictDuplicateTest("test/path", "test/path");
}
@Test
void duplicateParameterizedPath() {
doStrictDuplicateTest("test/{param}/path", "test/{parameterized}/path");
}
@Test
void laxDuplicatePath() {
PathTrie<Integer> trie = PathTrie.<Integer>builder(false)
.add("GET", "test/{one}", 1234)
.add("GET", "test/{two}", 4321)
.build();
PathTrie.Result<Integer> result = trie.resolve("GET", "test/foo");
// We don't care which result is returned as long as it is a valid one.
if (result.getRawParameters().containsKey("one")) {
assertThat(result.getResult(), is(1234));
assertThat(result.getRawParameters().get("one"), is("foo"));
} else {
assertThat(result.getResult(), is(4321));
assertThat(result.getRawParameters().get("two"), is("foo"));
}
}
@Test
void builderNullPath() {
try {
PathTrie.builder().add("GET", null, 1234);
fail("expected NullPointerException");
} catch (NullPointerException e) {
// expected
}
}
@Test
void builderNullValue() {
try {
PathTrie.builder().add("GET", "throws/an/exception", null);
fail("expected NullPointerException");
} catch (NullPointerException e) {
// expected
}
}
@Test
void resolveNullPath() {
try {
PathTrie<Integer> trie = PathTrie.<Integer>builder().build();
trie.resolve("GET", null);
fail("expected NullPointerException");
} catch (NullPointerException e) {
// expected
}
}
@Test
void invalidParameterName() {
try {
PathTrie.builder().add("GET", "bad/{[test}", 1234);
fail("expected IllegalArgumentException");
} catch (IllegalArgumentException e) {
// expected
}
}
@Test
void invalidPathParameterSyntax() {
try {
PathTrie.builder().add("GET", "bad/{test", 1234);
fail("expected IllegalArgumentException");
} catch (IllegalArgumentException e) {
// expected
}
}
@Test
void invalidParameterSegment() {
String invalids = "?#[]{}";
for (char c : invalids.toCharArray()) {
try {
PathTrie.builder().add("GET", "bad/" + c, 1234);
fail("expected IllegalArgumentException");
} catch (IllegalArgumentException e) {
// expected
}
}
}
private void doStrictDuplicateTest(String path, String duplicatePath) {
try {
PathTrie.builder()
.add("GET", path, 1234)
.add("GET", duplicatePath, 4321);
fail("expected IllegalArgumentException");
} catch (IllegalArgumentException e) {
// expected
}
}
private void assertSuccessfulGetResolution(PathTrie<Integer> trie, String path, Integer value) {
assertSuccessfulResolution(trie, "GET", path, value);
}
private void assertSuccessfulResolution(PathTrie<Integer> trie, String method, String path, Integer value) {
assertSuccessfulResolution(trie, method, path, value, Collections.emptyMap());
}
private void assertSuccessfulGetResolution(PathTrie<Integer> trie, String path, Integer value,
Map<String, String> rawParameters) {
assertSuccessfulResolution(trie, "GET", path, value, rawParameters);
}
private void assertSuccessfulResolution(PathTrie<Integer> trie, String method, String path, Integer value,
Map<String, String> rawParameters) {
PathTrie.Result<Integer> result = trie.resolve(method, path);
assertThat(result, notNullValue());
assertThat(result.getResult(), is(value));
assertThat(result.getRawParameters(), is(rawParameters));
}
private void assertFailedGetResolution(PathTrie<Integer> trie, String path) {
assertFailedGetResolution(trie, "GET", path);
}
private void assertFailedGetResolution(PathTrie<Integer> trie, String method, String path) {
assertThat(trie.resolve(method, path), nullValue());
}
}

View file

@ -4,7 +4,8 @@ import com.fasterxml.jackson.core.JsonParser;
import com.fasterxml.jackson.databind.JsonNode; import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper; import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.ObjectReader; import com.fasterxml.jackson.databind.ObjectReader;
import org.junit.Test;
import org.junit.jupiter.api.Test;
import org.xbib.net.template.expression.ExpressionType; import org.xbib.net.template.expression.ExpressionType;
import org.xbib.net.template.expression.TemplateExpression; import org.xbib.net.template.expression.TemplateExpression;
import org.xbib.net.template.expression.URITemplateExpression; import org.xbib.net.template.expression.URITemplateExpression;
@ -23,11 +24,11 @@ import org.xbib.net.template.vars.values.NullValue;
import org.xbib.net.template.vars.values.ScalarValue; import org.xbib.net.template.vars.values.ScalarValue;
import org.xbib.net.template.vars.values.VariableValue; import org.xbib.net.template.vars.values.VariableValue;
import static org.junit.Assert.assertEquals; import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.junit.Assert.assertFalse; import static org.junit.jupiter.api.Assertions.assertFalse;
import static org.junit.Assert.assertSame; import static org.junit.jupiter.api.Assertions.assertSame;
import static org.junit.Assert.assertTrue; import static org.junit.jupiter.api.Assertions.assertTrue;
import static org.junit.Assert.fail; import static org.junit.jupiter.api.Assertions.fail;
import java.nio.CharBuffer; import java.nio.CharBuffer;
import java.util.ArrayList; import java.util.ArrayList;
@ -38,12 +39,10 @@ import java.util.Iterator;
import java.util.List; import java.util.List;
import java.util.Map; import java.util.Map;
/** class URITemplateTest {
*/
public class URITemplateTest {
@Test @Test
public void simpleTest() { void simpleTest() {
String[] strings = new String[]{ String[] strings = new String[]{
"foo", "%33foo", "foo%20", "foo_%20bar", "FoOb%02ZAZE287", "foo.bar", "foo_%20bar.baz%af.r" "foo", "%33foo", "foo%20", "foo_%20bar", "FoOb%02ZAZE287", "foo.bar", "foo_%20bar.baz%af.r"
}; };
@ -57,7 +56,7 @@ public class URITemplateTest {
} }
@Test @Test
public void invalidTest() { void invalidTest() {
String[] strings = new String[]{"", "%", "foo..bar", ".", "foo%ra", "foo%ar"}; String[] strings = new String[]{"", "%", "foo..bar", ".", "foo%ra", "foo%ar"};
for (String s : strings) { for (String s : strings) {
try { try {
@ -71,7 +70,7 @@ public class URITemplateTest {
} }
@Test @Test
public void literalTest() { void literalTest() {
Variables vars = Variables.builder().build(); Variables vars = Variables.builder().build();
String[] strings = new String[]{"foo", "%23foo", "%23foo%24", "foo%24", "f%c4oo", "http://slashdot.org", String[] strings = new String[]{"foo", "%23foo", "%23foo%24", "foo%24", "f%c4oo", "http://slashdot.org",
"x?y=e", "urn:d:ze:/oize#/e/e", "ftp://ftp.foo.com/ee/z?a=b#e/dz", "x?y=e", "urn:d:ze:/oize#/e/e", "ftp://ftp.foo.com/ee/z?a=b#e/dz",
@ -85,7 +84,7 @@ public class URITemplateTest {
} }
@Test @Test
public void parsingEmptyInputGivesEmptyList() { void parsingEmptyInputGivesEmptyList() {
CharBuffer buffer = CharBuffer.wrap("").asReadOnlyBuffer(); CharBuffer buffer = CharBuffer.wrap("").asReadOnlyBuffer();
List<URITemplateExpression> list = URITemplateParser.parse(buffer); List<URITemplateExpression> list = URITemplateParser.parse(buffer);
assertTrue(list.isEmpty()); assertTrue(list.isEmpty());
@ -94,7 +93,7 @@ public class URITemplateTest {
@Test @Test
@SuppressWarnings("unchecked") @SuppressWarnings("unchecked")
public void parseExpressions() { void parseExpressions() {
List<Object[]> list = new ArrayList<>(); List<Object[]> list = new ArrayList<>();
String input; String input;
ExpressionType type; ExpressionType type;
@ -130,7 +129,7 @@ public class URITemplateTest {
} }
@Test @Test
public void parseInvalidExpressions() { void parseInvalidExpressions() {
try { try {
CharBuffer buffer = CharBuffer.wrap("{foo").asReadOnlyBuffer(); CharBuffer buffer = CharBuffer.wrap("{foo").asReadOnlyBuffer();
new ExpressionParser().parse(buffer); new ExpressionParser().parse(buffer);
@ -148,7 +147,7 @@ public class URITemplateTest {
} }
@Test @Test
public void parsePrefixes() { void parsePrefixes() {
String[] strings = new String[]{"foo:323", "%33foo:323", "foo%20:323", "foo_%20bar:323", "FoOb%02ZAZE287:323", String[] strings = new String[]{"foo:323", "%33foo:323", "foo%20:323", "foo_%20bar:323", "FoOb%02ZAZE287:323",
"foo.bar:323", "foo_%20bar.baz%af.r:323"}; "foo.bar:323", "foo_%20bar.baz%af.r:323"};
for (String s : strings) { for (String s : strings) {
@ -161,7 +160,7 @@ public class URITemplateTest {
} }
@Test @Test
public void parseInvalidPrefixes() { void parseInvalidPrefixes() {
String[] strings = new String[]{"foo:", "foo:-1", "foo:a", "foo:10001", "foo:2147483648"}; String[] strings = new String[]{"foo:", "foo:-1", "foo:a", "foo:10001", "foo:2147483648"};
for (String s : strings) { for (String s : strings) {
try { try {
@ -174,7 +173,7 @@ public class URITemplateTest {
} }
@Test @Test
public void parseExploded() { void parseExploded() {
String[] strings = new String[]{"foo*", "%33foo*", "foo%20*", "foo_%20bar*", "FoOb%02ZAZE287*", "foo.bar*", String[] strings = new String[]{"foo*", "%33foo*", "foo%20*", "foo_%20bar*", "FoOb%02ZAZE287*", "foo.bar*",
"foo_%20bar.baz%af.r*"}; "foo_%20bar.baz%af.r*"};
for (String s : strings) { for (String s : strings) {
@ -187,7 +186,7 @@ public class URITemplateTest {
} }
@Test @Test
public void parseExceptions() { void parseExceptions() {
String[] strings = new String[]{"foo%", "foo%r", "foo%ra", "foo%ar", "foo<", "foo{"}; String[] strings = new String[]{"foo%", "foo%r", "foo%ra", "foo%ar", "foo<", "foo{"};
for (String s : strings) { for (String s : strings) {
try { try {
@ -200,7 +199,7 @@ public class URITemplateTest {
} }
@Test @Test
public void testExamples() throws Exception { void testExamples() throws Exception {
JsonNode data = fromResource("/spec-examples.json"); JsonNode data = fromResource("/spec-examples.json");
List<Map<String, Object>> list = new ArrayList<>(); List<Map<String, Object>> list = new ArrayList<>();
for (JsonNode node : data) { for (JsonNode node : data) {
@ -240,7 +239,7 @@ public class URITemplateTest {
} }
@Test @Test
public void testExamplesBySection() throws Exception { void testExamplesBySection() throws Exception {
JsonNode data = fromResource("/spec-examples-by-section.json"); JsonNode data = fromResource("/spec-examples-by-section.json");
List<Map<String, Object>> list = new ArrayList<>(); List<Map<String, Object>> list = new ArrayList<>();
for (JsonNode node : data) { for (JsonNode node : data) {
@ -280,7 +279,7 @@ public class URITemplateTest {
} }
@Test @Test
public void extendedTests() throws Exception { void extendedTests() throws Exception {
JsonNode data = fromResource("/extended-tests.json"); JsonNode data = fromResource("/extended-tests.json");
List<Map<String, Object>> list = new ArrayList<>(); List<Map<String, Object>> list = new ArrayList<>();
for (JsonNode node : data) { for (JsonNode node : data) {
@ -320,7 +319,7 @@ public class URITemplateTest {
} }
@Test @Test
public void negativeTests() throws Exception { void negativeTests() throws Exception {
JsonNode data = fromResource("/negative-tests.json"); JsonNode data = fromResource("/negative-tests.json");
JsonNode node = data.get("Failure Tests").get("variables"); JsonNode node = data.get("Failure Tests").get("variables");
Variables.Builder builder = Variables.builder(); Variables.Builder builder = Variables.builder();
@ -347,7 +346,7 @@ public class URITemplateTest {
} }
@Test @Test
public void expansionTest() throws Exception { void expansionTest() throws Exception {
String[] strings = new String[]{"/rfcExamples.json", "/strings.json", "/multipleStrings.json", String[] strings = new String[]{"/rfcExamples.json", "/strings.json", "/multipleStrings.json",
"/lists.json", "/multipleLists.json"}; "/lists.json", "/multipleLists.json"};
for (String s : strings) { for (String s : strings) {