code:
# flake8: noqa: F401

from .youtube import (  # Youtube is moved to the top to improve performance
    YoutubeIE,
    YoutubeClipIE,
    YoutubeFavouritesIE,
    YoutubeNotificationsIE,
    YoutubeHistoryIE,
    YoutubeTabIE,
    YoutubeLivestreamEmbedIE,
    YoutubePlaylistIE,
    YoutubeRecommendedIE,
    YoutubeSearchDateIE,
    YoutubeSearchIE,
    YoutubeSearchURLIE,
    YoutubeMusicSearchURLIE,
    YoutubeSubscriptionsIE,
    YoutubeStoriesIE,
    YoutubeTruncatedIDIE,
    YoutubeTruncatedURLIE,
    YoutubeYtBeIE,
    YoutubeYtUserIE,
    YoutubeWatchLaterIE,
    YoutubeShortsAudioPivotIE
)

from .abc import (
    ABCIE,
    ABCIViewIE,
    ABCIViewShowSeriesIE,
)
from .abcnews import (
    AbcNewsIE,
    AbcNewsVideoIE,
)
from .abcotvs import (
    ABCOTVSIE,
    ABCOTVSClipsIE,
)
from .abematv import (
    AbemaTVIE,
    AbemaTVTitleIE,
)
from .academicearth import AcademicEarthCourseIE
from .acast import (
    ACastIE,
    ACastChannelIE,
)
from .acfun import AcFunVideoIE, AcFunBangumiIE
from .adn import ADNIE
from .adobeconnect import AdobeConnectIE
from .adobetv import (
    AdobeTVEmbedIE,
    AdobeTVIE,
    AdobeTVShowIE,
    AdobeTVChannelIE,
    AdobeTVVideoIE,
)
from .adultswim import AdultSwimIE
from .aenetworks import (
    AENetworksIE,
    AENetworksCollectionIE,
    AENetworksShowIE,
    HistoryTopicIE,
    HistoryPlayerIE,
    BiographyIE,
)
from .afreecatv import (
    AfreecaTVIE,
    AfreecaTVLiveIE,
    AfreecaTVUserIE,
)
from .airmozilla import AirMozillaIE
from .aljazeera import AlJazeeraIE
from .alphaporno import AlphaPornoIE
from .amara import AmaraIE
from .alura import (
    AluraIE,
    AluraCourseIE
)
from .amcnetworks import AMCNetworksIE
from .amazon import AmazonStoreIE
from .americastestkitchen import (
    AmericasTestKitchenIE,
    AmericasTestKitchenSeasonIE,
)
from .angel import AngelIE
from .anvato import AnvatoIE
from .aol import AolIE
from .allocine import AllocineIE
from .aliexpress import AliExpressLiveIE
from .alsace20tv import (
    Alsace20TVIE,
    Alsace20TVEmbedIE,
)
from .apa import APAIE
from .aparat import AparatIE
from .appleconnect import AppleConnectIE
from .appletrailers import (
    AppleTrailersIE,
    AppleTrailersSectionIE,
)
from .applepodcasts import ApplePodcastsIE
from .archiveorg import (
    ArchiveOrgIE,
    YoutubeWebArchiveIE,
)
from .arcpublishing import ArcPublishingIE
from .arkena import ArkenaIE
from .ard import (
    ARDBetaMediathekIE,
    ARDIE,
    ARDMediathekIE,
)
from .arte import (
    ArteTVIE,
    ArteTVEmbedIE,
    ArteTVPlaylistIE,
    ArteTVCategoryIE,
)
from .arnes import ArnesIE
from .asiancrush import (
    AsianCrushIE,
    AsianCrushPlaylistIE,
)
from .askmona import (
    AskMonaIE,
    AskMona3IE,
)
from .atresplayer import AtresPlayerIE
from .atscaleconf import AtScaleConfEventIE
from .atttechchannel import ATTTechChannelIE
from .atvat import ATVAtIE
from .audimedia import AudiMediaIE
from .audioboom import AudioBoomIE
from .audiodraft import (
    AudiodraftCustomIE,
    AudiodraftGenericIE,
)
from .audiomack import AudiomackIE, AudiomackAlbumIE
from .audius import (
    AudiusIE,
    AudiusTrackIE,
    AudiusPlaylistIE,
    AudiusProfileIE,
)
from .awaan import (
    AWAANIE,
    AWAANVideoIE,
    AWAANLiveIE,
    AWAANSeasonIE,
)
from .azmedien import AZMedienIE
from .baidu import BaiduVideoIE
from .banbye import (
    BanByeIE,
    BanByeChannelIE,
)
from .bandaichannel import BandaiChannelIE
from .bandcamp import (
    BandcampIE,
    BandcampAlbumIE,
    BandcampWeeklyIE,
    BandcampUserIE,
)
from .bannedvideo import BannedVideoIE
from .bbc import (
    BBCCoUkIE,
    BBCCoUkArticleIE,
    BBCCoUkIPlayerEpisodesIE,
    BBCCoUkIPlayerGroupIE,
    BBCCoUkPlaylistIE,
    BBCIE,
)
from .beeg import BeegIE
from .behindkink import BehindKinkIE
from .bellmedia import BellMediaIE
from .beatport import BeatportIE
from .bet import BetIE
from .bfi import BFIPlayerIE
from .bfmtv import (
    BFMTVIE,
    BFMTVLiveIE,
    BFMTVArticleIE,
)
from .bibeltv import BibelTVIE
from .bigflix import BigflixIE
from .bigo import BigoIE
from .bild import BildIE
from .bilibili import (
    BiliBiliIE,
    BiliBiliSearchIE,
    BilibiliCategoryIE,
    BiliBiliBangumiIE,
    BilibiliAudioIE,
    BilibiliAudioAlbumIE,
    BiliBiliPlayerIE,
    BilibiliSpaceVideoIE,
    BilibiliSpaceAudioIE,
    BilibiliSpacePlaylistIE,
    BiliIntlIE,
    BiliIntlSeriesIE,
    BiliLiveIE,
)
from .biobiochiletv import BioBioChileTVIE
from .bitchute import (
    BitChuteIE,
    BitChuteChannelIE,
)
from .bitwave import (
    BitwaveReplayIE,
    BitwaveStreamIE,
)
from .biqle import BIQLEIE
from .blackboardcollaborate import BlackboardCollaborateIE
from .bleacherreport import (
    BleacherReportIE,
    BleacherReportCMSIE,
)
from .blogger import BloggerIE
from .bloomberg import BloombergIE
from .bokecc import BokeCCIE
from .bongacams import BongaCamsIE
from .bostonglobe import BostonGlobeIE
from .box import BoxIE
from .bpb import BpbIE
from .br import (
    BRIE,
    BRMediathekIE,
)
from .bravotv import BravoTVIE
from .breakcom import BreakIE
from .breitbart import BreitBartIE
from .brightcove import (
    BrightcoveLegacyIE,
    BrightcoveNewIE,
)
from .businessinsider import BusinessInsiderIE
from .buzzfeed import BuzzFeedIE
from .byutv import BYUtvIE
from .c56 import C56IE
from .cableav import CableAVIE
from .callin import CallinIE
from .caltrans import CaltransIE
from .cam4 import CAM4IE
from .camdemy import (
    CamdemyIE,
    CamdemyFolderIE
)
from .cammodels import CamModelsIE
from .camtasia import CamtasiaEmbedIE
from .camwithher import CamWithHerIE
from .canalalpha import CanalAlphaIE
from .canalplus import CanalplusIE
from .canalc2 import Canalc2IE
from .canvas import (
    CanvasIE,
    CanvasEenIE,
    VrtNUIE,
    DagelijkseKostIE,
)
from .carambatv import (
    CarambaTVIE,
    CarambaTVPageIE,
)
from .cartoonnetwork import CartoonNetworkIE
from .cbc import (
    CBCIE,
    CBCPlayerIE,
    CBCGemIE,
    CBCGemPlaylistIE,
    CBCGemLiveIE,
)
from .cbs import CBSIE
from .cbslocal import (
    CBSLocalIE,
    CBSLocalArticleIE,
)
from .cbsinteractive import CBSInteractiveIE
from .cbsnews import (
    CBSNewsEmbedIE,
    CBSNewsIE,
    CBSNewsLiveVideoIE,
)
from .cbssports import (
    CBSSportsEmbedIE,
    CBSSportsIE,
    TwentyFourSevenSportsIE,
)
from .ccc import (
    CCCIE,
    CCCPlaylistIE,
)
from .ccma import CCMAIE
from .cctv import CCTVIE
from .cda import CDAIE
from .cellebrite import CellebriteIE
from .ceskatelevize import CeskaTelevizeIE
from .cgtn import CGTNIE
from .channel9 import Channel9IE
from .charlierose import CharlieRoseIE
from .chaturbate import ChaturbateIE
from .chilloutzone import ChilloutzoneIE
from .chingari import (
    ChingariIE,
    ChingariUserIE,
)
from .chirbit import (
    ChirbitIE,
    ChirbitProfileIE,
)
from .cinchcast import CinchcastIE
from .cinemax import CinemaxIE
from .ciscolive import (
    CiscoLiveSessionIE,
    CiscoLiveSearchIE,
)
from .ciscowebex import CiscoWebexIE
from .cjsw import CJSWIE
from .cliphunter import CliphunterIE
from .clippit import ClippitIE
from .cliprs import ClipRsIE
from .clipsyndicate import ClipsyndicateIE
from .closertotruth import CloserToTruthIE
from .cloudflarestream import CloudflareStreamIE
from .cloudy import CloudyIE
from .clubic import ClubicIE
from .clyp import ClypIE
from .cmt import CMTIE
from .cnbc import (
    CNBCIE,
    CNBCVideoIE,
)
from .cnn import (
    CNNIE,
    CNNBlogsIE,
    CNNArticleIE,
)
from .coub import CoubIE
from .comedycentral import (
    ComedyCentralIE,
    ComedyCentralTVIE,
)
from .commonmistakes import CommonMistakesIE, UnicodeBOMIE
from .commonprotocols import (
    MmsIE,
    RtmpIE,
)
from .condenast import CondeNastIE
from .contv import CONtvIE
from .corus import CorusIE
from .cpac import (
    CPACIE,
    CPACPlaylistIE,
)
from .cozytv import CozyTVIE
from .cracked import CrackedIE
from .crackle import CrackleIE
from .craftsy import CraftsyIE
from .crooksandliars import CrooksAndLiarsIE
from .crowdbunker import (
    CrowdBunkerIE,
    CrowdBunkerChannelIE,
)
from .crunchyroll import (
    CrunchyrollIE,
    CrunchyrollShowPlaylistIE,
    CrunchyrollBetaIE,
    CrunchyrollBetaShowIE,
)
from .cspan import CSpanIE, CSpanCongressIE
from .ctsnews import CtsNewsIE
from .ctv import CTVIE
from .ctvnews import CTVNewsIE
from .cultureunplugged import CultureUnpluggedIE
from .curiositystream import (
    CuriosityStreamIE,
    CuriosityStreamCollectionsIE,
    CuriosityStreamSeriesIE,
)
from .cwtv import CWTVIE
from .cybrary import (
    CybraryIE,
    CybraryCourseIE
)
from .daftsex import DaftsexIE
from .dailymail import DailyMailIE
from .dailymotion import (
    DailymotionIE,
    DailymotionPlaylistIE,
    DailymotionUserIE,
)
from .dailywire import (
    DailyWireIE,
    DailyWirePodcastIE,
)
from .damtomo import (
    DamtomoRecordIE,
    DamtomoVideoIE,
)
from .daum import (
    DaumIE,
    DaumClipIE,
    DaumPlaylistIE,
    DaumUserIE,
)
from .daystar import DaystarClipIE
from .dbtv import DBTVIE
from .dctp import DctpTvIE
from .deezer import (
    DeezerPlaylistIE,
    DeezerAlbumIE,
)
from .democracynow import DemocracynowIE
from .detik import Detik20IE
from .dfb import DFBIE
from .dhm import DHMIE
from .digg import DiggIE
from .dotsub import DotsubIE
from .douyutv import (
    DouyuShowIE,
    DouyuTVIE,
)
from .dplay import (
    DPlayIE,
    DiscoveryPlusIE,
    HGTVDeIE,
    GoDiscoveryIE,
    TravelChannelIE,
    CookingChannelIE,
    HGTVUsaIE,
    FoodNetworkIE,
    InvestigationDiscoveryIE,
    DestinationAmericaIE,
    AmHistoryChannelIE,
    ScienceChannelIE,
    DIYNetworkIE,
    DiscoveryLifeIE,
    AnimalPlanetIE,
    TLCIE,
    MotorTrendIE,
    DiscoveryPlusIndiaIE,
    DiscoveryNetworksDeIE,
    DiscoveryPlusItalyIE,
    DiscoveryPlusItalyShowIE,
    DiscoveryPlusIndiaShowIE,
)
from .dreisat import DreiSatIE
from .drbonanza import DRBonanzaIE
from .drtuber import DrTuberIE
from .drtv import (
    DRTVIE,
    DRTVLiveIE,
)
from .dtube import DTubeIE
from .dvtv import DVTVIE
from .duboku import (
    DubokuIE,
    DubokuPlaylistIE
)
from .dumpert import DumpertIE
from .defense import DefenseGouvFrIE
from .digitalconcerthall import DigitalConcertHallIE
from .discovery import DiscoveryIE
from .disney import DisneyIE
from .disneychris import DisneyChrisIE
from .dispeak import DigitallySpeakingIE
from .dnatube import DnaTubeIE
from .doodstream import DoodStreamIE
from .dropbox import DropboxIE
from .dropout import (
    DropoutSeasonIE,
    DropoutIE
)
from .dw import (
    DWIE,
    DWArticleIE,
)
from .eagleplatform import EaglePlatformIE, ClipYouEmbedIE
from .ebaumsworld import EbaumsWorldIE
from .echomsk import EchoMskIE
from .egghead import (
    EggheadCourseIE,
    EggheadLessonIE,
)
from .ehow import EHowIE
from .eighttracks import EightTracksIE
from .einthusan import EinthusanIE
from .eitb import EitbIE
from .ellentube import (
    EllenTubeIE,
    EllenTubeVideoIE,
    EllenTubePlaylistIE,
)
from .elonet import ElonetIE
from .elpais import ElPaisIE
from .embedly import EmbedlyIE
from .engadget import EngadgetIE
from .epicon import (
    EpiconIE,
    EpiconSeriesIE,
)
from .epoch import EpochIE
from .eporner import EpornerIE
from .eroprofile import (
    EroProfileIE,
    EroProfileAlbumIE,
)
from .ertgr import (
    ERTFlixCodenameIE,
    ERTFlixIE,
    ERTWebtvEmbedIE,
)
from .escapist import EscapistIE
from .espn import (
    ESPNIE,
    WatchESPNIE,
    ESPNArticleIE,
    FiveThirtyEightIE,
    ESPNCricInfoIE,
)
from .esri import EsriVideoIE
from .europa import EuropaIE
from .europeantour import EuropeanTourIE
from .eurosport import EurosportIE
from .euscreen import EUScreenIE
from .evoload import EvoLoadIE
from .expotv import ExpoTVIE
from .expressen import ExpressenIE
from .extremetube import ExtremeTubeIE
from .eyedotv import EyedoTVIE
from .eyny import EynyIE
from .facebook import (
    FacebookIE,
    FacebookPluginsVideoIE,
    FacebookRedirectURLIE,
    FacebookReelIE,
)
from .fancode import (
    FancodeVodIE,
    FancodeLiveIE
)

