1# coding: utf-8 2from __future__ import unicode_literals 3 4import functools 5import re 6 7from .common import InfoExtractor 8from ..compat import compat_str 9from ..utils import ( 10 int_or_none, 11 parse_resolution, 12 str_or_none, 13 try_get, 14 unified_timestamp, 15 url_or_none, 16 urljoin, 17 OnDemandPagedList, 18) 19 20 21class PeerTubeIE(InfoExtractor): 22 _INSTANCES_RE = r'''(?: 23 # Taken from https://instances.joinpeertube.org/instances 24 40two\.tube| 25 a\.metube\.ch| 26 advtv\.ml| 27 algorithmic\.tv| 28 alimulama\.com| 29 arcana\.fun| 30 archive\.vidicon\.org| 31 artefac-paris\.tv| 32 auf1\.eu| 33 battlepenguin\.video| 34 beertube\.epgn\.ch| 35 befree\.nohost\.me| 36 bideoak\.argia\.eus| 37 birkeundnymphe\.de| 38 bitcointv\.com| 39 cattube\.org| 40 clap\.nerv-project\.eu| 41 climatejustice\.video| 42 comf\.tube| 43 conspiracydistillery\.com| 44 darkvapor\.nohost\.me| 45 daschauher\.aksel\.rocks| 46 digitalcourage\.video| 47 dreiecksnebel\.alex-detsch\.de| 48 eduvid\.org| 49 evangelisch\.video| 50 exo\.tube| 51 fair\.tube| 52 fediverse\.tv| 53 film\.k-prod\.fr| 54 flim\.txmn\.tk| 55 fotogramas\.politicaconciencia\.org| 56 ftsi\.ru| 57 gary\.vger\.cloud| 58 graeber\.video| 59 greatview\.video| 60 grypstube\.uni-greifswald\.de| 61 highvoltage\.tv| 62 hpstube\.fr| 63 htp\.live| 64 hyperreal\.tube| 65 juggling\.digital| 66 kino\.kompot\.si| 67 kino\.schuerz\.at| 68 kinowolnosc\.pl| 69 kirche\.peertube-host\.de| 70 kodcast\.com| 71 kolektiva\.media| 72 kraut\.zone| 73 kumi\.tube| 74 lastbreach\.tv| 75 lepetitmayennais\.fr\.nf| 76 lexx\.impa\.me| 77 libertynode\.tv| 78 libra\.syntazia\.org| 79 libremedia\.video| 80 live\.libratoi\.org| 81 live\.nanao\.moe| 82 live\.toobnix\.org| 83 livegram\.net| 84 lolitube\.freedomchan\.moe| 85 lucarne\.balsamine\.be| 86 maindreieck-tv\.de| 87 mani\.tube| 88 manicphase\.me| 89 media\.gzevd\.de| 90 media\.inno3\.cricket| 91 media\.kaitaia\.life| 92 media\.krashboyz\.org| 93 media\.over-world\.org| 94 media\.skewed\.de| 95 media\.undeadnetwork\.de| 96 medias\.pingbase\.net| 97 melsungen\.peertube-host\.de| 98 mirametube\.fr| 99 mojotube\.net| 100 monplaisirtube\.ddns\.net| 101 mountaintown\.video| 102 my\.bunny\.cafe| 103 myfreetube\.de| 104 mytube\.kn-cloud\.de| 105 mytube\.madzel\.de| 106 myworkoutarenapeertube\.cf| 107 nanawel-peertube\.dyndns\.org| 108 nastub\.cz| 109 offenes\.tv| 110 orgdup\.media| 111 ovaltube\.codinglab\.ch| 112 p2ptv\.ru| 113 p\.eertu\.be| 114 p\.lu| 115 peer\.azurs\.fr| 116 peertube1\.zeteo\.me| 117 peertube\.020\.pl| 118 peertube\.0x5e\.eu| 119 peertube\.alpharius\.io| 120 peertube\.am-networks\.fr| 121 peertube\.anduin\.net| 122 peertube\.anzui\.dev| 123 peertube\.arbleizez\.bzh| 124 peertube\.art3mis\.de| 125 peertube\.atilla\.org| 126 peertube\.atsuchan\.page| 127 peertube\.aukfood\.net| 128 peertube\.aventer\.biz| 129 peertube\.b38\.rural-it\.org| 130 peertube\.beeldengeluid\.nl| 131 peertube\.be| 132 peertube\.bgzashtita\.es| 133 peertube\.bitsandlinux\.com| 134 peertube\.biz| 135 peertube\.boba\.best| 136 peertube\.br0\.fr| 137 peertube\.bridaahost\.ynh\.fr| 138 peertube\.bubbletea\.dev| 139 peertube\.bubuit\.net| 140 peertube\.cabaal\.net| 141 peertube\.cats-home\.net| 142 peertube\.chemnitz\.freifunk\.net| 143 peertube\.chevro\.fr| 144 peertube\.chrisspiegl\.com| 145 peertube\.chtisurel\.net| 146 peertube\.cipherbliss\.com| 147 peertube\.cloud\.sans\.pub| 148 peertube\.cpge-brizeux\.fr| 149 peertube\.ctseuro\.com| 150 peertube\.cuatrolibertades\.org| 151 peertube\.cybercirujas\.club| 152 peertube\.cythin\.com| 153 peertube\.davigge\.com| 154 peertube\.dc\.pini\.fr| 155 peertube\.debian\.social| 156 peertube\.demonix\.fr| 157 peertube\.designersethiques\.org| 158 peertube\.desmu\.fr| 159 peertube\.devloprog\.org| 160 peertube\.devol\.it| 161 peertube\.dtmf\.ca| 162 peertube\.ecologie\.bzh| 163 peertube\.eu\.org| 164 peertube\.european-pirates\.eu| 165 peertube\.euskarabildua\.eus| 166 peertube\.fenarinarsa\.com| 167 peertube\.fomin\.site| 168 peertube\.forsud\.be| 169 peertube\.francoispelletier\.org| 170 peertube\.freenet\.ru| 171 peertube\.freetalklive\.com| 172 peertube\.functional\.cafe| 173 peertube\.gardeludwig\.fr| 174 peertube\.gargantia\.fr| 175 peertube\.gcfamily\.fr| 176 peertube\.genma\.fr| 177 peertube\.get-racing\.de| 178 peertube\.gidikroon\.eu| 179 peertube\.gruezishop\.ch| 180 peertube\.habets\.house| 181 peertube\.hackerfraternity\.org| 182 peertube\.ichigo\.everydayimshuflin\.com| 183 peertube\.ignifi\.me| 184 peertube\.inapurna\.org| 185 peertube\.informaction\.info| 186 peertube\.interhop\.org| 187 peertube\.iselfhost\.com| 188 peertube\.it| 189 peertube\.jensdiemer\.de| 190 peertube\.joffreyverd\.fr| 191 peertube\.kalua\.im| 192 peertube\.kathryl\.fr| 193 peertube\.keazilla\.net| 194 peertube\.klaewyss\.fr| 195 peertube\.kodcast\.com| 196 peertube\.kx\.studio| 197 peertube\.lagvoid\.com| 198 peertube\.lavallee\.tech| 199 peertube\.le5emeaxe\.fr| 200 peertube\.lestutosdeprocessus\.fr| 201 peertube\.librenet\.co\.za| 202 peertube\.logilab\.fr| 203 peertube\.louisematic\.site| 204 peertube\.luckow\.org| 205 peertube\.luga\.at| 206 peertube\.lyceeconnecte\.fr| 207 peertube\.manalejandro\.com| 208 peertube\.marud\.fr| 209 peertube\.mattone\.net| 210 peertube\.maxweiss\.io| 211 peertube\.monlycee\.net| 212 peertube\.mxinfo\.fr| 213 peertube\.myrasp\.eu| 214 peertube\.nebelcloud\.de| 215 peertube\.netzbegruenung\.de| 216 peertube\.newsocial\.tech| 217 peertube\.nicolastissot\.fr| 218 peertube\.nz| 219 peertube\.offerman\.com| 220 peertube\.opencloud\.lu| 221 peertube\.orthus\.link| 222 peertube\.patapouf\.xyz| 223 peertube\.pi2\.dev| 224 peertube\.plataformess\.org| 225 peertube\.pl| 226 peertube\.portaesgnos\.org| 227 peertube\.r2\.enst\.fr| 228 peertube\.r5c3\.fr| 229 peertube\.radres\.xyz| 230 peertube\.red| 231 peertube\.robonomics\.network| 232 peertube\.rtnkv\.cloud| 233 peertube\.runfox\.tk| 234 peertube\.satoshishop\.de| 235 peertube\.scic-tetris\.org| 236 peertube\.securitymadein\.lu| 237 peertube\.semweb\.pro| 238 peertube\.social\.my-wan\.de| 239 peertube\.soykaf\.org| 240 peertube\.stefofficiel\.me| 241 peertube\.stream| 242 peertube\.su| 243 peertube\.swrs\.net| 244 peertube\.takeko\.cyou| 245 peertube\.tangentfox\.com| 246 peertube\.taxinachtegel\.de| 247 peertube\.thenewoil\.xyz| 248 peertube\.ti-fr\.com| 249 peertube\.tiennot\.net| 250 peertube\.troback\.com| 251 peertube\.tspu\.edu\.ru| 252 peertube\.tux\.ovh| 253 peertube\.tv| 254 peertube\.tweb\.tv| 255 peertube\.ucy\.de| 256 peertube\.underworld\.fr| 257 peertube\.us\.to| 258 peertube\.ventresmous\.fr| 259 peertube\.vlaki\.cz| 260 peertube\.w\.utnw\.de| 261 peertube\.westring\.digital| 262 peertube\.xwiki\.com| 263 peertube\.zoz-serv\.org| 264 peervideo\.ru| 265 periscope\.numenaute\.org| 266 perron-tube\.de| 267 petitlutinartube\.fr| 268 phijkchu\.com| 269 pierre\.tube| 270 piraten\.space| 271 play\.rosano\.ca| 272 player\.ojamajo\.moe| 273 plextube\.nl| 274 pocketnetpeertube1\.nohost\.me| 275 pocketnetpeertube3\.nohost\.me| 276 pocketnetpeertube4\.nohost\.me| 277 pocketnetpeertube5\.nohost\.me| 278 pocketnetpeertube6\.nohost\.me| 279 pt\.24-7\.ro| 280 pt\.apathy\.top| 281 pt\.diaspodon\.fr| 282 pt\.fedi\.tech| 283 pt\.maciej\.website| 284 ptb\.lunarviews\.net| 285 ptmir1\.inter21\.net| 286 ptmir2\.inter21\.net| 287 ptmir3\.inter21\.net| 288 ptmir4\.inter21\.net| 289 ptmir5\.inter21\.net| 290 ptube\.horsentiers\.fr| 291 ptube\.xmanifesto\.club| 292 queermotion\.org| 293 re-wizja\.re-medium\.com| 294 regarder\.sans\.pub| 295 ruraletv\.ovh| 296 s1\.gegenstimme\.tv| 297 s2\.veezee\.tube| 298 sdmtube\.fr| 299 sender-fm\.veezee\.tube| 300 serv1\.wiki-tube\.de| 301 serv3\.wiki-tube\.de| 302 sickstream\.net| 303 sleepy\.tube| 304 sovran\.video| 305 spectra\.video| 306 stream\.elven\.pw| 307 stream\.k-prod\.fr| 308 stream\.shahab\.nohost\.me| 309 streamsource\.video| 310 studios\.racer159\.com| 311 testtube\.florimond\.eu| 312 tgi\.hosted\.spacebear\.ee| 313 thaitube\.in\.th| 314 the\.jokertv\.eu| 315 theater\.ethernia\.net| 316 thecool\.tube| 317 tilvids\.com| 318 toob\.bub\.org| 319 tpaw\.video| 320 truetube\.media| 321 tuba\.lhub\.pl| 322 tube-aix-marseille\.beta\.education\.fr| 323 tube-amiens\.beta\.education\.fr| 324 tube-besancon\.beta\.education\.fr| 325 tube-bordeaux\.beta\.education\.fr| 326 tube-clermont-ferrand\.beta\.education\.fr| 327 tube-corse\.beta\.education\.fr| 328 tube-creteil\.beta\.education\.fr| 329 tube-dijon\.beta\.education\.fr| 330 tube-education\.beta\.education\.fr| 331 tube-grenoble\.beta\.education\.fr| 332 tube-lille\.beta\.education\.fr| 333 tube-limoges\.beta\.education\.fr| 334 tube-montpellier\.beta\.education\.fr| 335 tube-nancy\.beta\.education\.fr| 336 tube-nantes\.beta\.education\.fr| 337 tube-nice\.beta\.education\.fr| 338 tube-normandie\.beta\.education\.fr| 339 tube-orleans-tours\.beta\.education\.fr| 340 tube-outremer\.beta\.education\.fr| 341 tube-paris\.beta\.education\.fr| 342 tube-poitiers\.beta\.education\.fr| 343 tube-reims\.beta\.education\.fr| 344 tube-rennes\.beta\.education\.fr| 345 tube-strasbourg\.beta\.education\.fr| 346 tube-toulouse\.beta\.education\.fr| 347 tube-versailles\.beta\.education\.fr| 348 tube1\.it\.tuwien\.ac\.at| 349 tube\.abolivier\.bzh| 350 tube\.ac-amiens\.fr| 351 tube\.aerztefueraufklaerung\.de| 352 tube\.alexx\.ml| 353 tube\.amic37\.fr| 354 tube\.anufrij\.de| 355 tube\.apolut\.net| 356 tube\.arkhalabs\.io| 357 tube\.arthack\.nz| 358 tube\.as211696\.net| 359 tube\.avensio\.de| 360 tube\.azbyka\.ru| 361 tube\.azkware\.net| 362 tube\.bachaner\.fr| 363 tube\.bmesh\.org| 364 tube\.borked\.host| 365 tube\.bstly\.de| 366 tube\.chaoszone\.tv| 367 tube\.chatelet\.ovh| 368 tube\.cloud-libre\.eu| 369 tube\.cms\.garden| 370 tube\.cowfee\.moe| 371 tube\.cryptography\.dog| 372 tube\.darknight-coffee\.org| 373 tube\.dev\.lhub\.pl| 374 tube\.distrilab\.fr| 375 tube\.dsocialize\.net| 376 tube\.ebin\.club| 377 tube\.fdn\.fr| 378 tube\.florimond\.eu| 379 tube\.foxarmy\.ml| 380 tube\.foxden\.party| 381 tube\.frischesicht\.de| 382 tube\.futuretic\.fr| 383 tube\.gnous\.eu| 384 tube\.grap\.coop| 385 tube\.graz\.social| 386 tube\.grin\.hu| 387 tube\.hackerscop\.org| 388 tube\.hordearii\.fr| 389 tube\.jeena\.net| 390 tube\.kai-stuht\.com| 391 tube\.kockatoo\.org| 392 tube\.kotur\.org| 393 tube\.lacaveatonton\.ovh| 394 tube\.linkse\.media| 395 tube\.lokad\.com| 396 tube\.lucie-philou\.com| 397 tube\.melonbread\.xyz| 398 tube\.mfraters\.net| 399 tube\.motuhake\.xyz| 400 tube\.mrbesen\.de| 401 tube\.nah\.re| 402 tube\.nchoco\.net| 403 tube\.novg\.net| 404 tube\.nox-rhea\.org| 405 tube\.nuagelibre\.fr| 406 tube\.nx12\.net| 407 tube\.octaplex\.net| 408 tube\.odat\.xyz| 409 tube\.oisux\.org| 410 tube\.opportunis\.me| 411 tube\.org\.il| 412 tube\.ortion\.xyz| 413 tube\.others\.social| 414 tube\.picasoft\.net| 415 tube\.plomlompom\.com| 416 tube\.pmj\.rocks| 417 tube\.portes-imaginaire\.org| 418 tube\.pyngu\.com| 419 tube\.rebellion\.global| 420 tube\.rhythms-of-resistance\.org| 421 tube\.rita\.moe| 422 tube\.rsi\.cnr\.it| 423 tube\.s1gm4\.eu| 424 tube\.saumon\.io| 425 tube\.schleuss\.online| 426 tube\.schule\.social| 427 tube\.seditio\.fr| 428 tube\.shanti\.cafe| 429 tube\.shela\.nu| 430 tube\.skrep\.in| 431 tube\.sp-codes\.de| 432 tube\.sp4ke\.com| 433 tube\.superseriousbusiness\.org| 434 tube\.systest\.eu| 435 tube\.tappret\.fr| 436 tube\.tardis\.world| 437 tube\.toontoet\.nl| 438 tube\.tpshd\.de| 439 tube\.troopers\.agency| 440 tube\.tylerdavis\.xyz| 441 tube\.undernet\.uy| 442 tube\.vigilian-consulting\.nl| 443 tube\.vraphim\.com| 444 tube\.wehost\.lgbt| 445 tube\.wien\.rocks| 446 tube\.wolfe\.casa| 447 tube\.xd0\.de| 448 tube\.xy-space\.de| 449 tube\.yapbreak\.fr| 450 tubedu\.org| 451 tubes\.jodh\.us| 452 tuktube\.com| 453 turkum\.me| 454 tututu\.tube| 455 tuvideo\.encanarias\.info| 456 tv1\.cocu\.cc| 457 tv1\.gomntu\.space| 458 tv2\.cocu\.cc| 459 tv\.adn\.life| 460 tv\.atmx\.ca| 461 tv\.bitma\.st| 462 tv\.generallyrubbish\.net\.au| 463 tv\.lumbung\.space| 464 tv\.mattchristiansenmedia\.com| 465 tv\.netwhood\.online| 466 tv\.neue\.city| 467 tv\.piejacker\.net| 468 tv\.pirateradio\.social| 469 tv\.undersco\.re| 470 tvox\.ru| 471 twctube\.twc-zone\.eu| 472 unfilter\.tube| 473 v\.basspistol\.org| 474 v\.kisombrella\.top| 475 v\.lastorder\.xyz| 476 v\.lor\.sh| 477 v\.phreedom\.club| 478 v\.sil\.sh| 479 v\.szy\.io| 480 v\.xxxapex\.com| 481 veezee\.tube| 482 vid\.dascoyote\.xyz| 483 vid\.garwood\.io| 484 vid\.ncrypt\.at| 485 vid\.pravdastalina\.info| 486 vid\.qorg11\.net| 487 vid\.rajeshtaylor\.com| 488 vid\.samtripoli\.com| 489 vid\.werefox\.dev| 490 vid\.wildeboer\.net| 491 video-cave-v2\.de| 492 video\.076\.ne\.jp| 493 video\.1146\.nohost\.me| 494 video\.altertek\.org| 495 video\.anartist\.org| 496 video\.apps\.thedoodleproject\.net| 497 video\.artist\.cx| 498 video\.asgardius\.company| 499 video\.balsillie\.net| 500 video\.bards\.online| 501 video\.binarydad\.com| 502 video\.blast-info\.fr| 503 video\.catgirl\.biz| 504 video\.cigliola\.com| 505 video\.cm-en-transition\.fr| 506 video\.cnt\.social| 507 video\.coales\.co| 508 video\.codingfield\.com| 509 video\.comptoir\.net| 510 video\.comune\.trento\.it| 511 video\.cpn\.so| 512 video\.csc49\.fr| 513 video\.cybre\.town| 514 video\.demokratischer-sommer\.de| 515 video\.discord-insoumis\.fr| 516 video\.dolphincastle\.com| 517 video\.dresden\.network| 518 video\.ecole-89\.com| 519 video\.elgrillolibertario\.org| 520 video\.emergeheart\.info| 521 video\.eradicatinglove\.xyz| 522 video\.ethantheenigma\.me| 523 video\.exodus-privacy\.eu\.org| 524 video\.fbxl\.net| 525 video\.fhtagn\.org| 526 video\.greenmycity\.eu| 527 video\.guerredeclasse\.fr| 528 video\.gyt\.is| 529 video\.hackers\.town| 530 video\.hardlimit\.com| 531 video\.hooli\.co| 532 video\.igem\.org| 533 video\.internet-czas-dzialac\.pl| 534 video\.islameye\.com| 535 video\.kicik\.fr| 536 video\.kuba-orlik\.name| 537 video\.kyushojitsu\.ca| 538 video\.lavolte\.net| 539 video\.lespoesiesdheloise\.fr| 540 video\.liberta\.vip| 541 video\.liege\.bike| 542 video\.linc\.systems| 543 video\.linux\.it| 544 video\.linuxtrent\.it| 545 video\.lokal\.social| 546 video\.lono\.space| 547 video\.lunasqu\.ee| 548 video\.lundi\.am| 549 video\.marcorennmaus\.de| 550 video\.mass-trespass\.uk| 551 video\.mugoreve\.fr| 552 video\.mundodesconocido\.com| 553 video\.mycrowd\.ca| 554 video\.nogafam\.es| 555 video\.odayacres\.farm| 556 video\.ozgurkon\.org| 557 video\.p1ng0ut\.social| 558 video\.p3x\.de| 559 video\.pcf\.fr| 560 video\.pony\.gallery| 561 video\.potate\.space| 562 video\.pourpenser\.pro| 563 video\.progressiv\.dev| 564 video\.resolutions\.it| 565 video\.rw501\.de| 566 video\.screamer\.wiki| 567 video\.sdm-tools\.net| 568 video\.sftblw\.moe| 569 video\.shitposter\.club| 570 video\.skyn3t\.in| 571 video\.soi\.ch| 572 video\.stuartbrand\.co\.uk| 573 video\.thinkof\.name| 574 video\.toot\.pt| 575 video\.triplea\.fr| 576 video\.turbo\.chat| 577 video\.vaku\.org\.ua| 578 video\.veloma\.org| 579 video\.violoncello\.ch| 580 video\.wilkie\.how| 581 video\.wsf2021\.info| 582 videorelay\.co| 583 videos-passages\.huma-num\.fr| 584 videos\.3d-wolf\.com| 585 videos\.ahp-numerique\.fr| 586 videos\.alexandrebadalo\.pt| 587 videos\.archigny\.net| 588 videos\.benjaminbrady\.ie| 589 videos\.buceoluegoexisto\.com| 590 videos\.capas\.se| 591 videos\.casually\.cat| 592 videos\.cloudron\.io| 593 videos\.coletivos\.org| 594 videos\.danksquad\.org| 595 videos\.denshi\.live| 596 videos\.fromouter\.space| 597 videos\.fsci\.in| 598 videos\.globenet\.org| 599 videos\.hauspie\.fr| 600 videos\.hush\.is| 601 videos\.john-livingston\.fr| 602 videos\.jordanwarne\.xyz| 603 videos\.lavoixdessansvoix\.org| 604 videos\.leslionsfloorball\.fr| 605 videos\.lucero\.top| 606 videos\.martyn\.berlin| 607 videos\.mastodont\.cat| 608 videos\.monstro1\.com| 609 videos\.npo\.city| 610 videos\.optoutpod\.com| 611 videos\.petch\.rocks| 612 videos\.pzelawski\.xyz| 613 videos\.rampin\.org| 614 videos\.scanlines\.xyz| 615 videos\.shmalls\.pw| 616 videos\.sibear\.fr| 617 videos\.stadtfabrikanten\.org| 618 videos\.tankernn\.eu| 619 videos\.testimonia\.org| 620 videos\.thisishowidontdisappear\.com| 621 videos\.traumaheilung\.net| 622 videos\.trom\.tf| 623 videos\.wakkerewereld\.nu| 624 videos\.weblib\.re| 625 videos\.yesil\.club| 626 vids\.roshless\.me| 627 vids\.tekdmn\.me| 628 vidz\.dou\.bet| 629 vod\.lumikko\.dev| 630 vs\.uniter\.network| 631 vulgarisation-informatique\.fr| 632 watch\.breadtube\.tv| 633 watch\.deranalyst\.ch| 634 watch\.ignorance\.eu| 635 watch\.krazy\.party| 636 watch\.libertaria\.space| 637 watch\.rt4mn\.org| 638 watch\.softinio\.com| 639 watch\.tubelab\.video| 640 web-fellow\.de| 641 webtv\.vandoeuvre\.net| 642 wechill\.space| 643 wikileaks\.video| 644 wiwi\.video| 645 worldofvids\.com| 646 wwtube\.net| 647 www4\.mir\.inter21\.net| 648 www\.birkeundnymphe\.de| 649 www\.captain-german\.com| 650 www\.wiki-tube\.de| 651 xxivproduction\.video| 652 xxx\.noho\.st| 653 654 # from youtube-dl 655 peertube\.rainbowswingers\.net| 656 tube\.stanisic\.nl| 657 peer\.suiri\.us| 658 medias\.libox\.fr| 659 videomensoif\.ynh\.fr| 660 peertube\.travelpandas\.eu| 661 peertube\.rachetjay\.fr| 662 peertube\.montecsys\.fr| 663 tube\.eskuero\.me| 664 peer\.tube| 665 peertube\.umeahackerspace\.se| 666 tube\.nx-pod\.de| 667 video\.monsieurbidouille\.fr| 668 tube\.openalgeria\.org| 669 vid\.lelux\.fi| 670 video\.anormallostpod\.ovh| 671 tube\.crapaud-fou\.org| 672 peertube\.stemy\.me| 673 lostpod\.space| 674 exode\.me| 675 peertube\.snargol\.com| 676 vis\.ion\.ovh| 677 videosdulib\.re| 678 v\.mbius\.io| 679 videos\.judrey\.eu| 680 peertube\.osureplayviewer\.xyz| 681 peertube\.mathieufamily\.ovh| 682 www\.videos-libr\.es| 683 fightforinfo\.com| 684 peertube\.fediverse\.ru| 685 peertube\.oiseauroch\.fr| 686 video\.nesven\.eu| 687 v\.bearvideo\.win| 688 video\.qoto\.org| 689 justporn\.cc| 690 video\.vny\.fr| 691 peervideo\.club| 692 tube\.taker\.fr| 693 peertube\.chantierlibre\.org| 694 tube\.ipfixe\.info| 695 tube\.kicou\.info| 696 tube\.dodsorf\.as| 697 videobit\.cc| 698 video\.yukari\.moe| 699 videos\.elbinario\.net| 700 hkvideo\.live| 701 pt\.tux\.tf| 702 www\.hkvideo\.live| 703 FIGHTFORINFO\.com| 704 pt\.765racing\.com| 705 peertube\.gnumeria\.eu\.org| 706 nordenmedia\.com| 707 peertube\.co\.uk| 708 tube\.darfweb\.eu| 709 tube\.kalah-france\.org| 710 0ch\.in| 711 vod\.mochi\.academy| 712 film\.node9\.org| 713 peertube\.hatthieves\.es| 714 video\.fitchfamily\.org| 715 peertube\.ddns\.net| 716 video\.ifuncle\.kr| 717 video\.fdlibre\.eu| 718 tube\.22decembre\.eu| 719 peertube\.harmoniescreatives\.com| 720 tube\.fabrigli\.fr| 721 video\.thedwyers\.co| 722 video\.bruitbruit\.com| 723 peertube\.foxfam\.club| 724 peer\.philoxweb\.be| 725 videos\.bugs\.social| 726 peertube\.malbert\.xyz| 727 peertube\.bilange\.ca| 728 libretube\.net| 729 diytelevision\.com| 730 peertube\.fedilab\.app| 731 libre\.video| 732 video\.mstddntfdn\.online| 733 us\.tv| 734 peertube\.sl-network\.fr| 735 peertube\.dynlinux\.io| 736 peertube\.david\.durieux\.family| 737 peertube\.linuxrocks\.online| 738 peerwatch\.xyz| 739 v\.kretschmann\.social| 740 tube\.otter\.sh| 741 yt\.is\.nota\.live| 742 tube\.dragonpsi\.xyz| 743 peertube\.boneheadmedia\.com| 744 videos\.funkwhale\.audio| 745 watch\.44con\.com| 746 peertube\.gcaillaut\.fr| 747 peertube\.icu| 748 pony\.tube| 749 spacepub\.space| 750 tube\.stbr\.io| 751 v\.mom-gay\.faith| 752 tube\.port0\.xyz| 753 peertube\.simounet\.net| 754 play\.jergefelt\.se| 755 peertube\.zeteo\.me| 756 tube\.danq\.me| 757 peertube\.kerenon\.com| 758 tube\.fab-l3\.org| 759 tube\.calculate\.social| 760 peertube\.mckillop\.org| 761 tube\.netzspielplatz\.de| 762 vod\.ksite\.de| 763 peertube\.laas\.fr| 764 tube\.govital\.net| 765 peertube\.stephenson\.cc| 766 bistule\.nohost\.me| 767 peertube\.kajalinifi\.de| 768 video\.ploud\.jp| 769 video\.omniatv\.com| 770 peertube\.ffs2play\.fr| 771 peertube\.leboulaire\.ovh| 772 peertube\.tronic-studio\.com| 773 peertube\.public\.cat| 774 peertube\.metalbanana\.net| 775 video\.1000i100\.fr| 776 peertube\.alter-nativ-voll\.de| 777 tube\.pasa\.tf| 778 tube\.worldofhauru\.xyz| 779 pt\.kamp\.site| 780 peertube\.teleassist\.fr| 781 videos\.mleduc\.xyz| 782 conf\.tube| 783 media\.privacyinternational\.org| 784 pt\.forty-two\.nl| 785 video\.halle-leaks\.de| 786 video\.grosskopfgames\.de| 787 peertube\.schaeferit\.de| 788 peertube\.jackbot\.fr| 789 tube\.extinctionrebellion\.fr| 790 peertube\.f-si\.org| 791 video\.subak\.ovh| 792 videos\.koweb\.fr| 793 peertube\.zergy\.net| 794 peertube\.roflcopter\.fr| 795 peertube\.floss-marketing-school\.com| 796 vloggers\.social| 797 peertube\.iriseden\.eu| 798 videos\.ubuntu-paris\.org| 799 peertube\.mastodon\.host| 800 armstube\.com| 801 peertube\.s2s\.video| 802 peertube\.lol| 803 tube\.open-plug\.eu| 804 open\.tube| 805 peertube\.ch| 806 peertube\.normandie-libre\.fr| 807 peertube\.slat\.org| 808 video\.lacaveatonton\.ovh| 809 peertube\.uno| 810 peertube\.servebeer\.com| 811 peertube\.fedi\.quebec| 812 tube\.h3z\.jp| 813 tube\.plus200\.com| 814 peertube\.eric\.ovh| 815 tube\.metadocs\.cc| 816 tube\.unmondemeilleur\.eu| 817 gouttedeau\.space| 818 video\.antirep\.net| 819 nrop\.cant\.at| 820 tube\.ksl-bmx\.de| 821 tube\.plaf\.fr| 822 tube\.tchncs\.de| 823 video\.devinberg\.com| 824 hitchtube\.fr| 825 peertube\.kosebamse\.com| 826 yunopeertube\.myddns\.me| 827 peertube\.varney\.fr| 828 peertube\.anon-kenkai\.com| 829 tube\.maiti\.info| 830 tubee\.fr| 831 videos\.dinofly\.com| 832 toobnix\.org| 833 videotape\.me| 834 voca\.tube| 835 video\.heromuster\.com| 836 video\.lemediatv\.fr| 837 video\.up\.edu\.ph| 838 balafon\.video| 839 video\.ivel\.fr| 840 thickrips\.cloud| 841 pt\.laurentkruger\.fr| 842 video\.monarch-pass\.net| 843 peertube\.artica\.center| 844 video\.alternanet\.fr| 845 indymotion\.fr| 846 fanvid\.stopthatimp\.net| 847 video\.farci\.org| 848 v\.lesterpig\.com| 849 video\.okaris\.de| 850 tube\.pawelko\.net| 851 peertube\.mablr\.org| 852 tube\.fede\.re| 853 pytu\.be| 854 evertron\.tv| 855 devtube\.dev-wiki\.de| 856 raptube\.antipub\.org| 857 video\.selea\.se| 858 peertube\.mygaia\.org| 859 video\.oh14\.de| 860 peertube\.livingutopia\.org| 861 peertube\.the-penguin\.de| 862 tube\.thechangebook\.org| 863 tube\.anjara\.eu| 864 pt\.pube\.tk| 865 video\.samedi\.pm| 866 mplayer\.demouliere\.eu| 867 widemus\.de| 868 peertube\.me| 869 peertube\.zapashcanon\.fr| 870 video\.latavernedejohnjohn\.fr| 871 peertube\.pcservice46\.fr| 872 peertube\.mazzonetto\.eu| 873 video\.irem\.univ-paris-diderot\.fr| 874 video\.livecchi\.cloud| 875 alttube\.fr| 876 video\.coop\.tools| 877 video\.cabane-libre\.org| 878 peertube\.openstreetmap\.fr| 879 videos\.alolise\.org| 880 irrsinn\.video| 881 video\.antopie\.org| 882 scitech\.video| 883 tube2\.nemsia\.org| 884 video\.amic37\.fr| 885 peertube\.freeforge\.eu| 886 video\.arbitrarion\.com| 887 video\.datsemultimedia\.com| 888 stoptrackingus\.tv| 889 peertube\.ricostrongxxx\.com| 890 docker\.videos\.lecygnenoir\.info| 891 peertube\.togart\.de| 892 tube\.postblue\.info| 893 videos\.domainepublic\.net| 894 peertube\.cyber-tribal\.com| 895 video\.gresille\.org| 896 peertube\.dsmouse\.net| 897 cinema\.yunohost\.support| 898 tube\.theocevaer\.fr| 899 repro\.video| 900 tube\.4aem\.com| 901 quaziinc\.com| 902 peertube\.metawurst\.space| 903 videos\.wakapo\.com| 904 video\.ploud\.fr| 905 video\.freeradical\.zone| 906 tube\.valinor\.fr| 907 refuznik\.video| 908 pt\.kircheneuenburg\.de| 909 peertube\.asrun\.eu| 910 peertube\.lagob\.fr| 911 videos\.side-ways\.net| 912 91video\.online| 913 video\.valme\.io| 914 video\.taboulisme\.com| 915 videos-libr\.es| 916 tv\.mooh\.fr| 917 nuage\.acostey\.fr| 918 video\.monsieur-a\.fr| 919 peertube\.librelois\.fr| 920 videos\.pair2jeux\.tube| 921 videos\.pueseso\.club| 922 peer\.mathdacloud\.ovh| 923 media\.assassinate-you\.net| 924 vidcommons\.org| 925 ptube\.rousset\.nom\.fr| 926 tube\.cyano\.at| 927 videos\.squat\.net| 928 video\.iphodase\.fr| 929 peertube\.makotoworkshop\.org| 930 peertube\.serveur\.slv-valbonne\.fr| 931 vault\.mle\.party| 932 hostyour\.tv| 933 videos\.hack2g2\.fr| 934 libre\.tube| 935 pire\.artisanlogiciel\.net| 936 videos\.numerique-en-commun\.fr| 937 video\.netsyms\.com| 938 video\.die-partei\.social| 939 video\.writeas\.org| 940 peertube\.swarm\.solvingmaz\.es| 941 tube\.pericoloso\.ovh| 942 watching\.cypherpunk\.observer| 943 videos\.adhocmusic\.com| 944 tube\.rfc1149\.net| 945 peertube\.librelabucm\.org| 946 videos\.numericoop\.fr| 947 peertube\.koehn\.com| 948 peertube\.anarchmusicall\.net| 949 tube\.kampftoast\.de| 950 vid\.y-y\.li| 951 peertube\.xtenz\.xyz| 952 diode\.zone| 953 tube\.egf\.mn| 954 peertube\.nomagic\.uk| 955 visionon\.tv| 956 videos\.koumoul\.com| 957 video\.rastapuls\.com| 958 video\.mantlepro\.com| 959 video\.deadsuperhero\.com| 960 peertube\.musicstudio\.pro| 961 peertube\.we-keys\.fr| 962 artitube\.artifaille\.fr| 963 peertube\.ethernia\.net| 964 tube\.midov\.pl| 965 peertube\.fr| 966 watch\.snoot\.tube| 967 peertube\.donnadieu\.fr| 968 argos\.aquilenet\.fr| 969 tube\.nemsia\.org| 970 tube\.bruniau\.net| 971 videos\.darckoune\.moe| 972 tube\.traydent\.info| 973 dev\.videos\.lecygnenoir\.info| 974 peertube\.nayya\.org| 975 peertube\.live| 976 peertube\.mofgao\.space| 977 video\.lequerrec\.eu| 978 peertube\.amicale\.net| 979 aperi\.tube| 980 tube\.ac-lyon\.fr| 981 video\.lw1\.at| 982 www\.yiny\.org| 983 videos\.pofilo\.fr| 984 tube\.lou\.lt| 985 choob\.h\.etbus\.ch| 986 tube\.hoga\.fr| 987 peertube\.heberge\.fr| 988 video\.obermui\.de| 989 videos\.cloudfrancois\.fr| 990 betamax\.video| 991 video\.typica\.us| 992 tube\.piweb\.be| 993 video\.blender\.org| 994 peertube\.cat| 995 tube\.kdy\.ch| 996 pe\.ertu\.be| 997 peertube\.social| 998 videos\.lescommuns\.org| 999 tv\.datamol\.org| 1000 videonaute\.fr| 1001 dialup\.express| 1002 peertube\.nogafa\.org| 1003 megatube\.lilomoino\.fr| 1004 peertube\.tamanoir\.foucry\.net| 1005 peertube\.devosi\.org| 1006 peertube\.1312\.media| 1007 tube\.bootlicker\.party| 1008 skeptikon\.fr| 1009 video\.blueline\.mg| 1010 tube\.homecomputing\.fr| 1011 tube\.ouahpiti\.info| 1012 video\.tedomum\.net| 1013 video\.g3l\.org| 1014 fontube\.fr| 1015 peertube\.gaialabs\.ch| 1016 tube\.kher\.nl| 1017 peertube\.qtg\.fr| 1018 video\.migennes\.net| 1019 tube\.p2p\.legal| 1020 troll\.tv| 1021 videos\.iut-orsay\.fr| 1022 peertube\.solidev\.net| 1023 videos\.cemea\.org| 1024 video\.passageenseine\.fr| 1025 videos\.festivalparminous\.org| 1026 peertube\.touhoppai\.moe| 1027 sikke\.fi| 1028 peer\.hostux\.social| 1029 share\.tube| 1030 peertube\.walkingmountains\.fr| 1031 videos\.benpro\.fr| 1032 peertube\.parleur\.net| 1033 peertube\.heraut\.eu| 1034 tube\.aquilenet\.fr| 1035 peertube\.gegeweb\.eu| 1036 framatube\.org| 1037 thinkerview\.video| 1038 tube\.conferences-gesticulees\.net| 1039 peertube\.datagueule\.tv| 1040 video\.lqdn\.fr| 1041 tube\.mochi\.academy| 1042 media\.zat\.im| 1043 video\.colibris-outilslibres\.org| 1044 tube\.svnet\.fr| 1045 peertube\.video| 1046 peertube2\.cpy\.re| 1047 peertube3\.cpy\.re| 1048 videos\.tcit\.fr| 1049 peertube\.cpy\.re| 1050 canard\.tube 1051 )''' 1052 _UUID_RE = r'[\da-zA-Z]{22}|[\da-fA-F]{8}-[\da-fA-F]{4}-[\da-fA-F]{4}-[\da-fA-F]{4}-[\da-fA-F]{12}' 1053 _API_BASE = 'https://%s/api/v1/videos/%s/%s' 1054 _VALID_URL = r'''(?x) 1055 (?: 1056 peertube:(?P<host>[^:]+):| 1057 https?://(?P<host_2>%s)/(?:videos/(?:watch|embed)|api/v\d/videos|w)/ 1058 ) 1059 (?P<id>%s) 1060 ''' % (_INSTANCES_RE, _UUID_RE) 1061 _TESTS = [{ 1062 'url': 'https://framatube.org/videos/watch/9c9de5e8-0a1e-484a-b099-e80766180a6d', 1063 'md5': '8563064d245a4be5705bddb22bb00a28', 1064 'info_dict': { 1065 'id': '9c9de5e8-0a1e-484a-b099-e80766180a6d', 1066 'ext': 'mp4', 1067 'title': 'What is PeerTube?', 1068 'description': 'md5:3fefb8dde2b189186ce0719fda6f7b10', 1069 'thumbnail': r're:https?://.*\.(?:jpg|png)', 1070 'timestamp': 1538391166, 1071 'upload_date': '20181001', 1072 'uploader': 'Framasoft', 1073 'uploader_id': '3', 1074 'uploader_url': 'https://framatube.org/accounts/framasoft', 1075 'channel': 'A propos de PeerTube', 1076 'channel_id': '2215', 1077 'channel_url': 'https://framatube.org/video-channels/joinpeertube', 1078 'language': 'en', 1079 'license': 'Attribution - Share Alike', 1080 'duration': 113, 1081 'view_count': int, 1082 'like_count': int, 1083 'dislike_count': int, 1084 'tags': ['framasoft', 'peertube'], 1085 'categories': ['Science & Technology'], 1086 } 1087 }, { 1088 'url': 'https://peertube2.cpy.re/w/122d093a-1ede-43bd-bd34-59d2931ffc5e', 1089 'info_dict': { 1090 'id': '122d093a-1ede-43bd-bd34-59d2931ffc5e', 1091 'ext': 'mp4', 1092 'title': 'E2E tests', 1093 'uploader_id': '37855', 1094 'timestamp': 1589276219, 1095 'upload_date': '20200512', 1096 'uploader': 'chocobozzz', 1097 } 1098 }, { 1099 'url': 'https://peertube2.cpy.re/w/3fbif9S3WmtTP8gGsC5HBd', 1100 'info_dict': { 1101 'id': '3fbif9S3WmtTP8gGsC5HBd', 1102 'ext': 'mp4', 1103 'title': 'E2E tests', 1104 'uploader_id': '37855', 1105 'timestamp': 1589276219, 1106 'upload_date': '20200512', 1107 'uploader': 'chocobozzz', 1108 }, 1109 }, { 1110 'url': 'https://peertube2.cpy.re/api/v1/videos/3fbif9S3WmtTP8gGsC5HBd', 1111 'info_dict': { 1112 'id': '3fbif9S3WmtTP8gGsC5HBd', 1113 'ext': 'mp4', 1114 'title': 'E2E tests', 1115 'uploader_id': '37855', 1116 'timestamp': 1589276219, 1117 'upload_date': '20200512', 1118 'uploader': 'chocobozzz', 1119 }, 1120 }, { 1121 # Issue #26002 1122 'url': 'peertube:spacepub.space:d8943b2d-8280-497b-85ec-bc282ec2afdc', 1123 'info_dict': { 1124 'id': 'd8943b2d-8280-497b-85ec-bc282ec2afdc', 1125 'ext': 'mp4', 1126 'title': 'Dot matrix printer shell demo', 1127 'uploader_id': '3', 1128 'timestamp': 1587401293, 1129 'upload_date': '20200420', 1130 'uploader': 'Drew DeVault', 1131 } 1132 }, { 1133 'url': 'https://peertube.debian.social/videos/watch/0b04f13d-1e18-4f1d-814e-4979aa7c9c44', 1134 'only_matching': True, 1135 }, { 1136 # nsfw 1137 'url': 'https://vod.ksite.de/videos/watch/9bb88cd3-9959-46d9-9ab9-33d2bb704c39', 1138 'only_matching': True, 1139 }, { 1140 'url': 'https://vod.ksite.de/videos/embed/fed67262-6edb-4d1c-833b-daa9085c71d7', 1141 'only_matching': True, 1142 }, { 1143 'url': 'https://peertube.tv/api/v1/videos/c1875674-97d0-4c94-a058-3f7e64c962e8', 1144 'only_matching': True, 1145 }, { 1146 'url': 'peertube:framatube.org:b37a5b9f-e6b5-415c-b700-04a5cd6ec205', 1147 'only_matching': True, 1148 }] 1149 1150 @staticmethod 1151 def _extract_peertube_url(webpage, source_url): 1152 mobj = re.match( 1153 r'https?://(?P<host>[^/]+)/(?:videos/(?:watch|embed)|w)/(?P<id>%s)' 1154 % PeerTubeIE._UUID_RE, source_url) 1155 if mobj and any(p in webpage for p in ( 1156 'meta property="og:platform" content="PeerTube"', 1157 '<title>PeerTube<', 1158 'There will be other non JS-based clients to access PeerTube', 1159 '>We are sorry but it seems that PeerTube is not compatible with your web browser.<')): 1160 return 'peertube:%s:%s' % mobj.group('host', 'id') 1161 1162 @staticmethod 1163 def _extract_urls(webpage, source_url): 1164 entries = re.findall( 1165 r'''(?x)<iframe[^>]+\bsrc=["\'](?P<url>(?:https?:)?//%s/videos/embed/%s)''' 1166 % (PeerTubeIE._INSTANCES_RE, PeerTubeIE._UUID_RE), webpage) 1167 if not entries: 1168 peertube_url = PeerTubeIE._extract_peertube_url(webpage, source_url) 1169 if peertube_url: 1170 entries = [peertube_url] 1171 return entries 1172 1173 def _call_api(self, host, video_id, path, note=None, errnote=None, fatal=True): 1174 return self._download_json( 1175 self._API_BASE % (host, video_id, path), video_id, 1176 note=note, errnote=errnote, fatal=fatal) 1177 1178 def _get_subtitles(self, host, video_id): 1179 captions = self._call_api( 1180 host, video_id, 'captions', note='Downloading captions JSON', 1181 fatal=False) 1182 if not isinstance(captions, dict): 1183 return 1184 data = captions.get('data') 1185 if not isinstance(data, list): 1186 return 1187 subtitles = {} 1188 for e in data: 1189 language_id = try_get(e, lambda x: x['language']['id'], compat_str) 1190 caption_url = urljoin('https://%s' % host, e.get('captionPath')) 1191 if not caption_url: 1192 continue 1193 subtitles.setdefault(language_id or 'en', []).append({ 1194 'url': caption_url, 1195 }) 1196 return subtitles 1197 1198 def _real_extract(self, url): 1199 mobj = self._match_valid_url(url) 1200 host = mobj.group('host') or mobj.group('host_2') 1201 video_id = mobj.group('id') 1202 1203 video = self._call_api( 1204 host, video_id, '', note='Downloading video JSON') 1205 1206 title = video['name'] 1207 1208 formats = [] 1209 files = video.get('files') or [] 1210 for playlist in (video.get('streamingPlaylists') or []): 1211 if not isinstance(playlist, dict): 1212 continue 1213 playlist_files = playlist.get('files') 1214 if not (playlist_files and isinstance(playlist_files, list)): 1215 continue 1216 files.extend(playlist_files) 1217 for file_ in files: 1218 if not isinstance(file_, dict): 1219 continue 1220 file_url = url_or_none(file_.get('fileUrl')) 1221 if not file_url: 1222 continue 1223 file_size = int_or_none(file_.get('size')) 1224 format_id = try_get( 1225 file_, lambda x: x['resolution']['label'], compat_str) 1226 f = parse_resolution(format_id) 1227 f.update({ 1228 'url': file_url, 1229 'format_id': format_id, 1230 'filesize': file_size, 1231 }) 1232 if format_id == '0p': 1233 f['vcodec'] = 'none' 1234 else: 1235 f['fps'] = int_or_none(file_.get('fps')) 1236 formats.append(f) 1237 self._sort_formats(formats) 1238 1239 description = video.get('description') 1240 if description and len(description) >= 250: 1241 # description is shortened 1242 full_description = self._call_api( 1243 host, video_id, 'description', note='Downloading description JSON', 1244 fatal=False) 1245 1246 if isinstance(full_description, dict): 1247 description = str_or_none(full_description.get('description')) or description 1248 1249 subtitles = self.extract_subtitles(host, video_id) 1250 1251 def data(section, field, type_): 1252 return try_get(video, lambda x: x[section][field], type_) 1253 1254 def account_data(field, type_): 1255 return data('account', field, type_) 1256 1257 def channel_data(field, type_): 1258 return data('channel', field, type_) 1259 1260 category = data('category', 'label', compat_str) 1261 categories = [category] if category else None 1262 1263 nsfw = video.get('nsfw') 1264 if nsfw is bool: 1265 age_limit = 18 if nsfw else 0 1266 else: 1267 age_limit = None 1268 1269 webpage_url = 'https://%s/videos/watch/%s' % (host, video_id) 1270 1271 return { 1272 'id': video_id, 1273 'title': title, 1274 'description': description, 1275 'thumbnail': urljoin(webpage_url, video.get('thumbnailPath')), 1276 'timestamp': unified_timestamp(video.get('publishedAt')), 1277 'uploader': account_data('displayName', compat_str), 1278 'uploader_id': str_or_none(account_data('id', int)), 1279 'uploader_url': url_or_none(account_data('url', compat_str)), 1280 'channel': channel_data('displayName', compat_str), 1281 'channel_id': str_or_none(channel_data('id', int)), 1282 'channel_url': url_or_none(channel_data('url', compat_str)), 1283 'language': data('language', 'id', compat_str), 1284 'license': data('licence', 'label', compat_str), 1285 'duration': int_or_none(video.get('duration')), 1286 'view_count': int_or_none(video.get('views')), 1287 'like_count': int_or_none(video.get('likes')), 1288 'dislike_count': int_or_none(video.get('dislikes')), 1289 'age_limit': age_limit, 1290 'tags': try_get(video, lambda x: x['tags'], list), 1291 'categories': categories, 1292 'formats': formats, 1293 'subtitles': subtitles, 1294 'webpage_url': webpage_url, 1295 } 1296 1297 1298class PeerTubePlaylistIE(InfoExtractor): 1299 IE_NAME = 'PeerTube:Playlist' 1300 _TYPES = { 1301 'a': 'accounts', 1302 'c': 'video-channels', 1303 'w/p': 'video-playlists', 1304 } 1305 _VALID_URL = r'''(?x) 1306 https?://(?P<host>%s)/(?P<type>(?:%s))/ 1307 (?P<id>[^/]+) 1308 ''' % (PeerTubeIE._INSTANCES_RE, '|'.join(_TYPES.keys())) 1309 _TESTS = [{ 1310 'url': 'https://peertube.tux.ovh/w/p/3af94cba-95e8-4b74-b37a-807ab6d82526', 1311 'info_dict': { 1312 'id': '3af94cba-95e8-4b74-b37a-807ab6d82526', 1313 'description': 'playlist', 1314 'timestamp': 1611171863, 1315 'title': 'playlist', 1316 }, 1317 'playlist_mincount': 6, 1318 }, { 1319 'url': 'https://peertube.tux.ovh/w/p/wkyqcQBnsvFxtUB2pkYc1e', 1320 'info_dict': { 1321 'id': 'wkyqcQBnsvFxtUB2pkYc1e', 1322 'description': 'Cette liste de vidéos contient uniquement les jeux qui peuvent être terminés en une seule vidéo.', 1323 'title': 'Let\'s Play', 1324 'timestamp': 1604147331, 1325 }, 1326 'playlist_mincount': 6, 1327 }, { 1328 'url': 'https://peertube.debian.social/w/p/hFdJoTuyhNJVa1cDWd1d12', 1329 'info_dict': { 1330 'id': 'hFdJoTuyhNJVa1cDWd1d12', 1331 'description': 'Diversas palestras do Richard Stallman no Brasil.', 1332 'title': 'Richard Stallman no Brasil', 1333 'timestamp': 1599676222, 1334 }, 1335 'playlist_mincount': 9, 1336 }, { 1337 'url': 'https://peertube2.cpy.re/a/chocobozzz/videos', 1338 'info_dict': { 1339 'id': 'chocobozzz', 1340 'timestamp': 1553874564, 1341 'title': 'chocobozzz', 1342 }, 1343 'playlist_mincount': 2, 1344 }, { 1345 'url': 'https://framatube.org/c/bf54d359-cfad-4935-9d45-9d6be93f63e8/videos', 1346 'info_dict': { 1347 'id': 'bf54d359-cfad-4935-9d45-9d6be93f63e8', 1348 'timestamp': 1519917377, 1349 'title': 'Les vidéos de Framasoft', 1350 }, 1351 'playlist_mincount': 345, 1352 }, { 1353 'url': 'https://peertube2.cpy.re/c/blender_open_movies@video.blender.org/videos', 1354 'info_dict': { 1355 'id': 'blender_open_movies@video.blender.org', 1356 'timestamp': 1542287810, 1357 'title': 'Official Blender Open Movies', 1358 }, 1359 'playlist_mincount': 11, 1360 }] 1361 _API_BASE = 'https://%s/api/v1/%s/%s%s' 1362 _PAGE_SIZE = 30 1363 1364 def call_api(self, host, name, path, base, **kwargs): 1365 return self._download_json( 1366 self._API_BASE % (host, base, name, path), name, **kwargs) 1367 1368 def fetch_page(self, host, id, type, page): 1369 page += 1 1370 video_data = self.call_api( 1371 host, id, 1372 f'/videos?sort=-createdAt&start={self._PAGE_SIZE * (page - 1)}&count={self._PAGE_SIZE}&nsfw=both', 1373 type, note=f'Downloading page {page}').get('data', []) 1374 for video in video_data: 1375 shortUUID = video.get('shortUUID') or try_get(video, lambda x: x['video']['shortUUID']) 1376 video_title = video.get('name') or try_get(video, lambda x: x['video']['name']) 1377 yield self.url_result( 1378 f'https://{host}/w/{shortUUID}', PeerTubeIE.ie_key(), 1379 video_id=shortUUID, video_title=video_title) 1380 1381 def _extract_playlist(self, host, type, id): 1382 info = self.call_api(host, id, '', type, note='Downloading playlist information', fatal=False) 1383 1384 playlist_title = info.get('displayName') 1385 playlist_description = info.get('description') 1386 playlist_timestamp = unified_timestamp(info.get('createdAt')) 1387 channel = try_get(info, lambda x: x['ownerAccount']['name']) or info.get('displayName') 1388 channel_id = try_get(info, lambda x: x['ownerAccount']['id']) or info.get('id') 1389 thumbnail = info.get('thumbnailPath') 1390 thumbnail = f'https://{host}{thumbnail}' if thumbnail else None 1391 1392 entries = OnDemandPagedList(functools.partial( 1393 self.fetch_page, host, id, type), self._PAGE_SIZE) 1394 1395 return self.playlist_result( 1396 entries, id, playlist_title, playlist_description, 1397 timestamp=playlist_timestamp, channel=channel, channel_id=channel_id, thumbnail=thumbnail) 1398 1399 def _real_extract(self, url): 1400 type, host, id = self._match_valid_url(url).group('type', 'host', 'id') 1401 type = self._TYPES[type] 1402 return self._extract_playlist(host, type, id) 1403