1

Hello all,
I would like to download google-drive files directly to a folder on my pc rather than the standard download folder. Also, the name of the file should stay the same and not manually set.

I have tried downloading the files using the direct download link which downloads the file but you cannot decide where the file saves on your computer.

I also have tried these methods:
https://stackoverflow.com/a/39225272/13715296 (This method did not work for me) https://stackoverflow.com/a/47761459/13715296 (With this method I could not have the original name of the file)

In my code I basically have a lot of these type of urls:
https://drive.google.com/file/d/xxxxxxxxxxxxxxxxxxx/view?usp=drive_web

But I can easily convert them to these direct download urls:
https://drive.google.com/u/0/uc?id=xxxxxxxxxxxxxxxxxxx&export=download

I just have not found a method on how to download the files using python to a specific folder while keeping the original name of the file the same.

SOLUTION

With the method suggested by @Jacques-GuzelHeron I have now this code:

    creds = None
    # The file token.json stores the user's access and refresh tokens, and is
    # created automatically when the authorization flow completes for the first
    # time.
    if os.path.exists('token.json'):
        creds = Credentials.from_authorized_user_file('token.json', SCOPES)
    # If there are no (valid) credentials available, let the user log in.
    if not creds or not creds.valid:
        if creds and creds.expired and creds.refresh_token:
            creds.refresh(Request())
        else:
            flow = InstalledAppFlow.from_client_secrets_file(
                'credentials.json', SCOPES)
            creds = flow.run_local_server(port=0)
        # Save the credentials for the next run
        with open('token.json', 'w') as token:
            token.write(creds.to_json())

    service = build('drive', 'v3', credentials=creds)
    for id_url in list_urls:
        file_id = id_url
        results = service.files().get(fileId=file_id).execute()
        name = results['name']
        request = service.files().get_media(fileId=file_id)
        fh = io.BytesIO()
        downloader = MediaIoBaseDownload(fh, request)
        done = False
        while done is False:
            status, done = downloader.next_chunk()
            print("Download %d%%." % int(status.progress() * 100))

        fh.seek(0)
        # Write the received data to the file
        path = "PATH/TO/MY/FOLDER/" + name
        with open(path, 'wb') as f:
            shutil.copyfileobj(fh, f)

This is the code provided from the python quickstart page and the example code.

I used the google-drive-api to search for the name by ID, which I could later add back into the path:

        path = "PATH/TO/MY/FOLDER/" + name
        with open(path, 'wb') as f:
            shutil.copyfileobj(fh, f)

This allowed me to control the path where I stored the download and keep the name of the file unchanged. Definitely not my best code, but it did do the job.

  • In your situation, the file on Google Drive is publicly shared or non-publicly shared? If the file is non-publicly shared, you are the owner of the file and you have the access token for downloading the file? – Tanaike Jan 17 '22 at 00:38
  • Hi there @JordyvanDongen! I assume that you are using the `io` library to declare the output destination. Could you please show how you have configured it? If you are using any other approach, please show it too so we all can take a look. – Jacques-Guzel Heron Jan 17 '22 at 08:44
  • @Tanaike I honestly don't know if the file is shared or private. See, I get the files via email attachments from other people so I think it is shared. Is there any way to tell they are private or shared? – Jordy van Dongen Jan 17 '22 at 09:56
  • @Jacques-GuzelHeron I don't really have an approach yet, the only code I have written is to download all attachments from an email and extract the links of the google drive attachments. I have tried a few methods I have stated in the question but unfortunately they didn't work. – Jordy van Dongen Jan 17 '22 at 10:01
  • Thank you for replying. I have to apologize for my poor English skill. Unfortunately, from your replying, I cannot understand your current situation. But I would like to try to understand it. When I could correctly understand it, I would like to think of the solution. I would be grateful if you can forgive my poor English skill. – Tanaike Jan 17 '22 at 11:54
  • @Tanaike No problem, basically I don't have any code yet. I have a list of links like: `["https://drive.google.com/file/d/xxxxxxxxxxxxxxxxxxx/view?usp=drive_web", "https://drive.google.com/file/d/xxxxxxxxxxxxxxxxxxx/view?usp=drive_web", "https://drive.google.com/file/d/xxxxxxxxxxxxxxxxxxx/view?usp=drive_web"]` And I would like to know a method on how to download those files to a specific folder on my pc. – Jordy van Dongen Jan 17 '22 at 13:11

1 Answers1

2

I understand that you have an array of Drive file links, and you want to download them locally using Python. I am assuming that you want to to download files stored on Drive, not Workspace files (i.e. Docs, Sheets…). You can do it very easily by following the Drive API Python quickstart guide. That walkthrough will install all the necessary dependencies and show you an example code. Then, you only have to edit the main function to download the files instead of the sample operations.

To download the Python files you only need to know its id and use the Files.get method. I see that you already know the ids, so you are ready to make the request. To build the request you should introduce the id of the file and set the parameter alt to the value media. If you are using the example from the paragraph above, you can do it just by using the id like this example. If those guides don't work for you, please let me know.

Jacques-Guzel Heron
  • 2,480
  • 1
  • 7
  • 16