from .faz import FazIE
from .fc2 import (
    FC2IE,
    FC2EmbedIE,
    FC2LiveIE,
)
from .fczenit import FczenitIE
from .fifa import FifaIE
from .filmmodu import FilmmoduIE
from .filmon import (
    FilmOnIE,
    FilmOnChannelIE,
)
from .filmweb import FilmwebIE
from .firsttv import FirstTVIE
from .fivetv import FiveTVIE
from .flickr import FlickrIE
from .folketinget import FolketingetIE
from .footyroom import FootyRoomIE
from .formula1 import Formula1IE
from .fourtube import (
    FourTubeIE,
    PornTubeIE,
    PornerBrosIE,
    FuxIE,
)
from .fourzerostudio import (
    FourZeroStudioArchiveIE,
    FourZeroStudioClipIE,
)
from .fox import FOXIE
from .fox9 import (
    FOX9IE,
    FOX9NewsIE,
)
from .foxgay import FoxgayIE
from .foxnews import (
    FoxNewsIE,
    FoxNewsArticleIE,
)
from .foxsports import FoxSportsIE
from .fptplay import FptplayIE
from .franceinter import FranceInterIE
from .francetv import (
    FranceTVIE,
    FranceTVSiteIE,
    FranceTVInfoIE,
)
from .freesound import FreesoundIE
from .freespeech import FreespeechIE
from .frontendmasters import (
    FrontendMastersIE,
    FrontendMastersLessonIE,
    FrontendMastersCourseIE
)
from .freetv import (
    FreeTvIE,
    FreeTvMoviesIE,
)
from .fujitv import FujiTVFODPlus7IE
from .funimation import (
    FunimationIE,
    FunimationPageIE,
    FunimationShowIE,
)
from .funk import FunkIE
from .fusion import FusionIE
from .fuyintv import FuyinTVIE
from .gab import (
    GabTVIE,
)
from .gaia import GaiaIE
from .gameinformer import GameInformerIE
from .gamejolt import (
    GameJoltIE,
    GameJoltUserIE,
    GameJoltGameIE,
    GameJoltGameSoundtrackIE,
    GameJoltCommunityIE,
    GameJoltSearchIE,
)
from .gamespot import GameSpotIE
from .gamestar import GameStarIE
from .gaskrank import GaskrankIE
from .gazeta import GazetaIE
from .gdcvault import GDCVaultIE
from .gedidigital import GediDigitalIE
from .generic import GenericIE
from .gettr import (
    GettrIE,
    GettrStreamingIE,
)
from .gfycat import GfycatIE
from .giantbomb import GiantBombIE
from .giga import GigaIE
from .glide import GlideIE
from .globo import (
    GloboIE,
    GloboArticleIE,
)
from .go import GoIE
from .godtube import GodTubeIE
from .gofile import GofileIE
from .golem import GolemIE
from .goodgame import GoodGameIE
from .googledrive import (
    GoogleDriveIE,
    GoogleDriveFolderIE,
)
from .googlepodcasts import (
    GooglePodcastsIE,
    GooglePodcastsFeedIE,
)
from .googlesearch import GoogleSearchIE
from .gopro import GoProIE
from .goplay import GoPlayIE
from .gorin import (
    GorinLiveIE,
    GorinVideoIE,
)
from .goshgay import GoshgayIE
from .gotostage import GoToStageIE
from .gputechconf import GPUTechConfIE
from .gronkh import (
    GronkhIE,
    GronkhFeedIE,
    GronkhVodsIE
)
from .groupon import GrouponIE
from .harpodeon import HarpodeonIE
from .hbo import HBOIE
from .hearthisat import HearThisAtIE
from .heise import HeiseIE
from .hellporno import HellPornoIE
from .helsinki import HelsinkiIE
from .hentaistigma import HentaiStigmaIE
from .hgtv import HGTVComShowIE
from .hketv import HKETVIE
from .hidive import HiDiveIE
from .historicfilms import HistoricFilmsIE
from .hitbox import HitboxIE, HitboxLiveIE
from .hitrecord import HitRecordIE
from .holodex import HolodexIE
from .hotnewhiphop import HotNewHipHopIE
from .hotstar import (
    HotStarIE,
    HotStarPrefixIE,
    HotStarPlaylistIE,
    HotStarSeriesIE,
)
from .howcast import HowcastIE
from .howstuffworks import HowStuffWorksIE
from .hrfensehen import HRFernsehenIE
from .hrti import (
    HRTiIE,
    HRTiPlaylistIE,
)
from .hse import (
    HSEShowIE,
    HSEProductIE,
)
from .genericembeds import HTML5MediaEmbedIE
from .huajiao import HuajiaoIE
from .huya import HuyaLiveIE
from .huffpost import HuffPostIE
from .hungama import (
    HungamaIE,
    HungamaSongIE,
    HungamaAlbumPlaylistIE,
)
from .hypem import HypemIE
from .hytale import HytaleIE
from .icareus import IcareusIE
from .ichinanalive import (
    IchinanaLiveIE,
    IchinanaLiveClipIE,
)
from .ign import (
    IGNIE,
    IGNVideoIE,
    IGNArticleIE,
)
from .iheart import (
    IHeartRadioIE,
    IHeartRadioPodcastIE,
)
from .imdb import (
    ImdbIE,
    ImdbListIE
)
from .imgur import (
    ImgurIE,
    ImgurAlbumIE,
    ImgurGalleryIE,
)
from .ina import InaIE
from .inc import IncIE
from .indavideo import IndavideoEmbedIE
from .infoq import InfoQIE
from .instagram import (
    InstagramIE,
    InstagramIOSIE,
    InstagramUserIE,
    InstagramTagIE,
    InstagramStoryIE,
)
from .internazionale import InternazionaleIE
from .internetvideoarchive import InternetVideoArchiveIE
from .iprima import (
    IPrimaIE,
    IPrimaCNNIE
)
from .iqiyi import (
    IqiyiIE,
    IqIE,
    IqAlbumIE
)
from .islamchannel import (
    IslamChannelIE,
    IslamChannelSeriesIE,
)
from .itprotv import (
    ITProTVIE,
    ITProTVCourseIE
)
from .itv import (
    ITVIE,
    ITVBTCCIE,
)
from .ivi import (
    IviIE,
    IviCompilationIE
)
from .ivideon import IvideonIE
from .iwara import (
    IwaraIE,
    IwaraPlaylistIE,
    IwaraUserIE,
)
from .ixigua import IxiguaIE
from .izlesene import IzleseneIE
from .jable import (
    JableIE,
    JablePlaylistIE,
)
from .jamendo import (
    JamendoIE,
    JamendoAlbumIE,
)
from .jeuxvideo import JeuxVideoIE
from .jove import JoveIE
from .joj import JojIE
from .jwplatform import JWPlatformIE
from .kakao import KakaoIE
from .kaltura import KalturaIE
from .karaoketv import KaraoketvIE
from .karrierevideos import KarriereVideosIE
from .keezmovies import KeezMoviesIE
from .kelbyone import KelbyOneIE
from .ketnet import KetnetIE
from .khanacademy import (
    KhanAcademyIE,
    KhanAcademyUnitIE,
)
from .kicker import KickerIE
from .kickstarter import KickStarterIE
from .kinja import KinjaEmbedIE
from .kinopoisk import KinoPoiskIE
from .kompas import KompasVideoIE
from .konserthusetplay import KonserthusetPlayIE
from .koo import KooIE
from .kth import KTHIE
from .krasview import KrasViewIE
from .ku6 import Ku6IE
from .kusi import KUSIIE
from .kuwo import (
    KuwoIE,
    KuwoAlbumIE,
    KuwoChartIE,
    KuwoSingerIE,
    KuwoCategoryIE,
    KuwoMvIE,
)
from .la7 import (
    LA7IE,
    LA7PodcastEpisodeIE,
    LA7PodcastIE,
)
from .laola1tv import (
    Laola1TvEmbedIE,
    Laola1TvIE,
    EHFTVIE,
    ITTFIE,
)
from .lastfm import (
    LastFMIE,
    LastFMPlaylistIE,
    LastFMUserIE,
)
from .lbry import (
    LBRYIE,
    LBRYChannelIE,
)
from .lci import LCIIE
from .lcp import (
    LcpPlayIE,
    LcpIE,
)
from .lecture2go import Lecture2GoIE
from .lecturio import (
    LecturioIE,
    LecturioCourseIE,
    LecturioDeCourseIE,
)
from .leeco import (
    LeIE,
    LePlaylistIE,
    LetvCloudIE,
)
from .lego import LEGOIE
from .lemonde import LemondeIE
from .lenta import LentaIE
from .libraryofcongress import LibraryOfCongressIE
from .libsyn import LibsynIE
from .lifenews import (
    LifeNewsIE,
    LifeEmbedIE,
)
from .likee import (
    LikeeIE,
    LikeeUserIE
)
from .limelight import (
    LimelightMediaIE,
    LimelightChannelIE,
    LimelightChannelListIE,
)
from .line import (
    LineLiveIE,
    LineLiveChannelIE,
)
from .linkedin import (
    LinkedInIE,
    LinkedInLearningIE,
    LinkedInLearningCourseIE,
)
from .linuxacademy import LinuxAcademyIE
from .liputan6 import Liputan6IE
from .litv import LiTVIE
from .livejournal import LiveJournalIE
from .livestream import (
    LivestreamIE,
    LivestreamOriginalIE,
    LivestreamShortenerIE,
)
from .livestreamfails import LivestreamfailsIE
from .lnkgo import (
    LnkGoIE,
    LnkIE,
)
from .localnews8 import LocalNews8IE
from .lovehomeporn import LoveHomePornIE
from .lrt import (
    LRTVODIE,
    LRTStreamIE
)
from .lynda import (
    LyndaIE,
    LyndaCourseIE
)
from .m6 import M6IE
from .magentamusik360 import MagentaMusik360IE
from .mailru import (
    MailRuIE,
    MailRuMusicIE,
    MailRuMusicSearchIE,
)
from .mainstreaming import MainStreamingIE
from .malltv import MallTVIE
from .mangomolo import (
    MangomoloVideoIE,
    MangomoloLiveIE,
)
from .manoto import (
    ManotoTVIE,
    ManotoTVShowIE,
    ManotoTVLiveIE,
)
from .manyvids import ManyVidsIE
from .maoritv import MaoriTVIE
from .markiza import (
    MarkizaIE,
    MarkizaPageIE,
)
from .massengeschmacktv import MassengeschmackTVIE
from .masters import MastersIE
from .mastodon import (
    MastodonIE,
    MastodonUserIE,
    MastodonUserNumericIE,
)
from .matchtv import MatchTVIE
from .mdr import MDRIE
from .medaltv import MedalTVIE
from .mediaite import MediaiteIE
from .mediaklikk import MediaKlikkIE
from .mediaset import (
    MediasetIE,
    MediasetShowIE,
)
from .mediasite import (
    MediasiteIE,
    MediasiteCatalogIE,
    MediasiteNamedCatalogIE,
)
from .mediaworksnz import MediaWorksNZVODIE
from .medici import MediciIE
from .megaphone import MegaphoneIE
from .meipai import MeipaiIE
from .melonvod import MelonVODIE
from .meta import METAIE
from .metacafe import MetacafeIE
from .metacritic import MetacriticIE
from .mgoon import MgoonIE
from .mgtv import MGTVIE
from .miaopai import MiaoPaiIE
from .microsoftstream import MicrosoftStreamIE
from .microsoftvirtualacademy import (
    MicrosoftVirtualAcademyIE,
    MicrosoftVirtualAcademyCourseIE,
)
from .mildom import (
    MildomIE,
    MildomVodIE,
    MildomClipIE,
    MildomUserVodIE,
)
from .minds import (
    MindsIE,
    MindsChannelIE,
    MindsGroupIE,
)
from .ministrygrid import MinistryGridIE
from .minoto import MinotoIE
from .miomio import MioMioIE
from .mirrativ import (
    MirrativIE,
    MirrativUserIE,
)
from .mirrorcouk import MirrorCoUKIE
from .misskey import MisskeyIE, MisskeyUserIE
from .mit import TechTVMITIE, OCWMITIE
from .mitele import MiTeleIE
from .mixch import (
    MixchIE,
    MixchArchiveIE,
)
from .mixcloud import (
    MixcloudIE,
    MixcloudUserIE,
    MixcloudPlaylistIE,
)
from .mlb import (
    MLBIE,
    MLBVideoIE,
    MLBTVIE,
)
from .mlssoccer import MLSSoccerIE
from .mnet import MnetIE
from .mocha import MochaVideoIE
from .moevideo import MoeVideoIE
from .mofosex import (
    MofosexIE,
    MofosexEmbedIE,
)
from .mojvideo import MojvideoIE
from .morningstar import MorningstarIE
from .motherless import (
    MotherlessIE,
    MotherlessGroupIE
)
from .motorsport import MotorsportIE
from .movieclips import MovieClipsIE
from .moviepilot import MoviepilotIE
from .moview import MoviewPlayIE
from .moviezine import MoviezineIE
from .movingimage import MovingImageIE
from .msn import MSNIE
from .mtv import (
    MTVIE,
    MTVVideoIE,
    MTVServicesEmbeddedIE,
    MTVDEIE,
    MTVJapanIE,
    MTVItaliaIE,
    MTVItaliaProgrammaIE,
)
from .muenchentv import MuenchenTVIE
from .murrtube import MurrtubeIE, MurrtubeUserIE
from .musescore import MuseScoreIE
from .musicdex import (
    MusicdexSongIE,
    MusicdexAlbumIE,
    MusicdexArtistIE,
    MusicdexPlaylistIE,
)
from .mwave import MwaveIE, MwaveMeetGreetIE
from .mxplayer import (
    MxplayerIE,
    MxplayerShowIE,
)
from .mychannels import MyChannelsIE
from .myspace import MySpaceIE, MySpaceAlbumIE
from .myspass import MySpassIE
from .myvi import (
    MyviIE,
    MyviEmbedIE,
)
from .myvideoge import MyVideoGeIE
from .myvidster import MyVidsterIE
from .n1 import (
    N1InfoAssetIE,
    N1InfoIIE,
)
from .nate import (
    NateIE,
    NateProgramIE,
)
from .nationalgeographic import (
    NationalGeographicVideoIE,
    NationalGeographicTVIE,
)
from .naver import (
    NaverIE,
    NaverLiveIE,
    NaverNowIE,
)
from .nba import (
    NBAWatchEmbedIE,
    NBAWatchIE,
    NBAWatchCollectionIE,
    NBAEmbedIE,
    NBAIE,
    NBAChannelIE,
)
from .nbc import (
    NBCIE,
    NBCNewsIE,
    NBCOlympicsIE,
    NBCOlympicsStreamIE,
    NBCSportsIE,
    NBCSportsStreamIE,
    NBCSportsVPlayerIE,
)
from .ndr import (
    NDRIE,
    NJoyIE,
    NDREmbedBaseIE,
    NDREmbedIE,
    NJoyEmbedIE,
)
from .ndtv import NDTVIE
from .nebula import (
    NebulaIE,
    NebulaSubscriptionsIE,
    NebulaChannelIE,
)
from .nerdcubed import NerdCubedFeedIE
from .netzkino import NetzkinoIE
from .neteasemusic import (
    NetEaseMusicIE,
    NetEaseMusicAlbumIE,
    NetEaseMusicSingerIE,
    NetEaseMusicListIE,
    NetEaseMusicMvIE,
    NetEaseMusicProgramIE,
    NetEaseMusicDjRadioIE,
)
from .netverse import (
    NetverseIE,
    NetversePlaylistIE,
)
from .newgrounds import (
    NewgroundsIE,
    NewgroundsPlaylistIE,
    NewgroundsUserIE,
)
from .newspicks import NewsPicksIE
from .newstube import NewstubeIE
from .newsy import NewsyIE
from .nextmedia import (
    NextMediaIE,
    NextMediaActionNewsIE,
    AppleDailyIE,
    NextTVIE,
)
from .nexx import (
    NexxIE,
    NexxEmbedIE,
)
from .nfb import NFBIE
from .nfhsnetwork import NFHSNetworkIE
from .nfl import (
    NFLIE,
    NFLArticleIE,
)
from .nhk import (
    NhkVodIE,
    NhkVodProgramIE,
    NhkForSchoolBangumiIE,
    NhkForSchoolSubjectIE,
    NhkForSchoolProgramListIE,
)
from .nhl import NHLIE
from .nick import (
    NickIE,
    NickBrIE,
    NickDeIE,
    NickNightIE,
    NickRuIE,
)
from .niconico import (
    NiconicoIE,
    NiconicoPlaylistIE,
    NiconicoUserIE,
    NiconicoSeriesIE,
    NiconicoHistoryIE,
    NicovideoSearchDateIE,
    NicovideoSearchIE,
    NicovideoSearchURLIE,
    NicovideoTagURLIE,
    NiconicoLiveIE,
)
from .ninecninemedia import (
    NineCNineMediaIE,
    CPTwentyFourIE,
)
from .ninegag import NineGagIE
from .ninenow import NineNowIE
from .nintendo import NintendoIE
from .nitter import NitterIE
from .njpwworld import NJPWWorldIE
from .nobelprize import NobelPrizeIE
from .nonktube import NonkTubeIE
from .noodlemagazine import NoodleMagazineIE
from .noovo import NoovoIE
from .normalboots import NormalbootsIE
from .nosvideo import NosVideoIE
from .nova import (
    NovaEmbedIE,
    NovaIE,
)
from .novaplay import NovaPlayIE
from .nowness import (
    NownessIE,
    NownessPlaylistIE,
    NownessSeriesIE,
)
from .noz import NozIE
from .npo import (
    AndereTijdenIE,
    NPOIE,
    NPOLiveIE,
    NPORadioIE,
    NPORadioFragmentIE,
    SchoolTVIE,
    HetKlokhuisIE,
    VPROIE,
    WNLIE,
)
from .npr import NprIE
from .nrk import (
    NRKIE,
    NRKPlaylistIE,
    NRKSkoleIE,
    NRKTVIE,
    NRKTVDirekteIE,
    NRKRadioPodkastIE,
    NRKTVEpisodeIE,
    NRKTVEpisodesIE,
    NRKTVSeasonIE,
    NRKTVSeriesIE,
)
from .nrl import NRLTVIE
from .ntvcojp import NTVCoJpCUIE
from .ntvde import NTVDeIE
from .ntvru import NTVRuIE
from .nytimes import (
    NYTimesIE,
    NYTimesArticleIE,
    NYTimesCookingIE,
)
from .nuvid import NuvidIE
from .nzherald import NZHeraldIE
from .nzz import NZZIE
from .odatv import OdaTVIE
from .odnoklassniki import OdnoklassnikiIE
from .oktoberfesttv import OktoberfestTVIE
from .olympics import OlympicsReplayIE
from .on24 import On24IE
from .ondemandkorea import OnDemandKoreaIE
from .onefootball import OneFootballIE
from .onet import (
    OnetIE,
    OnetChannelIE,
    OnetMVPIE,
    OnetPlIE,
)
from .onionstudios import OnionStudiosIE
from .ooyala import (
    OoyalaIE,
    OoyalaExternalIE,
)
from .opencast import (
    OpencastIE,
    OpencastPlaylistIE,
)
from .openrec import (
    OpenRecIE,
    OpenRecCaptureIE,
    OpenRecMovieIE,
)
from .ora import OraTVIE
from .orf import (
    ORFTVthekIE,
    ORFFM4StoryIE,
    ORFRadioIE,
    ORFIPTVIE,
)
from .outsidetv import OutsideTVIE
from .packtpub import (
    PacktPubIE,
    PacktPubCourseIE,
)
from .palcomp3 import (
    PalcoMP3IE,
    PalcoMP3ArtistIE,
    PalcoMP3VideoIE,
)
from .pandoratv import PandoraTVIE
from .panopto import (
    PanoptoIE,
    PanoptoListIE,
    PanoptoPlaylistIE
)
from .paramountplus import (
    ParamountPlusIE,
    ParamountPlusSeriesIE,
)
from .parler import ParlerIE
from .parlview import ParlviewIE
from .patreon import (
    PatreonIE,
    PatreonCampaignIE
)
from .pbs import PBSIE
from .pearvideo import PearVideoIE
from .peekvids import PeekVidsIE, PlayVidsIE
from .peertube import (
    PeerTubeIE,
    PeerTubePlaylistIE,
    PeerTubeChannelIE,
    PeerTubeAccountIE,
)
from .peertv import PeerTVIE
from .peloton import (
    PelotonIE,
    PelotonLiveIE
)
from .people import PeopleIE
from .performgroup import PerformGroupIE
from .periscope import (
    PeriscopeIE,
    PeriscopeUserIE,
)
from .philharmoniedeparis import PhilharmonieDeParisIE
from .phoenix import PhoenixIE
from .photobucket import PhotobucketIE
from .piapro import PiaproIE
from .picarto import (
    PicartoIE,
    PicartoVodIE,
)
from .piksel import PikselIE
from .pinkbike import PinkbikeIE
from .pinterest import (
    PinterestIE,
    PinterestCollectionIE,
)
from .pixivsketch import (
    PixivSketchIE,
    PixivSketchUserIE,
)
from .pladform import PladformIE
from .planetmarathi import PlanetMarathiIE
from .platzi import (
    PlatziIE,
    PlatziCourseIE,
)
from .playfm import PlayFMIE
from .playplustv import PlayPlusTVIE
from .plays import PlaysTVIE
from .playstuff import PlayStuffIE
from .playsuisse import PlaySuisseIE
from .playtvak import PlaytvakIE
from .playvid import PlayvidIE
from .playwire import PlaywireIE
from .plutotv import PlutoTVIE
from .pluralsight import (
    PluralsightIE,
    PluralsightCourseIE,
)
from .podchaser import PodchaserIE
from .podomatic import PodomaticIE
from .pokemon import (
    PokemonIE,
    PokemonWatchIE,
)
from .pokergo import (
    PokerGoIE,
    PokerGoCollectionIE,
)
from .polsatgo import PolsatGoIE
from .polskieradio import (
    PolskieRadioIE,
    PolskieRadioCategoryIE,
    PolskieRadioPlayerIE,
    PolskieRadioPodcastIE,
    PolskieRadioPodcastListIE,
    PolskieRadioRadioKierowcowIE,
)
from .popcorntimes import PopcorntimesIE
from .popcorntv import PopcornTVIE
from .porn91 import Porn91IE
from .porncom import PornComIE
from .pornflip import PornFlipIE
from .pornhd import PornHdIE
from .pornhub import (
    PornHubIE,
    PornHubUserIE,
    PornHubPlaylistIE,
    PornHubPagedVideoListIE,
    PornHubUserVideosUploadIE,
)
from .pornotube import PornotubeIE
from .pornovoisines import PornoVoisinesIE
from .pornoxo import PornoXOIE
from .pornez import PornezIE
from .puhutv import (
    PuhuTVIE,
    PuhuTVSerieIE,
)
from .premiershiprugby import PremiershipRugbyIE
from .presstv import PressTVIE
from .projectveritas import ProjectVeritasIE
from .prosiebensat1 import ProSiebenSat1IE
from .prx import (
    PRXStoryIE,
    PRXSeriesIE,
    PRXAccountIE,
    PRXStoriesSearchIE,
    PRXSeriesSearchIE
)
from .puls4 import Puls4IE
from .pyvideo import PyvideoIE
from .qawebsites import (
    AskfmIE,
    MarshmallowQAIE,
    MottohometeIE,
    PeingIE,
)
from .qqmusic import (
    QQMusicIE,
    QQMusicSingerIE,
    QQMusicAlbumIE,
    QQMusicToplistIE,
    QQMusicPlaylistIE,
)
from .r7 import (
    R7IE,
    R7ArticleIE,
)
from .radiko import RadikoIE, RadikoRadioIE
from .radiocanada import (
    RadioCanadaIE,
    RadioCanadaAudioVideoIE,
)
from .radiode import RadioDeIE
from .radiojavan import RadioJavanIE
from .radiobremen import RadioBremenIE
from .radiofrance import FranceCultureIE, RadioFranceIE
from .radiozet import RadioZetPodcastIE
from .radiokapital import (
    RadioKapitalIE,
    RadioKapitalShowIE,
)
from .radlive import (
    RadLiveIE,
    RadLiveChannelIE,
    RadLiveSeasonIE,
)
from .rai import (
    RaiPlayIE,
    RaiPlayLiveIE,
    RaiPlayPlaylistIE,
    RaiPlaySoundIE,
    RaiPlaySoundLiveIE,
    RaiPlaySoundPlaylistIE,
    RaiNewsIE,
    RaiSudtirolIE,
    RaiIE,
)
from .raywenderlich import (
    RayWenderlichIE,
    RayWenderlichCourseIE,
)
from .rbmaradio import RBMARadioIE
from .rcs import (
    RCSIE,
    RCSEmbedsIE,
    RCSVariousIE,
)
from .rcti import (
    RCTIPlusIE,
    RCTIPlusSeriesIE,
    RCTIPlusTVIE,
)
from .rds import RDSIE
from .redbee import ParliamentLiveUKIE, RTBFIE
from .redbulltv import (
    RedBullTVIE,
    RedBullEmbedIE,
    RedBullTVRrnContentIE,
    RedBullIE,
)
from .reddit import RedditIE
from .redgifs import (
    RedGifsIE,
    RedGifsSearchIE,
    RedGifsUserIE,
)
from .redtube import RedTubeIE
from .regiotv import RegioTVIE
from .rentv import (
    RENTVIE,
    RENTVArticleIE,
)
from .restudy import RestudyIE
from .reuters import ReutersIE
from .reverbnation import ReverbNationIE
from .rice import RICEIE
from .rmcdecouverte import RMCDecouverteIE
from .rockstargames import RockstarGamesIE
from .rokfin import (
    RokfinIE,
    RokfinStackIE,
    RokfinChannelIE,
    RokfinSearchIE,
)
from .roosterteeth import RoosterTeethIE, RoosterTeethSeriesIE
from .rottentomatoes import RottenTomatoesIE
from .rozhlas import RozhlasIE
from .rte import RteIE, RteRadioIE
from .rtlnl import (
    RtlNlIE,
    RTLLuTeleVODIE,
    RTLLuArticleIE,
    RTLLuLiveIE,
    RTLLuRadioIE,
)
from .rtl2 import (
    RTL2IE,
    RTL2YouIE,
    RTL2YouSeriesIE,
)
from .rtnews import (
    RTNewsIE,
    RTDocumentryIE,
    RTDocumentryPlaylistIE,
    RuptlyIE,
)
from .rtp import RTPIE
from .rtrfm import RTRFMIE
from .rts import RTSIE
from .rtve import (
    RTVEALaCartaIE,
    RTVEAudioIE,
    RTVELiveIE,
    RTVEInfantilIE,
    RTVETelevisionIE,
)
from .rtvnh import RTVNHIE
from .rtvs import RTVSIE
from .rtvslo import RTVSLOIE
from .ruhd import RUHDIE
from .rule34video import Rule34VideoIE
from .rumble import (
    RumbleEmbedIE,
    RumbleChannelIE,
)
from .rutube import (
    RutubeIE,
    RutubeChannelIE,
    RutubeEmbedIE,
    RutubeMovieIE,
    RutubePersonIE,
    RutubePlaylistIE,
    RutubeTagsIE,
)
from .glomex import (
    GlomexIE,
    GlomexEmbedIE,
)
from .megatvcom import (
    MegaTVComIE,
    MegaTVComEmbedIE,
)
from .ant1newsgr import (
    Ant1NewsGrWatchIE,
    Ant1NewsGrArticleIE,
    Ant1NewsGrEmbedIE,
)
from .rutv import RUTVIE
from .ruutu import RuutuIE
from .ruv import (
    RuvIE,
    RuvSpilaIE
)
from .safari import (
    SafariIE,
    SafariApiIE,
    SafariCourseIE,
)
from .saitosan import SaitosanIE
from .samplefocus import SampleFocusIE
from .sapo import SapoIE
from .savefrom import SaveFromIE
from .sbs import SBSIE
from .screencast import ScreencastIE
from .screencastomatic import ScreencastOMaticIE
from .scrippsnetworks import (
    ScrippsNetworksWatchIE,
    ScrippsNetworksIE,
)
from .scte import (
    SCTEIE,
    SCTECourseIE,
)
from .scrolller import ScrolllerIE
from .seeker import SeekerIE
from .senategov import SenateISVPIE, SenateGovIE
from .sendtonews import SendtoNewsIE
from .servus import ServusIE
from .sevenplus import SevenPlusIE
from .sexu import SexuIE
from .seznamzpravy import (
    SeznamZpravyIE,
    SeznamZpravyArticleIE,
)
from .shahid import (
    ShahidIE,
    ShahidShowIE,
)
from .shared import (
    SharedIE,
    VivoIE,
)
from .sharevideos import ShareVideosEmbedIE
from .shemaroome import ShemarooMeIE
from .showroomlive import ShowRoomLiveIE
from .japandiet import (
    ShugiinItvLiveIE,
    ShugiinItvLiveRoomIE,
    ShugiinItvVodIE,
)
from .simplecast import (
    SimplecastIE,
    SimplecastEpisodeIE,
    SimplecastPodcastIE,
)
from .sina import SinaIE
from .sixplay import SixPlayIE
from .skeb import SkebIE
from .skyit import (
    SkyItPlayerIE,
    SkyItVideoIE,
    SkyItVideoLiveIE,
    SkyItIE,
    SkyItAcademyIE,
    SkyItArteIE,
    CieloTVItIE,
    TV8ItIE,
)
from .skylinewebcams import SkylineWebcamsIE
from .skynewsarabia import (
    SkyNewsArabiaIE,
    SkyNewsArabiaArticleIE,
)
from .skynewsau import SkyNewsAUIE
from .sky import (
    SkyNewsIE,
    SkyNewsStoryIE,
    SkySportsIE,
    SkySportsNewsIE,
)
from .slideshare import SlideshareIE
from .slideslive import SlidesLiveIE
from .slutload import SlutloadIE
from .snotr import SnotrIE
from .sohu import SohuIE
from .sonyliv import (
    SonyLIVIE,
    SonyLIVSeriesIE,
)
from .soundcloud import (
    SoundcloudEmbedIE,
    SoundcloudIE,
    SoundcloudSetIE,
    SoundcloudRelatedIE,
    SoundcloudUserIE,
    SoundcloudTrackStationIE,
    SoundcloudPlaylistIE,
    SoundcloudSearchIE,
)
from .soundgasm import (
    SoundgasmIE,
    SoundgasmProfileIE
)
from .southpark import (
    SouthParkIE,
    SouthParkDeIE,
    SouthParkDkIE,
    SouthParkEsIE,
    SouthParkLatIE,
    SouthParkNlIE
)
from .sovietscloset import (
    SovietsClosetIE,
    SovietsClosetPlaylistIE
)
from .spankbang import (
    SpankBangIE,
    SpankBangPlaylistIE,
)
from .spankwire import SpankwireIE
from .spiegel import SpiegelIE
from .spike import (
    BellatorIE,
    ParamountNetworkIE,
)
from .startrek import StarTrekIE
from .stitcher import (
    StitcherIE,
    StitcherShowIE,
)
from .sport5 import Sport5IE
from .sportbox import SportBoxIE
from .sportdeutschland import SportDeutschlandIE
from .spotify import (
    SpotifyIE,
    SpotifyShowIE,
)
from .spreaker import (
    SpreakerIE,
    SpreakerPageIE,
    SpreakerShowIE,
    SpreakerShowPageIE,
)
from .springboardplatform import SpringboardPlatformIE
from .sprout import SproutIE
from .srgssr import (
    SRGSSRIE,
    SRGSSRPlayIE,
)
from .srmediathek import SRMediathekIE
from .stanfordoc import StanfordOpenClassroomIE
from .startv import StarTVIE
from .steam import (
    SteamIE,
    SteamCommunityBroadcastIE,
)
from .storyfire import (
    StoryFireIE,
    StoryFireUserIE,
    StoryFireSeriesIE,
)
from .streamable import StreamableIE
from .streamanity import StreamanityIE
from .streamcloud import StreamcloudIE
from .streamcz import StreamCZIE
from .streamff import StreamFFIE
from .streetvoice import StreetVoiceIE
from .stretchinternet import StretchInternetIE
from .stripchat import StripchatIE
from .stv import STVPlayerIE
from .substack import SubstackIE
from .sunporno import SunPornoIE
from .sverigesradio import (
    SverigesRadioEpisodeIE,
    SverigesRadioPublicationIE,
)
from .svt import (
    SVTIE,
    SVTPageIE,
    SVTPlayIE,
    SVTSeriesIE,
)
from .swipevideo import SwipeVideoIE
from .swrmediathek import SWRMediathekIE
from .syvdk import SYVDKIE
from .syfy import SyfyIE
from .sztvhu import SztvHuIE
from .tagesschau import TagesschauIE
from .tass import TassIE
from .tbs import TBSIE
from .tdslifeway import TDSLifewayIE
from .teachable import (
    TeachableIE,
    TeachableCourseIE,
)
from .teachertube import (
    TeacherTubeIE,
    TeacherTubeUserIE,
)
from .teachingchannel import TeachingChannelIE
from .teamcoco import TeamcocoIE
from .teamtreehouse import TeamTreeHouseIE
from .techtalks import TechTalksIE
from .ted import (
    TedEmbedIE,
    TedPlaylistIE,
    TedSeriesIE,
    TedTalkIE,
)
from .tele5 import Tele5IE
from .tele13 import Tele13IE
from .telebruxelles import TeleBruxellesIE
from .telecinco import TelecincoIE
from .telegraaf import TelegraafIE
from .telegram import TelegramEmbedIE
from .telemb import TeleMBIE
from .telemundo import TelemundoIE
from .telequebec import (
    TeleQuebecIE,
    TeleQuebecSquatIE,
    TeleQuebecEmissionIE,
    TeleQuebecLiveIE,
    TeleQuebecVideoIE,
)
from .teletask import TeleTaskIE
from .telewebion import TelewebionIE
from .tempo import TempoIE
from .tencent import (
    VQQSeriesIE,
    VQQVideoIE,
    WeTvEpisodeIE,
    WeTvSeriesIE,
)
from .tennistv import TennisTVIE
from .tenplay import TenPlayIE
from .testurl import TestURLIE, TestInfoDictIE
from .tf1 import TF1IE
from .tfo import TFOIE
from .theholetv import TheHoleTvIE
from .theintercept import TheInterceptIE
from .theplatform import (
    ThePlatformIE,
    ThePlatformFeedIE,
)
from .thestar import TheStarIE
from .thesun import TheSunIE
from .theta import (
    ThetaVideoIE,
    ThetaStreamIE,
)
from .theweatherchannel import TheWeatherChannelIE
from .thisamericanlife import ThisAmericanLifeIE
from .thisav import ThisAVIE
from .thisoldhouse import ThisOldHouseIE
from .threespeak import (
    ThreeSpeakIE,
    ThreeSpeakUserIE,
)
from .threeqsdn import ThreeQSDNIE
from .tiktok import (
    TikTokIE,
    TikTokUserIE,
    TikTokSoundIE,
    TikTokEffectIE,
    TikTokTagIE,
    TikTokVMIE,
    DouyinIE,
)
from .tinypic import TinyPicIE
from .tmz import TMZIE
from .tnaflix import (
    TNAFlixNetworkEmbedIE,
    TNAFlixIE,
    EMPFlixIE,
    MovieFapIE,
)
from .toggle import (
    ToggleIE,
    MeWatchIE,
)
from .tokyomotion import (
    TokyoMotionIE,
    TokyoMotionUserFavsIE,
    TokyoMotionUserIE,
    TokyoMotionSearchesIE,
    TokyoMotionScannerIE,
)
from .toggo import (
    ToggoIE,
)
from .tokentube import (
    TokentubeIE,
    TokentubeChannelIE
)
from .tonline import TOnlineIE
from .toongoggles import ToonGogglesIE
from .toutv import TouTvIE
from .toypics import ToypicsUserIE, ToypicsIE
from .traileraddict import TrailerAddictIE
from .triller import (
    TrillerIE,
    TrillerUserIE,
)
from .trilulilu import TriluliluIE
from .trovo import (
    TrovoIE,
    TrovoVodIE,
    TrovoChannelVodIE,
    TrovoChannelClipIE,
)
from .trueid import TrueIDIE
from .trunews import TruNewsIE
from .trutv import TruTVIE
from .tube8 import Tube8IE
from .tubetugraz import TubeTuGrazIE, TubeTuGrazSeriesIE
from .tubitv import (
    TubiTvIE,
    TubiTvShowIE,
)
from .tumblr import TumblrIE
from .tunein import (
    TuneInClipIE,
    TuneInStationIE,
    TuneInProgramIE,
    TuneInTopicIE,
    TuneInShortenerIE,
)
from .tunepk import TunePkIE
from .turbo import TurboIE
from .tv2 import (
    TV2IE,
    TV2ArticleIE,
    KatsomoIE,
    MTVUutisetArticleIE,
)
from .tv2dk import (
    TV2DKIE,
    TV2DKBornholmPlayIE,
)
from .tv2hu import (
    TV2HuIE,
    TV2HuSeriesIE,
)
from .tv4 import TV4IE
from .tv5mondeplus import TV5MondePlusIE
from .tv5unis import (
    TV5UnisVideoIE,
    TV5UnisIE,
)
from .tva import (
    TVAIE,
    QubIE,
)
from .tvanouvelles import (
    TVANouvellesIE,
    TVANouvellesArticleIE,
)
from .tvc import (
    TVCIE,
    TVCArticleIE,
)
from .tver import TVerIE
from .tvigle import TvigleIE
from .tviplayer import TVIPlayerIE
from .tvland import TVLandIE
from .tvn24 import TVN24IE
from .tvnet import TVNetIE
from .tvnoe import TVNoeIE
from .tvnow import (
    TVNowIE,
    TVNowFilmIE,
    TVNowNewIE,
    TVNowSeasonIE,
    TVNowAnnualIE,
    TVNowShowIE,
)
from .tvopengr import (
    TVOpenGrWatchIE,
    TVOpenGrEmbedIE,
)
from .tvp import (
    TVPEmbedIE,
    TVPIE,
    TVPStreamIE,
    TVPWebsiteIE,
)
from .tvplay import (
    TVPlayIE,
    ViafreeIE,
    TVPlayHomeIE,
)
from .tvplayer import TVPlayerIE
from .tweakers import TweakersIE
from .twentyfourvideo import TwentyFourVideoIE
from .twentymin import TwentyMinutenIE
from .twentythreevideo import TwentyThreeVideoIE
from .twitcasting import (
    TwitCastingIE,
    TwitCastingLiveIE,
    TwitCastingUserIE,
)
from .twitch import (
    TwitchVodIE,
    TwitchCollectionIE,
    TwitchVideosIE,
    TwitchVideosClipsIE,
    TwitchVideosCollectionsIE,
    TwitchStreamIE,
    TwitchClipsIE,
)
from .twitter import (
    TwitterCardIE,
    TwitterIE,
    TwitterAmplifyIE,
    TwitterBroadcastIE,
    TwitterShortenerIE,
)
from .udemy import (
    UdemyIE,
    UdemyCourseIE
)
from .udn import UDNEmbedIE
from .ufctv import (
    UFCTVIE,
    UFCArabiaIE,
)
from .ukcolumn import UkColumnIE
from .uktvplay import UKTVPlayIE
from .digiteka import DigitekaIE
from .dlive import (
    DLiveVODIE,
    DLiveStreamIE,
)
from .drooble import DroobleIE
from .umg import UMGDeIE
from .unistra import UnistraIE
from .unity import UnityIE
from .uol import UOLIE
from .uplynk import (
    UplynkIE,
    UplynkPreplayIE,
)
from .urort import UrortIE
from .urplay import URPlayIE
from .usanetwork import USANetworkIE
from .usatoday import USATodayIE
from .ustream import UstreamIE, UstreamChannelIE
from .ustudio import (
    UstudioIE,
    UstudioEmbedIE,
)
from .utreon import UtreonIE
from .varzesh3 import Varzesh3IE
from .vbox7 import Vbox7IE
from .veehd import VeeHDIE
from .veo import VeoIE
from .veoh import VeohIE
from .vesti import VestiIE
from .vevo import (
    VevoIE,
    VevoPlaylistIE,
)
from .vgtv import (
    BTArticleIE,
    BTVestlendingenIE,
    VGTVIE,
)
from .vh1 import VH1IE
from .vice import (
    ViceIE,
    ViceArticleIE,
    ViceShowIE,
)
from .vidbit import VidbitIE
from .viddler import ViddlerIE
from .videa import VideaIE
from .videobin import VideobinIE
from .videocampus_sachsen import (
    VideocampusSachsenIE,
    ViMPPlaylistIE,
)
from .videodetective import VideoDetectiveIE
from .videofyme import VideofyMeIE
from .videomore import (
    VideomoreIE,
    VideomoreVideoIE,
    VideomoreSeasonIE,
)
from .videopress import VideoPressIE
from .vidio import (
    VidioIE,
    VidioPremierIE,
    VidioLiveIE
)
from .vidlii import VidLiiIE
from .viewlift import (
    ViewLiftIE,
    ViewLiftEmbedIE,
)
from .viidea import ViideaIE
from .vimeo import (
    VimeoIE,
    VimeoAlbumIE,
    VimeoChannelIE,
    VimeoGroupsIE,
    VimeoLikesIE,
    VimeoOndemandIE,
    VimeoReviewIE,
    VimeoUserIE,
    VimeoWatchLaterIE,
    VHXEmbedIE,
)
from .vimm import (
    VimmIE,
    VimmRecordingIE,
)
from .vimple import VimpleIE
from .vine import (
    VineIE,
    VineUserIE,
)
from .viki import (
    VikiIE,
    VikiChannelIE,
)
from .viqeo import ViqeoIE
from .viu import (
    ViuIE,
    ViuPlaylistIE,
    ViuOTTIE,
)
from .vk import (
    VKIE,
    VKUserVideosIE,
    VKWallPostIE,
)
from .vlive import (
    VLiveIE,
    VLivePostIE,
    VLiveChannelIE,
)
from .vodlocker import VodlockerIE
from .vodpl import VODPlIE
from .vodplatform import VODPlatformIE
from .voicerepublic import VoiceRepublicIE
from .voicy import (
    VoicyIE,
    VoicyChannelIE,
)
from .voot import (
    VootIE,
    VootSeriesIE,
)
from .voxmedia import (
    VoxMediaVolumeIE,
    VoxMediaIE,
)
from .vrt import VRTIE
from .vrak import VrakIE
from .vrv import (
    VRVIE,
    VRVSeriesIE,
)
from .vshare import VShareIE
from .vtm import VTMIE
from .medialaan import MedialaanIE
from .vuclip import VuClipIE
from .vupload import VuploadIE
from .vvvvid import (
    VVVVIDIE,
    VVVVIDShowIE,
)
from .vyborymos import VyboryMosIE
from .vzaar import VzaarIE
from .wakanim import WakanimIE
from .walla import WallaIE
from .washingtonpost import (
    WashingtonPostIE,
    WashingtonPostArticleIE,
)
from .wasdtv import (
    WASDTVStreamIE,
    WASDTVRecordIE,
    WASDTVClipIE,
)
from .wat import WatIE
from .watchbox import WatchBoxIE
from .watchindianporn import WatchIndianPornIE
from .wdr import (
    WDRIE,
    WDRPageIE,
    WDRElefantIE,
    WDRMobileIE,
)
from .webcaster import (
    WebcasterIE,
    WebcasterFeedIE,
)
from .webofstories import (
    WebOfStoriesIE,
    WebOfStoriesPlaylistIE,
)
from .weibo import (
    WeiboIE,
    WeiboMobileIE
)
from .weiqitv import WeiqiTVIE
from .wikimedia import WikimediaIE
from .willow import WillowIE
from .wimtv import WimTVIE
from .whatismyip import WhatIsMyIpIE
from .whowatch import WhoWatchIE
from .wistia import (
    WistiaIE,
    WistiaPlaylistIE,
)
from .worldstarhiphop import WorldStarHipHopIE
from .wppilot import (
    WPPilotIE,
    WPPilotChannelsIE,
)
from .wsj import (
    WSJIE,
    WSJArticleIE,
)
from .wwe import WWEIE
from .xbef import XBefIE
from .xboxclips import XboxClipsIE
from .xfileshare import XFileShareIE
from .xhamster import (
    XHamsterIE,
    XHamsterEmbedIE,
    XHamsterUserIE,
)
from .xiami import (
    XiamiSongIE,
    XiamiAlbumIE,
    XiamiArtistIE,
    XiamiCollectionIE
)
from .ximalaya import (
    XimalayaIE,
    XimalayaAlbumIE
)
from .xinpianchang import XinpianchangIE
from .xminus import XMinusIE
from .xnxx import XNXXIE
from .xstream import XstreamIE
from .xtube import XTubeUserIE, XTubeIE
from .xuite import XuiteIE
from .xvideos import XVideosIE
from .xxxymovies import XXXYMoviesIE
from .yahoo import (
    YahooIE,
    YahooSearchIE,
    YahooGyaOPlayerIE,
    YahooGyaOIE,
    YahooJapanNewsIE,
)
from .yandexdisk import YandexDiskIE
from .yandexmusic import (
    YandexMusicTrackIE,
    YandexMusicAlbumIE,
    YandexMusicPlaylistIE,
    YandexMusicArtistTracksIE,
    YandexMusicArtistAlbumsIE,
)
from .yandexvideo import (
    YandexVideoIE,
    YandexVideoPreviewIE,
    ZenYandexIE,
    ZenYandexChannelIE,
)
from .yapfiles import YapFilesIE
from .yesjapan import YesJapanIE
from .yinyuetai import YinYueTaiIE
from .ynet import YnetIE
from .youjizz import YouJizzIE
from .youku import (
    YoukuIE,
    YoukuShowIE,
)
from .younow import (
    YouNowLiveIE,
    YouNowChannelIE,
    YouNowMomentIE,
)
from .youporn import YouPornIE
from .yourporn import YourPornIE
from .yourupload import YourUploadIE
from .zapiks import ZapiksIE
from .zattoo import (
    BBVTVIE,
    BBVTVLiveIE,
    BBVTVRecordingsIE,
    EinsUndEinsTVIE,
    EinsUndEinsTVLiveIE,
    EinsUndEinsTVRecordingsIE,
    EWETVIE,
    EWETVLiveIE,
    EWETVRecordingsIE,
    GlattvisionTVIE,
    GlattvisionTVLiveIE,
    GlattvisionTVRecordingsIE,
    MNetTVIE,
    MNetTVLiveIE,
    MNetTVRecordingsIE,
    NetPlusTVIE,
    NetPlusTVLiveIE,
    NetPlusTVRecordingsIE,
    OsnatelTVIE,
    OsnatelTVLiveIE,
    OsnatelTVRecordingsIE,
    QuantumTVIE,
    QuantumTVLiveIE,
    QuantumTVRecordingsIE,
    SaltTVIE,
    SaltTVLiveIE,
    SaltTVRecordingsIE,
    SAKTVIE,
    SAKTVLiveIE,
    SAKTVRecordingsIE,
    VTXTVIE,
    VTXTVLiveIE,
    VTXTVRecordingsIE,
    WalyTVIE,
    WalyTVLiveIE,
    WalyTVRecordingsIE,
    ZattooIE,
    ZattooLiveIE,
    ZattooMoviesIE,
    ZattooRecordingsIE,
)
from .zdf import ZDFIE, ZDFChannelIE
from .zee5 import (
    Zee5IE,
    Zee5SeriesIE,
)
from .zhihu import ZhihuIE
from .zingmp3 import (
    ZingMp3IE,
    ZingMp3AlbumIE,
    ZingMp3ChartHomeIE,
    ZingMp3WeekChartIE,
    ZingMp3ChartMusicVideoIE,
    ZingMp3UserIE,
)
from .zoom import ZoomIE
from .zype import ZypeIE

