我应该把 completer.complete() 放在这一系列 Future 函数的什么位置?

Where should I put completer.complete() in this series of Future functions?

我的功能必须创建一个目录,并将整个文件夹层次结构从另一个目录复制到这个新目录。所有操作都是异步完成的,但我希望此函数 return 一个 Future ,当我对其调用 .then(result) 时,它将完成所有异步工作。

但我不知道我应该把 completer.complete() 放在哪里才能实现。

Future<Directory> createCopyDirectory(Directory directoryToCreate){
  Completer<Directory> completer = new Completer<Directory>();
  completer.complete(
      directoryToCreate.create().then((directory){
        Directory contentToCopy = new Directory(globalPathOfDirectoryToCopy);
        List<Future> creatingContent = new List<Future>();
        contentToCopy.list(recursive:true, followLinks:false).forEach((f){
          if (f is File){
            File fileToCreate = new File(f.path.replaceFirst('pages', userID));
            creatingContent.add(fileToCreate.create(recursive:true).then((_){
              f.readAsString().then((fileContent){
                fileToCreate.writeAsString(fileContent);
              });
            }));
          }
        });
        return Future.wait(creatingContent).then((_){ return directoryToCreate;});
    })
  );
  return completer.future;
}

我确定我的函数按预期工作,但是如果我尝试直接访问我应该在此函数中创建的内容,例如在 then() 调用中,Dart 会给我一个我没有的期望创建了内容。所以 completer.complete() 肯定放错了,在创建内容之前调用 then()

我试过在结尾 Future.wait(creatingContent) 上使用 completer.complete() 或将 return directoryToCreate 替换为 completer.complete(directoryToCreate) 但结果是一样的。

在这种情况下,我对如何构建一个合适的基于 Future 的函数有点困惑。

这里不需要 Completer

Future<Directory> createCopyDirectory(Directory directoryToCreate) {
  return directoryToCreate.create().then((directory) {
    String userID = split(userDirectory.path).last;
    Directory contentToCopy = new Directory(globalPathOfDirectoryToCopy);
    List<Future> creatingContent = new List<Future>();
    return contentToCopy
        .list(recursive: true, followLinks: false)
        .forEach((File f) {
      if (f is File) {
        File fileToCreate = new File(f.path.replaceFirst('pages', userID));
        creatingContent.add(fileToCreate.create(recursive: true).then((_) {
          return f.readAsString().then((fileContent) {
            return fileToCreate.writeAsString(fileContent);
          });
        }));
      }
    }).then((_) {
      return Future.wait(creatingContent).then((_) {
        return directoryToCreate;
      });
    });
  });
}

只是为了演示如何使用 Completer:

Future<Directory> createCopyDirectory(Directory directoryToCreate) {
  Completer<Directory> completer = new Completer<Directory>();
  directoryToCreate.create().then((directory) {
    String userID = split(userDirectory.path).last;
    Directory contentToCopy = new Directory(globalPathOfDirectoryToCopy);
    List<Future> creatingContent = new List<Future>();
    contentToCopy.list(recursive: true, followLinks: false).forEach((f) {
      if (f is File) {
        File fileToCreate = new File(f.path.replaceFirst('pages', userID));
        creatingContent.add(fileToCreate.create(recursive: true).then((_) {
          return f.readAsString().then((fileContent) {
            return fileToCreate.writeAsString(fileContent);
          });
        }));
      }
    }).then((_) => Future
        .wait(creatingContent)
        .then((_) => completer.complete(directoryToCreate)));
  });
  return completer.future;
}