Use the new URL encode/decode methods introduced in Java 10 (#1196)

* Use Java 10 URLDecoder/URLEncoder methods

* Simplify compatParseMap
This commit is contained in:
Isira Seneviratne 2024-07-21 19:45:28 +05:30 committed by GitHub
parent 592f1596e6
commit 9a29f9ee2d
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
14 changed files with 69 additions and 150 deletions

View File

@ -21,7 +21,7 @@ If you're using Gradle, you could add NewPipe Extractor as a dependency with the
-dontwarn org.mozilla.javascript.tools.** -dontwarn org.mozilla.javascript.tools.**
``` ```
**Note:** To use NewPipe Extractor in Android projects with a `minSdk` below 26, [API desugaring](https://developer.android.com/studio/write/java8-support#library-desugaring) is required. If the `minSdk` is below 19, the `desugar_jdk_libs_nio` artifact is required, which requires Android Gradle Plugin (AGP) version 7.4.0. **Note:** To use NewPipe Extractor in Android projects with a `minSdk` below 33, [core library desugaring](https://developer.android.com/studio/write/java8-support#library-desugaring) with the `desugar_jdk_libs_nio` artifact is required.
### Testing changes ### Testing changes

View File

@ -8,7 +8,6 @@ import org.schabi.newpipe.extractor.exceptions.ParsingException;
import org.schabi.newpipe.extractor.linkhandler.SearchQueryHandlerFactory; import org.schabi.newpipe.extractor.linkhandler.SearchQueryHandlerFactory;
import org.schabi.newpipe.extractor.utils.Utils; import org.schabi.newpipe.extractor.utils.Utils;
import java.io.UnsupportedEncodingException;
import java.util.List; import java.util.List;
public final class BandcampSearchQueryHandlerFactory extends SearchQueryHandlerFactory { public final class BandcampSearchQueryHandlerFactory extends SearchQueryHandlerFactory {
@ -28,10 +27,6 @@ public final class BandcampSearchQueryHandlerFactory extends SearchQueryHandlerF
final List<String> contentFilter, final List<String> contentFilter,
final String sortFilter) final String sortFilter)
throws ParsingException, UnsupportedOperationException { throws ParsingException, UnsupportedOperationException {
try { return BASE_URL + "/search?q=" + Utils.encodeUrlUtf8(query) + "&page=1";
return BASE_URL + "/search?q=" + Utils.encodeUrlUtf8(query) + "&page=1";
} catch (final UnsupportedEncodingException e) {
throw new ParsingException("query \"" + query + "\" could not be encoded", e);
}
} }
} }

View File

@ -4,7 +4,6 @@ import org.schabi.newpipe.extractor.exceptions.ParsingException;
import org.schabi.newpipe.extractor.linkhandler.SearchQueryHandlerFactory; import org.schabi.newpipe.extractor.linkhandler.SearchQueryHandlerFactory;
import org.schabi.newpipe.extractor.utils.Utils; import org.schabi.newpipe.extractor.utils.Utils;
import java.io.UnsupportedEncodingException;
import java.util.List; import java.util.List;
public final class MediaCCCSearchQueryHandlerFactory extends SearchQueryHandlerFactory { public final class MediaCCCSearchQueryHandlerFactory extends SearchQueryHandlerFactory {
@ -42,10 +41,6 @@ public final class MediaCCCSearchQueryHandlerFactory extends SearchQueryHandlerF
final List<String> contentFilter, final List<String> contentFilter,
final String sortFilter) final String sortFilter)
throws ParsingException, UnsupportedOperationException { throws ParsingException, UnsupportedOperationException {
try { return "https://media.ccc.de/public/events/search?q=" + Utils.encodeUrlUtf8(query);
return "https://media.ccc.de/public/events/search?q=" + Utils.encodeUrlUtf8(query);
} catch (final UnsupportedEncodingException e) {
throw new ParsingException("Could not create search string with query: " + query, e);
}
} }
} }

View File

