Re: InedxedDB events : misconception?

2013-04-22 Thread Michaël Rouges
Oh, sorry... and thank you all for your explanations. :)


Re: InedxedDB events : misconception?

2013-04-22 Thread Michaël Rouges
Ok, the example of console.log () has made ​​me realize something I had
never seen that.

In short, if I understood from my tests, asynchronous instruction is
executed at the earliest, after the last statement of the scope in which it
is declared.

There was a misconception ... in my mind.

Please apologize for the inconvenience.

Cordially,

Michaël


Re: InedxedDB events : misconception?

2013-04-22 Thread Elliott Sprehn
On Mon, Apr 22, 2013 at 12:32 PM, Alec Flett  wrote:

> On Mon, Apr 22, 2013 at 9:56 AM, Michaël Rouges 
> wrote:
>
>>
>> Hum ... thank you for this answer, but ...
>>
>> Are you sure there is no possibility that the application is completed
>> before adding events?
>>
>> I find it hard to perceive how it couldn't happen.
>>
>
> Just to close the loop on this concern: the reason there is no possibility
> is that this part of the IndexedDB specification - all browsers must
> guarantee this behavior to have a working IndexedDB - in fact the rest of
> IndexedDB itself would be unusable if this guarantee was not met.
>
> Stuff like this can feel a little awkward if you're using to dealing in a
> multi-threaded world, but this API is fairly normal for a web api, at least
> in this respect. In fact XHR is the outlier here in requiring a specific
> xhrrequest.send() call.
>
>
Yeah, there's a bunch of APIs like this; EventSource, Notification,
IndexDB's stuff, ...

- E


Re: InedxedDB events : misconception?

2013-04-22 Thread Joshua Bell
On Mon, Apr 22, 2013 at 1:57 PM, Kyle Huey  wrote:

> On Mon, Apr 22, 2013 at 1:50 PM, Joshua Bell  wrote:
>
>> FWIW, we had a Chrome IDB bug report where someone used the developer
>> tools to set a script breakpoint between the open() call and the event
>> handler assignments. The debugger spins the event loop, so the event was
>> dispatched before the handlers were assigned. The answer was "so don't do
>> that", but it's a similar API/platform gotcha leading to developer
>> confusion.
>>
>
> I would claim that's an implementation bug
>

Agreed, and apologies for implying I felt otherwise otherwise. To clarify:
"don't do that  until the debugger architecture is changed".

(Also, apologies if you get this more or less than one time. I'm trying to
switch my mailing list subscription over to my @google.com account but
hitting a list server problem.)


Re: InedxedDB events : misconception?

2013-04-22 Thread Kyle Huey
On Mon, Apr 22, 2013 at 1:50 PM, Joshua Bell  wrote:

> FWIW, we had a Chrome IDB bug report where someone used the developer
> tools to set a script breakpoint between the open() call and the event
> handler assignments. The debugger spins the event loop, so the event was
> dispatched before the handlers were assigned. The answer was "so don't do
> that", but it's a similar API/platform gotcha leading to developer
> confusion.
>

I would claim that's an implementation bug.

- Kyle


Re: InedxedDB events : misconception?

2013-04-22 Thread Joshua Bell
Resending from the correct account:




FWIW, we had a Chrome IDB bug report where someone used the developer tools
to set a script breakpoint between the open() call and the event handler
assignments. The debugger spins the event loop, so the event was dispatched
before the handlers were assigned. The answer was "so don't do that", but
it's a similar API/platform gotcha leading to developer confusion.

On Mon, Apr 22, 2013 at 10:36 AM, Boris Zbarsky  wrote:

> On 4/22/13 1:31 PM, Tab Atkins Jr. wrote:
>
>> Is there a reason to not pass the success/error/upgradeneeded callbacks
>>> in a
>>> dictionary to open() in this case, so that the request object is born
>>> with
>>> the right bits and the actual reques it not kicked off until _after_ the
>>> side-effects of getting them off the dictionary have fully run to
>>> completion?
>>>
>>
>> Dunno, ask sicking.  But events do have some benefits over passed
>> callbacks.
>>
>
> I don't understand the distinction.
>
> My straw-man proposal here is just that there is a dictionary with the
> three callbacks and then the return value has its 
> onsuccess/onerror/**onupgradeneeded
> set to those three callbacks before the actual request is kicked off and
> the request object is returned.
>
>
> (The right answer is to figure out some way to accommodate IDB's
>> locking semantics in a future.  sicking and annevk have some
>> discussion on this.  Then there's no possibility of event races,
>> because your callback will still be fired even if you lose the race.)
>>
>
> That would be good, yes.
>
>
>
Given the "upgradeneeded" mechanism, it might end up being a hybrid of
passed-callbacks and futures, e.g.

futureSavvyIndexedDB.open(name, ver, {
  upgradeneeded: function(db) { /* upgrade logic */ }
).then(
  function(db) { /* success */ },
  function(err) { /* failure */ }
);

