W3C home > Mailing lists > Public > public-webapps@w3.org > July to September 2009

Re: File API Feedback

From: Jonas Sicking <jonas@sicking.cc>
Date: Mon, 6 Jul 2009 13:38:10 -0700
Message-ID: <63df84f0907061338p26dd040dh787b606fd2a62009@mail.gmail.com>
To: Garrett Smith <dhtmlkitchen@gmail.com>
Cc: arun@mozilla.com, Boris Zbarsky <bzbarsky@mit.edu>, Ian Hickson <ian@hixie.ch>, Anne van Kesteren <annevk@opera.com>, WebApps WG <public-webapps@w3.org>
On Wed, Jul 1, 2009 at 9:01 PM, Garrett Smith<dhtmlkitchen@gmail.com> wrote:
> On Tue, Jun 30, 2009 at 7:36 PM, Jonas Sicking<jonas@sicking.cc> wrote:
>> On Tue, Jun 30, 2009 at 6:13 PM, Garrett Smith<dhtmlkitchen@gmail.com> wrote:
>>> On Tue, Jun 30, 2009 at 4:29 PM, Jonas Sicking<jonas@sicking.cc> wrote:
>>>> On Tue, Jun 30, 2009 at 4:22 PM, Garrett Smith<dhtmlkitchen@gmail.com> wrote:
>>>>>> With that in mind, do you still think it makes sense to have progress
>>>>>> events and all the other events you are proposing?
>>>>> I've reread my message. The arguments and reasoning given for Events
>>>>> seem clear and concise. The argument for Progress Events was
>>>>> illustrated with an example and a comparison. What was confusing?
>>>> What is the use case for the API you are proposing?
>>> The program wants to attach more than one "success" callback at places
>>> in the code. The program wants to attach a "timeout" callback, to
>>> handle cases where the read operation is too slow.
>> But *why* would someone want to attach more than one success callback?
> Why would someone want to attach more than one "click" handler to
> document? It doesn't really matter why, but it is not hard to imagine
> situations.
> For example, a notification for all success reads of files to notify
> the user of "done", but then specific notifications about the current
> file read. Not hard to imagine, but, AISB, it is not necessary to
> consider all possible contexts. You have snipped and ignored that and
> all other questions. Please don't do that.
> AISB, "An asynchronous file read is like an asynchronous XHR, in a
> way." It can be desirable to want to have more than one callback for
> XHR.

I don't know that I've ever seen someone attach more than one
eventhandler to an XHR request. In fact, I'm not even sure that IE
supports more than one. For the longest time firefox didn't, and I
don't think I ever saw a request for attaching more than one.

Similarly, any API for file access that I have ever seen has only used
a single callback. And file system APIs have existed for many many

UI handling is a lot different from file handling so I don't think the
analogy with the "click" event is that strong. The only similarity is
the use of a callback.

So again, can you give an example of where you'd like two listeners
notified with data read from the file?

> The requirement that determines "inordinately long" comes from a
> human, or humans. It is realized in code via a timeout mechanism to
> cancel the call. This is prevalent in code that must perform
> asynchronously e.g. XHR, animations, etc.
> MSDN's XHR and XDR documentation[1] has an example of timeout that is
> of particular relevance here; XHR is a data request over http,
> FileUpload is a data request in the local network. It is a very common
> pattern to have a timeout[2]. Even progress events has a timeout event
> (shoehorned into "error")[3].

If we add a cancelPendingReads() function (or whatever we decide to
call it) then the following code would work to implement timeouts:

myFile.dataAsText(dataCallback, errorCallback);
timer = setTimeout(function() { myFile.cancelPendingReads(); }, 10000);

function dataCallback(data) {
  ... do stuff with data ...

The two use cases for the timeout property on XDR are:

1. When using synchronous requests. In this case the timeout code
above doesn't work since timers don't fire during synchronous reads.
2. As a more convenient API than the above.

1 doesn't apply to the file API since there are no synchronous
requests. As for use case 2, I'm not convinced that timeouts for local
file reads are common enough that we need to add convenience APIs to
deal with it. Especially not in the first revision of the spec.

However if others think it's important, we could add a .timeout
property on the File object. This would cancel any reads that took
longer than the set time and call the error callback.

>> And it gets worse if you want to read the data both as raw data and as
>> a data-url. For example in order to process the raw data and send it
>> to the server, as well as use the data-url to display a preview using
>> an <img>. In that case the code would be more something like:
>> file.onsuccess = handleDataUrl;
>> file.onerror = genericError;
>> file.readAsDataURL();
>> function handleDataUrl() {
>>  ...
>>  file.onsuccess = handleTextDatal;
>>  file.readAsText();
>> }
> Spaghetti code.
> The documentation for FileDialog[0] has named the callback parameter
> to getAsDataURI as "FileAsText ". From the editor's draft:
> | getAsDataURI(in FileAsText callback, [Optional] in FileErrorCallback
> errorCallback);
> Your example raises a good point. There are two reads, each with
> different behavior, but callbacks are a shared behavior. Why not have
> a Reader for each behavior?
>  var reader = file.textReader;
>  reader.success = textReadSuccess;
>  reader.read();
>  reader = file.uriReader;
>  reader.success = uriReadSuccess;
>  reader.read();
> That makes the individual callbacks a lot simpler. It also provides a
> "read" interface that works on any type of Reader. It really makes
> more sense when you think about it; a File does not read; a Reader
> does.

So what if you're reading two parts of the file and want different
callbacks. Say for example that you're reading data out of a video
file and you want to read both the index of the video to see how long
it is, as well as read read the first frame in order to display a
preview. Once we have an API for reading ranges of a file, you'd do:

file.getDataAtRange(0, 1024, indexHandler, genericError);
file.getDataAtRange(4711, 5735, indexHandler, genericError);

(the example assumes that the index is located at byte 0, and the
first video frame is located at byte 4711).

How would you do that using the API you are proposing?

/ Jonas
Received on Monday, 6 July 2009 20:39:06 GMT

This archive was generated by hypermail 2.3.1 : Tuesday, 26 March 2013 18:49:32 GMT