from ._trashed import (
    HANMIE,
    HANMPLIE,
    HANMALLIE,
    GANMIE,
    VDSIE,
)
from ._youtube_download_services import (
    Y2mateIE,
    ClipConverterIE,
    YtAlternateIE,
)


code:
from __future__ import unicode_literals

import itertools
import json

from .common import InfoExtractor
from ..compat import compat_str
from ..utils import (
    ExtractorError,
    clean_html,
    float_or_none,
    int_or_none,
    parse_qs,
    smuggle_url,
    unsmuggle_url,
    time_millis,
    traverse_obj,
)

class HANMIE(InfoExtractor):
    IE_DESC = False
    _VALID_URL = r'https?://(?P<host>(?:www\.)?(?:members\.)?han' \
        r'ime\.tv)/videos/hentai/(?P<id>[a-zA-Z0-9-]+$)'
    _TESTS = [{
        'url': 'https://h' 'a' 'n' 'i' 'm' 'e.tv/videos/hentai/enjo-kouhai-1',
        'md5': 'a3a08ac2180ed75ee731aff92d16f447',
        'info_dict': {
            'id': 'enjo-kouhai-1',
            'ext': 'mp4',
            'title': 'Enjo Kouhai 1',
            'age_limit': 18,
            'upload_date': '20200130',
            'description': 'md5:81b00795abd5ffa50a2e463ea321886e',
            'timestamp': 1580398865,
        }
    }, {
        'url': 'https://h' 'a' 'n' 'i' 'm' 'e.tv/videos/hentai/enjo-kouhai-2',
        'md5': '5fad67745e1ba911c041031d9e1ce2a7',
        'info_dict': {
            'id': 'enjo-kouhai-2',
            'ext': 'mp4',
            'title': 'Enjo Kouhai 2',
            'age_limit': 18,
            'upload_date': '20200228',
            'description': 'md5:5277f19882544683e698b91f9e2634e3',
            'timestamp': 1582850492,
        }
    }, {
        'url': 'https://h' 'a' 'n' 'i' 'm' 'e.tv/videos/hentai/enjo-kouhai-3',
        'md5': 'a3a08ac2180ed75ee731aff92d16f447',
        'info_dict': {
            'id': 'enjo-kouhai-3',
            'ext': 'mp4',
            'title': 'Enjo Kouhai 3',
            'age_limit': 18,
            'upload_date': '20200326',
            'timestamp': 1585237316,
            'description': 'md5:0d67e22b89a5f7e1ca079d974019d08d',
        }
    }, {
        'url': 'https://h' 'a' 'n' 'i' 'm' 'e.tv/videos/hentai/chizuru-chan-kaihatsu-nikki-1',
        'md5': 'b54b00535369c8cc0ad344cbef3429f5',
        'info_dict': {
            'id': 'chizuru-chan-kaihatsu-nikki-1',
            'ext': 'mp4',
            'title': 'Chizuru-chan Kaihatsu Nikki 1',
            'age_limit': 18,
            'upload_date': '20210930',
            'timestamp': 1633016879,
            'description': 'A serious honor student "Chizuru Shiina" was shunned by her classmates due to her being a teacher\'s pet, but none of that mattered whenever she ran into her favorite teacher that she so deeply admired...',
        }
    }, {
        'url': 'https://h' 'a' 'n' 'i' 'm' 'e.tv/videos/hentai/chizuru-chan-kaihatsu-nikki-2',
        'md5': 'b54b00535369c8cc0ad344cbef3429f5',
        'info_dict': {
            'id': 'chizuru-chan-kaihatsu-nikki-2',
            'ext': 'mp4',
            'title': 'Chizuru-chan Kaihatsu Nikki 2',
            'age_limit': 18,
            'upload_date': '20210930',
            'timestamp': 1633016880,
            'description': 'A serious honor student "Chizuru Shiina" was shunned by her classmates due to her being a teacher\'s pet, but none of that mattered whenever she ran into her favorite teacher that she so deeply admired...',
        }
    }, {
        'url': 'https://h' 'a' 'n' 'i' 'm' 'e.tv/videos/hentai/kutsujoku-2-ep-2',
        'info_dict': {
            'series': 'Kutsujoku 2',
            'episode_number': 2,
        }
    }, {
        'url': 'https://h' 'a' 'n' 'i' 'm' 'e.tv/videos/hentai/doukyuusei-2-ep-7',
        'info_dict': {
            'series': 'Doukyuusei 2',
            'episode_number': 7,
        }
    }]

    @classmethod
    def suitable(cls, url):
        return super(HANMIE, cls).suitable(url) and not HANMPLIE.suitable(url)

    def _real_extract(self, url):
        video_id = self._match_id(url)

        webpage = self._download_webpage(url, video_id)
        json_data = self._html_search_regex(r'window\.__NUXT__=(\{.+?});\s*<\/script>', webpage, 'json data')
        json_data = self._parse_json(json_data, video_id)['state']['data']['video']

        formats = []
        streams = traverse_obj(json_data, ('videos_manifest', 'servers', ..., 'streams', ...))
        for stream in streams or []:
            url = stream['url']
            if not url:
                continue
            formats.append({
                'format_id': '%s-%d-%d' % (stream['slug'], stream['id'], stream['server_id']),
                'url': url,
                'width': int_or_none(stream['width']),
                'height': int_or_none(stream['height']),
                'ext': 'mp4',
                'protocol': 'm3u8',
                'filesize_approx': float_or_none(stream.get('filesize_mbs'), invscale=1000 ** 2),
                'duration': float_or_none(stream.get('duration_in_ms'), 1000),
            })

        hentai_video = traverse_obj(json_data, 'hentai_video')

        title = traverse_obj(hentai_video, 'name', default=video_id)
        series_and_episode = self._search_regex(
            r'(?i)^(.+?)(?:[\s-]*Ep(?:\.|isode)?)?[\s-]*(\d+)$', title, 'series and episode', default=(None, None),
            fatal=False, group=(1, 2))

        release_date = traverse_obj(hentai_video, 'released_at')
        if release_date:
            release_date = release_date[:10].replace('-', '')

        self._sort_formats(formats)
        return {
            'id': video_id,
            'formats': formats,
            'description': clean_html(traverse_obj(hentai_video, 'description')),
            'creator': traverse_obj(hentai_video, 'brand'),
            'title': title,
            'alt_title': traverse_obj(hentai_video, ('titles', ..., 'title'), get_all=False),
            'tags': traverse_obj(hentai_video, ('hentai_tags', ..., 'text')),
            'release_date': release_date,
            'thumbnails': [{
                'url': traverse_obj(hentai_video, 'poster_url'),
                'id': 'poster',
            }, {
                'url': traverse_obj(hentai_video, 'cover_url'),
                'id': 'cover',
            }],

            'series': series_and_episode[0],
            'episode_number': int_or_none(series_and_episode[1]),

            'timestamp': traverse_obj(hentai_video, 'released_at_unix'),
            'view_count': traverse_obj(hentai_video, 'views'),
            'like_count': traverse_obj(hentai_video, 'likes'),
            'dislike_count': traverse_obj(hentai_video, 'dislikes'),
            'age_limit': 18,
        }

