Re: [XHR2] why have an asBlob attribute at all?

2010-10-28 Thread Boris Zbarsky

On 10/28/10 5:22 PM, David Flanagan wrote:

In fact, I'd go further and ask why the blob case needs to be special
cased at all. The bytes are stored somewhere. Returning them as a blob
doesn't seem any harder than returning them as an ArrayBuffer.


David, the issue is that if you make a request for a 4GB resource and 
ask for it as an array buffer and you're on a 32-bit system, the only 
thing the browser can do is throw an out of memory exception.


On the other hand, if you access the same response as a blob, the 
browser can let you do that; you just won't be able to get it all into a 
single JS string.


So there are definitely use cases for being able to access as a Blob.


I know that Blobs are an outgrowth of the File API, but won't many Blobs
(created by BlobBuilders, for example) be in-memory objects rather than
on-disk objects?


I believe BlobBuilder can stick the data anywhere it wants.


And shouldn't the decision about whether to spool a
response to disk or not be implementation-dependent?


It is, yes.  But we still need an API that doesn't force the response 
into memory in its entirety.



and then memory map it
to make it look like it is in memory.


That doesn't help for the truly large responses; the OS won't let you 
memory map them in its entirety...



(Probably because I'm missing something fundamental about the nature of
Blobs... I'd love to know what it is!)


The key part with a blob is that you can access parts of it without 
forcing the whole thing into the process's address space.


-Boris



Re: [XHR2] why have an asBlob attribute at all?

2010-10-28 Thread David Flanagan

On 10/28/2010 06:24 PM, Boris Zbarsky wrote:

On 10/28/10 5:22 PM, David Flanagan wrote:

In fact, I'd go further and ask why the blob case needs to be special
cased at all. The bytes are stored somewhere. Returning them as a blob
doesn't seem any harder than returning them as an ArrayBuffer.


David, the issue is that if you make a request for a 4GB resource and
ask for it as an array buffer and you're on a 32-bit system, the only
thing the browser can do is throw an out of memory exception.

On the other hand, if you access the same response as a blob, the
browser can let you do that; you just won't be able to get it all into a
single JS string.


Thanks for the explanation, Boris.  The L in Blob is an order of 
magnitude larger than anything I was imagining.  Now I understand why 
both Blobs and ArrayBuffer are required. I still don't get, however, why 
the API needs distinct blob/non-blob modes. Why not do it like this:


- The implementation decides whether to store the response in a file or 
not based on its own knowledge of the Content-Length and of the system's 
hardware.  (And perhaps the developer can set some kind of reallyBig 
flag as a hint that the implementation should consider saving the 
response to disk.)


- The response body is always available through responseBlob. No special 
asBlob flag is required.


- If the response is too big to fit in memory, then accessing 
responseText, responseArrayBuffer or responseXML will throw an 
out-of-memory exception.  This is what would happen if you naively tried 
to use the FileReader interface on the un-sliced Blob, so why can't that 
happen here?


With the API as it is now, a web developer who wants to download a 
gigantic chunk of data has to know in advance to use a blob to avoid the 
possibility of out-of-memory errors. They have to put their XHR object 
into a special asBlob mode in order to do so.  And once they ar in that 
mode if they try to use responseText or responseArrayBuffer, they're 
guaranteed to get a INVALID_STATE_ERR exception at runtime.


With my proposal, the developer still has to know in advance that they 
probably ought to use a blob.  But they don't have to set a special flag 
to do it.  And if they do use responseText or responseArrayBuffer, they 
might get an out-of-memory error at runtime, but there's also a decent 
chance that things will just work (maybe with some disk swapping slowing 
things down a bit).


I doubt I understand all the implementation issues.  But if there really 
is some reason to have this blob/non-blob decision point before calling 
send(), can I suggest that instead of confusing the XHR API with it, it 
be moved into a separate BlobHttpRequest interface that has only 
reponseBlob and does not even define responseText, etc.


David





Re: [XHR2] why have an asBlob attribute at all?

2010-10-29 Thread Anne van Kesteren
On Fri, 29 Oct 2010 07:55:58 +0200, David Flanagan  
 wrote:
I doubt I understand all the implementation issues.  But if there really  
is some reason to have this blob/non-blob decision point before calling  
send(), can I suggest that instead of confusing the XHR API with it, it  
be moved into a separate BlobHttpRequest interface that has only  
reponseBlob and does not even define responseText, etc.


Brainstorming here. We could choose to always expose resonseArrayBuffer  
and keep it together with responseText and responseXML. And for  
applications that are worried about memory usage or care about very large  
files we could have BlobXMLHttpRequest similar to AnonXMLHttpRequest. We'd  
abstract some things out from XMLHttpRequest so BlobXMLHttpRequest does  
not have the other response* members and so that AnonXMLHttpRequest does  
not need withCredentials and the fourth and fifth parameter to open().



--
Anne van Kesteren
http://annevankesteren.nl/



Re: [XHR2] why have an asBlob attribute at all?

2010-10-29 Thread Tab Atkins Jr.
On Fri, Oct 29, 2010 at 4:08 AM, Anne van Kesteren  wrote:
> On Fri, 29 Oct 2010 07:55:58 +0200, David Flanagan 
> wrote:
>>
>> I doubt I understand all the implementation issues.  But if there really
>> is some reason to have this blob/non-blob decision point before calling
>> send(), can I suggest that instead of confusing the XHR API with it, it be
>> moved into a separate BlobHttpRequest interface that has only reponseBlob
>> and does not even define responseText, etc.
>
> Brainstorming here. We could choose to always expose resonseArrayBuffer and
> keep it together with responseText and responseXML. And for applications
> that are worried about memory usage or care about very large files we could
> have BlobXMLHttpRequest similar to AnonXMLHttpRequest. We'd abstract some
> things out from XMLHttpRequest so BlobXMLHttpRequest does not have the other
> response* members and so that AnonXMLHttpRequest does not need
> withCredentials and the fourth and fifth parameter to open().

Could we, um, not include the word "XML" in any new things?
BlobHttpRequest seems much less silly.

~TJ



Re: [XHR2] why have an asBlob attribute at all?

2010-10-29 Thread Anne van Kesteren
On Fri, 29 Oct 2010 13:08:07 +0200, Anne van Kesteren   
wrote:
Brainstorming here. We could choose to always expose resonseArrayBuffer  
and keep it together with responseText and responseXML. And for  
applications that are worried about memory usage or care about very  
large files we could have BlobXMLHttpRequest similar to  
AnonXMLHttpRequest. We'd abstract some things out from XMLHttpRequest so  
BlobXMLHttpRequest does not have the other response* members and so that  
AnonXMLHttpRequest does not need withCredentials and the fourth and  
fifth parameter to open().


Nevermind, then we'd need AnonBlobXMLHttpRequest too for completeness. Not  
so great.



--
Anne van Kesteren
http://annevankesteren.nl/



Re: [XHR2] why have an asBlob attribute at all?

2010-10-29 Thread David Flanagan

On 10/29/2010 06:07 AM, Anne van Kesteren wrote:
> On Fri, 29 Oct 2010 13:08:07 +0200, Anne van Kesteren 
> wrote:
>> Brainstorming here. We could choose to always expose
>> resonseArrayBuffer and keep it together with responseText and
>> responseXML. And for applications that are worried about memory usage
>> or care about very large files we could have BlobXMLHttpRequest
>> similar to AnonXMLHttpRequest. We'd abstract some things out from
>> XMLHttpRequest so BlobXMLHttpRequest does not have the other response*
>> members and so that AnonXMLHttpRequest does not need withCredentials
>> and the fourth and fifth parameter to open().
>
> Nevermind, then we'd need AnonBlobXMLHttpRequest too for completeness.
> Not so great.
>

Too bad.  If you were okay with BlobHttpRequest and AnonBlobHttpRequest, 
I was going to propose BufferHttpRequest and AnonBufferHttpRequest as 
well.  If adding a responseType flag would break jQuery, and not adding 
responseType would double the memory usage of all XHR requests, then  it 
seems like defining a new API is the way out of the dilemma.


So if I can continue the brainstorm...

Note that a new BufferHttpRequest need not be binary-only.  It can still 
have a decodeResponseAsText() method or something equivalent.

And it creates the opportunity to get rid of XML in the name!

Why can't the Anon part be taken care of with a constructor parameter?
(And is there any value in putting other things in the constructor like 
a cross-origin flag and the withCredentials flag?)


XMLHttpRequest(anon): has today's responseText and responseXML 
properties only.  (Is there a case for anonymous legacy XHR at all?)


BufferHttpRequest(anon): has a single response property that is an 
ArrayBuffer.  For convenience, it also has a responseAsText property 
that decodes the buffer to text when read.  (Purposely avoiding 
"responseText" so legacy code that checks responseText.length can't be 
ported to BufferHttpRequest)


BlobHttpRequest(anon): has a single response property that is a Blob.
Of course defining a BufferHttpRequest type really invites a 
StreamingHttpRequest as well, and I have the suspicion that a streaming 
API solves a more fundamental problem than Blobs do...


David