Comments (16)
I originally got involved because...
Your involvement has been greatly appreciated, and I'm sure I speak not only for myself but also the other stakeholders @domenic @allenwb. It's a huge step forward. Thank you!
What do you want with this PR?
I haven't had a chance to review the current state of the tests, but I still plan to take a look soon. From what I recall as todo's (you may have already addressed some or all of these):
-
Check to make sure that the only tests in there are tests of the
Promise(..)
,Promise.race(..)
,Promise.all(..)
,Promise.resolve(..)
andPromise.reject(..)
APIs.Any other tests which are testing conditions of a promise instance's behavior itself, such as
then(..)
, are strictly unnecessary as that would be duplicative work of the Promises/A+ test suite. We need to remove any of those tests. -
Separate the test suite that we do have into two "layers" as I was calling them:
- Layer 1 is purely the tests of behavior that is exposable, and thus testable, in ES5. This is the stuff that's reasonable to test against polyfills like NPO. It's important to note that this layer will come close to ES6 spec compliance in many ways, but it's not strictly ES6 compliant (as it can't be). We probably need to figure out what to name it and call it so that it's not misleading/confusing about that nuance. Needs more thought.
- Layer 2 is an optional set of additional tests that when combined with Layer 1 does attain full ES6 compliance. This full ES6 compliance is reasonable to test in ES6 compliant environments against, for example, the built-in
Promise
. This test suite layer must include testing ES6'isms likePromise[@@create]
,Promise.prototype
, ES6 sub-classing, etc.
For the most cross-library usefulness, I think Layer 1 and Layer 2 need to be separately submitted to the promise-unwrapping repo, at least in such a way that someone can easily choose to run only Layer 1 or run both.
The combination of both layers is the test-suite that will eventually be submitted to Test-262, but that's actually something the promise-unwrapping repo should drive IMO, so we don't need to worry about that detail.
from native-promise-only.
I can make the three constructor tests pass by adding a little bit of logic to the beginning of function Promise()
I'm still holding off on making the change to NPO to get those constructor checks to pass. To me it's still an open question exactly what checks should be in Layer 1 vs. Layer 2, and I only care about making NPO pass Layer 1, obviously.
I have a strong feeling from that previous thread, but I don't think we had any final consensus, so please everyone double check me here if I'm missing anything:
-
Testing the constructor for whether the
this
is a "real" promise should not be based onthis instanceof Promise
checks, that much was clear. IOW, the check has to rely on some sort of branding, because there's just no other way to do it. -
As for NPO's implementation specifically, one brand (with different shadowed values) can support two of the test cases with just one
if
statement:- on
Promise.prototype
, we need an.__npo__
brand, with value"uninitialized"
, which enables this assertion:Promise.call( {}, ..); // should throw
. IOW,this.__npo__ === "uninitialized"
has to pass. - on each promise instance, we need to shadow that brand by setting
this.__npo__
to"initialized"
, which enables this assertion:Promise.call( new Promise(..), .. ); // should throw
. IOW,this.__npo__ === "uninitialized"
still has to pass. Same internal check, enables two different assertions in two different tests.
- on
-
I think the conclusion was there's no practical way in the ES5 Layer 1 tests to check and enforce this third assertion:
Promise.call( Object.create(Promise.prototype), .. ); // should throw
.That test thus has to be moved to Layer 2, and needs to be checked in conjunction with testing
Promise[@@create]
. IOW,Promise.call( Promise[Symbol.create](), .. )
has to pass, and anything else you pass in has to fail.
If we can reach any kind of agreement on these observations, then I will patch NPO with the same.
from native-promise-only.
I like the Layer 1 / Layer 2 framing, and to be honest I think we could even do with more granularity.
I have already grouped the tests by section of the spec. I could also separate them into layers (essentially all the tests written so far are layer 1 tests, because I am able to make them all pass using ES5 alone).
Even tests I have not yet implemented -- for example tests on the Promise prototype object (25.4.5) -- are in some sense Layer 1 in that a conforming polyfill could implement them in ES5.
Eventually it would be possible to use the test suite to make a claim like "X implementation passes Layer 1 tests for 25.4.3 (Promises), 25.4.4 (Promise object static functions), but NOT 25.4.5 (Promise prototype object static functions)"
from native-promise-only.
I think Layer 1 should be only the minimum required stuff for ES5. Prototypes and sub-classing are, IMO, inappropriate, as they cannot be implemented in ES5 while maintaining the spirit of external state immutability. As such, those tests belong to a Layer 2 test only.
I'm not sure I see why we need to have more granularity than that other than for trivia purposes, but I wouldn't object to it if there was a clean way to do it.
I just want to make sure there's a simple "layer 1" (or collection of "layer 1 sections") that fully exercises an ES5-only Promise implementation (sans sub-classing, sans Symbol.create
, etc), and another layer or layer-collection for "everything else" which is for purely ES6 compliance and is appropriate only for ES6-only implementations (native or self-hosted).
I think it's quite possible, though I'm not sure off the top of my head, that grouping the tests by spec section number might not be adequate because there could be parts of some X.Y.Z spec section which are ES5 implementable and parts which can only be implemented/tested in ES6.
from native-promise-only.
I think it's quite possible, though I'm not sure off the top of my head, that grouping the tests by spec section number might not be adequate because there could be parts of some X.Y.Z spec section which are ES5 implementable and parts which can only be implemented/tested in ES6.
They're independent dimensions. As I said, so far I've only implemented tests on ES5-visible functionality, across all the spec sections (25.4.3 - 25.4.5). At a later point, it would be possible to add essentially a whole second directory worth of tests, again organized by section, that hit the ES6-visible things like Symbol.create
.
from native-promise-only.
I will trust your lead on that since you are much deeper in those details at the moment. If you think that's the right way to organize, it certainly matches how the Promises/A+ test suite is organized, so it makes sense.
Let's just make sure there isn't any limitation that makes it hard for a given library to pick out the tests that are applicable to its implementation.
from native-promise-only.
The combination of both layers is the test-suite that will eventually be submitted to Test-262, but that's actually something the promise-unwrapping repo should drive IMO, so we don't need to worry about that detail.
Actually in order to incorporate these into Test232 anyone who has contributed to these tests needs to go through the process of registering as a non-member TC39 contributor. http://www.ecma-international.org/memento/contribute_TC39_Royalty_Free_Task_Group.php . In addition to the on-line form on that page you need to fill in and sign the contributor software copyright license http://www.ecma-international.org/memento/TC39%20exhibit%20B.pdf
from native-promise-only.
@allenwb That's interesting. I didn't realize that our draft work here would require such coverage, since we don't intend to officially submit to TC39/Test262 directly, but rather submit to @domenic's efforts (who I presume is already covered) for his consideration.
I for one have no problem signing such an agreement, since I'm independent. I will have to leave it to @smikes to decide himself how that impacts his participation.
Thanks for clarifying what we need to think about.
from native-promise-only.
@getify Unless somebody else is paying for the work (or the author is otherwise contractually encumbered), the original author of any material is the copyright owner. For @domenic (really Google, now) to contribute you work to Ecma you would first have to license and/or transfer you copyright interest to them. Who knows what the process for that might me.
The easiest path is for everybody who is authoring tests to register as a TC39 contributor.
from native-promise-only.
I wrote the tests and I am happy to sign those agreements, and I can
definitely get employer approval.
If that would be useful to contribute towards test-262. I have not yet
looked at the test-262 repository to see how compatible the test frameworks
are.
from native-promise-only.
- CLA - I have done the online portion and have completed the written portion, ready to go in tomorrow's mail.
- I have now installed and tested against node 0.11 (which includes a version of v8 that implements Promise with known problems.) This test shows two failed assertions which are due to errors in my tests. I will fix those errors and commit a change to this branch.
from native-promise-only.
@allenwb I looked at the Test262 code and there are two problems, neither insurmountable, with adding what I have:
-
Test262 does not currently seem to have any asynchronous tests. Although many of the tests I have written can be run synchronously (static tests and claims about the presence or arity of particular functions), some tests do require asynchrony. Someone more familiar with test262 should choose a framework for async tests.
-
I am not familiar enough with ES6 to write idiomatic ES6 tests. Notably, when using node 0.11.13 (a recent development version of Google's v8) attempting to instantiate a promise "manually" via
Promise.call(Object.create(Promise.prototype), function () {})
throws the remarkable errorTypeError: #<Promise> is not a promise
1) 25.4.3 The Promise Constructor can be called as a function: TypeError: #<Promise> is not a promise at Z:\Code\github\native-promise-only\test\tests\constructor.js:17:14 at Function._throws (assert.js:293:5) at Function.assert.doesNotThrow (assert.js:324:11) at Context.<anonymous> (Z:\Code\github\native-promise-only\test\tests\constructor.js:16:9) at callFn (Z:\Code\github\native-promise-only\node_modules\mocha\lib\runnable.js:223:21) at Test.Runnable.run (Z:\Code\github\native-promise-only\node_modules\mocha\lib\runnable.js:216:7) at Runner.runTest (Z:\Code\github\native-promise-only\node_modules\mocha\lib\runner.js:373:10) at Z:\Code\github\native-promise-only\node_modules\mocha\lib\runner.js:451:12 at next (Z:\Code\github\native-promise-only\node_modules\mocha\lib\runner.js:298:14) at Z:\Code\github\native-promise-only\node_modules\mocha\lib\runner.js:308:7
I believe that I am seeing this because Object.create() is not the correct ES6 way to call Promise[ @@create ]()
, but I am also not sure what the correct way is -- besides of course new Promise()
from native-promise-only.
I believe that I am seeing this because Object.create() is not the correct ES6 way to call Promise @@create , but I am also not sure what the correct way is -- besides of course new Promise()
Correct, Object.create(..)
is very different from @@create
.
In a conforming ES6 implementation (dunno if v8 in node 0.11.x is or not in this respect), IIUC, you would call it like this:
Promise.call( Promise[Symbol.create](), .. );
from native-promise-only.
It appears that the version of v8 currently shipping in node 0.11.13 does not handle that part of ES6 yet, then:
> Symbol.create
TypeError: Object.keys called on non-object
at Function.keys (native)
at formatValue (util.js:235:21)
at Object.inspect (util.js:147:10)
at REPLServer.self.writer (repl.js:209:19)
at finish (repl.js:316:38)
at REPLServer.defaultEval (repl.js:145:5)
at bound (domain.js:257:14)
at REPLServer.runBound [as eval] (domain.js:270:12)
at REPLServer.<anonymous> (repl.js:277:12)
at REPLServer.EventEmitter.emit (events.js:107:17)
from native-promise-only.
With that test removed, I now have a suite of tests which passes on v8 promises -- as long as I do not include the promises/A+ tests, which are known to fail on node 0.11.13 because of bugs in the Promise implementation that is included.
In particular, the three constructor tests from 25.4.3.1 are all satisfied by v8 Promise:
- throws TypeError when 'this' is not of type Object
- throws TypeError if 'this' is a constructed by unresolved Promise
- throws TypeError if 'this' is a resolved Promise
Tomorrow if I have some time I will try to run against the Mozilla implementation of ES6 Promises.
from native-promise-only.
@smikes There is an on-going discussion about Test262 async tests, see tc39/test262#34
In general, you should coordinate with @bterlson on Test262 issues.
from native-promise-only.
Related Issues (20)
- browsers support information HOT 7
- Cross-Browser Support & Tests HOT 3
- Support IE8 HOT 5
- What is correct execution sequence when attach multiple handlers to the same promise. HOT 8
- Better native support detection? HOT 3
- Create tag for v0.7.6-a HOT 1
- Android 4.0 issue HOT 17
- AMD? HOT 19
- handling uncaught exceptions HOT 5
- Promise.resolve(1) throws on Android 4.0 HOT 1
- `resolve(..)` should call a thenable's `then(..)` async, not sync. HOT 5
- Unhandled rejection detection HOT 9
- Suggestion: make Promise.prototype aliases of `then` and `catch` HOT 5
- Error when running through babel compiler HOT 5
- Module with unminified code should be exported by default
- on nodejs, exceptions are not shown. HOT 4
- Microtasks? HOT 1
- Ponyfill support? HOT 1
- Missing tag for version 0.7.8-a used by jQuery HOT 7
- Promise finally not supported HOT 1
Recommend Projects
-
React
A declarative, efficient, and flexible JavaScript library for building user interfaces.
-
Vue.js
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
-
Typescript
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
-
TensorFlow
An Open Source Machine Learning Framework for Everyone
-
Django
The Web framework for perfectionists with deadlines.
-
Laravel
A PHP framework for web artisans
-
D3
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
-
Recommend Topics
-
javascript
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
-
web
Some thing interesting about web. New door for the world.
-
server
A server is a program made to process requests and deliver data to clients.
-
Machine learning
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
-
Visualization
Some thing interesting about visualization, use data art
-
Game
Some thing interesting about game, make everyone happy.
Recommend Org
-
Facebook
We are working to build community through open source technology. NB: members must have two-factor auth.
-
Microsoft
Open source projects and samples from Microsoft.
-
Google
Google ❤️ Open Source for everyone.
-
Alibaba
Alibaba Open Source for everyone
-
D3
Data-Driven Documents codes.
-
Tencent
China tencent open source team.
from native-promise-only.