class HANMPLIE(InfoExtractor):
    IE_DESC = False
    _VALID_URL = r'https?://(?P<host>(?:www\.)?(?:members\.)?han' \
        r'ime\.tv)/videos/hentai/(?P<vid>[a-zA-Z0-9-]+?)\?playlist_id=(?P<id>[a-zA-Z0-9-]+)'

    def _entries(self, url, host, playlist_id):
        for page_num in itertools.count(1):
            page_data = self._download_json(
                'https://hw.h' 'a' 'n' 'i' 'm' 'e.tv/api/v8/playlist_hentai_videos', playlist_id,
                note='Downloading page %d' % page_num,
                query={
                    'playlist_id': playlist_id,
                    '__order': 'sequence,DESC',
                    '__offset': str(24 * (page_num - 1)),
                    '__count': '24',
                    'personalized': '0',
                }, headers={
                    'X-Signature': 'null',
                    'X-Signature-Version': 'web2',
                    'X-Time': str(int(time_millis() / 1000)),
                    'X-Token': 'null',
                })
            if page_num == 1:
                # yield page_data only once to extract more data in _real_extract
                yield page_data
            videos = page_data['fapi']['data']
            if not videos:
                break
            for vid in videos:
                yield self.url_result(
                    f'https://{host}/videos/hentai/{vid["slug"]}',
                    video_id=vid["slug"], video_title=vid.get('name'))

    def _real_extract(self, url):
        host, video_id, playlist_id = self._match_valid_url(url).group('host', 'vid', 'id')

        if self.get_param('noplaylist'):
            self.to_screen('Downloading just video %s because of --no-playlist' % video_id)
            return self.url_result(f'https://{host}/videos/hentai/{video_id}', ie=HANMIE.ie_key(), video_id=video_id)
        # self.to_screen('Downloading playlist %s; add --no-playlist to just download video %s' % (playlist_id, video_id))

        entries = self._entries(url, host, playlist_id)
        playlist_info = next(entries)['playlist']
        return self.playlist_result(
            entries, playlist_id, playlist_title=playlist_info['title'])