... with "blocked" events wedged in there somehow as future progress
notifications or some such. (I haven't followed the latest on that.)



> Synchronously spinning the event loop is the devil. :/
>>
>
> Well, yes.  ;)
>
> -Boris
>
>
>


Re: InedxedDB events : misconception?

2013-04-22 Thread Boris Zbarsky

On 4/22/13 4:36 PM, Joshua Bell wrote:

The debugger spins the event loop


Fwiw, that seems like a bug in the debugger (albeit a common one in 
browser debuggers)  :(


-Boris



Re: InedxedDB events : misconception?

2013-04-22 Thread Alec Flett
On Mon, Apr 22, 2013 at 9:56 AM, Michaël Rouges wrote:

>
> Hum ... thank you for this answer, but ...
>
> Are you sure there is no possibility that the application is completed
> before adding events?
>
> I find it hard to perceive how it couldn't happen.
>

Just to close the loop on this concern: the reason there is no possibility
is that this part of the IndexedDB specification - all browsers must
guarantee this behavior to have a working IndexedDB - in fact the rest of
IndexedDB itself would be unusable if this guarantee was not met.

Stuff like this can feel a little awkward if you're using to dealing in a
multi-threaded world, but this API is fairly normal for a web api, at least
in this respect. In fact XHR is the outlier here in requiring a specific
xhrrequest.send() call.


Alec


Re: InedxedDB events : misconception?

2013-04-22 Thread Jonas Sicking
On Mon, Apr 22, 2013 at 9:56 AM, Michaël Rouges
 wrote:
>
> Hum ... thank you for this answer, but ...
>
> Are you sure there is no possibility that the application is completed
> before adding events?
>
> I find it hard to perceive how it couldn't happen.

Do you also worry that if you wrote:

x = 0;
setTimeout(function() { x = 1; }, 0);
console.log(x);
console.log(x);
console.log(x);
console.log(x);
console.log(x);
console.log(x);

that there's a risk that you'd get a few 0's in the log, but at some
point it would switch to logging 1's?

No developer that I've talked to think that that could happen in JS.
And it can't. It's clear to everyone that you'll only get 0's. The
reason is that JS is single threaded and the setTimeout callback is
run asynchronously.

It's the same thing in IDB. The .onsuccess property is triggered
asynchronously which means that it couldn't happen in the middle of
your execution.

/ Jonas



Re: InedxedDB events : misconception?

2013-04-22 Thread Boris Zbarsky

On 4/22/13 1:41 PM, Tab Atkins Jr. wrote:

On Mon, Apr 22, 2013 at 10:36 AM, Boris Zbarsky  wrote:

On 4/22/13 1:31 PM, Tab Atkins Jr. wrote:

Is there a reason to not pass the success/error/upgradeneeded callbacks
in a
dictionary to open() in this case, so that the request object is born
with
the right bits and the actual reques it not kicked off until _after_ the
side-effects of getting them off the dictionary have fully run to
completion?


Dunno, ask sicking.  But events do have some benefits over passed
callbacks.


I don't understand the distinction.


Callback arguments can only be "registered" once.  Events can be
listened to multiple times.


What I meant is that I don't understand the distinction between the two 
in this particular case, when I am proposing that the callback arguments 
be registered as event listeners by the call.  I understand the general 
difference between the two, thanks.  ;)


This does mean that if you have more than one success listener you lose, 
of course


-Boris



Re: InedxedDB events : misconception?

