Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Display download progress #1104

Open
eloquence opened this issue Jun 8, 2020 · 9 comments · May be fixed by #2327
Open

Display download progress #1104

eloquence opened this issue Jun 8, 2020 · 9 comments · May be fixed by #2327

Comments

@eloquence
Copy link
Member

We're currently only displaying a spinner for download activity. For a large download, it would be useful to let the user know how much of the file has already been downloaded.

Key questions to address include:

  • What implementation strategy do we want to use to update the client's knowledge of download progress?
  • What information do we want to display (in a first iteration, in future iterations)? For comparison, Firefox shows:
    • estimated time remaining
    • [kilo/mega]bytes downloaded
    • [kilo/mega]bytes remaining
    • estimated throughput
    • progress bar
  • Is that information constrained by the technical choice above?
  • If a file is not yet downloading but only queued to be downloaded, what should the progress indicator say?
@ninavizz
Copy link
Member

ninavizz commented Jun 8, 2020

Cross-referencing to Conversation Pane refinement EPIC in SD-UX repo.

@philmcmahon
Copy link
Contributor

Just adding some user feedback on this - any indication of download progress would be very useful as it's not currently clear whether a download is still in progress or has failed:

"We've not yet successfully downloaded any files larger than a megabyte, whereas we frequently receive files of up to 500Mb. All I see is "Downloading" for long periods (involving multiple screenlocks) until giving up after an hour or so."

@cfm
Copy link
Member

cfm commented Jan 24, 2023

Last Thursday @tina-ux and I discussed @eloquence's question in #1104 (comment):

What implementation strategy do we want to use to update the client's knowledge of download progress?

When downloading messages and files we already do—

return api.download_submission(
sdk_object, timeout=self._get_realistic_timeout(db_object.size)
)

—meaning that we have access to both (a) the actual size of the file we're downloading and (b) an estimate of how long it should take to download.

When fetching metadata takes a long time, it appears that we do get a Content-Length header we could pass to a generalized form of _get_realistic_timeout(size_in_bytes: int):

headers:
Content-Length:
- '13467'

In either case, to report on actual progress, we'll need securedrop-proxy to support streaming responses (e.g.).

@rocodes
Copy link
Contributor

rocodes commented Mar 7, 2023

get_realistic_timeout is a theoretical ceiling above which we are declaring the download to be failed/stalled, and is not based on the user's current network conditions. Ideally we want a way of reporting true connection speed (and/or comparing true download progress to some benchmark numbers to decide if we're making "good" or "poor" progress), which is maybe what you're suggesting with sd-proxy

@cfm
Copy link
Member

cfm commented Mar 7, 2023

Yes, exactly.

@rocodes
Copy link
Contributor

rocodes commented Mar 7, 2023

Ok, so the only small issue I see there is we probably want another option (get_non_depressing_realistic_timeout? 😭) to benchmark against, since I will probably bump up our defintion of "realistic" in order to accommodate wider range of network conditions. But it won't be hard to include that logic.

I haven't looked at the proxy code. Do you have a sense of how readily those changes could be made? Even if we haven't finalized the UX implications for the client (in terms of how we report on the download speed/progress), we could start by making sure the info is accessible in the client.

@legoktm legoktm added this to the 0.16.0 milestone Aug 7, 2024
legoktm added a commit that referenced this issue Dec 9, 2024
Display a vanilla progress bar for file downloads that simply shows how
much of the file has been downloaded so far.

A new FileDownloadProgressBar widget replaces the existing animated
spinner, and we inject a signal through to the SDK to pass the current
progress back to the widget.

TODO:
* Download speed?
* Visual alignment issue; need padding on the right side
* tests?

Fixes #1104.
@legoktm legoktm linked a pull request Dec 9, 2024 that will close this issue
6 tasks
@legoktm
Copy link
Member

legoktm commented Dec 9, 2024

I've submitted #2327 as a pretty naive implementation; it just has a progress bar with a numerical % of how much has been completed using the builtin QProgressBar widget. I think it would be straightforward to add speed as well; just need to think a bit on how to lay that out visually.

Edit: I've included download speed

@legoktm legoktm moved this to In Progress in SecureDrop dev cycle Dec 9, 2024
@legoktm legoktm self-assigned this Dec 9, 2024
legoktm added a commit that referenced this issue Dec 10, 2024
Display a vanilla progress bar for file downloads that simply shows how
much of the file has been downloaded so far.

A new FileDownloadProgressBar widget replaces the existing animated
spinner, and we inject a signal through to the SDK to pass the current
progress back to the widget.

TODO:
* Visual alignment issue; need padding on the right side
* tests?

Fixes #1104.
legoktm added a commit that referenced this issue Dec 10, 2024
Display a vanilla progress bar for file downloads that simply shows how
much of the file has been downloaded so far.

A new FileDownloadProgressBar widget replaces the existing animated
spinner, and we inject a signal through to the SDK to pass the current
progress back to the widget.

TODO:
* Visual alignment issue; need padding on the right side
* tests?

Fixes #1104.
legoktm added a commit that referenced this issue Dec 10, 2024
Display a vanilla progress bar for file downloads that simply shows how
much of the file has been downloaded so far.