class HANMALLIE(InfoExtractor):
    IE_DESC = False
    _VALID_URL = r'han' \
        'ime-all'

    def _entries(self):
        for i in itertools.count(0):
            page = self._download_json(
                'https://search.htv-services.com/', 'h' 'a' 'n' 'i' 'm' 'e-all',
                note=f'Downloading page {i}', data=json.dumps({
                    'blacklist': [],
                    'brands': [],
                    'order_by': 'created_at_unix',
                    'ordering': 'desc',
                    'page': i,
                    'search_text': '',
                    'tags': [],
                    'tags_mode': 'AND',
                }).encode('utf-8'), headers={
                    'Content-Type': 'application/json;charset=utf-8',
                    'Accept': 'application/json, text/plain, */*',
                    'Origin': 'https://h' 'a' 'n' 'i' 'm' 'e.tv',
                })
            hits = self._parse_json(page['hits'], 'h' 'a' 'n' 'i' 'm' 'e-all')
            if not hits:
                break
            yield from (self.url_result('https://h' 'a' 'n' 'i' 'm' 'e.tv/videos/hentai/%s' % x['slug']) for x in hits)

    def _real_extract(self, url):
        return self.playlist_result(self._entries())

class GANMIE(InfoExtractor):
    IE_DESC = False
    _VALID_URL = r'https?://gog' 'oan' \
        r'ime\.be/watch/(?P<id>[^/]+)'

    def _real_extract(self, url):
        video_id = self._match_id(url)
        webpage = self._download_webpage(url, video_id)

        json_ld = self._search_json_ld(webpage, video_id)

        embed_vids = self._search_regex(
            (r'(?x)"embedUrl": "(https?://vids[^"]+?)",',
             r'(?x)data-embed="(https?://vids[^"]+?)"'),
            webpage, 'embed player url')
        if not embed_vids:
            raise ExtractorError('Boomer moment')
        embed_vids = smuggle_url(embed_vids, {
            'referrer': url,
        })

        json_ld.update({
            '_type': 'url_transparent',
            'url': embed_vids,
            'ie_key': VDSIE.ie_key(),
        })

        return json_ld