2013-04-22 Thread Tab Atkins Jr.
On Mon, Apr 22, 2013 at 10:36 AM, Boris Zbarsky  wrote:
> On 4/22/13 1:31 PM, Tab Atkins Jr. wrote:
>>> Is there a reason to not pass the success/error/upgradeneeded callbacks
>>> in a
>>> dictionary to open() in this case, so that the request object is born
>>> with
>>> the right bits and the actual reques it not kicked off until _after_ the
>>> side-effects of getting them off the dictionary have fully run to
>>> completion?
>>
>> Dunno, ask sicking.  But events do have some benefits over passed
>> callbacks.
>
> I don't understand the distinction.

Callback arguments can only be "registered" once.  Events can be
listened to multiple times.  Whether or not that distinction is useful
here can be debated, but it's a salient difference.

~TJ



Re: InedxedDB events : misconception?

2013-04-22 Thread Boris Zbarsky

On 4/22/13 1:31 PM, Tab Atkins Jr. wrote:

Is there a reason to not pass the success/error/upgradeneeded callbacks in a
dictionary to open() in this case, so that the request object is born with
the right bits and the actual reques it not kicked off until _after_ the
side-effects of getting them off the dictionary have fully run to
completion?


Dunno, ask sicking.  But events do have some benefits over passed callbacks.


I don't understand the distinction.

My straw-man proposal here is just that there is a dictionary with the 
three callbacks and then the return value has its 
onsuccess/onerror/onupgradeneeded set to those three callbacks before 
the actual request is kicked off and the request object is returned.



(The right answer is to figure out some way to accommodate IDB's
locking semantics in a future.  sicking and annevk have some
discussion on this.  Then there's no possibility of event races,
because your callback will still be fired even if you lose the race.)


That would be good, yes.


Synchronously spinning the event loop is the devil. :/


Well, yes.  ;)

-Boris




Re: InedxedDB events : misconception?

2013-04-22 Thread Tab Atkins Jr.
On Mon, Apr 22, 2013 at 10:17 AM, Boris Zbarsky  wrote:
> On 4/22/13 12:47 PM, Tab Atkins Jr. wrote:
>> As long as you don't spin the event loop
>
> That's tricky.  Here's some simple code at global scope:
>
>
> request = indexedDB.open('database');
> request.onsuccess = function () {};
>
> Can that code spin the event loop between the open() call and the onsuccess
> setter being invoked?
>
> Sure: all it takes is someone defining a setter for "request" on the window
> that just saves the given value and a getter for "request" that calls
> showModalDialog to ask the user whether to allow the get and then returns
> the saved value.
>
> Now why someone would do that, I have no idea, but that's true for a lot of
> things people do in practice in websites.  ;)  My point is that whether the
> event loop spins is a very non-local property of the code. It's annoying to
> have to depend on such things.
>
> Is there a reason to not pass the success/error/upgradeneeded callbacks in a
> dictionary to open() in this case, so that the request object is born with
> the right bits and the actual reques it not kicked off until _after_ the
> side-effects of getting them off the dictionary have fully run to
> completion?

Dunno, ask sicking.  But events do have some benefits over passed callbacks.

(The right answer is to figure out some way to accommodate IDB's
locking semantics in a future.  sicking and annevk have some
discussion on this.  Then there's no possibility of event races,
because your callback will still be fired even if you lose the race.)

>> This... is precisely the sort of thing that you shouldn't do.  Just
>> don't do this, and you're golden.
>
> I don't believe you are; see above.
>
>
>> The "request.execute()" is more or less implied by hitting the bottom
>> of your function, when it returns control back to the browsers.
>
> We wish; see above.

Synchronously spinning the event loop is the devil. :/

~TJ



Re: InedxedDB events : misconception?

2013-04-22 Thread Michaël Rouges
Sorry, I usually speak french and my english is quite experimental.

The example I gave, with SetTimeout() is useless, if not illustrate that
the interpreter does not expect that the events are attached to execute the
query.

My surprise comes from the comparison with the XMLHttpRequest object, which
is usually added events before executing the query.

This behavior (XMLHttpRequest) seems more natural to me. It creates the
object and its properties and only then starts the execution may require
these properties.

As it happens, with IndexedDB objects, we can only hope that the events are
attached before, by the interpreter.


Re: InedxedDB events : misconception?

2013-04-22 Thread Boris Zbarsky

On 4/22/13 12:47 PM, Tab Atkins Jr. wrote:

As long as you don't spin the event loop


That's tricky.  Here's some simple code at global scope:

request = indexedDB.open('database');
request.onsuccess = function () {};

Can that code spin the event loop between the open() call and the 
onsuccess setter being invoked?


