文件移动 Google 驱动器 API v3 PHP
File Move Google Drive API v3 PHP
使用 Google API v3 我尝试将文件从一个文件夹移动到另一个文件夹。我在 Laravel 中使用包装器 class,文件和父 ID 是正确的。从文档开发,我已经尝试过代码:
public function moveFileFromTo($fileID, $toParentID) {
$fromFile = $this->service->files->get($fileID, ['fields' => '*']);
$fromParentID = $fromFile->getParents();
$blankFile = new Google_Service_Drive_DriveFile();
$this->service->files->update($fileID, $blankFile, [
"removeParents" => $fromParentID,
"addParents" => $toParentID
]);
}
但是,这似乎移动了文件但删除了所有元数据。
我也试过
public function moveFileFromTo($fileID, $toParentID) {
$fromFile = $this->service->files->get($fileID, ['fields' => '*']);
$fromParentID = $fromFile->getParents();
$fromFile->setParents($fromParentID);
$this->service->files->update($fileID, $fromFile);
}
然而,这给出了错误:
Google\Service\Exception
{ "error": { "errors": [ { "domain": "global", "reason":
"fieldNotWritable", "message": "The resource body includes fields
which are not directly writable." } ], "code": 403, "message": "The
resource body includes fields which are not directly writable." } }
我希望简单地移动文件并保留其所有元数据。从文档中,似乎更新中需要一个新的空文件(真的很奇怪)或者我必须以某种方式删除第二个参数($fromFile)中使用的对象的字段,它不喜欢被写入(即使我只是更新文件 parents - 这是可写的)。
另见 https://issuetracker.google.com/issues/199921300
目前回答的问题:
但感谢回复
$fromFile = $this->service->files->get($fileID, ['fields' => 'parents, id']);
returns 所有 ~75 个属性,其中很多是不可写的。
而不是根据 PHPStorm 调试预期的 2(请注意,中断位于 GET 请求之后的语句中,因此此时无关紧要
使用
unset($fromFile->shared);
仍然保留其他可写属性
而且文件实际上并未共享
更新我的编码
public function moveFileFromTo($fileID, $toParentID) {
$fromFile = $this->service->files->get($fileID, ["fields" => "id,parents"]);
$fromFile = $this->getParsedWritableFile($fromFile);
$fromFile->setParents($toParentID);
$this->service->files->update($fileID, $fromFile, ['addParents' => $toParentID]);
}
getParsedWritableFile 正在尝试在新的 Google 驱动器文件对象上设置可写属性:
public function getParsedWritableFile($gdrivefile) {
$gdrivefile = new \Google_Service_Drive_DriveFile();//comment or delete, just here to check auto complete function names
$parsedFile = new \Google_Service_Drive_DriveFile();
//$parsedFile=$gdrivefile;
// currently only allow these according to https://developers.google.com/drive/api/v3/reference/files#resource-representations
$parsedFile->setName($gdrivefile->getName());//name
$parsedFile->setMimeType($gdrivefile->getMimeType());//mimeType
$parsedFile->setDescription($gdrivefile->getDescription());//description
$parsedFile->setStarred($gdrivefile->getStarred());//starred
$parsedFile->setTrashed($gdrivefile->getTrashed());//trashed
$parsedFile->setParents($gdrivefile->getParents());//parents
$parsedFile->setProperties($gdrivefile->getProperties());//properties [object]
$parsedFile->setAppProperties($gdrivefile->getAppProperties());//appProperties [object]
$parsedFile->setCreatedTime($gdrivefile->getCreatedTime());//createdTime
$parsedFile->setModifiedTime($gdrivefile->getModifiedTime());//modifiedTime
$parsedFile->setWritersCanShare($gdrivefile->getWritersCanShare());//writersCanShare
$parsedFile->setViewedByMeTime($gdrivefile->getViewedByMeTime());//viewedByMeTime
$parsedFile->setFolderColorRgb($gdrivefile->getFolderColorRgb());//folderColorRgb
$parsedFile->setOriginalFilename($gdrivefile->getOriginalFilename());//originalFilename
$parsedFile->setCopyRequiresWriterPermission($gdrivefile->getCopyRequiresWriterPermission());//copyRequiresWriterPermission
/*complex permissions*/
/*
contentHints.thumbnail.image
contentHints.thumbnail.mimeType
contentHints.indexableText
*/
$contenthints=$gdrivefile->getContentHints();//could be null meaning further functions eg getThumbnail cause exception
if($contenthints){
$parsedFile->setContentHints($contenthints->getThumbnail()->getImage());
$parsedFile->setContentHints($contenthints->getThumbnail()->getMimeType());
$parsedFile->setContentHints($contenthints->getIndexableText());
}
/*no function to get indiviual attributes*/
/*
contentRestrictions[].readOnly
ccontentRestrictions[].reason
*/
$parsedFile->setContentRestrictions($gdrivefile->getContentRestrictions());
//</ end>
return $parsedFile;
}
这被证明有点成功,但这是原始元
上面的代码确实移动了它,看起来正确的元数据、创建时间和 EXIF 数据现在完好无损
我不知道如何在 laravel 但问题可能是
我也遇到过同样的问题,在互联网上搜索了几个月后一无所获,有一天参考 documentation,看到 shared
不是可写字段。
就是这样,如果您正在共享文件并尝试移动文件,它不会移动。尝试取消共享文件,然后尝试移动文件。
问题是您使用的是 file.update which uses HTTP PATCH 方法。通过使用 PATCH,它会尝试更新您发送的文件 object 中的所有属性。
您做了 file.get 并且包含了文件 *
$fromFile = $this->service->files->get($fileID, ['fields' => '*']);
通过包含 'fields' => '*'
,您将 API 至 return 告诉您该文件具有的所有属性。一个file resource有很多属性,并不是所有的都可以写。
通过向 file.update 方法发送您告诉它您想要更新所有内容的所有字段,包括您不允许更新的一些属性。 api 响应 fieldNotWritable
解决方案是执行以下操作
$fromFile = $this->service->files->get($fileID, ['fields' => 'parents, id']);
这将导致该方法仅 return 您实际需要的两个参数。 id 和 parents 参数。 (说实话,您可能只需要 parents 部分,我需要对其进行测试。)
{
"id": "1x8-vD-XiA5Spf3qp8x2wltablGF22Lpwup8VtxNY",
"parents": ["0B1bbSFgVLpoXcVDRFRF8tTkU"
]
}
然后您应该可以更新 parent 并移动您的文件。
我最终创建了一个自定义函数,只包含 Google 文档中指定的可写属性:
public function getParsedWritableFile($gdrivefile) {
$gdrivefile = new \Google_Service_Drive_DriveFile();//comment or delete, just here to check auto complete function names
$parsedFile = new \Google_Service_Drive_DriveFile();
// currently only allow these according to https://developers.google.com/drive/api/v3/reference/files#resource-representations
$parsedFile->setName($gdrivefile->getName());//name
$parsedFile->setMimeType($gdrivefile->getMimeType());//mimeType
$parsedFile->setDescription($gdrivefile->getDescription());//description
$parsedFile->setStarred($gdrivefile->getStarred());//starred
$parsedFile->setTrashed($gdrivefile->getTrashed());//trashed
$parsedFile->setParents($gdrivefile->getParents());//parents
$parsedFile->setProperties($gdrivefile->getProperties());//properties [object]
$parsedFile->setAppProperties($gdrivefile->getAppProperties());//appProperties [object]
$parsedFile->setCreatedTime($gdrivefile->getCreatedTime());//createdTime
$parsedFile->setModifiedTime($gdrivefile->getModifiedTime());//modifiedTime
$parsedFile->setWritersCanShare($gdrivefile->getWritersCanShare());//writersCanShare
$parsedFile->setViewedByMeTime($gdrivefile->getViewedByMeTime());//viewedByMeTime
$parsedFile->setFolderColorRgb($gdrivefile->getFolderColorRgb());//folderColorRgb
$parsedFile->setOriginalFilename($gdrivefile->getOriginalFilename());//originalFilename
$parsedFile->setCopyRequiresWriterPermission($gdrivefile->getCopyRequiresWriterPermission());//copyRequiresWriterPermission
/*complex permissions*/
/*
contentHints.thumbnail.image
contentHints.thumbnail.mimeType
contentHints.indexableText
*/
$contenthints=$gdrivefile->getContentHints();//could be null meaning further functions eg getThumbnail cause exception
if($contenthints){
$parsedFile->setContentHints($contenthints->getThumbnail()->getImage());
$parsedFile->setContentHints($contenthints->getThumbnail()->getMimeType());
$parsedFile->setContentHints($contenthints->getIndexableText());
}
/*no function to get indiviual attributes*/
/*
contentRestrictions[].readOnly
ccontentRestrictions[].reason
*/
$parsedFile->setContentRestrictions($gdrivefile->getContentRestrictions());
return $parsedFile;
}
并调用
public function moveFileFromTo($fileID, $toParentID) {
$fromFile = $this->service->files->get($fileID, ["fields" => "id,parents"]);
$fromFile = $this->getParsedWritableFile($fromFile);
$fromFile->setParents($toParentID);
$this->service->files->update($fileID, $fromFile, ['addParents' => $toParentID]);
}
使用 Google API v3 我尝试将文件从一个文件夹移动到另一个文件夹。我在 Laravel 中使用包装器 class,文件和父 ID 是正确的。从文档开发,我已经尝试过代码:
public function moveFileFromTo($fileID, $toParentID) {
$fromFile = $this->service->files->get($fileID, ['fields' => '*']);
$fromParentID = $fromFile->getParents();
$blankFile = new Google_Service_Drive_DriveFile();
$this->service->files->update($fileID, $blankFile, [
"removeParents" => $fromParentID,
"addParents" => $toParentID
]);
}
但是,这似乎移动了文件但删除了所有元数据。 我也试过
public function moveFileFromTo($fileID, $toParentID) {
$fromFile = $this->service->files->get($fileID, ['fields' => '*']);
$fromParentID = $fromFile->getParents();
$fromFile->setParents($fromParentID);
$this->service->files->update($fileID, $fromFile);
}
然而,这给出了错误:
Google\Service\Exception
{ "error": { "errors": [ { "domain": "global", "reason":
"fieldNotWritable", "message": "The resource body includes fields
which are not directly writable." } ], "code": 403, "message": "The
resource body includes fields which are not directly writable." } }
我希望简单地移动文件并保留其所有元数据。从文档中,似乎更新中需要一个新的空文件(真的很奇怪)或者我必须以某种方式删除第二个参数($fromFile)中使用的对象的字段,它不喜欢被写入(即使我只是更新文件 parents - 这是可写的)。
另见 https://issuetracker.google.com/issues/199921300
目前回答的问题: 但感谢回复
$fromFile = $this->service->files->get($fileID, ['fields' => 'parents, id']);
returns 所有 ~75 个属性,其中很多是不可写的。 而不是根据 PHPStorm 调试预期的 2(请注意,中断位于 GET 请求之后的语句中,因此此时无关紧要
使用
unset($fromFile->shared);
仍然保留其他可写属性
而且文件实际上并未共享
更新我的编码
public function moveFileFromTo($fileID, $toParentID) {
$fromFile = $this->service->files->get($fileID, ["fields" => "id,parents"]);
$fromFile = $this->getParsedWritableFile($fromFile);
$fromFile->setParents($toParentID);
$this->service->files->update($fileID, $fromFile, ['addParents' => $toParentID]);
}
getParsedWritableFile 正在尝试在新的 Google 驱动器文件对象上设置可写属性:
public function getParsedWritableFile($gdrivefile) {
$gdrivefile = new \Google_Service_Drive_DriveFile();//comment or delete, just here to check auto complete function names
$parsedFile = new \Google_Service_Drive_DriveFile();
//$parsedFile=$gdrivefile;
// currently only allow these according to https://developers.google.com/drive/api/v3/reference/files#resource-representations
$parsedFile->setName($gdrivefile->getName());//name
$parsedFile->setMimeType($gdrivefile->getMimeType());//mimeType
$parsedFile->setDescription($gdrivefile->getDescription());//description
$parsedFile->setStarred($gdrivefile->getStarred());//starred
$parsedFile->setTrashed($gdrivefile->getTrashed());//trashed
$parsedFile->setParents($gdrivefile->getParents());//parents
$parsedFile->setProperties($gdrivefile->getProperties());//properties [object]
$parsedFile->setAppProperties($gdrivefile->getAppProperties());//appProperties [object]
$parsedFile->setCreatedTime($gdrivefile->getCreatedTime());//createdTime
$parsedFile->setModifiedTime($gdrivefile->getModifiedTime());//modifiedTime
$parsedFile->setWritersCanShare($gdrivefile->getWritersCanShare());//writersCanShare
$parsedFile->setViewedByMeTime($gdrivefile->getViewedByMeTime());//viewedByMeTime
$parsedFile->setFolderColorRgb($gdrivefile->getFolderColorRgb());//folderColorRgb
$parsedFile->setOriginalFilename($gdrivefile->getOriginalFilename());//originalFilename
$parsedFile->setCopyRequiresWriterPermission($gdrivefile->getCopyRequiresWriterPermission());//copyRequiresWriterPermission
/*complex permissions*/
/*
contentHints.thumbnail.image
contentHints.thumbnail.mimeType
contentHints.indexableText
*/
$contenthints=$gdrivefile->getContentHints();//could be null meaning further functions eg getThumbnail cause exception
if($contenthints){
$parsedFile->setContentHints($contenthints->getThumbnail()->getImage());
$parsedFile->setContentHints($contenthints->getThumbnail()->getMimeType());
$parsedFile->setContentHints($contenthints->getIndexableText());
}
/*no function to get indiviual attributes*/
/*
contentRestrictions[].readOnly
ccontentRestrictions[].reason
*/
$parsedFile->setContentRestrictions($gdrivefile->getContentRestrictions());
//</ end>
return $parsedFile;
}
这被证明有点成功,但这是原始元
上面的代码确实移动了它,看起来正确的元数据、创建时间和 EXIF 数据现在完好无损
我不知道如何在 laravel 但问题可能是
我也遇到过同样的问题,在互联网上搜索了几个月后一无所获,有一天参考 documentation,看到 shared
不是可写字段。
就是这样,如果您正在共享文件并尝试移动文件,它不会移动。尝试取消共享文件,然后尝试移动文件。
问题是您使用的是 file.update which uses HTTP PATCH 方法。通过使用 PATCH,它会尝试更新您发送的文件 object 中的所有属性。
您做了 file.get 并且包含了文件 *
$fromFile = $this->service->files->get($fileID, ['fields' => '*']);
通过包含 'fields' => '*'
,您将 API 至 return 告诉您该文件具有的所有属性。一个file resource有很多属性,并不是所有的都可以写。
通过向 file.update 方法发送您告诉它您想要更新所有内容的所有字段,包括您不允许更新的一些属性。 api 响应 fieldNotWritable
解决方案是执行以下操作
$fromFile = $this->service->files->get($fileID, ['fields' => 'parents, id']);
这将导致该方法仅 return 您实际需要的两个参数。 id 和 parents 参数。 (说实话,您可能只需要 parents 部分,我需要对其进行测试。)
{
"id": "1x8-vD-XiA5Spf3qp8x2wltablGF22Lpwup8VtxNY",
"parents": ["0B1bbSFgVLpoXcVDRFRF8tTkU"
]
}
然后您应该可以更新 parent 并移动您的文件。
我最终创建了一个自定义函数,只包含 Google 文档中指定的可写属性:
public function getParsedWritableFile($gdrivefile) {
$gdrivefile = new \Google_Service_Drive_DriveFile();//comment or delete, just here to check auto complete function names
$parsedFile = new \Google_Service_Drive_DriveFile();
// currently only allow these according to https://developers.google.com/drive/api/v3/reference/files#resource-representations
$parsedFile->setName($gdrivefile->getName());//name
$parsedFile->setMimeType($gdrivefile->getMimeType());//mimeType
$parsedFile->setDescription($gdrivefile->getDescription());//description
$parsedFile->setStarred($gdrivefile->getStarred());//starred
$parsedFile->setTrashed($gdrivefile->getTrashed());//trashed
$parsedFile->setParents($gdrivefile->getParents());//parents
$parsedFile->setProperties($gdrivefile->getProperties());//properties [object]
$parsedFile->setAppProperties($gdrivefile->getAppProperties());//appProperties [object]
$parsedFile->setCreatedTime($gdrivefile->getCreatedTime());//createdTime
$parsedFile->setModifiedTime($gdrivefile->getModifiedTime());//modifiedTime
$parsedFile->setWritersCanShare($gdrivefile->getWritersCanShare());//writersCanShare
$parsedFile->setViewedByMeTime($gdrivefile->getViewedByMeTime());//viewedByMeTime
$parsedFile->setFolderColorRgb($gdrivefile->getFolderColorRgb());//folderColorRgb
$parsedFile->setOriginalFilename($gdrivefile->getOriginalFilename());//originalFilename
$parsedFile->setCopyRequiresWriterPermission($gdrivefile->getCopyRequiresWriterPermission());//copyRequiresWriterPermission
/*complex permissions*/
/*
contentHints.thumbnail.image
contentHints.thumbnail.mimeType
contentHints.indexableText
*/
$contenthints=$gdrivefile->getContentHints();//could be null meaning further functions eg getThumbnail cause exception
if($contenthints){
$parsedFile->setContentHints($contenthints->getThumbnail()->getImage());
$parsedFile->setContentHints($contenthints->getThumbnail()->getMimeType());
$parsedFile->setContentHints($contenthints->getIndexableText());
}
/*no function to get indiviual attributes*/
/*
contentRestrictions[].readOnly
ccontentRestrictions[].reason
*/
$parsedFile->setContentRestrictions($gdrivefile->getContentRestrictions());
return $parsedFile;
}
并调用
public function moveFileFromTo($fileID, $toParentID) {
$fromFile = $this->service->files->get($fileID, ["fields" => "id,parents"]);
$fromFile = $this->getParsedWritableFile($fromFile);
$fromFile->setParents($toParentID);
$this->service->files->update($fileID, $fromFile, ['addParents' => $toParentID]);
}