class VDSIE(InfoExtractor):
    IE_DESC = False
    _VALID_URL = r'https?://vidst' \
        r'ream\.pro/e/(?P<id>[^/?]+)'

    def _real_extract(self, url):
        url, data = unsmuggle_url(url)
        video_id = self._match_id(url)
        referrer = traverse_obj(data, 'referrer', expected_type=compat_str)
        request_header = {}
        if referrer:
            request_header['Referer'] = referrer
        origin_domain = traverse_obj(parse_qs(url), ('domain', 0))

        webpage = self._download_webpage(
            url, video_id, headers=request_header)
        title = self._html_extract_title(webpage, video_id)
        skey = self._search_regex(
            r'window\.skey\s*=\s*(["\'])(?P<skey>[a-zA-Z0-9]+?)\1', webpage, 'skey',
            group='skey')

        info_response = self._download_json(
            f'https://v' 'idst' f'ream.pro/info/{video_id}', video_id,
            query={
                'domain': origin_domain,
                'skey': skey,
            }, headers={
                'Accept': 'application/json, text/javascript',
                'Referer': url,
                'X-Requested-With': 'XMLHttpRequest',
            })
        if not info_response.get('success'):
            raise ExtractorError('There was an error in info request')

        formats = []
        for fm in traverse_obj(info_response, ('media', 'sources', ..., 'file'), default=[]):
            formats.extend(self._extract_m3u8_formats(fm, video_id, ext='mp4'))
        self._sort_formats(formats)

        return {
            'id': video_id,
            'title': title,
            'formats': formats,
        }

repo_name: Lesmiscore/ytdl


code:
# automating YouTube downloading services to download deleted videos
import re

from ..utils import (
    ExtractorError,
    int_or_none,
    parse_filesize,
    parse_qs,
    urlencode_postdata,
    try_get,
)
from .common import InfoExtractor
from .youtube import YoutubeIE

class CustomPrefixedBaseIE(InfoExtractor):
    BASE_IE = InfoExtractor
    PREFIXES = ()
    _VALID_URL = r'(?P<id>)'

    @classmethod
    def remove_prefix(cls, url):
        for pfx in cls.PREFIXES:
            if not url.startswith(pfx):
                continue
            return url[len(pfx):]
        return url

    @classmethod
    def suitable(cls, url):
        for pfx in cls.PREFIXES:
            if not url.startswith(pfx):
                continue
            return cls.BASE_IE.suitable(url[len(pfx):])
        return False

