0

I have the next Angular service to upload files to Amazon S3 using presinged URL:

    import { Injectable } from "@angular/core";
    import { HttpClient, HttpRequest, HttpHeaders, HttpEvent, HttpEventType, HttpErrorResponse, HttpParams } from "@angular/common/http";
    import { map, tap, last } from 'rxjs/operators';

    @Injectable()
    export class S3FileUploadService {
      constructor(private _http: HttpClient) {
      }

      upload(url: string, file: File | Blob, progress: (percent: number) => void, result: (msg: StateMessage) => void) {
        const req = new HttpRequest('PUT', url, file, {
          headers: new HttpHeaders().set("Content-Type", "binary/octet-stream"),
          reportProgress: true,
        });

        this._http.request(req).pipe(
          map(event => this._getProgress(event)),
          tap(value => progress(value)),
          last()
        ).subscribe(() => {
          result({ err: false, msg: "Uploaded" });
        }, (err) => {
          result({ err: true, msg: this._errorMsg(err, "Not uploaded") });
        });
      }

      private _getProgress(event: HttpEvent<any>) {
        switch (event.type) {
          case HttpEventType.Sent:
            return 0;
          case HttpEventType.UploadProgress:
            return Math.round(10000 * event.loaded / event.total) / 100;
          case HttpEventType.Response:
            return 100;
        }
      }
    }

The service works fine in the development environment. However, in production for some reason progress event is not fired (update happens when the upload is completely finished). I've also tried to add the next params to HttpRequest object according to some examples with similar problems over the internet, but looks like it's an outdated thing and it doesn't affect anything:

    const params = new HttpParams().set("observe", "events");

What can the problem be caused by? Can it originate not from Angular build but from S3 not returning the progress?

1 Answer 1

0

I had the same issue and traced it to service worker. If you have service worker enabled in prod (service worker may not be built when you do ng serve) then it could be handing your POST request differently

If that's the case, then you can do some hacks as suggested here Progress bar doesn't work using service workers with angular cli

Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.