2020import javax .annotation .Nonnull ;
2121import java .io .IOException ;
2222
23- import static org .schabi .newpipe .extractor .services .youtube .YoutubeParsingHelper .fixThumbnailUrl ;
24- import static org .schabi .newpipe .extractor .services .youtube .YoutubeParsingHelper .getJsonResponse ;
25- import static org .schabi .newpipe .extractor .services .youtube .YoutubeParsingHelper .getTextFromObject ;
23+ import static org .schabi .newpipe .extractor .services .youtube .YoutubeParsingHelper .*;
2624import static org .schabi .newpipe .extractor .utils .JsonUtils .EMPTY_STRING ;
2725import static org .schabi .newpipe .extractor .utils .Utils .isNullOrEmpty ;
2826
@@ -230,9 +228,9 @@ public InfoItemsPage<StreamInfoItem> getInitialPage() throws ExtractionException
230228 .getArray ("contents" ).getObject (0 ).getObject ("itemSectionRenderer" )
231229 .getArray ("contents" ).getObject (0 ).getObject ("gridRenderer" );
232230
233- collectStreamsFrom (collector , gridRenderer .getArray ("items" ));
231+ final JsonObject continuation = collectStreamsFrom (collector , gridRenderer .getArray ("items" ));
234232
235- nextPage = getNextPageFrom (gridRenderer . getArray ( "continuations" ) );
233+ nextPage = getNextPageFrom (continuation );
236234 }
237235
238236 return new InfoItemsPage <>(collector , nextPage );
@@ -252,36 +250,47 @@ public InfoItemsPage<StreamInfoItem> getPage(final Page page) throws IOException
252250 final JsonArray ajaxJson = getJsonResponse (page .getUrl (), getExtractorLocalization ());
253251
254252 JsonObject sectionListContinuation = ajaxJson .getObject (1 ).getObject ("response" )
255- .getObject ( "continuationContents " ).getObject ("gridContinuation " );
253+ .getArray ( "onResponseReceivedActions " ).getObject (0 ). getObject ( "appendContinuationItemsAction " );
256254
257- collectStreamsFrom (collector , sectionListContinuation .getArray ("items " ));
255+ final JsonObject continuation = collectStreamsFrom (collector , sectionListContinuation .getArray ("continuationItems " ));
258256
259- return new InfoItemsPage <>(collector , getNextPageFrom (sectionListContinuation . getArray ( "continuations" ) ));
257+ return new InfoItemsPage <>(collector , getNextPageFrom (continuation ));
260258 }
261259
262- private Page getNextPageFrom (final JsonArray continuations ) {
260+ private Page getNextPageFrom (final JsonObject continuations ) {
263261 if (isNullOrEmpty (continuations )) {
264262 return null ;
265263 }
266264
267- final JsonObject nextContinuationData = continuations .getObject (0 ). getObject ( "nextContinuationData " );
268- final String continuation = nextContinuationData . getString ("continuation " );
269- final String clickTrackingParams = nextContinuationData .getString ("clickTrackingParams" );
265+ final JsonObject continuationEndpoint = continuations .getObject ("continuationEndpoint " );
266+ final String continuation = continuationEndpoint . getObject ( "continuationCommand" ). getString ("token " );
267+ final String clickTrackingParams = continuationEndpoint .getString ("clickTrackingParams" );
270268 return new Page ("https://www.youtube.com/browse_ajax?ctoken=" + continuation
271269 + "&continuation=" + continuation + "&itct=" + clickTrackingParams );
272270 }
273271
274- private void collectStreamsFrom (StreamInfoItemsCollector collector , JsonArray videos ) throws ParsingException {
272+ /**
273+ * Collect streams from an array of items
274+ *
275+ * @param collector the collector where videos will be commited
276+ * @param videos the array to get videos from
277+ * @return the continuation object
278+ * @throws ParsingException if an error happened while extracting
279+ */
280+ private JsonObject collectStreamsFrom (StreamInfoItemsCollector collector , JsonArray videos ) throws ParsingException {
275281 collector .reset ();
276282
277283 final String uploaderName = getName ();
278284 final String uploaderUrl = getUrl ();
279285 final TimeAgoParser timeAgoParser = getTimeAgoParser ();
280286
281- for (Object video : videos ) {
282- if (((JsonObject ) video ).has ("gridVideoRenderer" )) {
287+ JsonObject continuation = null ;
288+
289+ for (Object object : videos ) {
290+ final JsonObject video = (JsonObject ) object ;
291+ if (video .has ("gridVideoRenderer" )) {
283292 collector .commit (new YoutubeStreamInfoItemExtractor (
284- (( JsonObject ) video ) .getObject ("gridVideoRenderer" ), timeAgoParser ) {
293+ video .getObject ("gridVideoRenderer" ), timeAgoParser ) {
285294 @ Override
286295 public String getUploaderName () {
287296 return uploaderName ;
@@ -292,8 +301,12 @@ public String getUploaderUrl() {
292301 return uploaderUrl ;
293302 }
294303 });
304+ } else if (video .has ("continuationItemRenderer" )) {
305+ continuation = video .getObject ("continuationItemRenderer" );
295306 }
296307 }
308+
309+ return continuation ;
297310 }
298311
299312 private JsonObject getVideoTab () throws ParsingException {
0 commit comments