A new FileDownloadProgressBar widget replaces the existing animated
spinner, and we inject a signal through to the SDK to pass the current
progress back to the widget.

TODO:
* Visual alignment issue; need padding on the right side
* tests?

Fixes #1104.
@legoktm
Copy link
Member

legoktm commented Dec 10, 2024

Unfortunately I'm not set up to do a screen recording on Qubes, so here are some screenshots for now:

1 2 3 4
Screenshot_2024-12-10_14-39-07 Screenshot_2024-12-10_14-39-24 Screenshot_2024-12-10_14-39-35 Screenshot_2024-12-10_14-39-47

There's a visual alignment issue (needs some right-side padding), but other than that I think (hope) it's in a reasonable enough state to ship.

Features:

  • progress bar appears when you click download, staying at 0% until it is at the top of the queue and starts
  • smoothing of download speed using a exponential moving average (I'm sure there are smarter algorithms out there but this worked out reasonably well and was straightforward to implement)
  • said download speed is rounded to try our best to get a consistent length of digits so there's less visual shifting
  • at 0% and 100% we hide the speed since nothing is happening

Rough edges:

  • It'll sit at 100% for a few seconds while decryption happens
  • if the download stalls, it'll spend like 3-5 seconds comically decreasing the download speed until it hits 0B/s.

I explicitly skipped implementing time remaining because I feel that opens up a lot of pitfalls in predictions; for now I think we're better off reporting facts we know (total progress and download speed) and later we can try to add in predicted time based on whatever heuristics.

legoktm added a commit that referenced this issue Dec 10, 2024
Display a vanilla progress bar for file downloads that simply shows how
much of the file has been downloaded so far.

A new FileDownloadProgressBar widget replaces the existing animated
spinner, and we inject a signal through to the SDK to pass the current
progress back to the widget.

The widget both displays the overall total progress as a percentage and
also calculates the download speed by using an exponential moving
average to smooth it out. A timer runs every 100ms to recalculate the
speed.

A new utils.humanize_speed() is used to translate the raw bytes/second
into a human-readable version with a focus on keeping the length of the
string roughly consistent so there's less visual shifting.

TODO:
* Visual alignment issue; need padding on the right side
* tests?

Fixes #1104.
legoktm added a commit that referenced this issue Dec 10, 2024
Display a vanilla progress bar for file downloads that simply shows how
much of the file has been downloaded so far.

A new FileDownloadProgressBar widget replaces the existing animated
spinner, and we inject a signal through to the SDK to pass the current
progress back to the widget.

The widget both displays the overall total progress as a percentage and
also calculates the download speed by using an exponential moving
average to smooth it out. A timer runs every 100ms to recalculate the
speed.

A new utils.humanize_speed() is used to translate the raw bytes/second
into a human-readable version with a focus on keeping the length of the
string roughly consistent so there's less visual shifting.

TODO:
* Visual alignment issue; need padding on the right side
* tests?

Fixes #1104.
legoktm added a commit that referenced this issue Dec 11, 2024
Display a vanilla progress bar for file downloads that simply shows how
much of the file has been downloaded so far.

A new FileDownloadProgressBar widget replaces the existing animated
spinner, and we inject a signal through to the SDK to pass the current
progress back to the widget.

The widget both displays the overall total progress as a percentage and
also calculates the download speed by using an exponential moving
average to smooth it out. A timer runs every 100ms to recalculate the
speed.

A new utils.humanize_speed() is used to translate the raw bytes/second
into a human-readable version with a focus on keeping the length of the
string roughly consistent so there's less visual shifting.

TODO:
* Visual alignment issue; need padding on the right side
* tests?

Fixes #1104.
@deeplow
Copy link
Contributor

deeplow commented Dec 11, 2024

Unfortunately I'm not set up to do a screen recording on Qubes, so here are some screenshots for now:

FYI, I've been using byzanz (available in dom0 repos) to "record" the screen into gifs. Here's a usage example:

export NAME="$RANDOM.gif" && byzanz-record -x 0 -y 50 -w 1050 -h 770 -d 15 $NAME && qvm-move-to-vm <YOUR_BROWSER_VM> $NAME

legoktm added a commit that referenced this issue Dec 12, 2024
Display a vanilla progress bar for file downloads that simply shows how
much of the file has been downloaded so far.

A new FileDownloadProgressBar widget replaces the existing animated
spinner, and we inject a signal through to the SDK to pass the current
progress back to the widget.

The widget both displays the overall total progress as a percentage and
also calculates the download speed by using an exponential moving
average to smooth it out. A timer runs every 100ms to recalculate the
speed.

A new utils.humanize_speed() is used to translate the raw bytes/second
into a human-readable version with a focus on keeping the length of the
string roughly consistent so there's less visual shifting.

Once the download has finished, an indeterminate progress bar is shown
while decrypting since we don't (currently) have a way to report
specific progress on that.

TODO:
* tests?

Fixes #1104.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
Status: In Progress
Development

Successfully merging a pull request may close this issue.

7 participants