krypton-byte / tiktok-downloader

Tiktok Downloader/Scraper using requests & bs4
https://tiktok-dl.id
GNU General Public License v3.0
296 stars 82 forks source link

if service fails than use next service #36

Open TrajanWJ opened 1 year ago

TrajanWJ commented 1 year ago

I have no idea if this is necessary or not


from tiktok_downloader import Tikmate, snaptik, tikdown, VideoInfo, ttdownloader, tikwm, mdown

class TikScrape:
    def __init__(self):
        self.downloadtypes = [Tikmate, snaptik, tikdown, VideoInfo, ttdownloader, tikwm, mdown]

    def downloadTok(self, link, path, type=0):

        if type >= len(self.downloadtypes): # if the type is not in the list of download types, raise an error
            # raise Exception("Invalid service selected OR every service failed, exiting.")
            return False

        try:

            loader = self.downloadtypes[type]() # load the service selected in type, initally "Tikmate", then the rest of the services in self.downloadtypes, which are listed in order of reliability
            vidInfo = loader.get_media(link)

            if vidInfo != []: # if the service returned a video, download the video and return True

                vidInfo[0].download(path)
                return True

            else:
                raise Exception(f"Service {self.downloadtypes[type].__name__} returned nothing, possibly due to rate limiting or malformated link.")
                # if the service returned nothing, raise an error to try the next one

        except Exception as e: # if the service failed, try the next one

            print(f"Service {self.downloadtypes[type].__name__} failed, automatically retrying with service {self.downloadtypes[type+1].__name__}. \nReason error: {e}")
            # say it failed, then try the next one
            self.downloadTok(link, path, type=type+1)

x = TikScrape()
x.downloadTok("LINK", "tiktok.mp4")
TrajanWJ commented 1 year ago

idek if this is stupid or not, or if im reinventing the wheel, but I did this.

TrajanWJ commented 1 year ago

This code doesnt work, someone help fix it for me, idk what kind of link it wants or when to use it, im just confused ig

TrajanWJ commented 1 year ago
"""
Takes in:
- link: str, tiktok link to download, been struggling to find too much information about what this link should look like, will add handlers for different forms of tiktok links later
- path: str, path to save .mp4 file to
- max_retries: int, the number of retries to do before giving up and either exiting or offering the user to exit
- service: str, string from list of valid services

services = {
    'snaptik': snaptik,
    'ssstik': ssstik,
    'tikmate': tikmate,
    'mdown': mdown,
    'ttdownloader': ttdownloader,
    'tikdown': tikdown,
    'tiktok': VideoInfo.service,
    'tikwm': tikwm
}

"""
    def downloadTok(self, link: str, path: str, max_retries: int = len(tiktok_downloader.services), use_service: str = "snaptik", __retries=0):
        # HANDLE SPECIFIC SERVICE STRINGS. If service is a string, set service to associated index in downloads_services.
        try:
            service = tiktok_downloader.services[use_service.lower().strip()]
        except:
            raise Exception(f"Invalid service \"{service}\" selected or every service failed. Valid services include: \"{list(tiktok_downloader.services.keys())}\"")

        if __retries > max_retries:
            raise Exception(f"Max retries hit. Tiktok download failed. Exiting.")

        try:
            # Code to download a tiktok link using a service (integer index)
            vidInfo = service(link)
            if vidInfo:
                vidInfo[0].download(path)
                print(f"Successfully downloaded tiktok with service {service.__name__}")
            else:
                raise Exception(f"Service {service.__name__} returned nothing, possibly due to rate limiting or malformed link. This error is usually not an issue with a specific service and is an issue with input.")

        except Exception as e:
            print(f"Service {service.__name__} failed\nReason error: {e}\nRetrying with the next service...")
            return self.downloadTok(link, path, service=(tiktok_downloader.services.index(use_service) + 1) % len(tiktok_downloader.services), __retries=__retries + 1)
TrajanWJ commented 1 year ago
    def downloadTok(self, link: str, path: str, max_retries: int = len(tiktok_downloader.services), use_service: str = "snaptik", __retries=0):
        # HANDLE SPECIFIC SERVICE STRINGS. If service is a string, set service to associated index in downloads_services.
        try:
            service = tiktok_downloader.services[use_service.lower().strip()]
        except:
            raise Exception(f"Invalid service \"{service}\" selected or every service failed. Valid services include: \"{list(tiktok_downloader.services.keys())}\"")

        # If retries are too many
        if __retries > max_retries:
            service_names = [
                tiktok_downloader.services[(list(tiktok_downloader.services.keys())[tiktok_downloader.services.keys().index(use_service) - i]) % len(tiktok_downloader.services)]
                for i in range(1, __retries + 1)
            ]
            retries_per_service = max_retries // len(tiktok_downloader.services)
            additional_retries = max_retries % len(tiktok_downloader.services)
            tried_every_service = f"every service {retries_per_service} times" if max_retries >= len(tiktok_downloader.services) else ""
            tried_additional_services = " and then tried " if additional_retries != 0 and max_retries >= len(tiktok_downloader.services) else ""
            tried_service_plural = "services" if __retries > 1 else "service"
            service_list = ", ".join(service_names[:-1]) + f", and {service_names[-1]}" if len(service_names) > 1 else service_names[0]

            raise Exception(f"Tried {tried_every_service}{tried_additional_services}{tried_service_plural}: {service_list} and tiktok download failed. Exiting.")

        try:
            # Code to download a tiktok link using a service (integer index)
            vidInfo = service(link)
            if vidInfo:
                vidInfo[0].download(path)
                print(f"Successfully downloaded tiktok with service {service.__name__}")
            else:
                raise Exception(f"Service {service.__name__} returned nothing, possibly due to rate limiting or malformed link. This error is usually not an issue with a specific service and is an issue with input.")

        # If the service used encounters an error, cycle the function to the next service and try again
        except Exception as e:
            print(f"Service {service.__name__} failed\nReason error: {e}\nRetrying with the next service...")

            # Cycle to the next service to try
            return self.downloadTok(link, path, service=(tiktok_downloader.services.index(use_service) + 1) % len(tiktok_downloader.services), __retries=__retries + 1)