Sure: all it takes is someone defining a setter for "request" on the 
window that just saves the given value and a getter for "request" that 
calls showModalDialog to ask the user whether to allow the get and then 
returns the saved value.


Now why someone would do that, I have no idea, but that's true for a lot 
of things people do in practice in websites.  ;)  My point is that 
whether the event loop spins is a very non-local property of the code. 
It's annoying to have to depend on such things.


Is there a reason to not pass the success/error/upgradeneeded callbacks 
in a dictionary to open() in this case, so that the request object is 
born with the right bits and the actual reques it not kicked off until 
_after_ the side-effects of getting them off the dictionary have fully 
run to completion?



This... is precisely the sort of thing that you shouldn't do.  Just
don't do this, and you're golden.


I don't believe you are; see above.


The "request.execute()" is more or less implied by hitting the bottom
of your function, when it returns control back to the browsers.


We wish; see above.

-Boris




Re: InedxedDB events : misconception?

2013-04-22 Thread Tab Atkins Jr.
On Mon, Apr 22, 2013 at 9:56 AM, Michaël Rouges
 wrote:
> Hum ... thank you for this answer, but ...
>
> Are you sure there is no possibility that the application is completed
> before adding events?
>
> I find it hard to perceive how it couldn't happen.

I don't quite understand what you're asking.  Are you asking if I'm
sure that events will never be sent before the end of your function?
Yes, I'm sure of this - it's part of Javascript's core semantics.  As
long as you register your callbacks before you yield control back to
the browser, there is absolutely no chance of you missing any events.

~TJ



Re: InedxedDB events : misconception?

2013-04-22 Thread Michaël Rouges
Hum ... thank you for this answer, but ...

Are you sure there is no possibility that the application is completed
before adding events?

I find it hard to perceive how it couldn't happen.


Re: InedxedDB events : misconception?

2013-04-22 Thread Tab Atkins Jr.
On Mon, Apr 22, 2013 at 9:43 AM, Michaël Rouges
 wrote:
> Hello everyone,
>
> I'm surprised by how events are added to IndexedDB objects.
>
> For example, base, opening a database:
>
> var request;
> request = indexedDB.open('database');
> request.onsuccess = function () {};
> request.onupgradeneeded = function () {};
> request.onerror = function () {};
>
> As you can see, the events are added after the query execution.
>
> It does not seem natural and can cause stability problems.
>
> Indeed, if the application had to be completed by the addition of events,
> they will never be triggered.

Events don't fire until the next tick.  As long as you don't spin the
event loop, there's no race conditions and everything's fine.

> Here is an example generates an error:
>
> var request;
> request = indexedDB.open('database');
> setTimeout(function () {
> request.onsuccess = function () {};
> request.onupgradeneeded = function () {};
> request.onerror = function () {};
> }, 1500);

This... is precisely the sort of thing that you shouldn't do.  Just
don't do this, and you're golden.

> In my view, any item requiring events should be set first, then we add the
> events and finally, we execute it.
>
> The code should look like this:
>
> var request;
> request = indexedDB.open('database');
> request.onsuccess = function () {};
> request.onupgradeneeded = function () {};
> request.onerror = function () {};
> request.execute();

The "request.execute()" is more or less implied by hitting the bottom
of your function, when it returns control back to the browsers.

~TJ



InedxedDB events : misconception?

2013-04-22 Thread Michaël Rouges
Hello everyone,

I'm surprised by how events are added to IndexedDB objects.

For example, base, opening a database:

var request;
request = indexedDB.open('database');
request.onsuccess = function () {};
request.onupgradeneeded = function () {};
request.onerror = function () {};

As you can see, the events are added after the query execution.

It does not seem natural and can cause stability problems.

Indeed, if the application had to be completed by the addition of events,
they will never be triggered.

Here is an example generates an error:

var request;
request = indexedDB.open('database');
setTimeout(function () {
request.onsuccess = function () {};
request.onupgradeneeded = function () {};
request.onerror = function () {};
}, 1500);

In my view, any item requiring events should be set first, then we add the
events and finally, we execute it.

The code should look like this:

var request;
request = indexedDB.open('database');
request.onsuccess = function () {};
request.onupgradeneeded = function () {};
request.onerror = function () {};
request.execute();

For additional information and / or feedback, do not hesitate to contact
me. ;)