Closed
Bug 911063
Opened 11 years ago
Closed 11 years ago
[FMRadio] Write marionette tests for WebFM
Categories
(Firefox OS Graveyard :: Gaia::FMRadio, defect)
Tracking
(b2g18 unaffected, b2g-v1.1hd unaffected, b2g-v1.2 fixed)
RESOLVED
FIXED
1.3 Sprint 1 - 9/27
Tracking | Status | |
---|---|---|
b2g18 | --- | unaffected |
b2g-v1.1hd | --- | unaffected |
b2g-v1.2 | --- | fixed |
People
(Reporter: pzhang, Assigned: pzhang)
References
Details
Attachments
(1 file, 3 obsolete files)
15.71 KB,
patch
|
pzhang
:
review+
|
Details | Diff | Splinter Review |
Here is the review notes given by Justin about the tests patch: (In reply to Justin Lebar [:jlebar] from comment #149) > Comment on attachment 796409 [details] [diff] [review] > Part III: Marionette tests > > We need to make sure that all of these tests run twice, once in the main > process and once in a child process. > > >diff --git a/dom/fmradio/test/marionette/manifest.ini b/dom/fmradio/test/marionette/manifest.ini > >new file mode 100644 > >--- /dev/null > >+++ b/dom/fmradio/test/marionette/manifest.ini > > >@@ -0,0 +1,13 @@ > >+[DEFAULT] > >+b2g = true > >+browser = false > >+qemu = false > > Nit: Maybe add a comment here explaining why we can't use QEMU? > > >diff --git a/dom/fmradio/test/marionette/test_bug862672.js b/dom/fmradio/test/marionette/test_bug862672.js > >new file mode 100644 > >--- /dev/null > >+++ b/dom/fmradio/test/marionette/test_bug862672.js > > >@@ -0,0 +1,46 @@ > >+/* Any copyright is dedicated to the Public Domain. > >+ * http://creativecommons.org/publicdomain/zero/1.0/ */ > >+ > >+MARIONETTE_TIMEOUT = 10000; > >+ > >+SpecialPowers.addPermission("fmradio", true, document); > >+ > >+let FMRadio = window.navigator.mozFMRadio; > >+ > >+function verifyInitialState() { > >+ log("Verifying initial state."); > >+ ok(FMRadio, "FMRadio"); > >+ is(FMRadio.enabled, false, "FMRadio.enabled"); > > In our other test harnesses, when a test fails it tells us which line it > failed > on. If that's true in Marionette, I'm not sure that the strings here which > just repeat the condition are useful. > > >+ enableThenDisable(); > >+} > >+ > >+function enableThenDisable() { > >+ log("Enable FM Radio and disable it immediately."); > >+ var request = FMRadio.enable(90); > >+ ok(request, "request should not be null."); > >+ > >+ request.onsuccess = function() { > >+ ok(false, "Enable request should fail."); > >+ }; > >+ > >+ var failedToEnable = false; > >+ request.onerror = function() { > >+ failedToEnable = true; > >+ }; > >+ > >+ var disableReq = FMRadio.disable(); > >+ ok(disableReq, "Disable request should not be null."); > >+ > >+ disableReq.onsuccess = function() { > >+ ok(failedToEnable, "Enable request failed."); > >+ ok(!FMRadio.enabled, "FMRadio.enabled is false."); > >+ finish(); > >+ }; > >+ > >+ disableReq.onerror = function() { > >+ ok(false, "Disable request should not fail."); > >+ }; > >+} > > I still have the concern about these tests from bug 862672 comment 26. > Unless > the implementation has changed significantly, I don't think this is correct. > > Last time I looked at this code, the following ordering was possible: > > website: FMRadio.enable(); > gecko: Start enabling FM radio on separate thread. > gecko: Finish enabling FM radio on separate thread, post "enable > successful" message to the main thread's event loop. > website: FMRadio.disable(); > gecko: Post "disable successful" message to main thread's event loop. > > I think this is also possible if this test runs in a child process: > > website: FMRadio.enable(); > gecko child: Send "enable FM radio" message to parent > gecko parent: Send "FM radio enabled" message to child > gecko child: Post "enable successful" message to the main thread's event > loop. > website: FMRadio.disable(); > (and so on) > > If this ordering occurs, this test will fail. > > It seems that the only thing we can check here is that either > > - enable fails (as tested here), or > - enable's onsuccess fires before disable's onsuccess > > But this is still tricky, because when enable's onsuccess fires, should > FMRadio.enabled be true? As currently written, it might not be. I'm not > sure > whether we care. > > >diff --git a/dom/fmradio/test/marionette/test_bug876597.js b/dom/fmradio/test/marionette/test_bug876597.js > >new file mode 100644 > >--- /dev/null > >+++ b/dom/fmradio/test/marionette/test_bug876597.js > > This one looks good. > > >+function cleanUp() { > > We should ask the marionette folks if there's a way to ensure that this code > gets run, even when the test fails or times out. As is, we won't run this > code, and that creates a situation where many FM radio tests after this one > might also fail. > > >diff --git a/dom/fmradio/test/marionette/test_cancel_seek.js b/dom/fmradio/test/marionette/test_cancel_seek.js > >new file mode 100644 > >--- /dev/null > >+++ b/dom/fmradio/test/marionette/test_cancel_seek.js > > I think this has a similar race condition. > > >diff --git a/dom/fmradio/test/marionette/test_enable_disable.js b/dom/fmradio/test/marionette/test_enable_disable.js > >new file mode 100644 > >--- /dev/null > >+++ b/dom/fmradio/test/marionette/test_enable_disable.js > > >@@ -0,0 +1,97 @@ > >+/* Any copyright is dedicated to the Public Domain. > >+ * http://creativecommons.org/publicdomain/zero/1.0/ */ > >+ > >+MARIONETTE_TIMEOUT = 10000; > >+ > >+SpecialPowers.addPermission("fmradio", true, document); > >+ > >+let FMRadio = window.navigator.mozFMRadio; > >+ > >+function verifyInitialState() { > >+ log("Verifying initial state."); > >+ ok(FMRadio, "FMRadio"); > >+ is(FMRadio.enabled, false, "FMRadio.enabled"); > >+ verifyAttributesWhenDisabled(); > >+ enableFMRadio(); > >+} > >+ > >+function verifyAttributesWhenDisabled() { > > This function is used only once; maybe it should be inlined? > > >+ log("Verifying attributes when disabled."); > >+ is(FMRadio.frequency, null, "FMRadio.frequency == null"); > >+ ok(FMRadio.frequencyLowerBound, "FMRadio.frequencyLowerBound"); > >+ ok(FMRadio.frequencyUpperBound, "FMRadio.frequencyUpperBound"); > >+ ok(FMRadio.frequencyUpperBound > FMRadio.frequencyLowerBound, > >+ "FMRadio.frequencyUpperBound > FMRadio.frequencyLowerBound"); > >+ ok(FMRadio.channelWidth, "FMRadio.channelWidth") > >+} > > >+function enableFMRadio() { > >+ log("Verifying behaviors when enabled."); > >+ var request = FMRadio.enable(90); > >+ ok(request, "FMRadio.enable(90) returns request"); > >+ > >+ request.onsuccess = function() { > >+ ok(FMRadio.enabled, "FMRadio.enabled"); > >+ ok(!isNaN(FMRadio.frequency), "FMRadio.frequency is a number"); > > This doesn't quite get what you want, because isNaN(null) is false. > > >+ ok(FMRadio.frequency > FMRadio.frequencyLowerBound, > >+ "FMRadio.frequency > FMRadio.frequencyLowerBound"); > > >= ? > > >+ var seekRequest = FMRadio.seekUp(); > >+ > >+ seekRequest.onerror = function() { > >+ results.seekErrorFired = true; > >+ checkResults(); > >+ }; > >+ > >+ seekRequest.onsuccess = function() { > >+ ok(false, "Seek request should fail after FMRadio.disable is called."); > >+ }; > >+ > >+ FMRadio.disable(); > >+ FMRadio.ondisabled = function() { > >+ FMRadio.ondisabled = null; > >+ results.onDisabledEventFired = true; > >+ ok(!FMRadio.enabled, "FMRadio.enabled is false"); > >+ checkResults(); > >+ }; > >+} > > Similarly I think this part with the seek is racy. > > I'm going to stop reviewing here, since it seems there's enough to work > through.
Assignee | ||
Updated•11 years ago
|
Whiteboard: [MemShrink:P3]
Assignee | ||
Comment 1•11 years ago
|
||
> It seems that the only thing we can check here is that either > > - enable fails (as tested here), or > - enable's onsuccess fires before disable's onsuccess > I agree that it's almost the only thing we can check here, but I still have questions about this, first, since we don't support multi-process (Bug 867831) yet, how can we verify the logics for the potential race condition? second, if enable's onsuccess fires before disable's onsuccess, i don't think it means we pass the test, because it might happen when the tests runs in parent process which I think it means we failed to run the test on the contrary, how can we handle such a case?
Assignee | ||
Comment 2•11 years ago
|
||
> >+
> >+ request.onsuccess = function() {
> >+ ok(FMRadio.enabled, "FMRadio.enabled");
> >+ ok(!isNaN(FMRadio.frequency), "FMRadio.frequency is a number");
>
> This doesn't quite get what you want, because isNaN(null) is false.
Since FMRadio.frequency is null when it's disabled, and it might be null too even when it's enabled if something is wrong, so what I want here is to make sure we can get a number from FMRadio.frequency instead of null or something else when FM radio enabled.
Assignee | ||
Comment 3•11 years ago
|
||
>
> >+function cleanUp() {
>
> We should ask the marionette folks if there's a way to ensure that this code
> gets run, even when the test fails or times out. As is, we won't run this
> code, and that creates a situation where many FM radio tests after this one
> might also fail.
Hi, Malini, can we ensure that |cleanUp| runs even the test fails? In all of my tests, I assume the FM radio is disabled before the tests run, and disable the FM radio in |cleanUp| when the tests finished, so if we can't ensure |cleanUp| runs, then I need to check if it's enabled or disabled before the new test starts.
Flags: needinfo?(mdas)
Comment 4•11 years ago
|
||
> since we don't support multi-process (Bug 867831) yet, how can we verify the logics for > the potential race condition? Like I said in the bit copy-pasted in comment 0, I think this race occurs even if the test runs in-process: > website: FMRadio.enable(); > gecko: Start enabling FM radio on separate thread. > gecko: Finish enabling FM radio on separate thread, post "enable > successful" message to the main thread's event loop. > website: FMRadio.disable(); > gecko: Post "disable successful" message to main thread's event loop. I could be misremembering how this code works, though.
Assignee | ||
Comment 5•11 years ago
|
||
Attachment #798350 -
Flags: review?(justin.lebar+bug)
Assignee | ||
Updated•11 years ago
|
Attachment #798350 -
Attachment description: 0003-Bug-870676-Part-III-marionette-tests.patch → marionette tests
Comment 6•11 years ago
|
||
Comment on attachment 798350 [details] [diff] [review] marionette tests My last day was Friday. You'll need to find someone else to review this; sorry!
Attachment #798350 -
Flags: review?(justin.lebar+bug) → review?
Assignee | ||
Comment 7•11 years ago
|
||
(In reply to Justin Lebar (not reading bugmail) from comment #6) > Comment on attachment 798350 [details] [diff] [review] > marionette tests > > My last day was Friday. You'll need to find someone else to review this; > sorry! Is there any reviewer you would recommend?
Comment 8•11 years ago
|
||
If it were me, I'd ask khuey, and if he didn't want to do it, I'd ask him to find someone. :) Thankfully this test might as well be a mochitest; there's no marionette magic here.
Assignee | ||
Comment 9•11 years ago
|
||
(In reply to Justin Lebar (not reading bugmail) from comment #8) > If it were me, I'd ask khuey, and if he didn't want to do it, I'd ask him to > find someone. :) Thankfully this test might as well be a mochitest; > there's no marionette magic here. Hi, :khuey, could you help to find someone to review the tests' patch?
(In reply to Pin Zhang [:pzhang] from comment #9) > (In reply to Justin Lebar (not reading bugmail) from comment #8) > > If it were me, I'd ask khuey, and if he didn't want to do it, I'd ask him to > > find someone. :) Thankfully this test might as well be a mochitest; > > there's no marionette magic here. > > Hi, :khuey, could you help to find someone to review the tests' patch? I'm still not qualified to review these patches but since Justin has left nobody is so I may as well review them.
Attachment #798350 -
Flags: review? → review?(khuey)
Comment 11•11 years ago
|
||
(In reply to Pin Zhang [:pzhang] from comment #3) > > > > >+function cleanUp() { > > > > We should ask the marionette folks if there's a way to ensure that this code > > gets run, even when the test fails or times out. As is, we won't run this > > code, and that creates a situation where many FM radio tests after this one > > might also fail. > > Hi, Malini, can we ensure that |cleanUp| runs even the test fails? In all of > my tests, I assume the FM radio is disabled before the tests run, and > disable the FM radio in |cleanUp| when the tests finished, so if we can't > ensure |cleanUp| runs, then I need to check if it's enabled or disabled > before the new test starts. I've filed Bug 916015 to track this feature.
Flags: needinfo?(mdas)
Comment on attachment 798350 [details] [diff] [review] marionette tests Review of attachment 798350 [details] [diff] [review]: ----------------------------------------------------------------- r-, but only because of the possible race in test_enable_disable.js. Other than that this looks pretty good. We should probably redesign this API at some point in the future so it's not so racy ... ::: dom/fmradio/test/marionette/test_bug862672.js @@ +26,5 @@ > + }; > + > + var enableCompleted = false; > + request.onsuccess = function() { > + of(!failedToEnable); Is this supposed to be 'ok'? @@ +37,5 @@ > + disableReq.onsuccess = function() { > + // There are two possibilities which depends on the system > + // process scheduling (bug 911063 comment 0): > + // - enable fails > + // - enable's onsuccess fires before disable's onsucess It seems like unfortunate API Design that the result here is non-deterministic, but I guess we don't need to worry about that here. ::: dom/fmradio/test/marionette/test_bug876597.js @@ +55,5 @@ > + enableFMRadioWithAirplanModeEnabled(); > + }; > + > + mozSettings.createLock().set({ > + "ril.radio.disabled": true You may as well use KEY here. @@ +72,5 @@ > +} > + > +function cleanUp() { > + let req = mozSettings.createLock().set({ > + "ril.radio.disabled": false And here. ::: dom/fmradio/test/marionette/test_enable_disable.js @@ +12,5 @@ > + ok(FMRadio); > + is(FMRadio.enabled, false); > + > + log("Verifying attributes when disabled."); > + is(FMRadio.frequency, null, "FMRadio.frequency == null"); As jlebar said, strings that duplicate the condition aren't very useful. @@ +30,5 @@ > + ok(request, "FMRadio.enable(r" + frequency + ") returns request"); > + > + request.onsuccess = function() { > + ok(FMRadio.enabled, "FMRadio.enabled"); > + ok(!isNaN(FMRadio.frequency), "FMRadio.frequency is a number"); isNaN(null) is false, so this doesn't test what you want. How about 'typeof FMRadio.frequency == "number"'? @@ +82,5 @@ > + seekRequest.onsuccess = function() { > + ok(false, "Seek request should fail after FMRadio.disable is called."); > + }; > + > + FMRadio.disable(); Why doesn't this have the same race condition? Can seek request complete before we get to call FMRadio.disable()? ::: dom/fmradio/test/marionette/test_seek_up_and_down.js @@ +45,5 @@ > + > + request.onerror = function() { > + ok(false, "Seekdown request should not fail."); > + }; > + nit: extra newline
Attachment #798350 -
Flags: review?(khuey) → review-
Assignee | ||
Comment 13•11 years ago
|
||
Attachment #798350 -
Attachment is obsolete: true
Attachment #805894 -
Flags: review?(khuey)
Comment on attachment 805894 [details] [diff] [review] Patch V2 Review of attachment 805894 [details] [diff] [review]: ----------------------------------------------------------------- ::: dom/fmradio/test/marionette/test_bug876597.js @@ +59,5 @@ > + settings[KEY] = true; > + mozSettings.createLock().set(settings); > +} > + > +function enableFMRadioWithAirplanModeEnabled() { you're missing an 'e' on the end of Airplane in this function name
Attachment #805894 -
Flags: review?(khuey) → review+
Assignee | ||
Comment 15•11 years ago
|
||
Added the missing 'e' mentioned in comment 14, r=khuey. Hi, @khuey, thanks for your help!
Attachment #805894 -
Attachment is obsolete: true
Attachment #806385 -
Flags: review+
Assignee | ||
Comment 16•11 years ago
|
||
Attachment #806385 -
Attachment is obsolete: true
Attachment #806386 -
Flags: review+
Assignee | ||
Updated•11 years ago
|
Keywords: checkin-needed
Comment 17•11 years ago
|
||
https://hg.mozilla.org/integration/b2g-inbound/rev/a156e6a7757c For the future, please use your full name in the hg commit information.
Flags: in-testsuite+
Keywords: checkin-needed
Comment 18•11 years ago
|
||
https://hg.mozilla.org/mozilla-central/rev/a156e6a7757c
Status: NEW → RESOLVED
Closed: 11 years ago
Resolution: --- → FIXED
Comment 19•11 years ago
|
||
These tests were landed but never actually enabled. Looking at the logs, indeed they are *not* running on trunk.
Status: RESOLVED → REOPENED
Flags: needinfo?(pzhang)
Resolution: FIXED → ---
Comment 20•11 years ago
|
||
Try run to see if they timeout when enabled like they do on v1.1hd. https://tbpl.mozilla.org/?tree=Try&rev=8a7ec1685530
Comment 21•11 years ago
|
||
These fail when enabled on Try the same as how they did when enabled on b2g18_v1_1_0hd. https://tbpl.mozilla.org/?tree=Try&rev=dd5034864253
Assignee | ||
Comment 22•11 years ago
|
||
These tests only work on b2g, because we don't support fm radio emulation yet, see bug 872417.
Flags: needinfo?(pzhang)
Comment 23•11 years ago
|
||
Gotcha, thanks.
Status: REOPENED → RESOLVED
Closed: 11 years ago → 11 years ago
Resolution: --- → FIXED
Comment 24•11 years ago
|
||
https://hg.mozilla.org/releases/mozilla-b2g26_v1_2/rev/8ba2e5166ed3
status-b2g18:
--- → unaffected
status-b2g-v1.1hd:
--- → unaffected
status-b2g-v1.2:
--- → fixed
Target Milestone: --- → 1.3 Sprint 1 - 9/27
You need to log in
before you can comment on or make changes to this bug.
Description
•