# Y2Mate
class Y2mateIE(CustomPrefixedBaseIE):
    BASE_IE = YoutubeIE
    IE_NAME = 'y2mate'
    PREFIXES = ('y2:', 'y2mate:')

    def _real_extract(self, url):
        video_id = self.BASE_IE._match_id(self.remove_prefix(url))
        self._download_webpage(f'https://www.y2mate.com/youtube/{video_id}', video_id)
        common_headers = {'X-Requested-With': 'XMLHttpRequest', 'Content-Type': 'application/x-www-form-urlencoded; charset=UTF-8'}
        anazylze = self._download_json(
            'https://www.y2mate.com/mates/analyze/ajax', video_id,
            note='Fetching size specs', errnote='This video is unavailable', headers=common_headers,
            form_params={
                'url': f'https://www.youtube.com/watch?v={video_id}',
                'q_auto': '1',
                'ajax': '1'
            })
        if anazylze.get('status') != 'success':
            raise ExtractorError(f'Server responded with status {anazylze.get("status")}')
        size_specs = anazylze['result']
        title = self._search_regex(r'(.+?)', size_specs, 'video title', group=1)
        request_id = self._search_regex(r'var k__id\s*=\s*(["\'])(.+?)\1', size_specs, 'request ID', group=2)
        tables = re.findall(r'
(.+?)
', size_specs)

        formats = [x for tbl in (tables[0], tables[-1]) for x in self._find_formats(request_id, video_id, common_headers, tbl)]
        self._sort_formats(formats)

        return {
            'id': video_id,
            'title': title,
            'formats': formats,
        }

    def _find_formats(self, request_id, video_id, headers, table):
        for rows in re.finditer(r'''(?x)
\s*
                    .*?(\d+p|\d+[kMG]?bps).*?	\s* # resolution name or kbps
                    (.*?\s*[kMG]?B)	\s* # estimate size
                    .+?(?:data-ftype="(.+?)".+?)?(?:data-fquality="(.+?)".+?)?	\s* # download button

''', table):
            format_name, estimate_size, format_ext, request_format = rows.groups()
            estimate_size = re.sub(r'\s*([kMG])B', r'\1iB', estimate_size)
            request_data = urlencode_postdata({
                'type': 'youtube',
                '_id': request_id,
                'v_id': video_id,
                'ajax': '1',
                'token': '',
                'ftype': format_ext,
                'fquality': request_format,
            })
            video_url = None
            for retry in self.RetryManager(fatal=False):
                try:
                    url_data = self._download_json(
                        'https://www.y2mate.com/mates/convert', video_id,
                        note=f'Fetching infomation for {format_name} ({format_ext})', data=request_data,
                        headers=headers)
                except ExtractorError as e:
                    retry.error = e
                    continue
                if url_data.get('status') != 'success':
                    retry.error = ExtractorError(f'Server responded with status {url_data.get("status")}', expected=True)
                    continue
                try:
                    video_url = self._search_regex(
                        r'<a\s+(?:[a-zA-Z-_]+=\".+?\"\s+)*href=\"(https?://.+?)\"(?:\s+[a-zA-Z-_]+=\".+?\")*', url_data['result'],
                        f'Download url for {format_name}', group=1, default=None)
                except ExtractorError as e:
                    retry.error = e
                    continue

            if not video_url or 'app.y2mate.com' in video_url:
                continue

            yield {
                'format_id': f'{format_name}-{format_ext}',
                'filesize_approx': parse_filesize(estimate_size),
                'ext': format_ext,
                'url': video_url,
                'acodec': 'unknown',

                **({
                    # audio
                    'vcodec': 'none',
                    'abr': int_or_none(parse_filesize(format_name[:-2]), scale=1000),
                } if format_name.endswith('bps') else {
                    # video
                    'vcodec': 'unknown',
                    'height': int_or_none(format_name[:-1]),
                    'resolution': format_name,
                }),
            }

# ClipConverter
class ClipConverterIE(CustomPrefixedBaseIE):
    BASE_IE = YoutubeIE
    PREFIXES = ('cc:', 'clipconverter:')

    def _real_extract(self, url):
        video_id = self.BASE_IE._match_id(self.remove_prefix(url))
        post_data = {
            'mediaurl': f"https://www.youtube.com/watch?v={video_id}",
            'service': 'YouTube',
            'ref': '',
            'lang': 'en',
            'client_urlmap': 'none',
            'addon_urlmap': '',
            'cookie': '',
            'addon_cookie': '',
            'addon_title': '',
            'ablock': '1',
            'clientside': '1',
            'addon_page': 'none',
            'addon_browser': '',
            'addon_version': '',
            'filetype': 'MP4',
            'format': '',
            'audiovol': '0',
            'audiochannel': '2',
            'audiobr': '128'
        }
        response = self._download_json(
            'https://www.clipconverter.cc/check.php', video_id, note='Requesting for extraction',
            form_params=post_data,
            headers={
                'Origin': 'https://www.clipconverter.cc',
                'Referer': 'https://www.clipconverter.cc/2/',
                'X-Requested-With': 'XMLHttpRequest',
                'Content-Type': 'application/x-www-form-urlencoded',
            })

        formats = []
        for fmt in response.get('url') or []:
            text = fmt.get('text')
            resol = self._search_regex(r'(\d+p)', text, 'resolution', default=None)
            fps = self._search_regex(r'(\d+)fps', text, 'framerate', default=None)
            filetype = try_get(fmt, lambda x: x['filetype'])
            height = int_or_none(resol[:-1]) if resol else None
            is_vonly = filetype == 'webm' or (height and height > 1080)
            formats.append({
                'format_id': f'{resol}-{filetype}',
                'url': fmt.get('url'),
                'filesize': int_or_none(fmt.get('size')),
                'resolution': resol,
                'height': height,
                'ext': filetype.lower() if filetype else None,
                'fps': int_or_none(fps),
                'acodec': 'none' if is_vonly else None,
                'quality': -10 if is_vonly else None
            })

        # convert mode isn't implemented yet; this is just Download mode
        if not formats:
            raise ExtractorError(parse_qs(response['redirect'])['errorstr'][0], expected=True)
        self._sort_formats(formats)

        return {
            'id': video_id,
            'title': response.get('filename') or response.get('id3title'),
            'uploader': response.get('channel') or response.get('id3artist'),
            'category': response.get('category'),
            'formats': formats,
        }

# Combined
class YtAlternateIE(CustomPrefixedBaseIE):
    BASE_IE = YoutubeIE
    PREFIXES = ('yta:', 'dig:', 'ytalternate:')
    # _CALL_IES = ('Y2mate', 'ClipConverter', 'Youtube')
    _CALL_IES = ('ClipConverter', 'Y2mate')

    def _real_extract(self, url):
        video_id = self.BASE_IE._match_id(self.remove_prefix(url))
        infodicts = []
        for exn in self._CALL_IES:
            try:
                dct = self._downloader.get_info_extractor(exn).extract(video_id)
                for fmt in dct['formats']:
                    fmt['format_note'] = exn
                infodicts.append(dct)
            except KeyboardInterrupt:
                raise
            except BaseException as ex:
                self.report_warning(f'{ex}')

        if not infodicts:
            raise ExtractorError('Extraction failed.', expected=True)
        return self._merge_video_infodicts(infodicts)


code:
import hashlib
import hmac
import re
import time

from .common import InfoExtractor
from ..compat import compat_str
from ..utils import (
    dict_get,
    ExtractorError,
    js_to_json,
    int_or_none,
    parse_iso8601,
    str_or_none,
    try_get,
    unescapeHTML,
    update_url_query,
)

class ABCIE(InfoExtractor):
    IE_NAME = 'abc.net.au'
    _VALID_URL = r'https?://(?:www\.)?abc\.net\.au/(?:news|btn)/(?:[^/]+/){1,4}(?P<id>\d{5,})'

    _TESTS = [{
        'url': 'http://www.abc.net.au/news/2014-11-05/australia-to-staff-ebola-treatment-centre-in-sierra-leone/5868334',
        'md5': 'cb3dd03b18455a661071ee1e28344d9f',
        'info_dict': {
            'id': '5868334',
            'ext': 'mp4',
            'title': 'Australia to help staff Ebola treatment centre in Sierra Leone',
            'description': 'md5:809ad29c67a05f54eb41f2a105693a67',
        },
        'skip': 'this video has expired',
    }, {
        'url': 'http://www.abc.net.au/news/2015-08-17/warren-entsch-introduces-same-sex-marriage-bill/6702326',
        'md5': '4ebd61bdc82d9a8b722f64f1f4b4d121',
        'info_dict': {
            'id': 'NvqvPeNZsHU',
            'ext': 'mp4',
            'upload_date': '20150816',
            'uploader': 'ABC News (Australia)',
            'description': 'Government backbencher Warren Entsch introduces a cross-party sponsored bill to legalise same-sex marriage, saying the bill is designed to promote "an inclusive Australia, not a divided one.". Read more here: http://ab.co/1Mwc6ef',
            'uploader_id': 'NewsOnABC',
            'title': 'Marriage Equality: Warren Entsch introduces same sex marriage bill',
        },
        'add_ie': ['Youtube'],
        'skip': 'Not accessible from Travis CI server',
    }, {
        'url': 'http://www.abc.net.au/news/2015-10-23/nab-lifts-interest-rates-following-westpac-and-cba/6880080',
        'md5': 'b96eee7c9edf4fc5a358a0252881cc1f',
        'info_dict': {
            'id': '6880080',
            'ext': 'mp3',
            'title': 'NAB lifts interest rates, following Westpac and CBA',
            'description': 'md5:f13d8edc81e462fce4a0437c7dc04728',
        },
    }, {
        'url': 'http://www.abc.net.au/news/2015-10-19/6866214',
        'only_matching': True,
    }, {
        'url': 'https://www.abc.net.au/btn/classroom/wwi-centenary/10527914',
        'info_dict': {
            'id': '10527914',
            'ext': 'mp4',
            'title': 'WWI Centenary',
            'description': 'md5:c2379ec0ca84072e86b446e536954546',
        }
    }, {
        'url': 'https://www.abc.net.au/news/programs/the-world/2020-06-10/black-lives-matter-protests-spawn-support-for/12342074',
        'info_dict': {
            'id': '12342074',
            'ext': 'mp4',
            'title': 'Black Lives Matter protests spawn support for Papuans in Indonesia',
            'description': 'md5:2961a17dc53abc558589ccd0fb8edd6f',
        }
    }, {
        'url': 'https://www.abc.net.au/btn/newsbreak/btn-newsbreak-20200814/12560476',
        'info_dict': {
            'id': 'tDL8Ld4dK_8',
            'ext': 'mp4',
            'title': 'Fortnite Banned From Apple and Google App Stores',
            'description': 'md5:a6df3f36ce8f816b74af4bd6462f5651',
            'upload_date': '20200813',
            'uploader': 'Behind the News',
            'uploader_id': 'behindthenews',
        }
    }]

    def _real_extract(self, url):
        video_id = self._match_id(url)
        webpage = self._download_webpage(url, video_id)

        mobj = re.search(r'<a\s+href="(?P<url>[^"]+)"\s+data-duration="\d+"\s+title="Download audio directly">', webpage)
        if mobj:
            urls_info = mobj.groupdict()
            youtube = False
            video = False
        else:
            mobj = re.search(r'<a href="(?P<url>http://www\.youtube\.com/watch\?v=[^"]+)">External Link:',
                             webpage)
            if mobj is None:
                mobj = re.search(r'<iframe width="100%" src="(?P<url>//www\.youtube-nocookie\.com/embed/[^?"]+)', webpage)
            if mobj:
                urls_info = mobj.groupdict()
                youtube = True
                video = True

        if mobj is None:
            mobj = re.search(r'(?P<type>)"sources": (?P<json_data>\[[^\]]+\]),', webpage)
            if mobj is None:
                mobj = re.search(
                    r'inline(?P<type>Video|Audio|YouTube)Data\.push\((?P<json_data>[^)]+)\);',
                    webpage)
                if mobj is None:
                    expired = self._html_search_regex(r'(?s)class="expired-(?:video|audio)".+?(.+?)', webpage, 'expired', None)
                    if expired:
                        raise ExtractorError('%s said: %s' % (self.IE_NAME, expired), expected=True)
                    raise ExtractorError('Unable to extract video urls')

            urls_info = self._parse_json(
                mobj.group('json_data'), video_id, transform_source=js_to_json)
            youtube = mobj.group('type') == 'YouTube'
            video = mobj.group('type') == 'Video' or urls_info[0]['contentType'] == 'video/mp4'

        if not isinstance(urls_info, list):
            urls_info = [urls_info]

        if youtube:
            return self.playlist_result([
                self.url_result(url_info['url']) for url_info in urls_info])

        formats = []
        for url_info in urls_info:
            height = int_or_none(url_info.get('height'))
            bitrate = int_or_none(url_info.get('bitrate'))
            width = int_or_none(url_info.get('width'))
            format_id = None
            mobj = re.search(r'_(?:(?P<height>\d+)|(?P<bitrate>\d+)k)\.mp4$', url_info['url'])
            if mobj:
                height_from_url = mobj.group('height')
                if height_from_url:
                    height = height or int_or_none(height_from_url)
                    width = width or int_or_none(url_info.get('label'))
                else:
                    bitrate = bitrate or int_or_none(mobj.group('bitrate'))
                    format_id = str_or_none(url_info.get('label'))
            formats.append({
                'url': url_info['url'],
                'vcodec': url_info.get('codec') if video else 'none',
                'width': width,
                'height': height,
                'tbr': bitrate,
                'filesize': int_or_none(url_info.get('filesize')),
                'format_id': format_id
            })

        self._sort_formats(formats)

        return {
            'id': video_id,
            'title': self._og_search_title(webpage),
            'formats': formats,
            'description': self._og_search_description(webpage),
            'thumbnail': self._og_search_thumbnail(webpage),
        }

class ABCIViewIE(InfoExtractor):
    IE_NAME = 'abc.net.au:iview'
    _VALID_URL = r'https?://iview\.abc\.net\.au/(?:[^/]+/)*video/(?P<id>[^/?#]+)'
    _GEO_COUNTRIES = ['AU']

    # ABC iview programs are normally available for 14 days only.
    _TESTS = [{
        'url': 'https://iview.abc.net.au/show/gruen/series/11/video/LE1927H001S00',
        'md5': '67715ce3c78426b11ba167d875ac6abf',
        'info_dict': {
            'id': 'LE1927H001S00',
            'ext': 'mp4',
            'title': "Series 11 Ep 1",
            'series': "Gruen",
            'description': 'md5:52cc744ad35045baf6aded2ce7287f67',
            'upload_date': '20190925',
            'uploader_id': 'abc1',
            'timestamp': 1569445289,
        },
        'params': {
            'skip_download': True,
        },
    }]

    def _real_extract(self, url):
        video_id = self._match_id(url)
        video_params = self._download_json(
            'https://iview.abc.net.au/api/programs/' + video_id, video_id)
        title = unescapeHTML(video_params.get('title') or video_params['seriesTitle'])
        stream = next(s for s in video_params['playlist'] if s.get('type') in ('program', 'livestream'))

        house_number = video_params.get('episodeHouseNumber') or video_id
        path = '/auth/hls/sign?ts={0}&hn={1}&d=android-tablet'.format(
            int(time.time()), house_number)
        sig = hmac.new(
            b'android.content.res.Resources',
            path.encode('utf-8'), hashlib.sha256).hexdigest()
        token = self._download_webpage(
            'http://iview.abc.net.au{0}&sig={1}'.format(path, sig), video_id)

        def tokenize_url(url, token):
            return update_url_query(url, {
                'hdnea': token,
            })

        for sd in ('1080', '720', 'sd', 'sd-low'):
            sd_url = try_get(
                stream, lambda x: x['streams']['hls'][sd], compat_str)
            if not sd_url:
                continue
            formats = self._extract_m3u8_formats(
                tokenize_url(sd_url, token), video_id, 'mp4',
                entry_protocol='m3u8_native', m3u8_id='hls', fatal=False)
            if formats:
                break
        self._sort_formats(formats)

        subtitles = {}
        src_vtt = stream.get('captions', {}).get('src-vtt')
        if src_vtt:
            subtitles['en'] = [{
                'url': src_vtt,
                'ext': 'vtt',
            }]

        is_live = video_params.get('livestream') == '1'

        return {
            'id': video_id,
            'title': title,
            'description': video_params.get('description'),
            'thumbnail': video_params.get('thumbnail'),
            'duration': int_or_none(video_params.get('eventDuration')),
            'timestamp': parse_iso8601(video_params.get('pubDate'), ' '),
            'series': unescapeHTML(video_params.get('seriesTitle')),
            'series_id': video_params.get('seriesHouseNumber') or video_id[:7],
            'season_number': int_or_none(self._search_regex(
                r'\bSeries\s+(\d+)\b', title, 'season number', default=None)),
            'episode_number': int_or_none(self._search_regex(
                r'\bEp\s+(\d+)\b', title, 'episode number', default=None)),
            'episode_id': house_number,
            'uploader_id': video_params.get('channel'),
            'formats': formats,
            'subtitles': subtitles,
            'is_live': is_live,
        }

class ABCIViewShowSeriesIE(InfoExtractor):
    IE_NAME = 'abc.net.au:iview:showseries'
    _VALID_URL = r'https?://iview\.abc\.net\.au/show/(?P<id>[^/]+)(?:/series/\d+)?$'
    _GEO_COUNTRIES = ['AU']

    _TESTS = [{
        'url': 'https://iview.abc.net.au/show/upper-middle-bogan',
        'info_dict': {
            'id': '124870-1',
            'title': 'Series 1',
            'description': 'md5:93119346c24a7c322d446d8eece430ff',
            'series': 'Upper Middle Bogan',
            'season': 'Series 1',
            'thumbnail': r're:^https?://cdn\.iview\.abc\.net\.au/thumbs/.*\.jpg$'
        },
        'playlist_count': 8,
    }, {
        'url': 'https://iview.abc.net.au/show/upper-middle-bogan',
        'info_dict': {
            'id': 'CO1108V001S00',
            'ext': 'mp4',
            'title': 'Series 1 Ep 1 I\'m A Swan',
            'description': 'md5:7b676758c1de11a30b79b4d301e8da93',
            'series': 'Upper Middle Bogan',
            'uploader_id': 'abc1',
            'upload_date': '20210630',
            'timestamp': 1625036400,
        },
        'params': {
            'noplaylist': True,
            'skip_download': 'm3u8',
        },
    }]

    def _real_extract(self, url):
        show_id = self._match_id(url)
        webpage = self._download_webpage(url, show_id)
        webpage_data = self._search_regex(
            r'window\.__INITIAL_STATE__\s*=\s*[\'"](.+?)[\'"]\s*;',
            webpage, 'initial state')
        video_data = self._parse_json(
            unescapeHTML(webpage_data).encode('utf-8').decode('unicode_escape'), show_id)
        video_data = video_data['route']['pageData']['_embedded']

        highlight = try_get(video_data, lambda x: x['highlightVideo']['shareUrl'])
        if not self._yes_playlist(show_id, bool(highlight), video_label='highlight video'):
            return self.url_result(highlight, ie=ABCIViewIE.ie_key())

        series = video_data['selectedSeries']
        return {
            '_type': 'playlist',
            'entries': [self.url_result(episode['shareUrl'])
                        for episode in series['_embedded']['videoEpisodes']],
            'id': series.get('id'),
            'title': dict_get(series, ('title', 'displaySubtitle')),
            'description': series.get('description'),
            'series': dict_get(series, ('showTitle', 'displayTitle')),
            'season': dict_get(series, ('title', 'displaySubtitle')),
            'thumbnail': series.get('thumbnail'),
        }


code:
from .amp import AMPIE
from .common import InfoExtractor
from ..utils import (
    parse_duration,
    parse_iso8601,
    try_get,
)

class AbcNewsVideoIE(AMPIE):
    IE_NAME = 'abcnews:video'
    _VALID_URL = r'''(?x)
                    https?://
                        (?:
                            abcnews\.go\.com/
                            (?:
                                (?:[^/]+/)*video/(?P<display_id>[0-9a-z-]+)-|
                                video/(?:embed|itemfeed)\?.*?\bid=
                            )|
                            fivethirtyeight\.abcnews\.go\.com/video/embed/\d+/
                        )
                        (?P<id>\d+)
                    '''

    _TESTS = [{
        'url': 'http://abcnews.go.com/ThisWeek/video/week-exclusive-irans-foreign-minister-zarif-20411932',
        'info_dict': {
            'id': '20411932',
            'ext': 'mp4',
            'display_id': 'week-exclusive-irans-foreign-minister-zarif',
            'title': '\'This Week\' Exclusive: Iran\'s Foreign Minister Zarif',
            'description': 'George Stephanopoulos goes one-on-one with Iranian Foreign Minister Dr. Javad Zarif.',
            'duration': 180,
            'thumbnail': r're:^https?://.*\.jpg$',
            'timestamp': 1380454200,
            'upload_date': '20130929',
        },
        'params': {
            # m3u8 download
            'skip_download': True,
        },
    }, {
        'url': 'http://abcnews.go.com/video/embed?id=46979033',
        'only_matching': True,
    }, {
        'url': 'http://abcnews.go.com/2020/video/2020-husband-stands-teacher-jail-student-affairs-26119478',
        'only_matching': True,
    }, {
        'url': 'http://abcnews.go.com/video/itemfeed?id=46979033',
        'only_matching': True,
    }, {
        'url': 'https://abcnews.go.com/GMA/News/video/history-christmas-story-67894761',
        'only_matching': True,
    }]

    def _real_extract(self, url):
        mobj = self._match_valid_url(url)
        display_id = mobj.group('display_id')
        video_id = mobj.group('id')
        info_dict = self._extract_feed_info(
            'http://abcnews.go.com/video/itemfeed?id=%s' % video_id)
        info_dict.update({
            'id': video_id,
            'display_id': display_id,
        })
        return info_dict

class AbcNewsIE(InfoExtractor):
    IE_NAME = 'abcnews'
    _VALID_URL = r'https?://abcnews\.go\.com/(?:[^/]+/)+(?P<display_id>[0-9a-z-]+)/story\?id=(?P<id>\d+)'

    _TESTS = [{
        # Youtube Embeds
        'url': 'https://abcnews.go.com/Entertainment/peter-billingsley-child-actor-christmas-story-hollywood-power/story?id=51286501',
        'info_dict': {
            'id': '51286501',
            'title': "Peter Billingsley: From child actor in 'A Christmas Story' to Hollywood power player",
            'description': 'Billingsley went from a child actor to Hollywood power player.',
        },
        'playlist_count': 5,
    }, {
        'url': 'http://abcnews.go.com/Entertainment/justin-timberlake-performs-stop-feeling-eurovision-2016/story?id=39125818',
        'info_dict': {
            'id': '38897857',
            'ext': 'mp4',
            'title': 'Justin Timberlake Drops Hints For Secret Single',
            'description': 'Lara Spencer reports the buzziest stories of the day in "GMA" Pop News.',
            'upload_date': '20160505',
            'timestamp': 1462442280,
        },
        'params': {
            # m3u8 download
            'skip_download': True,
            # The embedded YouTube video is blocked due to copyright issues
            'playlist_items': '1',
        },
        'add_ie': ['AbcNewsVideo'],
    }, {
        'url': 'http://abcnews.go.com/Technology/exclusive-apple-ceo-tim-cook-iphone-cracking-software/story?id=37173343',
        'only_matching': True,
    }, {
        # inline.type == 'video'
        'url': 'http://abcnews.go.com/Technology/exclusive-apple-ceo-tim-cook-iphone-cracking-software/story?id=37173343',
        'only_matching': True,
    }]

    def _real_extract(self, url):
        story_id = self._match_id(url)
        webpage = self._download_webpage(url, story_id)
        story = self._parse_json(self._search_regex(
            r"window\['__abcnews__'\]\s*=\s*({.+?});",
            webpage, 'data'), story_id)['page']['content']['story']['everscroll'][0]
        article_contents = story.get('articleContents') or {}

        def entries():
            featured_video = story.get('featuredVideo') or {}
            feed = try_get(featured_video, lambda x: x['video']['feed'])
            if feed:
                yield {
                    '_type': 'url',
                    'id': featured_video.get('id'),
                    'title': featured_video.get('name'),
                    'url': feed,
                    'thumbnail': featured_video.get('images'),
                    'description': featured_video.get('description'),
                    'timestamp': parse_iso8601(featured_video.get('uploadDate')),
                    'duration': parse_duration(featured_video.get('duration')),
                    'ie_key': AbcNewsVideoIE.ie_key(),
                }

            for inline in (article_contents.get('inlines') or []):
                inline_type = inline.get('type')
                if inline_type == 'iframe':
                    iframe_url = try_get(inline, lambda x: x['attrs']['src'])
                    if iframe_url:
                        yield self.url_result(iframe_url)
                elif inline_type == 'video':
                    video_id = inline.get('id')
                    if video_id:
                        yield {
                            '_type': 'url',
                            'id': video_id,
                            'url': 'http://abcnews.go.com/video/embed?id=' + video_id,
                            'thumbnail': inline.get('imgSrc') or inline.get('imgDefault'),
                            'description': inline.get('description'),
                            'duration': parse_duration(inline.get('duration')),
                            'ie_key': AbcNewsVideoIE.ie_key(),
                        }

        return self.playlist_result(
            entries(), story_id, article_contents.get('headline'),
            article_contents.get('subHead'))


code:
from .common import InfoExtractor
from ..compat import compat_str
from ..utils import (
    dict_get,
    int_or_none,
    try_get,
)

class ABCOTVSIE(InfoExtractor):
    IE_NAME = 'abcotvs'
    IE_DESC = 'ABC Owned Television Stations'
    _VALID_URL = r'https?://(?P<site>abc(?:7(?:news|ny|chicago)?|11|13|30)|6abc)\.com(?:(?:/[^/]+)*/(?P<display_id>[^/]+))?/(?P<id>\d+)'
    _TESTS = [
        {
            'url': 'http://abc7news.com/entertainment/east-bay-museum-celebrates-vintage-synthesizers/472581/',
            'info_dict': {
                'id': '472548',
                'display_id': 'east-bay-museum-celebrates-vintage-synthesizers',
                'ext': 'mp4',
                'title': 'East Bay museum celebrates synthesized music',
                'description': 'md5:24ed2bd527096ec2a5c67b9d5a9005f3',
                'thumbnail': r're:^https?://.*\.jpg$',
                'timestamp': 1421118520,
                'upload_date': '20150113',
            },
            'params': {
                # m3u8 download
                'skip_download': True,
            },
        },
        {
            'url': 'http://abc7news.com/472581',
            'only_matching': True,
        },
        {
            'url': 'https://6abc.com/man-75-killed-after-being-struck-by-vehicle-in-chester/5725182/',
            'only_matching': True,
        },
    ]
    _SITE_MAP = {
        '6abc': 'wpvi',
        'abc11': 'wtvd',
        'abc13': 'ktrk',
        'abc30': 'kfsn',
        'abc7': 'kabc',
        'abc7chicago': 'wls',
        'abc7news': 'kgo',
        'abc7ny': 'wabc',
    }

    def _real_extract(self, url):
        site, display_id, video_id = self._match_valid_url(url).groups()
        display_id = display_id or video_id
        station = self._SITE_MAP[site]

        data = self._download_json(
            'https://api.abcotvs.com/v2/content', display_id, query={
                'id': video_id,
                'key': 'otv.web.%s.story' % station,
                'station': station,
            })['data']
        video = try_get(data, lambda x: x['featuredMedia']['video'], dict) or data
        video_id = compat_str(dict_get(video, ('id', 'publishedKey'), video_id))
        title = video.get('title') or video['linkText']

        formats = []
        m3u8_url = video.get('m3u8')
        if m3u8_url:
            formats = self._extract_m3u8_formats(
                video['m3u8'].split('?')[0], display_id, 'mp4', m3u8_id='hls', fatal=False)
        mp4_url = video.get('mp4')
        if mp4_url:
            formats.append({
                'abr': 128,
                'format_id': 'https',
                'height': 360,
                'url': mp4_url,
                'width': 640,
            })
        self._sort_formats(formats)

        image = video.get('image') or {}

        return {
            'id': video_id,
            'display_id': display_id,
            'title': title,
            'description': dict_get(video, ('description', 'caption'), try_get(video, lambda x: x['meta']['description'])),
            'thumbnail': dict_get(image, ('source', 'dynamicSource')),
            'timestamp': int_or_none(video.get('date')),
            'duration': int_or_none(video.get('length')),
            'formats': formats,
        }

class ABCOTVSClipsIE(InfoExtractor):
    IE_NAME = 'abcotvs:clips'
    _VALID_URL = r'https?://clips\.abcotvs\.com/(?:[^/]+/)*video/(?P<id>\d+)'
    _TEST = {
        'url': 'https://clips.abcotvs.com/kabc/video/214814',
        'info_dict': {
            'id': '214814',
            'ext': 'mp4',
            'title': 'SpaceX launch pad explosion destroys rocket, satellite',
            'description': 'md5:9f186e5ad8f490f65409965ee9c7be1b',
            'upload_date': '20160901',
            'timestamp': 1472756695,
        },
        'params': {
            # m3u8 download
            'skip_download': True,
        },
    }

    def _real_extract(self, url):
        video_id = self._match_id(url)
        video_data = self._download_json('https://clips.abcotvs.com/vogo/video/getByIds?ids=' + video_id, video_id)['results'][0]
        title = video_data['title']
        formats = self._extract_m3u8_formats(
            video_data['videoURL'].split('?')[0], video_id, 'mp4')
        self._sort_formats(formats)

        return {
            'id': video_id,
            'title': title,
            'description': video_data.get('description'),
            'thumbnail': video_data.get('thumbnailURL'),
            'duration': int_or_none(video_data.get('duration')),
            'timestamp': int_or_none(video_data.get('pubDate')),
            'formats': formats,
        }