使用Google Drive REST Api v3上传下载文件时文件损坏问题咨询
问题原因
你的代码存在两个核心问题导致下载的文件损坏、体积异常:
- 未明确指定文件MIME类型,Google Drive会自动将未知类型的文件转换为Google Docs/Sheets等Workspace应用格式,你下载时拿到的是转换后的文件元数据而非原始二进制内容,因此体积远小于原文件且无法读取。你单独给
FileContent传image/jpeg仍有问题,是因为没有同步给文件元数据设置对应MIME类型,自动转换逻辑依然生效。 - 缺少共享盘兼容配置,且流处理逻辑不完善,可能出现文件写入不完整的情况。
修复方案
第一步:补充MIME类型探测工具方法
自定义后缀的配置文件统一兜底为application/octet-stream通用二进制类型,避免Google Drive做格式转换:
private String getMimeType(String filePath) { String mimeType = null; String extension = MimeTypeMap.getFileExtensionFromUrl(filePath); if (extension != null) { mimeType = MimeTypeMap.getSingleton().getMimeTypeFromExtension(extension.toLowerCase()); } // 未知类型统一用通用二进制格式,确保Drive原样存储 return mimeType == null ? "application/octet-stream" : mimeType; }
第二步:修正上传代码
String UploadFileToGoogleDrive(String sFullPath, String sFileName, String sParentFolderId) { com.google.api.services.drive.model.File fileMetadata = new com.google.api.services.drive.model.File(); fileMetadata.setName(sFileName); fileMetadata.setParents(Collections.singletonList(sParentFolderId)); java.io.File filePath = new java.io.File(sFullPath); String mimeType = getMimeType(sFullPath); // 元数据同步设置MIME类型,禁止自动转换 fileMetadata.setMimeType(mimeType); FileContent mediaContent = new FileContent(mimeType, filePath); try { com.google.api.services.drive.model.File file = googleDriveService.files().create(fileMetadata, mediaContent) .setSupportsAllDrives(true) // 兼容个人盘和共享盘 .setFields("id, parents, size") // 新增size字段可校验上传是否完整 .execute(); // 可选:校验上传文件大小和本地是否一致 long localFileSize = filePath.length(); if (file.getSize() != null && file.getSize() != localFileSize) { // 大小不一致说明上传失败,可加重试逻辑 return null; } return file.getId(); } catch (IOException e) { e.printStackTrace(); return null; } }
第三步:修正下载代码
优化流处理逻辑,自动释放资源,补充兼容配置:
boolean DownloadFileFromGoogleDrive(String sFileId, String sDestinationPath) { java.io.File destFile = new java.io.File(sDestinationPath); // 提前创建目标路径的父文件夹,避免写入失败 if (!destFile.getParentFile().exists()) { destFile.getParentFile().mkdirs(); } // try-with-resources自动关闭输出流,无需手动调用close try (FileOutputStream oFileOutputStream = new FileOutputStream(destFile)) { googleDriveService.files().get(sFileId) .setSupportsAllDrives(true) // 兼容共享盘 .executeAndDownloadTo(oFileOutputStream); return true; } catch (IOException e) { e.printStackTrace(); // 下载失败删除不完整的损坏文件 if (destFile.exists()) { destFile.delete(); } return false; } }
验证建议
上传完成后可以直接在Google Drive网页端查看对应文件的大小、是否可以正常预览,如果网页端文件大小和本地一致,说明上传环节已经正常,再验证下载逻辑即可。
内容的提问来源于stack exchange,提问作者Ton
相关产品推荐
相关产品推荐

