首页 > 解决方案 > 只有当文件完全上传到 Firebase 存储时,如何才能从此方法返回 Observable?

问题描述

我在尝试从我的 Angular 应用程序上传 Firebase Storage 上的文件时遇到了一些困难。

我有以下情况:在服务类中,我有这样的事情:

if(file != null) {
    this.uploadFileIntoFirebaseStore(file)
        .subscribe(url => {
                              console.log("RETRIEVING URL")
                              console.log(url);
                              console.log("END RETRIEVING URL");
                              ...................................
                              ...................................
                              OTHER OPERATIONS
                              ...................................
                              ...................................
                           });
}

正如您在前面的代码片段中看到的那样,我正在调用一个名为uploadFileIntoFirebaseStore()将文件传递给它的方法,并且我正在订阅返回的 observable。此方法必须将文件上传到 Firebase 存储,我认为它的实现并不完全正确。

这是我的uploadFileIntoFirebaseStore()方法的代码:

uploadFileIntoFirebaseStore(fileToBeUploaded) {
    var n = Date.now();
    const filePath = `user_avatar/${n}`;
    const fileRef = this.storage.ref(filePath);

    return this.storage.upload(`user_avatar/${n}`, fileToBeUploaded)
             .snapshotChanges()
             .pipe(
                switchMap(refStatus => {
                  console.log("refStatus: ", refStatus);

                  if(refStatus.state == "running")
                    console.log("UPLOAD RUNNING");
                  else {
                    console.log("UPLOAD COMPLETED");
                    console.log("fileRef.getDownloadURL() OUTPUT: ", fileRef.getDownloadURL());
                    //return fileRef.getDownloadURL();
                  }

                  console.log("fileRef.getDownloadURL() OUTPUT: ", fileRef.getDownloadURL());
                  return fileRef.getDownloadURL();
                })
             );
}

问题如下:此方法正确地将我的文件上传到 Firebase Storage。它首先进入

if (refStatus.state == "running")

表示上传过程仍未完成。此时它是return fileRef.getDownloadURL();可观察的,但它(此时)指的是尚未完全上传的文件(因此尚不存在 URL)。

所以我的uploadFileIntoFirebaseStore()方法的订阅尝试使用这个 observable 来检索和打印 url(必须由 打印console.log(url);),我得到一个错误。

然后上传过程继续,直到它进入else打印上传文件的URL的语句。但是此时我的应用程序已损坏,因为似乎在uploadFileIntoFirebaseStore()订阅中我还收到了一个不包含 URL 的值。

我真的不知道如何解决这个问题。我的想法是,uploadFileIntoFirebaseStore()只有当文件完全上传并且该文件的 URL 存在时,该方法才必须发出一个值。

我该如何解决这个问题?

标签: angularfirebaserxjsfirebase-storage

解决方案


我认为您需要过滤器运算符。只有当您的条件通过时,它才会继续。

...
.pipe(
    filter(refStatus => refStatus.state != "running"),
    switchMap(refStatus => {
        ...

推荐阅读