如何使用Google Drive API下载使用Javascript的文件

时间:2016-06-16 13:35:33

标签: javascript google-api google-drive-api

我想使用javascript API从google drive下载文件。我已设法使用gapi.client.drive.files请求验证和加载文件列表。但是,我坚持下载这些文件 我尝试下载文件:

var request = gapi.client.drive.files.get({
        fileId:id,
        alt:'media'
});
request.execute(function(resp){
        console.log(resp);
});

尝试运行上述内容时出现以下错误:

(403) The user has not granted the app 336423653212 read access to the file 0B0UFTVo1BFVmeURrWnpDSloxQlE.

(400) Bad Request

我认识到不是谷歌驱动文件(google doc,google slide)的文件会返回403错误。
我是新来的。任何帮助和回答都非常感谢。

更新0

关于Handling API Error的Google云端硬盘文档,以下是400 errors

的部分说明
  

这可能意味着尚未提供必填字段或参数   提供的值无效,或提供的字段的组合是   无效。

这是因为我的参数对象中有alt:'media'

我尝试了gapi.client.drive.files.export,但它也不起作用,它返回(403) Insufficient Permission,尽管我的Google云端硬盘帐户拥有这些文件的编辑权限。这是我的代码:

var request = gapi.client.drive.files.get({
    fileId:element.id,
});
request.then(function(resp){
    console.log(resp.result);
    type = resp.result.mimeType;
    id = resp.result.id;
    var request = gapi.client.drive.files.export({
        fileId:id,
        mimeType:type
    })
    request.execute(function(resp){
        console.log(resp);
    });
});

更新1

基于abielita's answer,我尝试发出授权的HTTP请求但不下载该文件。它实际上会返回response对象中responseTextXMLHttpRequest属性中的文件信息。

  function test() {
    var accessToken = gapi.auth.getToken().access_token;
    var xhr = new XMLHttpRequest();
    xhr.open("GET", "https://www.googleapis.com/drive/v3/files/"+'1A1RguZpYFLyO9qEs-EnnrpikIpzAbDcZs3Gcsc7Z4nE', true);
    xhr.setRequestHeader('Authorization','Bearer '+accessToken);
    xhr.onload = function(){
        console.log(xhr);
    }
    xhr.send('alt=media');
  }

______________________________________________________

我发现我可以使用文件“webViewLinkwebViewContent属性从文件夹中检索所有这些文件的网址。

  • 来自Google云端硬盘类型的文件(Google Doc,Google Sheet, etc ...)将具有webViewLink属性。 webViewLink将会打开 Google云端硬盘中的文件。

  • 非Google云端硬盘类型文件将包含webContentLink。一个 webContentLink将下载该文件。

我的代码:

var request = gapi.client.drive.files.list({
    q:"'0Bz9_vPIAWUcSWWo0UHptQ005cnM' in parents", //folder ID
    'fields': "files(id, name, webContentLink, webViewLink)"
  });
request.execute(function(resp) {
        console.log(resp);
}

5 个答案:

答案 0 :(得分:4)

根据此documentation,如果您使用alt=media,则需要向文件的resource URL发出授权的HTTP GET请求,并包含查询参数alt=media

GET https://www.googleapis.com/drive/v3/files/0B9jNhSvVjoIVM3dKcGRKRmVIOVU?alt=media
Authorization: Bearer ya29.AHESVbXTUv5mHMo3RYfmS1YJonjzzdTOFZwvyOAUVhrs

使用我们的Drive API客户端库检查here执行文件下载的示例。

String fileId = "0BwwA4oUTeiV1UVNwOHItT0xfa2M";
OutputStream outputStream = new ByteArrayOutputStream();
driveService.files().get(fileId)
        .executeMediaAndDownloadTo(outputStream);

对于错误(403)权限不足,可能这是您的访问令牌的问题,而不是您的项目配置。

如果在检索访问令牌时未请求所需的范围,则会返回权限不足错误。您可以通过将access_token传递到此端点来检查您请求的范围:https://www.googleapis.com/oauth2/v1/tokeninfo?access_token=ACCESS_TOKEN

检查以下链接:

答案 1 :(得分:3)

Phu,你太近了!

感谢您分享使用webContentLink和webViewLink的方法。我认为这对大多数用途来说都是最好的。但是在我的应用程序中,我无法使用viewContentLink,因为需要能够将图像输入到画布中,并且谷歌提供的图像不是CORS准备好的。

所以这是一个方法



var fileId = '<your file id>';
var accessToken = gapi.auth2.getAuthInstance().currentUser.get().getAuthResponse().access_token;// or this: gapi.auth.getToken().access_token;
var xhr = new XMLHttpRequest();
xhr.open("GET", "https://www.googleapis.com/drive/v3/files/"+fileId+'?alt=media', true);
xhr.setRequestHeader('Authorization','Bearer '+accessToken);
xhr.responseType = 'arraybuffer'
xhr.onload = function(){
    //base64ArrayBuffer from https://gist.github.com/jonleighton/958841
    var base64 = 'data:image/png;base64,' + base64ArrayBuffer(xhr.response);

    //do something with the base64 image here

}
xhr.send();
&#13;
&#13;
&#13;

请注意,我将响应类型设置为arraybuffer,并将alt=media移至xhr.open来电。我还抓住了一个函数,将数组缓冲区从https://gist.github.com/jonleighton/958841转换为base64。

答案 2 :(得分:2)

我发现我实际上可以使用文件&#39;从文件夹中检索所有这些文件的网址。是webViewLinkwebViewContent属性。 Google云端硬盘类型(Google文档,Google表格等)的文件将具有webViewLink属性,非Google云端硬盘类型文件将具有webContentLinkwebViewLink将在Google云端硬盘中打开该文件,webContentLink将下载该文件。我的代码:

var request = gapi.client.drive.files.list({
    q:"'0Bz9_vPIAWUcSWWo0UHptQ005cnM' in parents", //folder ID
    fields: "files(id, name, webContentLink, webViewLink)"
});
request.execute(function(resp) {
    console.log(resp); //access to files in this variable
}

答案 3 :(得分:0)

任务:下载文件并创建File对象; 环境:浏览器;

const URL = 'https://www.googleapis.com/drive/v3/files';
const FIELDS = 'name, mimeType, modifiedTime';

const getFile = async (fileId) => {
  const { gapi: { auth, client: { drive: { files } } } } = window;
  const { access_token: accessToken } = auth.getToken();
  const fetchOptions = { headers: { Authorization: `Bearer ${accessToken}` } };
  
  const {
    result: { name, mimeType, modifiedTime }
  } = await files.get({ fileId, fields: FIELDS });
  
  const blob = await fetch(`${URL}/${fileId}?alt=media`, fetchOptions).then(res => res.blob());
  const fileOptions = {
    type: mimeType,
    lastModified: new Date(modifiedTime).getTime(),
  };
  
  return new File([blob], name, fileOptions);
};

答案 4 :(得分:0)

我能够使用 files.get API 进行下载:

var fileId = '<your file id>';
gapi.client.drive.files.get(
    {fileId: fileId, alt: 'media'}
).then(function (response) {
    // response.body has the file data
}, function (reason) {
    alert(`Failed to get file: ${reason}`);
});