Google Drive API for Android会返回空文件

时间:2016-08-20 08:59:41

标签: android google-play-services google-drive-android-api drive

我使用google drive api将一些文件存储在google drive app文件夹中,但在某些设备上,当我尝试下载文件时,它只返回大小为0字节的文件。

上传代码:

/**
 * It's a blocking method
 *
 * @param file the file to upload to google drive.
 */
private boolean uploadToDrive(@NonNull File file) {
    final DriveApi.DriveContentsResult driveContentsResult = Drive.DriveApi
            .newDriveContents(mGoogleApiClient)
            .await();
    // If the operation was not successful, we cannot do anything and must fail.
    if (!driveContentsResult.getStatus().isSuccess()) {
        Logger.t(TAG).e("Failed to create new contents.");
        return false;
    }
    // Otherwise, we can write our data to the new contents.
    Logger.t(TAG).i("New empty contents created.");

    //Creates a file in app folder with provided metadata.
    final DriveFolder.DriveFileResult driveFileResult = Drive.DriveApi
            .getAppFolder(mGoogleApiClient)
            .createFile(mGoogleApiClient, getDatabaseMeta(file.getName().replace("temp-", "")), driveContentsResult.getDriveContents())
            .await();

    if (!driveContentsResult.getStatus().isSuccess()) {
        Logger.t(TAG).e("Error while trying to create the file in app folder.");
        return false;
    }

    final DriveApi.DriveContentsResult contentsResult = driveFileResult
            .getDriveFile()
            .open(mGoogleApiClient, DriveFile.MODE_WRITE_ONLY, null)
            .await();

    if (!contentsResult.getStatus().isSuccess()) {
        Logger.t(TAG).e("cant create a file in app folder");
        return false;
    }

    final DriveContents driveContents = contentsResult.getDriveContents();

    if (!writeFileToDrive(file, driveContents)) {
        Logger.t(TAG).e("Cannot read or write to file");
        return false;
    }

    final Status status = driveContents.commit(mGoogleApiClient, null).await();

    if (!status.getStatus().isSuccess()) {
        Logger.t(TAG).e("Cannot upload the file to drive");
        return false;
    }
    // TODO: 2016-01-19 Store this to use this this file later.
    Logger.t(TAG).e("getDriveId:" + driveFileResult.getDriveFile().getDriveId().encodeToString());
    return true;
}
/**
 * Write the source file to destination drive contents file.
 *
 * @param file          the source {@link File} to read from.
 * @param driveContents the destination {@link DriveContents} to write to.
 */
private boolean writeFileToDrive(File file, DriveContents driveContents) {
    try {
        FileInputStream is = new FileInputStream(file);
        BufferedInputStream in = new BufferedInputStream(is);
        byte[] buffer = new byte[8 * 1024];

        BufferedOutputStream out = new BufferedOutputStream(driveContents.getOutputStream());
        int n;
        while ((n = in.read(buffer)) > 0) {
            out.write(buffer, 0, n);
        }
        in.close();
        is.close();
        out.close();
        return true;
    } catch (IOException e) {
        e.printStackTrace();
        return false;
    }
}

下载代码:

@Nullable
private DriveContents downloadFileFromDrive(@NonNull DriveId driveId) {

    final DriveApi.DriveContentsResult driveContentsResult = driveId.asDriveFile().open(mGoogleApiClient, DriveFile.MODE_READ_ONLY, new DriveFile.DownloadProgressListener() {
        @Override
        public void onProgress(long bytesDownloaded, long bytesExpected) {
            Log.d(TAG, "onProgress() called with: bytesDownloaded = [" + bytesDownloaded + "], bytesExpected = [" + bytesExpected + "]");
        }
    }).await();
    if (!driveContentsResult.getStatus().isSuccess()) {
        Logger.t(TAG).e("Cannot download the file");
        return null;
    }
    return driveContentsResult.getDriveContents();
}

/**
 * Writes the drive contents to the destination file.
 *
 * @param source
 * @param destination
 * @return true if the write is successful.
 */
private boolean writeFileToDisk(@NonNull DriveContents source, @NonNull File destination) {
    try {
        final InputStream in = source.getInputStream();
        final BufferedOutputStream out = new BufferedOutputStream(new FileOutputStream(destination));
        byte[] buffer = new byte[8 * 1024];

        int n;
        while ((n = in.read(buffer)) > 0) {
            out.write(buffer, 0, n);
        }
        out.close();
        in.close();
        return true;
    } catch (IOException e) {
        e.printStackTrace();
        return false;
    }
}

上传的文件在模拟器和大多数设备中正确下载,但在某些设备上下载的文件大小为0字节。

实际上当我从具有此问题的设备上传文件然后我再次请求使用同一设备下载它时,如果我尝试从另一台设备下载该文件,我会从缓存中收到一个长度为零的文件这个问题只是下载它没有问题。

我认为它的缓存策略有问题,它只是检查文件是否已经存在于缓存中并以0字节大小返回它。

我遇到此问题的设备是api 21及以下版本。

Google Drive Api 9.2.1

Google Play服务9。9。5日期:2016年7月19日最新版本

1 个答案:

答案 0 :(得分:0)

我有同样的错误。我发现,我想下载的DriveId是一个初步的' DriveId(关注此resourceID of file is null)。我保存了那个初步的' DriveId到我的数据库,无法下载该文件。 我通过在创建和编辑文件时接收CompletionEvents来修复此问题,以便在GDAA将文件提交到Drive时获取文件的真实资源ID(receiving Completion Events)。抱歉我的英语不好。