diff --git a/extractor/src/main/java/org/schabi/newpipe/extractor/services/youtube/YoutubeParsingHelper.java b/extractor/src/main/java/org/schabi/newpipe/extractor/services/youtube/YoutubeParsingHelper.java index 40bb12bb2d..76bf2b0a9b 100644 --- a/extractor/src/main/java/org/schabi/newpipe/extractor/services/youtube/YoutubeParsingHelper.java +++ b/extractor/src/main/java/org/schabi/newpipe/extractor/services/youtube/YoutubeParsingHelper.java @@ -109,25 +109,25 @@ private static boolean isGoogleURL(String url) { } } - public static boolean isYoutubeURL(final URL url) { + public static boolean isYoutubeURL(@Nonnull final URL url) { final String host = url.getHost(); return host.equalsIgnoreCase("youtube.com") || host.equalsIgnoreCase("www.youtube.com") || host.equalsIgnoreCase("m.youtube.com") || host.equalsIgnoreCase("music.youtube.com"); } - public static boolean isYoutubeServiceURL(final URL url) { + public static boolean isYoutubeServiceURL(@Nonnull final URL url) { final String host = url.getHost(); return host.equalsIgnoreCase("www.youtube-nocookie.com") || host.equalsIgnoreCase("youtu.be"); } - public static boolean isHooktubeURL(final URL url) { + public static boolean isHooktubeURL(@Nonnull final URL url) { final String host = url.getHost(); return host.equalsIgnoreCase("hooktube.com"); } - public static boolean isInvidioURL(final URL url) { + public static boolean isInvidioURL(@Nonnull final URL url) { final String host = url.getHost(); return host.equalsIgnoreCase("invidio.us") || host.equalsIgnoreCase("dev.invidio.us") @@ -156,7 +156,7 @@ public static boolean isInvidioURL(final URL url) { * @return the duration in seconds * @throws ParsingException when more than 3 separators are found */ - public static int parseDurationString(final String input) + public static int parseDurationString(@Nonnull final String input) throws ParsingException, NumberFormatException { // If time separator : is not detected, try . instead final String[] splitInput = input.contains(":") @@ -197,7 +197,8 @@ public static int parseDurationString(final String input) + Integer.parseInt(Utils.removeNonDigitCharacters(seconds)); } - public static String getFeedUrlFrom(final String channelIdOrUser) { + @Nonnull + public static String getFeedUrlFrom(@Nonnull final String channelIdOrUser) { if (channelIdOrUser.startsWith("user/")) { return FEED_BASE_USER + channelIdOrUser.replace("user/", ""); } else if (channelIdOrUser.startsWith("channel/")) { @@ -228,7 +229,7 @@ public static OffsetDateTime parseDateFrom(final String textualUploadDate) * @param playlistId the id of the playlist * @return Whether given id belongs to a YouTube Mix */ - public static boolean isYoutubeMixId(final String playlistId) { + public static boolean isYoutubeMixId(@Nonnull final String playlistId) { return playlistId.startsWith("RD") && !isYoutubeMusicMixId(playlistId); } @@ -239,7 +240,7 @@ public static boolean isYoutubeMixId(final String playlistId) { * @param playlistId the playlist id * @return Whether given id belongs to a YouTube Music Mix */ - public static boolean isYoutubeMusicMixId(final String playlistId) { + public static boolean isYoutubeMusicMixId(@Nonnull final String playlistId) { return playlistId.startsWith("RDAMVM") || playlistId.startsWith("RDCLAK"); } @@ -249,7 +250,7 @@ public static boolean isYoutubeMusicMixId(final String playlistId) { * * @return Whether given id belongs to a YouTube Channel Mix */ - public static boolean isYoutubeChannelMixId(final String playlistId) { + public static boolean isYoutubeChannelMixId(@Nonnull final String playlistId) { return playlistId.startsWith("RDCM"); } @@ -258,7 +259,9 @@ public static boolean isYoutubeChannelMixId(final String playlistId) { * * @throws ParsingException If the playlistId is a Channel Mix or not a mix. */ - public static String extractVideoIdFromMixId(final String playlistId) throws ParsingException { + @Nonnull + public static String extractVideoIdFromMixId(@Nonnull final String playlistId) + throws ParsingException { if (playlistId.startsWith("RDMM")) { // My Mix return playlistId.substring(4); @@ -547,7 +550,7 @@ public static String[] getYoutubeMusicKey() throws IOException, ReCaptchaExcepti } @Nullable - public static String getUrlFromNavigationEndpoint(final JsonObject navigationEndpoint) + public static String getUrlFromNavigationEndpoint(@Nonnull final JsonObject navigationEndpoint) throws ParsingException { if (navigationEndpoint.has("urlEndpoint")) { String internUrl = navigationEndpoint.getObject("urlEndpoint").getString("url"); @@ -660,7 +663,7 @@ public static String getTextFromObject(final JsonObject textObject) throws Parsi } @Nullable - public static String getTextAtKey(final JsonObject jsonObject, final String key) + public static String getTextAtKey(@Nonnull final JsonObject jsonObject, final String key) throws ParsingException { if (jsonObject.isString(key)) { return jsonObject.getString(key); @@ -669,7 +672,7 @@ public static String getTextAtKey(final JsonObject jsonObject, final String key) } } - public static String fixThumbnailUrl(String thumbnailUrl) { + public static String fixThumbnailUrl(@Nonnull String thumbnailUrl) { if (thumbnailUrl.startsWith("//")) { thumbnailUrl = thumbnailUrl.substring(2); } @@ -683,7 +686,8 @@ public static String fixThumbnailUrl(String thumbnailUrl) { return thumbnailUrl; } - public static String getValidJsonResponseBody(final Response response) + @Nonnull + public static String getValidJsonResponseBody(@Nonnull final Response response) throws ParsingException, MalformedURLException { if (response.responseCode() == 404) { throw new ContentNotAvailableException("Not found" @@ -740,7 +744,8 @@ public static JsonObject getJsonPostResponse(final String endpoint, public static JsonObject getJsonMobilePostResponse(final String endpoint, final byte[] body, - final ContentCountry contentCountry, + @Nonnull final ContentCountry + contentCountry, final Localization localization) throws IOException, ExtractionException { final Map> headers = new HashMap<>(); @@ -768,7 +773,8 @@ public static JsonArray getJsonResponse(final String url, final Localization loc return JsonUtils.toJsonArray(getValidJsonResponseBody(response)); } - public static JsonArray getJsonResponse(final Page page, final Localization localization) + public static JsonArray getJsonResponse(@Nonnull final Page page, + final Localization localization) throws IOException, ExtractionException { final Map> headers = new HashMap<>(); addYouTubeHeaders(headers); @@ -778,8 +784,11 @@ public static JsonArray getJsonResponse(final Page page, final Localization loca return JsonUtils.toJsonArray(getValidJsonResponseBody(response)); } - public static JsonBuilder prepareJsonBuilder(final Localization localization, - final ContentCountry contentCountry) + @Nonnull + public static JsonBuilder prepareJsonBuilder(@Nonnull final Localization + localization, + @Nonnull final ContentCountry + contentCountry) throws IOException, ExtractionException { // @formatter:off return JsonObject.builder() @@ -794,8 +803,10 @@ public static JsonBuilder prepareJsonBuilder(final Localization loca // @formatter:on } - public static JsonBuilder prepareMobileJsonBuilder(final Localization localization, - final ContentCountry + @Nonnull + public static JsonBuilder prepareMobileJsonBuilder(@Nonnull final Localization + localization, + @Nonnull final ContentCountry contentCountry) throws IOException, ExtractionException { // @formatter:off @@ -827,7 +838,7 @@ public static void addYouTubeHeaders(final Map> headers) * Origin, and Referer headers. * @param headers The headers which should be completed */ - public static void addClientInfoHeaders(final Map> headers) + public static void addClientInfoHeaders(@Nonnull final Map> headers) throws IOException, ExtractionException { if (headers.get("Origin") == null) { headers.put("Origin", Collections.singletonList("https://www.youtube.com")); @@ -848,7 +859,7 @@ public static void addClientInfoHeaders(final Map> headers) * @see #CONSENT_COOKIE * @param headers the headers which should be completed */ - public static void addCookieHeader(final Map> headers) { + public static void addCookieHeader(@Nonnull final Map> headers) { if (headers.get("Cookie") == null) { headers.put("Cookie", Arrays.asList(generateConsentCookie())); } else { @@ -856,11 +867,13 @@ public static void addCookieHeader(final Map> headers) { } } + @Nonnull public static String generateConsentCookie() { return CONSENT_COOKIE + 100 + numberGenerator.nextInt(900); } - public static String extractCookieValue(final String cookieName, final Response response) { + public static String extractCookieValue(final String cookieName, + @Nonnull final Response response) { final List cookies = response.responseHeaders().get("set-cookie"); int startIndex; String result = ""; @@ -883,7 +896,8 @@ public static String extractCookieValue(final String cookieName, final Response * @param initialData the object which will be checked if an alert is present * @throws ContentNotAvailableException if an alert is detected */ - public static void defaultAlertsCheck(final JsonObject initialData) throws ParsingException { + public static void defaultAlertsCheck(@Nonnull final JsonObject initialData) + throws ParsingException { final JsonArray alerts = initialData.getArray("alerts"); if (!isNullOrEmpty(alerts)) { final JsonObject alertRenderer = alerts.getObject(0).getObject("alertRenderer"); @@ -893,7 +907,7 @@ public static void defaultAlertsCheck(final JsonObject initialData) throws Parsi if (alertText != null && alertText.contains("This account has been terminated")) { if (alertText.contains("violation") || alertText.contains("violating") || alertText.contains("infringement")) { - // possible error messages: + // Possible error messages: // "This account has been terminated for a violation of YouTube's Terms of Service." // "This account has been terminated due to multiple or severe violations of YouTube's policy prohibiting hate speech." // "This account has been terminated due to multiple or severe violations of YouTube's policy prohibiting content designed to harass, bully or threaten." @@ -913,7 +927,8 @@ public static void defaultAlertsCheck(final JsonObject initialData) throws Parsi } @Nonnull - public static List getMetaInfo(final JsonArray contents) throws ParsingException { + public static List getMetaInfo(@Nonnull final JsonArray contents) + throws ParsingException { final List metaInfo = new ArrayList<>(); for (final Object content : contents) { final JsonObject resultObject = (JsonObject) content; @@ -939,7 +954,7 @@ public static List getMetaInfo(final JsonArray contents) throws Parsin } @Nonnull - private static MetaInfo getInfoPanelContent(final JsonObject infoPanelContentRenderer) + private static MetaInfo getInfoPanelContent(@Nonnull final JsonObject infoPanelContentRenderer) throws ParsingException { final MetaInfo metaInfo = new MetaInfo(); final StringBuilder sb = new StringBuilder(); @@ -972,7 +987,7 @@ private static MetaInfo getInfoPanelContent(final JsonObject infoPanelContentRen } @Nonnull - private static MetaInfo getClarificationRendererContent(final JsonObject clarificationRenderer) + private static MetaInfo getClarificationRendererContent(@Nonnull final JsonObject clarificationRenderer) throws ParsingException { final MetaInfo metaInfo = new MetaInfo(); @@ -1009,7 +1024,7 @@ private static MetaInfo getClarificationRendererContent(final JsonObject clarifi .has("secondarySource")) { final String url = getUrlFromNavigationEndpoint(clarificationRenderer .getObject("secondaryEndpoint")); - // ignore Google URLs, because those point to a Google search about "Covid-19" + // Ignore Google URLs, because those point to a Google search about "Covid-19" if (url != null && !isGoogleURL(url)) { try { metaInfo.addUrl(new URL(url)); @@ -1059,7 +1074,8 @@ public static boolean isVerified(final JsonArray badges) { return false; } - public static String unescapeDocument(final String doc) { + @Nonnull + public static String unescapeDocument(@Nonnull final String doc) { return doc .replaceAll("\\\\x22", "\"") .replaceAll("\\\\x7b", "{")