如何通过API向Google云端硬盘添加/创建/插入文件?

Nir*_*nja 32 google-api google-api-client google-drive-api

需要有关通过api将文件插入谷歌驱动器的帮助.用于此目的的api文档没有清楚地解释如何通过http post请求发送文件的实际主体.

Nic*_*ier 65

有关插入操作文档已经包含了一堆编程语言中的示例,以下是如何使用Google Drive API的基于HTTP的协议来完成此操作.

首先,将新文件元数据POST到Drive端点.它必须是File资源JSON对象的形式:

POST /drive/v2/files HTTP/1.1
Host: www.googleapis.com
Authorization: Bearer <OAuth 2.0 access token here>
...

{
  "title": "file_name.extension",
  "mimeType": "mime/type",
  "description": "Stuff about the file"
}
Run Code Online (Sandbox Code Playgroud)

响应主体将是新创建的文件资源的JSON表示.它看起来像:

{
  "kind": "drive#file",
  "id": string,
  "etag": etag,
  "selfLink": string,
  "title": "file_name",
  "mimeType": "mime/type",
  "description": "Stuff about the file"
  ...
  "downloadUrl": string,
  ...
}
Run Code Online (Sandbox Code Playgroud)

这是对已创建文件条目的确认.现在您需要上传内容.为此,您需要获取上面响应中id JSON属性给出的文件的ID,并使用OAuth 2.0授权请求将实际文件的内容PUT到上载端点.它应该看起来像:

PUT /upload/drive/v2/files/{id}?uploadType=media HTTP/1.1
Host: www.googleapis.com
Authorization: Bearer <OAuth 2.0 access token here>
Content-Type: mime/type

<file content here>
Run Code Online (Sandbox Code Playgroud)

你完成了:)

还有一种方法可以使用多部分请求在单个POST请求中执行此操作,其中您可以在内容的同时发布文件的元数据.这是一个例子:

POST /upload/drive/v2/files HTTP/1.1
Host: www.googleapis.com
Authorization: Bearer <OAuth 2.0 access token here>
Content-Type: multipart/form-data; boundary=287032381131322
...

--287032381131322
Content-Type: application/json

{
  "title": "file_name.extension",
  "mimeType": "mime/type",
  "description": "Stuff about the file"
}
--287032381131322
Content-Type: mime/type

<file content here>
--287032381131322--
Run Code Online (Sandbox Code Playgroud)

响应将包含新创建的文件的元数据.您还可以在请求的子部分中使用Content-Transfer-Encoding:base64标头,以便能够将文件的数据作为Base 64编码传递.

最后,还有一个可恢复的上传协议,可以方便地上传大文件,提供暂停/恢复功能和/或上传带有片状互联网连接的文件.

PS:现在大部分内容都在Drive的文件上传文档中进行了描述.


use*_*023 16

感谢您的解释!我花了几个小时的时间与蹩脚的谷歌SDK文档一起转圈(抱歉,我不得不咆哮).

这是我做的一个函数,它将更新一个文本文件(你可以看到我正在更新html):

  function gd_updateFile(fileId, folderId, text, callback) {

    const boundary = '-------314159265358979323846';
    const delimiter = "\r\n--" + boundary + "\r\n";
    const close_delim = "\r\n--" + boundary + "--";

    var contentType = "text/html";
    var metadata = {'mimeType': contentType,};

    var multipartRequestBody =
        delimiter +  'Content-Type: application/json\r\n\r\n' +
        JSON.stringify(metadata) +
        delimiter + 'Content-Type: ' + contentType + '\r\n' + '\r\n' +
        text +
        close_delim;

    if (!callback) { callback = function(file) { console.log("Update Complete ",file) }; }

    gapi.client.request({
        'path': '/upload/drive/v2/files/'+folderId+"?fileId="+fileId+"&uploadType=multipart",
        'method': 'PUT',
        'params': {'fileId': fileId, 'uploadType': 'multipart'},
        'headers': {'Content-Type': 'multipart/mixed; boundary="' + boundary + '"'},
        'body': multipartRequestBody,
        callback:callback,
    });
  }
Run Code Online (Sandbox Code Playgroud)

它是google示例的混搭(使用上传的二进制文件),以及@Nivco上面的精彩解释.


Mun*_*war 7

4年后,这仍然很难搞清楚.我拿了@ user1158023的答案来支持上传图片.我正在使用API​​ v3和superagent.js来帮助我(因为gapi.client.request正在向content.googleapis.com发送请求!?).希望有人可能会觉得这很有用.

function gd_uploadFile(name, contentType, data, callback) {
    const boundary = '-------314159265358979323846';
    const delimiter = "\r\n--" + boundary + "\r\n";
    const close_delim = "\r\n--" + boundary + "--";

    contentType = contentType || "text/html";
    var metadata = {
        name: name,
        'mimeType': contentType
    };

    var multipartRequestBody =
        delimiter +  'Content-Type: application/json\r\n\r\n' +
        JSON.stringify(metadata) +
        delimiter +
        'Content-Type: ' + contentType + '\r\n';

    //Transfer images as base64 string.
    if (contentType.indexOf('image/') === 0) {
        var pos = data.indexOf('base64,');
        multipartRequestBody += 'Content-Transfer-Encoding: base64\r\n' + '\r\n' +
            data.slice(pos < 0 ? 0 : (pos + 'base64,'.length));
    } else {
        multipartRequestBody +=  + '\r\n' + data;
    }
    multipartRequestBody += close_delim;

    if (!callback) { callback = function(file) { console.log("Update Complete ", file) }; }

    superagent.post('https://www.googleapis.com/upload/drive/v3/files?uploadType=multipart').
        set('Content-Type', 'multipart/form-data;  boundary="' + boundary + '"').
        set('Authorization', 'Bearer ' + gapi.auth.getToken().access_token).
        send(multipartRequestBody).
        end(function () {
            console.log(arguments);
        });
}

//On upload
$('#file')[0].onchange = function () {
    var file = $('#file')[0].files[0];
    if (file && file.type === 'image/jpeg') {
        var reader = new FileReader();
        reader.onloadend = function () {
            var data = reader.result;
            gd_uploadFile('img.jpg', 'image/jpeg', data, function () {
                console.log(arguments);
            });
        }
        reader.readAsDataURL(file);
    }
};
Run Code Online (Sandbox Code Playgroud)

的index.html

...
<form>
    <span>Upload: </span><input id="file" type="file" name="myFile">
</form>
...
Run Code Online (Sandbox Code Playgroud)