如何使用 CloudRail 指定 Google Drive API 空间

How to specify Google Drive API spaces using CloudRail

我正在编写一个 Android 应用程序以通过 CloudRail 服务访问 Google Drive Photos。我能够对相关 Google 帐户进行身份验证,并在 Google 驱动器中查看我的所有 files/folders,但我无法访问 Google Photos 中的照片。

在浏览 Drive API 文档时,它引用了 spaces,具体定义了 3 个 spaces:drive、photos 和 allDataFolder。

在哪里指定我感兴趣的 space?但默认情况下,驱动器 space 正在被访问。尽管如此,我特别指定了照片的范围:

https://www.googleapis.com/auth/drive.photos.readonly

并且当 Google 身份验证页面在移动浏览器中打开时,它表明我的应用程序想要访问用户的 Google 照片并且我授予此访问权限。但是调用CloudRail服务获取children时,看不到照片

`googledriveChildren = mGoogledriveService.getChildren("/"); // returns goole drive top level files/folders


`googledriveChildren = mGoogledriveService.getChildren("/photos"); // generates a NotFoundException

我已经沿着这条路走下去并实现了集成 - 来自 Cloudrail 的 help/guidance。您应该注意,我的集成仅限于 Google 照片中的 reading/downloading。我还没有找到 write/upload 的任何方法。我也没有找到任何方法来读取可以在 Google 照片中设置的相册结构。

首先,您需要包含 Google 照片的范围。我这样做如下:

 public static final String GOOGLE_PHOTOS_SCOPE = "https://www.googleapis.com/auth/drive.photos.readonly";

 private final AtomicReference<CloudStorage> googlephotos = new AtomicReference<>();


  List<String> scope = new ArrayList<>();
    scope.add(My_Constants.GOOGLE_PHOTOS_SCOPE);
    googlephotos.set(new GoogleDrive(context, google_client_id, "", Get.GetString(R.string.google_redirect_uri),
            Get.GetString(R.string.google_authentication_state), scope));
    ((GoogleDrive) googlephotos.get()).useAdvancedAuthentication();

然后您需要构建一个 Cloudrail advancedRequest 来下载您想要的任何数据。我按如下方式下载我需要的元数据:

CloudStrorage service = googlephotos.get();

   private void searchForGooglePhotos(final CloudStorage service) throws Throwable {
    GoogleDrive google_drive = (GoogleDrive) service;
    boolean more = true;
    String pageToken = null;
    while (more) {
        StringBuilder builder = new StringBuilder();
        String query = URLEncoder.encode("mimeType='image/jpeg' and trashed = false", "utf-8");
        builder.append("/files?spaces=photos");
        if (pageToken != null) {
            builder.append("&pageToken=");
            builder.append(pageToken);
        }
        builder.append("&q=");
        builder.append(query);
        builder.append("&fields=nextPageToken,files(id,name,modifiedTime,description,size," +
                "imageMediaMetadata(height,rotation,width,time))");
        AdvancedRequestSpecification specification = new AdvancedRequestSpecification(builder.toString());
        AdvancedRequestResponse response = google_drive.advancedRequest(specification);
        @SuppressWarnings("unchecked")
        Map<String, Object> resultObjectMap = (Map<String, Object>) response.getBodyJsonParsed();
        pageToken = (String) resultObjectMap.get("nextPageToken");
        @SuppressWarnings("unchecked")
        ArrayList<Map<String, Object>> filesObjectMap = ((ArrayList<Map<String, Object>>) resultObjectMap.get("files"));
        for (Map<String, Object> fileObjectMap : filesObjectMap) {
            // process downloaded files
        }
        more = (pageToken != null);
    }
}

随后在我的应用程序中,我使用 Glide 在需要时自行下载照片。在 Glide DataFetcher 中,我使用以下方法获取 inputStream:

if (model.getSourceRecord().isTypeGooglePhotos()) {
        AdvancedRequestSpecification specification;
        AdvancedRequestResponse response;
        if (model.getIsThumbnail()) {
            specification = new AdvancedRequestSpecification("/files" + model.getSourceId() +
                    "?spaces=photos&fields=thumbnailLink");
            response = ((GoogleDrive) service).advancedRequest(specification);
            @SuppressWarnings("unchecked")
            Map<String, Object> parsed = (Map<String, Object>) response.getBodyJsonParsed();
            String link = (String) parsed.get("thumbnailLink");
            specification = new AdvancedRequestSpecification(link);
            specification.disableBaseUrl();
        } else {
            specification = new AdvancedRequestSpecification("/files" + model.getSourceId() + "?spaces=photos&alt=media");
        }
        response = ((GoogleDrive) service).advancedRequest(specification);
        input_stream = response.getBodyAsStream();
    } else {
        if (model.getIsThumbnail()) {
            input_stream = service.getThumbnail(model.getSourceId());
        } else {
            input_stream = service.download(model.getSourceId());
        }
    }

此处,"model" 包含与每张照片相关的各种信息。 sourceId来自"id"下载:

String source_id = java.io.File.separator + fileObjectMap.get("id");

希望对您有所帮助。

任何人到达这个问题/答复时请注意,截至 2018 年 1 月中旬,Google 有 "sunset"(原文如此)照片 space(space s=上面的照片)。这意味着上述解决方案不再有效。

关于 Google REST API 文档:"The photos space will sunset in early January 2018. Your users can continue to access Google Photos via the drive space by enabling the Google Photos folder in My Drive in the Drive client settings"

呃!