You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用ServiceAccount调用Google Drive API的文件列表与上传异常咨询

问题描述

我想编写一个简单的Python脚本,递归列出指定文件夹ID下的文件/文件夹,但遇到了以下问题:

  • 将根文件夹ID设为“root”(本应对应Google Drive的“My Drive”根目录),首次运行列表脚本时未返回任何结果。
  • 测试上传脚本时,将父ID改为“root”,期望在“My Drive”下创建文件夹/文件,脚本运行无报错,但在“My Drive”中找不到上传的内容;再次运行列表脚本,仅返回该上传脚本创建的文件夹和文件,看不到My Drive里的其他内容。

请问:

  1. 这种情况为何会发生?上传的文件夹/文件存放在哪里?
  2. 为何我在My Drive中看不到它们?
  3. 为何脚本仅列出通过脚本上传的文件,而非My Drive中的其余内容?

列表脚本代码

from googleapiclient.discovery import build
from google.oauth2 import service_account

# Set up the Google Drive API service
scope = ['https://www.googleapis.com/auth/drive']
service_account_json_key = 'credentials.json'
credentials = service_account.Credentials.from_service_account_file(
    filename=service_account_json_key,
    scopes=scope)
service = build('drive', 'v3', credentials=credentials)

# Function to list files and folders recursively
def list_files_and_folders(folder_id, indent=""):
    results = service.files().list(
        q=f"'{folder_id}' in parents",
        fields="files(id, name, mimeType)").execute()
    items = results.get('files', [])

    if not items:
        print(indent + "No files or folders found.")
    else:
        for item in items:
            print(indent + f"{item['name']} ({item['id']}) - {item['mimeType']}")
            if item['mimeType'] == 'application/vnd.google-apps.folder':
                list_files_and_folders(item['id'], indent + "  ")

# Call the function to list files and folders starting from the specified folder ID
root_folder_id = 'root'
print(f"Listing files and folders recursively from root folder (ID: {root_folder_id}):")
list_files_and_folders(root_folder_id)

上传脚本代码

from googleapiclient.discovery import build
from googleapiclient.http import MediaFileUpload
from google.oauth2 import service_account

# Replace 'FOLDER_NAME' with the name you want to give your new folder
folder_name = 'Test Upload 2'

# setup google drive
credentials = service_account.Credentials.from_service_account_file(
        'credentials.json', scopes=['https://www.googleapis.com/auth/drive']
    )
service = build("drive", "v3", credentials=credentials)
folder_metadata = {
    'name': folder_name,
    "parents": ['root'],
    'mimeType': 'application/vnd.google-apps.folder'
}

# create folder 
new_folder = service.files().create(body=folder_metadata).execute()

#upload file inside the folder
file_metadata = {'name': 'image2.webp', 'parents': [new_folder['id']]}
media = MediaFileUpload('image2.webp')
file = service.files().create(body=file_metadata, media_body=media).execute()

# list the file inside of the folder
results = service.files().list(q=f"'{new_folder['id']}' in parents", fields="files(name)").execute()
items = results.get('files', [])
print(f"Files inside the folder , {items}")

问题解答

1. 原因与文件存储位置

你使用的是**服务账号(Service Account)**身份调用Google Drive API,服务账号拥有独立的Google Drive存储空间,和你个人账号的“My Drive”是完全独立的两个空间。
当你把父ID设为“root”时,这个“root”对应的是服务账号自己的Drive根目录,而非你个人账号的“My Drive”。上传的文件/文件夹都存在服务账号的独立Drive空间里,和你的个人Drive无关。

2. 个人My Drive看不到的原因

服务账号的Drive是独立隔离的,默认不会与你的个人账号共享任何内容。所以你在自己的“My Drive”里看不到服务账号上传的文件,除非手动给服务账号上传的内容设置共享权限,将你的个人账号添加为协作者。

3. 脚本仅列出自身上传内容的原因

列表脚本使用服务账号身份,只能访问服务账号自己Drive空间内的内容。你个人“My Drive”里的文件不在服务账号的存储空间中,自然无法被列出;而脚本上传的内容都存在服务账号的Drive里,所以能被正常读取。


补充解决方案

如果需要让脚本访问你个人账号的“My Drive”内容,有两种可行方式:

  • 共享文件夹:将你个人“My Drive”中的目标文件夹共享给服务账号的邮箱(在credentials.json文件的client_email字段中),然后在脚本中使用该共享文件夹的ID代替“root”。
  • 改用OAuth 2.0授权:替换服务账号授权流程为OAuth 2.0授权,让脚本以你个人账号的身份访问Drive API,这样就能直接操作你的“My Drive”。

内容的提问来源于stack exchange,提问作者x0100

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.09 09:40:40