views:

2261

answers:

5

I am retrieving a list of files from a web service and displaying them as links. When someone clicks on the link, the file should start downloading. The problem is that no direct access to the file exists. Here is the process to download a file:

  1. User clicks on link
  2. Server calls web service to retrieve file
  3. Browser is loading for as long as it takes to bring the file back from the web service
  4. Browser finally offers file to user for download

To counter the unfavorable user experience of having to wait for the web service before the download starts, I would like to display a "Loading..." feedback dialog when a link is clicked, and have the dialog go away when the file is ready.

I am using jQuery, and have been playing around with adding an iframe to the page to load the file, but the problem I am having is I don't know how to determine that the file is ready.

I am looking for tips, not only on the client side to give ample feedback, but perhaps also on the server side (using ASP.Net), just in case I can do something to streamline the process. Thank you.

Update: To clarify, this is for downloading a file to a user's machine. What I'm specifically looking for is a way to determine when the file is ready for download. So, when step #4 above takes place, I'd like to remove the "Loading..." message.

+1  A: 

you can use the complete option for $.ajax function in jquery which should get called when the request completes

Temple
Thanks for the suggestion. I tried $.ajax, but for whatever reason the complete function returns success way before the file is ready.
ern
+1  A: 

You can have jQuery to wait for the click of the link and when the link is clicked show the display loading message.

Example that shows how to 'Loading - Please wait' Message Display Script you can follow.

EDIT-

Basically you want a progress bar monitor, which I have never seen it done with just javascript, but with flash or ajax.

Here is a File Upload Demo that should help.

TStamper
+1  A: 

If you're linking to an ASHX that is grabbing the file and writing it back to a stream, you can modify the links click event to display a message.

$(function () {
  $("a.someClass").click(function () {
    $("div.message").fadeIn();  // show a loading message
    return true; // make sure the link still gets followed
  });
});

The loading message can just be a spinner or something while waiting for the ASHX to write the response back.

Edit: Since you're not directly linking to the ASHX:

$(function () {
  var ashxCallback = function (data, textStatus) {
    // data could be: xmlDoc, jsonObj, html, text, etc...
    this; // the options for this ajax request
    // textStatus can be one of: "timeout", "error", "notmodified", "success", "parsererror" 
    alert(textStatus);
  };

  $("a.someClass").click(function () {
    $("div.message").fadeIn();  // show a loading message
    $.get("some.ashx?id=1234", "", ashxCallback);
    return false;
  });
});

Using jQuery.get() and jQuery.post().

Edit #2: I just had another thought. What if the Loading... message was in an iframe that redirected to the file? So you would display the iframe with jQuery, it would have the default message of Loading... and a little spinner animation, then set the iframe's src/location to the ASHX that takes forever to load. You could then give it an onload handler from the iframe's parent page that would hide/remove it. Let me know if you need sample code.

travis
Thanks, the problem though is I don't know how to tell when the ASHX responds back.
ern
Ah ok, I thought that the user would just be downloading the file directly from clicking on the ASHX link.
travis
Have you tried $.get() or $.post() to call the ASHX?http://docs.jquery.com/Ajax/jQuery.get#urldatacallbacktypehttp://docs.jquery.com/Ajax/jQuery.post#urldatacallbacktype
travis
Yeah, same problem as my $.ajax comment above. The response comes back too early.
ern
Does the response time out or does it just instantly get called back? About how long does it take for your script to call the web service and grab the file?
travis
I believe I've run into a bug with jQuery and IE8. With Firefox the AJAX call works as expected.
ern
Interesting. Does switching IE8 to IE7 compatibility mode help at all?
travis
Referring to edit #2: I was trying that very idea, but I couldn't successfully attach a load handler to the iframe. I was using jQuery's load method.
ern
A: 

If preparation for the file takes less than default timeout of AJAX request, you may start AJAX request, displaying "Loading..." message to user. AJAX call then checks for file's availability, and when it becomes available - returns with the message (success or not) and gives a link for the file. AJAX request can even do file download, but that's for your option.

Thevs
+2  A: 

It sounds like you need to expose a new request URL on your server, whose only job is to reply whether the web-service-retrieval has completed (or if not, how far it has got).

Have AJAX poll that service every few seconds, and remove the "Loading..." message when it replied that the file is ready.

The client should send the session ID (maybe also a file ID), so that the server knows which file is being asked about. The server side will need to be able to contact the running web-service-retrieval process/thread to ask it how far it got. (If it can't find the thread then presumably it has finished.)

joeytwiddle
Great idea. I was also toying around with the idea of downloading the file to a temp directory on the server. The new web service request could just check for the existence of the file as well.
ern