首页 > 解决方案 > Google Drive API - 文件监视不通知

问题描述

我在共享驱动器的两个文件夹中创建了两个手表。如果有人添加或更新文件夹中的任何文件,我希望收到通知。

它工作了大约1个月。现在我注意到,如果文件夹中的某些内容发生了变化,Google 不会点击我的 URL。我尝试添加文件、删除文件、更改文件名,但没有任何内容触发更改事件。

仅当我在文件夹上更新(创建新)手表时,Google 才会点击我的 URL。然后我不知道API,直到我再次更新。

我使用 PHP 库:

public function createFileWatch(string $fileId, ?string $token = NULL): Google_Service_Drive_Channel
{
    $optParams = [
        'fields' => '*',
        'supportsAllDrives' => TRUE,
    ];

    $channel = new Google_Service_Drive_Channel();
    $channel->setId(Random::generate());
    $channel->setType('web_hook');
    $channel->setAddress(self::WATCH_REQUEST_URL);
    $channel->setExpiration((new DateTime('+1 week'))->getTimestamp() * 1000);
    if ($token) {
        $channel->setToken($token);
    }

    return $this->drive->files->watch($fileId, $channel, $optParams);
}

标签: phpgoogle-apigoogle-drive-api

解决方案


您必须使用APIchanges.watch而不是files.watchAPI,因为共享驱动器的更改集合与用户特定的更改集合不同:https ://developers.google.com/drive/api/v3/about-changes#track_shared_drives

我遇到了同样的问题,并使用以下代码解决了它(在我的例子中是用 TypeScript 为 NodeJS 编写的)。

const drive = google.drive({ version: "v3" });
const channelId = uuidv4();
const fileId = '<FileID to watch>'

const startPageTokenRes = await drive.changes.getStartPageToken({
  driveId: "<Shared Drive ID>",
  supportsAllDrives: true,
  supportsTeamDrives: true, // This seems to be necessary even though it's deprecated. If not provided explicitly, it seems to be set as `false` under the hood. NodeJS lib's bug?
});
const startPageToken = startPageTokenRes.data.startPageToken;
if (startPageToken == null) {
  throw new Error("startPageToken is unexpectedly null");
}
const res = await drive.changes.watch({
  supportsAllDrives: true,
  supportsTeamDrives: true, // This seems to be necessary even though it's deprecated. If not provided explicitly, it seems to be set as `false` under the hood. NodeJS lib's bug?
  pageToken: startPageToken,
  requestBody: {
    kind: "api#channel",
    id: channelId,
    resourceId: fileId,
    type: "web_hook",
    address: "https://<My domain>/webhook",
  },
});

仅供参考:以下代码出现此错误。我认为这段代码和你的 PHP 代码一样。

const drive = google.drive({ version: "v3", auth: oAuth2Client });
const channelId = uuidv4();
const fileId = '<FileID>'

const res = await drive.files.watch({
  fileId: fileId,
  supportsAllDrives: true,
  supportsTeamDrives: true,
  requestBody: {
    id: channelId,
    type: "web_hook",
    address: "https://<My domain>/webhook",
  },
});

推荐阅读