2

将应用程序连接到云端硬盘后,我就创建了一个文件夹。

现在,我想在该文件夹中创建另一个文件夹,但我不知道它的DriveId.

@Override
    public void onConnected(Bundle connectionHint) {
        Log.d("DEBUG", "Succesfully connected to Drive.");

        MetadataChangeSet metadata = new MetadataChangeSet.Builder()
                                            .setTitle(getResources().getString(R.string.app_name_short))
                                            .build();

        Drive.DriveApi.getRootFolder(mGoogleApiClient).createFolder(mGoogleApiClient, metadata);

        // Here I would like to retrieve the just created folder and create a subfolder in it

    }

我应该如何实现这一目标?

此外,我想提前检查是否已经存在具有该名称的文件夹,因为上面的代码会在每个连接上创建一个新文件夹。Drive 似乎允许创建许多同名的文件夹。

4

3 回答 3

0

设置一个ResultCallback在创建完成时调用,您可以在其中获取ContentsResult传入的值。

文档中的示例如下:

public class CreateFileActivity {

    // ...

    ResultCallback<ContentsResult> contentsCallback = new
            ResultCallback<ContentsResult>() {
        @Override
        public void onResult(ContentsResult result) {
            if (!result.getStatus().isSuccess()) {
                // Handle error
                return;
            }

            MetadataChangeSet changeSet = new MetadataChangeSet.Builder()
                    .setTitle("New file")
                    .setMimeType("text/plain").build();
            // Create a file in the root folder
            Drive.DriveApi.getRootFolder(getGoogleApiClient())
                    .createFile(getGoogleApiClient(), changeSet, result.getContents())
                    .addResultCallback(this);
        }
    }
}
于 2014-05-06T17:30:11.603 回答
0

这是解决方案的“等待”版本(为简单起见 - 必须在非 UI 线程上运行)(GoogleApiClient 的初始化/连接是标准的,可以在其他地方找到):

  static final String MIMEFLDR  = "application/vnd.google-apps.folder";
  private GoogleApiClient  _gac;

  DriveFolder myFldr = getOrCreateFldr(null, "myFolder");
  DriveFolder myChildFldr = getOrCreateFldr(myFldr, "myChildFolder");

  private DriveId findFirst(String title, String mime, DriveFolder fldr) {
    ArrayList<Filter> fltrs = new ArrayList<Filter>();
    fltrs.add(Filters.eq(SearchableField.TRASHED, false));
    if (title != null)  fltrs.add(Filters.eq(SearchableField.TITLE, title));
    if (mime  != null)  fltrs.add(Filters.eq(SearchableField.MIME_TYPE, mime));
    Query qry = new Query.Builder().addFilter(Filters.and(fltrs)).build(); 
    MetadataBufferResult rslt = (fldr == null) ? Drive.DriveApi.query(_gac, qry).await() : 
                                                   fldr.queryChildren(_gac, qry).await();
    MetadataBuffer mdb = null;
    if (rslt.getStatus().isSuccess()) try {
      mdb = rslt.getMetadataBuffer();
      for (Metadata md : mdb) {
        if ((md == null) || (!md.isDataValid()) || md.isTrashed()) continue;
        return md.getDriveId();
      }
    } catch (Exception e) {}
    finally { if (mdb != null) mdb.close(); } 
    return null;
  }

  private DriveFolder getOrCreateFldr(DriveFolder fldr, String titl) {
    DriveFolder df = null;
    try {
      DriveId dId = findFirst(titl, MIMEFLDR, fldr);
      if (dId != null) {                 // exists
        df = Drive.DriveApi.getFolder(_gac, dId);
      } else {                           // doesn't exist, create in folder / root
        df = createFldr((fldr == null) ? Drive.DriveApi.getRootFolder(_gac) : fldr,  titl);
      }
    } catch (Exception e) {UT.le(e);}
    return df;
  }

  private DriveFolder createFldr(DriveFolder fldr, String name) {
    DriveFolder drvFldr = null;
    try { 
      MetadataChangeSet meta = 
              new MetadataChangeSet.Builder().setTitle(name).setMimeType(MIMEFLDR).build();
      drvFldr = fldr.createFolder(_gac, meta).await().getDriveFolder();
    } catch (Exception e) {}
    return drvFldr;
  }

它可以很容易地变成回调版本,但看起来很乱。不过要小心 findFirst() 方法,Google Drive 允许多个具有相同名称的文件/文件夹(因为只有 ResourceId / DriveId 是唯一标识符)。

如果您想更深入地挖掘,此GitHub 项目中显示了递归文件夹的创建。

于 2014-05-09T05:02:32.917 回答
0

我尝试整合几个答案,并添加了我的部分以获得一种有效的方法。肯定会有比我开发的这个更优雅和封装的方式,但它是我现在能提供的最好的方式。

从元数据中获取 DriveId 对象后,接下来就是使用asDriveFolder ( )方法获取DriveFolder对象。

感谢@Bikesh M Annur@seanpj,他们在How to get DriveId of created folder in Google Drive Android API 中做出了贡献。

private DriveFolder mFolder;

private void getDriveFolder(String folderName) {

    Query query = new Query.Builder().addFilter(Filters.and(
            Filters.eq(SearchableField.TITLE, folderName),
            Filters.eq(SearchableField.TRASHED, false))).build();

    getDriveResourceClient().query(query).addOnSuccessListener(new OnSuccessListener<MetadataBuffer>() {
        @Override
        public void onSuccess(MetadataBuffer metadata) {
            mFolder = null;

            for (Metadata md : metadata) {
                if (md == null) continue;
                DriveId dId  = md.getDriveId();      // here is the "Drive ID"
                String title = md.getTitle();
                String mime  = md.getMimeType();

                if (md.isFolder()) {
                    mFolder = dId.asDriveFolder();   // Returns the "DriveFolder" object
                    break;
                }
            }

            if (mFolder != null) {
                // Or better from here you can take your actions
                //...
            }
        }
    });
}

注意:请记住,在 Google Drive 中,您可以多次创建同名文件夹。此例程将返回列表中的第一个。您可以自行决定要进行哪些重复。

于 2018-02-15T01:05:58.790 回答