pythonpytube

How to make pytube print all available resolutions and the user inputs one


Intro: So I am trying to make a pytube project but I am stuck on this one step,

Problem: I can't figure out how to make pytube list all the available resolutions


from pytube import YouTube

# import the package
print("Please Paste The URL of the youtube video")
url = input()
# URL (user input)
my_video = YouTube(url)
print(my_video.title)
# Title of The Video

#Now for the Thumbnail Image
print("Thumbnail URL")
print(my_video.thumbnail_url)

#To Download the video with the users Choice of resolution

print("Choose A Resolution Please")
for stream in my_video.stream:
    print(stream)
#command for downloading the video
my_video.download()

Solution

  • There's an attribute for the stream object that goes by resolution. For example

    You have:

    for stream in my_video.stream:
        print(stream)
    

    But since you want to display the resolution of each stream objects, you can try:

    for stream in my_video.streams:
        print(stream.resolution)
    

    (Note this also corrects my_video.stream to my_video.streams)

    I took the time to write a script to test my thought.

    from pytube import YouTube
    
    def download(video_resolutions, videos):
        while True:
            # Looping through the video_resolutions list to be displayed on the screen for user selection...
            i = 1
            for resolution in video_resolutions:
                print(f'{i}. {resolution}')
                i += 1
    
            # To Download the video with the users Choice of resolution
            choice = int(input('\nChoose A Resolution Please: '))
            
            # To validate if the user enters a number displayed on the screen...
            if 1 <= choice < i:
                resolution_to_download = video_resolutions[choice - 1]
                print(f"You're now downloading the video with resolution {resolution_to_download}...")
    
                # command for downloading the video
                videos[choice - 1].download()
    
                print("\nVideo was successfully downloaded!")
                break
    
            else:
                print("Invalid choice!!\n\n")
    
    
    def sort_resolutions(url):
        # URL (user input)
        my_video = YouTube(url)
        print(my_video.title)
        # Title of The Video
    
        # Now for the Thumbnail Image
        print("Thumbnail URL")
        print(my_video.thumbnail_url)
    
        video_resolutions = []
        videos = []
    
        for stream in my_video.streams.order_by('resolution'):
            # print(stream)
            video_resolutions.append(stream.resolution)
            videos.append(stream)
    
        # print(video_resolutions)
    
        return video_resolutions, videos
    
    
    print("Please Paste The URL of the youtube video")
    url = "https://youtu.be/o9aaoiyJlcM"
    
    video_resolutions, videos = sort_resolutions(url)
    
    download(video_resolutions, videos)
    

    The url = "https://youtu.be/o9aaoiyJlcM" is just a static line that I don't have to be re-entering the url, you can change it back to the input if you wish. After assigning the link to the url variable I then pass that url to a function called sort_resolutions(url) where the link will be used and extract all that we will need. I used the function because it just makes the code more organized.

    Within the sort_resolution function notice where I have created two lists objects... video_resolutions and videos, video_resolutions = [], videos = [], I have these populated by the stream objects.

    for stream in my_video.streams.order_by('resolution'):
        video_resolutions.append(stream.resolution) # Populating the resolution list
        videos.append(stream) # Populating the video list
    

    my_video.streams.order_by('resolution') this is just sorting the stream objects by resolution in order.

    return video_resolutions, videos is just returning the lists that has been populated, video_resolutions, videos = sort_resolutions(url).

    The values returned is now going to be passed to the download function download(video_resolutions, videos). Please note that within this function the while loop is to keep a display of the menu on the screen of all the available resolutions that can be downloaded. If the user selects a valid number that choice variable collects the value and we will then use choice - 1 to find that index of the desired resolution by resolution_to_download = video_resolutions[choice - 1], but this will only find the resolution. In order to download the video that matches the same index number in the videos list, you'll have to videos[choice - 1].download(). In order words, videos[choice - 1] is a stream object so by calling the download method videos[choice - 1].download() still works.

    One more notice, the resolution list may contain duplication for the resolution. So maybe you can fine tune that.