@ -38,7 +38,6 @@ import org.schabi.newpipe.extractor.utils.JsonUtils;
import org.schabi.newpipe.extractor.utils.Utils; import org.schabi.newpipe.extractor.utils.Utils;
import java.io.IOException; import java.io.IOException;
import java.io.UnsupportedEncodingException;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.Collections; import java.util.Collections;
import java.util.List; import java.util.List;
@ -379,8 +378,7 @@ public class PeertubeStreamExtractor extends StreamExtractor {
} }
@Nonnull @Nonnull
private String getRelatedItemsUrl(@Nonnull final List<String> tags) private String getRelatedItemsUrl(@Nonnull final List<String> tags) {
throws UnsupportedEncodingException {
final String url = baseUrl + PeertubeSearchQueryHandlerFactory.SEARCH_ENDPOINT_VIDEOS; final String url = baseUrl + PeertubeSearchQueryHandlerFactory.SEARCH_ENDPOINT_VIDEOS;
final StringBuilder params = new StringBuilder(); final StringBuilder params = new StringBuilder();
params.append("start=0&count=8&sort=-createdAt"); params.append("start=0&count=8&sort=-createdAt");

View File

@ -5,7 +5,6 @@ import org.schabi.newpipe.extractor.exceptions.ParsingException;
import org.schabi.newpipe.extractor.linkhandler.SearchQueryHandlerFactory; import org.schabi.newpipe.extractor.linkhandler.SearchQueryHandlerFactory;
import org.schabi.newpipe.extractor.utils.Utils; import org.schabi.newpipe.extractor.utils.Utils;
import java.io.UnsupportedEncodingException;
import java.util.List; import java.util.List;
public final class PeertubeSearchQueryHandlerFactory extends SearchQueryHandlerFactory { public final class PeertubeSearchQueryHandlerFactory extends SearchQueryHandlerFactory {
@ -49,21 +48,17 @@ public final class PeertubeSearchQueryHandlerFactory extends SearchQueryHandlerF
final String sortFilter, final String sortFilter,
final String baseUrl) final String baseUrl)
throws ParsingException, UnsupportedOperationException { throws ParsingException, UnsupportedOperationException {
try { final String endpoint;
final String endpoint; if (contentFilters.isEmpty()
if (contentFilters.isEmpty() || contentFilters.get(0).equals(VIDEOS)
|| contentFilters.get(0).equals(VIDEOS) || contentFilters.get(0).equals(SEPIA_VIDEOS)) {
|| contentFilters.get(0).equals(SEPIA_VIDEOS)) { endpoint = SEARCH_ENDPOINT_VIDEOS;
endpoint = SEARCH_ENDPOINT_VIDEOS; } else if (contentFilters.get(0).equals(CHANNELS)) {
} else if (contentFilters.get(0).equals(CHANNELS)) { endpoint = SEARCH_ENDPOINT_CHANNELS;
endpoint = SEARCH_ENDPOINT_CHANNELS; } else {
} else { endpoint = SEARCH_ENDPOINT_PLAYLISTS;
endpoint = SEARCH_ENDPOINT_PLAYLISTS;
}
return baseUrl + endpoint + "?search=" + Utils.encodeUrlUtf8(searchString);
} catch (final UnsupportedEncodingException e) {
throw new ParsingException("Could not encode query", e);
} }
return baseUrl + endpoint + "?search=" + Utils.encodeUrlUtf8(searchString);
} }
@Override @Override

View File

@ -23,7 +23,6 @@ import org.schabi.newpipe.extractor.search.SearchExtractor;
import org.schabi.newpipe.extractor.utils.Parser; import org.schabi.newpipe.extractor.utils.Parser;
import java.io.IOException; import java.io.IOException;
import java.io.UnsupportedEncodingException;
import java.net.MalformedURLException; import java.net.MalformedURLException;
import java.net.URL; import java.net.URL;
import java.util.Collections; import java.util.Collections;
@ -159,7 +158,7 @@ public class SoundcloudSearchExtractor extends SearchExtractor {
private int getOffsetFromUrl(final String url) throws ParsingException { private int getOffsetFromUrl(final String url) throws ParsingException {
try { try {
return Integer.parseInt(Parser.compatParseMap(new URL(url).getQuery()).get("offset")); return Integer.parseInt(Parser.compatParseMap(new URL(url).getQuery()).get("offset"));
} catch (MalformedURLException | UnsupportedEncodingException e) { } catch (final MalformedURLException e) {
throw new ParsingException("Could not get offset from page URL", e); throw new ParsingException("Could not get offset from page URL", e);
} }
} }

View File

@ -39,7 +39,6 @@ import org.schabi.newpipe.extractor.stream.VideoStream;
import org.schabi.newpipe.extractor.utils.Utils; import org.schabi.newpipe.extractor.utils.Utils;
import java.io.IOException; import java.io.IOException;
import java.io.UnsupportedEncodingException;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.Collections; import java.util.Collections;
import java.util.List; import java.util.List;
@ -317,14 +316,6 @@ public class SoundcloudStreamExtractor extends StreamExtractor {
} }
} }
private static String urlEncode(final String value) {
try {
return Utils.encodeUrlUtf8(value);
} catch (final UnsupportedEncodingException e) {
throw new IllegalStateException(e);
}
}
@Override @Override
public List<VideoStream> getVideoStreams() { public List<VideoStream> getVideoStreams() {
return Collections.emptyList(); return Collections.emptyList();
@ -344,9 +335,8 @@ public class SoundcloudStreamExtractor extends StreamExtractor {
@Override @Override
public StreamInfoItemsCollector getRelatedItems() throws IOException, ExtractionException { public StreamInfoItemsCollector getRelatedItems() throws IOException, ExtractionException {
final StreamInfoItemsCollector collector = new StreamInfoItemsCollector(getServiceId()); final StreamInfoItemsCollector collector = new StreamInfoItemsCollector(getServiceId());
final String apiUrl = SOUNDCLOUD_API_V2_URL + "tracks/" + Utils.encodeUrlUtf8(getId())
final String apiUrl = SOUNDCLOUD_API_V2_URL + "tracks/" + urlEncode(getId()) + "/related?client_id=" + Utils.encodeUrlUtf8(clientId());
+ "/related?client_id=" + urlEncode(clientId());
SoundcloudParsingHelper.getStreamsFromApi(collector, apiUrl); SoundcloudParsingHelper.getStreamsFromApi(collector, apiUrl);
return collector; return collector;

View File

@ -10,7 +10,6 @@ import org.schabi.newpipe.extractor.services.soundcloud.SoundcloudParsingHelper;
import org.schabi.newpipe.extractor.utils.Utils; import org.schabi.newpipe.extractor.utils.Utils;
import java.io.IOException; import java.io.IOException;
import java.io.UnsupportedEncodingException;
import java.util.List; import java.util.List;
public final class SoundcloudSearchQueryHandlerFactory extends SearchQueryHandlerFactory { public final class SoundcloudSearchQueryHandlerFactory extends SearchQueryHandlerFactory {
@ -60,9 +59,6 @@ public final class SoundcloudSearchQueryHandlerFactory extends SearchQueryHandle
return url + "?q=" + Utils.encodeUrlUtf8(id) return url + "?q=" + Utils.encodeUrlUtf8(id)
+ "&client_id=" + SoundcloudParsingHelper.clientId() + "&client_id=" + SoundcloudParsingHelper.clientId()
+ "&limit=" + ITEMS_PER_PAGE + "&offset=0"; + "&limit=" + ITEMS_PER_PAGE + "&offset=0";
} catch (final UnsupportedEncodingException e) {
throw new ParsingException("Could not encode query", e);
} catch (final ReCaptchaException e) { } catch (final ReCaptchaException e) {
throw new ParsingException("ReCaptcha required", e); throw new ParsingException("ReCaptcha required", e);
} catch (final IOException | ExtractionException e) { } catch (final IOException | ExtractionException e) {

View File

@ -52,7 +52,6 @@ import org.schabi.newpipe.extractor.utils.RandomStringFromAlphabetGenerator;
import org.schabi.newpipe.extractor.utils.Utils; import org.schabi.newpipe.extractor.utils.Utils;
import java.io.IOException; import java.io.IOException;
import java.io.UnsupportedEncodingException;
import java.net.MalformedURLException; import java.net.MalformedURLException;
import java.net.URL; import java.net.URL;
import java.nio.charset.StandardCharsets; import java.nio.charset.StandardCharsets;
@ -810,11 +809,7 @@ public final class YoutubeParsingHelper {
final String[] params = internUrl.split("&"); final String[] params = internUrl.split("&");
for (final String param : params) { for (final String param : params) {
if (param.split("=")[0].equals("q")) { if (param.split("=")[0].equals("q")) {
try { return Utils.decodeUrlUtf8(param.split("=")[1]);
return Utils.decodeUrlUtf8(param.split("=")[1]);
} catch (final UnsupportedEncodingException e) {
return null;
}
} }
} }
} else if (internUrl.startsWith("http")) { } else if (internUrl.startsWith("http")) {

View File

@ -96,7 +96,6 @@ import java.util.Arrays;
import java.util.Collections; import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.Locale; import java.util.Locale;
import java.util.Map;
import java.util.Objects; import java.util.Objects;
import java.util.stream.Collectors; import java.util.stream.Collectors;
@ -1304,7 +1303,7 @@ public class YoutubeStreamExtractor extends StreamExtractor {
return buildAndAddItagInfoToList(videoId, formatData, itagItem, return buildAndAddItagInfoToList(videoId, formatData, itagItem,
itagItem.itagType, contentPlaybackNonce); itagItem.itagType, contentPlaybackNonce);
} }
} catch (final IOException | ExtractionException ignored) { } catch (final ExtractionException ignored) {
// if the itag is not supported and getItag fails, we end up here // if the itag is not supported and getItag fails, we end up here
} }
return null; return null;
@ -1317,19 +1316,18 @@ public class YoutubeStreamExtractor extends StreamExtractor {
@Nonnull final JsonObject formatData, @Nonnull final JsonObject formatData,
@Nonnull final ItagItem itagItem, @Nonnull final ItagItem itagItem,
@Nonnull final ItagItem.ItagType itagType, @Nonnull final ItagItem.ItagType itagType,
@Nonnull final String contentPlaybackNonce) throws IOException, ExtractionException { @Nonnull final String contentPlaybackNonce) throws ExtractionException {
String streamUrl; String streamUrl;
if (formatData.has("url")) { if (formatData.has("url")) {
streamUrl = formatData.getString("url"); streamUrl = formatData.getString("url");
} else { } else {
// This url has an obfuscated signature // This url has an obfuscated signature
final String cipherString = formatData.has(CIPHER) final String cipherString = formatData.getString(CIPHER,
? formatData.getString(CIPHER) formatData.getString(SIGNATURE_CIPHER));
: formatData.getString(SIGNATURE_CIPHER); final var cipher = Parser.compatParseMap(cipherString);
final Map<String, String> cipher = Parser.compatParseMap( final String signature = YoutubeJavaScriptPlayerManager.deobfuscateSignature(videoId,
cipherString); cipher.getOrDefault("s", ""));
streamUrl = cipher.get("url") + "&" + cipher.get("sp") + "=" streamUrl = cipher.get("url") + "&" + cipher.get("sp") + "=" + signature;
+ YoutubeJavaScriptPlayerManager.deobfuscateSignature(videoId, cipher.get("s"));
} }
// Add the content playback nonce to the stream URL // Add the content playback nonce to the stream URL

View File

@ -6,7 +6,6 @@ import static org.schabi.newpipe.extractor.utils.Utils.isNullOrEmpty;
import org.schabi.newpipe.extractor.exceptions.ParsingException; import org.schabi.newpipe.extractor.exceptions.ParsingException;
import org.schabi.newpipe.extractor.linkhandler.SearchQueryHandlerFactory; import org.schabi.newpipe.extractor.linkhandler.SearchQueryHandlerFactory;
import java.io.UnsupportedEncodingException;
import java.util.List; import java.util.List;
import javax.annotation.Nonnull; import javax.annotation.Nonnull;
@ -40,31 +39,22 @@ public final class YoutubeSearchQueryHandlerFactory extends SearchQueryHandlerFa
@Nonnull final List<String> contentFilters, @Nonnull final List<String> contentFilters,
final String sortFilter) final String sortFilter)
throws ParsingException, UnsupportedOperationException { throws ParsingException, UnsupportedOperationException {
try { final String contentFilter = !contentFilters.isEmpty() ? contentFilters.get(0) : "";
if (!contentFilters.isEmpty()) { switch (contentFilter) {
final String contentFilter = contentFilters.get(0); case VIDEOS:
switch (contentFilter) { return SEARCH_URL + encodeUrlUtf8(searchString) + "&sp=EgIQAfABAQ%253D%253D";
case VIDEOS: case CHANNELS:
return SEARCH_URL + encodeUrlUtf8(searchString) return SEARCH_URL + encodeUrlUtf8(searchString) + "&sp=EgIQAvABAQ%253D%253D";
+ "&sp=EgIQAfABAQ%253D%253D"; case PLAYLISTS:
case CHANNELS: return SEARCH_URL + encodeUrlUtf8(searchString) + "&sp=EgIQA_ABAQ%253D%253D";
return SEARCH_URL + encodeUrlUtf8(searchString) case MUSIC_SONGS:
+ "&sp=EgIQAvABAQ%253D%253D"; case MUSIC_VIDEOS:
case PLAYLISTS: case MUSIC_ALBUMS:
return SEARCH_URL + encodeUrlUtf8(searchString) case MUSIC_PLAYLISTS:
+ "&sp=EgIQA_ABAQ%253D%253D"; case MUSIC_ARTISTS:
case MUSIC_SONGS: return MUSIC_SEARCH_URL + encodeUrlUtf8(searchString);
case MUSIC_VIDEOS: default:
case MUSIC_ALBUMS: return SEARCH_URL + encodeUrlUtf8(searchString) + "&sp=8AEB";
case MUSIC_PLAYLISTS:
case MUSIC_ARTISTS:
return MUSIC_SEARCH_URL + encodeUrlUtf8(searchString);
}
}
return SEARCH_URL + encodeUrlUtf8(searchString) + "&sp=8AEB";
} catch (final UnsupportedEncodingException e) {
throw new ParsingException("Could not encode query", e);
} }
} }

View File

@ -22,11 +22,11 @@ package org.schabi.newpipe.extractor.utils;
import org.schabi.newpipe.extractor.exceptions.ParsingException; import org.schabi.newpipe.extractor.exceptions.ParsingException;
import java.io.UnsupportedEncodingException; import java.util.Arrays;
import java.util.HashMap;
import java.util.Map; import java.util.Map;
import java.util.regex.Matcher; import java.util.regex.Matcher;
import java.util.regex.Pattern; import java.util.regex.Pattern;
import java.util.stream.Collectors;
import javax.annotation.Nonnull; import javax.annotation.Nonnull;
@ -121,17 +121,12 @@ public final class Parser {
} }
@Nonnull @Nonnull
public static Map<String, String> compatParseMap(@Nonnull final String input) public static Map<String, String> compatParseMap(@Nonnull final String input) {
throws UnsupportedEncodingException { return Arrays.stream(input.split("&"))
final Map<String, String> map = new HashMap<>(); .map(arg -> arg.split("="))
for (final String arg : input.split("&")) { .filter(splitArg -> splitArg.length > 1)
final String[] splitArg = arg.split("="); .collect(Collectors.toMap(splitArg -> splitArg[0],
if (splitArg.length > 1) { splitArg -> Utils.decodeUrlUtf8(splitArg[1]),
map.put(splitArg[0], Utils.decodeUrlUtf8(splitArg[1])); (existing, replacement) -> replacement));
} else {
map.put(splitArg[0], "");
}
}
return map;
} }
} }

View File

@ -2,7 +2,6 @@ package org.schabi.newpipe.extractor.utils;
import org.schabi.newpipe.extractor.exceptions.ParsingException; import org.schabi.newpipe.extractor.exceptions.ParsingException;
import java.io.UnsupportedEncodingException;
import java.net.MalformedURLException; import java.net.MalformedURLException;
import java.net.URL; import java.net.URL;
import java.net.URLDecoder; import java.net.URLDecoder;
@ -33,22 +32,18 @@ public final class Utils {
* *
* @param string The string to be encoded. * @param string The string to be encoded.
* @return The encoded URL. * @return The encoded URL.
* @throws UnsupportedEncodingException This shouldn't be thrown, as UTF-8 should be supported.
*/ */
public static String encodeUrlUtf8(final String string) throws UnsupportedEncodingException { public static String encodeUrlUtf8(final String string) {
// TODO: Switch to URLEncoder.encode(String, Charset) in Java 10. return URLEncoder.encode(string, StandardCharsets.UTF_8);
return URLEncoder.encode(string, StandardCharsets.UTF_8.name());
} }
/** /**
* Decodes a URL using the UTF-8 character set. * Decodes a URL using the UTF-8 character set.
* @param url The URL to be decoded. * @param url The URL to be decoded.
* @return The decoded URL. * @return The decoded URL.
* @throws UnsupportedEncodingException This shouldn't be thrown, as UTF-8 should be supported.
*/ */
public static String decodeUrlUtf8(final String url) throws UnsupportedEncodingException { public static String decodeUrlUtf8(final String url) {
// TODO: Switch to URLDecoder.decode(String, Charset) in Java 10. return URLDecoder.decode(url, StandardCharsets.UTF_8);
return URLDecoder.decode(url, StandardCharsets.UTF_8.name());
} }
/** /**
@ -155,22 +150,10 @@ public final class Utils {
if (urlQuery != null) { if (urlQuery != null) {
for (final String param : urlQuery.split("&")) { for (final String param : urlQuery.split("&")) {
final String[] params = param.split("=", 2); final String[] params = param.split("=", 2);
final String query = decodeUrlUtf8(params[0]);
String query;
try {
query = decodeUrlUtf8(params[0]);
} catch (final UnsupportedEncodingException e) {
// Cannot decode string with UTF-8, using the string without decoding
query = params[0];
}
if (query.equals(parameterName)) { if (query.equals(parameterName)) {
try { return decodeUrlUtf8(params[1]);
return decodeUrlUtf8(params[1]);
} catch (final UnsupportedEncodingException e) {
// Cannot decode string with UTF-8, using the string without decoding
return params[1];
}
} }
} }
} }

View File

@ -1,6 +1,5 @@
package org.schabi.newpipe.extractor.services.soundcloud.search; package org.schabi.newpipe.extractor.services.soundcloud.search;
import static org.junit.jupiter.api.Assertions.assertFalse;
import static org.junit.jupiter.api.Assertions.assertTrue; import static org.junit.jupiter.api.Assertions.assertTrue;
import static org.schabi.newpipe.extractor.ServiceList.SoundCloud; import static org.schabi.newpipe.extractor.ServiceList.SoundCloud;
import static org.schabi.newpipe.extractor.services.DefaultTests.assertNoDuplicatedItems; import static org.schabi.newpipe.extractor.services.DefaultTests.assertNoDuplicatedItems;
@ -23,7 +22,6 @@ import org.schabi.newpipe.extractor.services.DefaultSearchExtractorTest;
import org.schabi.newpipe.extractor.utils.Utils; import org.schabi.newpipe.extractor.utils.Utils;
import java.io.IOException; import java.io.IOException;
import java.io.UnsupportedEncodingException;
import java.util.List; import java.util.List;
import javax.annotation.Nullable; import javax.annotation.Nullable;
@ -46,8 +44,8 @@ public class SoundcloudSearchExtractorTest {
@Override public StreamingService expectedService() { return SoundCloud; } @Override public StreamingService expectedService() { return SoundCloud; }
@Override public String expectedName() { return QUERY; } @Override public String expectedName() { return QUERY; }
@Override public String expectedId() { return QUERY; } @Override public String expectedId() { return QUERY; }
@Override public String expectedUrlContains() { return "soundcloud.com/search?q=" + urlEncode(QUERY); } @Override public String expectedUrlContains() { return "soundcloud.com/search?q=" + Utils.encodeUrlUtf8(QUERY); }
@Override public String expectedOriginalUrlContains() { return "soundcloud.com/search?q=" + urlEncode(QUERY); } @Override public String expectedOriginalUrlContains() { return "soundcloud.com/search?q=" + Utils.encodeUrlUtf8(QUERY); }
@Override public String expectedSearchString() { return QUERY; } @Override public String expectedSearchString() { return QUERY; }
@Nullable @Override public String expectedSearchSuggestion() { return null; } @Nullable @Override public String expectedSearchSuggestion() { return null; }
// @formatter:on // @formatter:on
@ -69,8 +67,8 @@ public class SoundcloudSearchExtractorTest {
@Override public StreamingService expectedService() { return SoundCloud; } @Override public StreamingService expectedService() { return SoundCloud; }
@Override public String expectedName() { return QUERY; } @Override public String expectedName() { return QUERY; }
@Override public String expectedId() { return QUERY; } @Override public String expectedId() { return QUERY; }
@Override public String expectedUrlContains() { return "soundcloud.com/search/tracks?q=" + urlEncode(QUERY); } @Override public String expectedUrlContains() { return "soundcloud.com/search/tracks?q=" + Utils.encodeUrlUtf8(QUERY); }
@Override public String expectedOriginalUrlContains() { return "soundcloud.com/search/tracks?q=" + urlEncode(QUERY); } @Override public String expectedOriginalUrlContains() { return "soundcloud.com/search/tracks?q=" + Utils.encodeUrlUtf8(QUERY); }
@Override public String expectedSearchString() { return QUERY; } @Override public String expectedSearchString() { return QUERY; }
@Nullable @Override public String expectedSearchSuggestion() { return null; } @Nullable @Override public String expectedSearchSuggestion() { return null; }
@Override public InfoItem.InfoType expectedInfoItemType() { return InfoItem.InfoType.STREAM; } @Override public InfoItem.InfoType expectedInfoItemType() { return InfoItem.InfoType.STREAM; }
@ -93,8 +91,8 @@ public class SoundcloudSearchExtractorTest {
@Override public StreamingService expectedService() { return SoundCloud; } @Override public StreamingService expectedService() { return SoundCloud; }
@Override public String expectedName() { return QUERY; } @Override public String expectedName() { return QUERY; }
@Override public String expectedId() { return QUERY; } @Override public String expectedId() { return QUERY; }
@Override public String expectedUrlContains() { return "soundcloud.com/search/users?q=" + urlEncode(QUERY); } @Override public String expectedUrlContains() { return "soundcloud.com/search/users?q=" + Utils.encodeUrlUtf8(QUERY); }
@Override public String expectedOriginalUrlContains() { return "soundcloud.com/search/users?q=" + urlEncode(QUERY); } @Override public String expectedOriginalUrlContains() { return "soundcloud.com/search/users?q=" + Utils.encodeUrlUtf8(QUERY); }
@Override public String expectedSearchString() { return QUERY; } @Override public String expectedSearchString() { return QUERY; }
@Nullable @Override public String expectedSearchSuggestion() { return null; } @Nullable @Override public String expectedSearchSuggestion() { return null; }
@Override public InfoItem.InfoType expectedInfoItemType() { return InfoItem.InfoType.CHANNEL; } @Override public InfoItem.InfoType expectedInfoItemType() { return InfoItem.InfoType.CHANNEL; }
@ -117,8 +115,8 @@ public class SoundcloudSearchExtractorTest {
@Override public StreamingService expectedService() { return SoundCloud; } @Override public StreamingService expectedService() { return SoundCloud; }
@Override public String expectedName() { return QUERY; } @Override public String expectedName() { return QUERY; }
@Override public String expectedId() { return QUERY; } @Override public String expectedId() { return QUERY; }
@Override public String expectedUrlContains() { return "soundcloud.com/search/playlists?q=" + urlEncode(QUERY); } @Override public String expectedUrlContains() { return "soundcloud.com/search/playlists?q=" + Utils.encodeUrlUtf8(QUERY); }
@Override public String expectedOriginalUrlContains() { return "soundcloud.com/search/playlists?q=" + urlEncode(QUERY); } @Override public String expectedOriginalUrlContains() { return "soundcloud.com/search/playlists?q=" + Utils.encodeUrlUtf8(QUERY); }
@Override public String expectedSearchString() { return QUERY; } @Override public String expectedSearchString() { return QUERY; }
@Nullable @Override public String expectedSearchSuggestion() { return null; } @Nullable @Override public String expectedSearchSuggestion() { return null; }
@Override public InfoItem.InfoType expectedInfoItemType() { return InfoItem.InfoType.PLAYLIST; } @Override public InfoItem.InfoType expectedInfoItemType() { return InfoItem.InfoType.PLAYLIST; }
@ -139,14 +137,6 @@ public class SoundcloudSearchExtractorTest {
} }
} }
private static String urlEncode(String value) {
try {
return Utils.encodeUrlUtf8(value);
} catch (UnsupportedEncodingException e) {
throw new RuntimeException(e);
}
}
public static class UserVerified extends DefaultSearchExtractorTest { public static class UserVerified extends DefaultSearchExtractorTest {
private static SearchExtractor extractor; private static SearchExtractor extractor;
private static final String QUERY = "David Guetta"; private static final String QUERY = "David Guetta";
@ -162,8 +152,8 @@ public class SoundcloudSearchExtractorTest {
@Override public StreamingService expectedService() { return SoundCloud; } @Override public StreamingService expectedService() { return SoundCloud; }
@Override public String expectedName() { return QUERY; } @Override public String expectedName() { return QUERY; }
@Override public String expectedId() { return QUERY; } @Override public String expectedId() { return QUERY; }
@Override public String expectedUrlContains() { return "soundcloud.com/search/users?q=" + urlEncode(QUERY); } @Override public String expectedUrlContains() { return "soundcloud.com/search/users?q=" + Utils.encodeUrlUtf8(QUERY); }
@Override public String expectedOriginalUrlContains() { return "soundcloud.com/search/users?q=" + urlEncode(QUERY); } @Override public String expectedOriginalUrlContains() { return "soundcloud.com/search/users?q=" + Utils.encodeUrlUtf8(QUERY); }
@Override public String expectedSearchString() { return QUERY; } @Override public String expectedSearchString() { return QUERY; }
@Nullable @Override public String expectedSearchSuggestion() { return null; } @Nullable @Override public String expectedSearchSuggestion() { return null; }
@ -200,8 +190,8 @@ public class SoundcloudSearchExtractorTest {
@Override public StreamingService expectedService() throws Exception { return SoundCloud; } @Override public StreamingService expectedService() throws Exception { return SoundCloud; }
@Override public String expectedName() throws Exception { return QUERY; } @Override public String expectedName() throws Exception { return QUERY; }
@Override public String expectedId() throws Exception { return QUERY; } @Override public String expectedId() throws Exception { return QUERY; }
@Override public String expectedUrlContains() { return "soundcloud.com/search?q=" + urlEncode(QUERY); } @Override public String expectedUrlContains() { return "soundcloud.com/search?q=" + Utils.encodeUrlUtf8(QUERY); }
@Override public String expectedOriginalUrlContains() { return "soundcloud.com/search?q=" + urlEncode(QUERY); } @Override public String expectedOriginalUrlContains() { return "soundcloud.com/search?q=" + Utils.encodeUrlUtf8(QUERY); }
@Override public String expectedSearchString() { return QUERY; } @Override public String expectedSearchString() { return QUERY; }
@Nullable @Override public String expectedSearchSuggestion() { return null; } @Nullable @Override public String expectedSearchSuggestion() { return null; }
} }