Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(547)

Side by Side Diff: third_party/WebKit/LayoutTests/imported/wpt/custom-elements/CustomElementRegistry.html

Issue 2376103007: Import wpt@09907a9c4bcee14986431d53e4381384c7c69107 (Closed)
Patch Set: update platform expectations Created 4 years, 2 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
(Empty)
1 <!DOCTYPE html>
2 <html>
3 <head>
4 <title>Custom Elements: CustomElementRegistry interface</title>
5 <meta name="author" title="Ryosuke Niwa" href="mailto:rniwa@webkit.org">
6 <meta name="assert" content="CustomElementRegistry interface must exist">
7 <script src="/resources/testharness.js"></script>
8 <script src="/resources/testharnessreport.js"></script>
9 </head>
10 <body>
11 <div id="log"></div>
12 <script>
13
14 test(function () {
15 assert_true('define' in CustomElementRegistry.prototype, '"define" exists on CustomElementRegistry.prototype');
16 assert_true('define' in customElements, '"define" exists on window.customEle ments');
17 }, 'CustomElementRegistry interface must have define as a method');
18
19 test(function () {
20 assert_throws({'name': 'TypeError'}, function () { customElements.define('ba dname', 1); },
21 'customElements.define must throw a TypeError when the element interface is a number');
22 assert_throws({'name': 'TypeError'}, function () { customElements.define('ba dname', '123'); },
23 'customElements.define must throw a TypeError when the element interface is a string');
24 assert_throws({'name': 'TypeError'}, function () { customElements.define('ba dname', {}); },
25 'customElements.define must throw a TypeError when the element interface is an object');
26 assert_throws({'name': 'TypeError'}, function () { customElements.define('ba dname', []); },
27 'customElements.define must throw a TypeError when the element interface is an array');
28 }, 'customElements.define must throw when the element interface is not a constru ctor');
29
30 test(function () {
31 customElements.define('custom-html-element', HTMLElement);
32 }, 'customElements.define must not throw the constructor is HTMLElement');
33
34 test(function () {
35 class MyCustomElement extends HTMLElement {};
36
37 assert_throws({'name': 'SyntaxError'}, function () { customElements.define(n ull, MyCustomElement); },
38 'customElements.define must throw a SyntaxError if the tag name is null' );
39 assert_throws({'name': 'SyntaxError'}, function () { customElements.define(' ', MyCustomElement); },
40 'customElements.define must throw a SyntaxError if the tag name is empty ');
41 assert_throws({'name': 'SyntaxError'}, function () { customElements.define(' abc', MyCustomElement); },
42 'customElements.define must throw a SyntaxError if the tag name does not contain "-"');
43 assert_throws({'name': 'SyntaxError'}, function () { customElements.define(' a-Bc', MyCustomElement); },
44 'customElements.define must throw a SyntaxError if the tag name contains an upper case letter');
45
46 var builtinTagNames = [
47 'annotation-xml',
48 'color-profile',
49 'font-face',
50 'font-face-src',
51 'font-face-uri',
52 'font-face-format',
53 'font-face-name',
54 'missing-glyph'
55 ];
56
57 for (var tagName of builtinTagNames) {
58 assert_throws({'name': 'SyntaxError'}, function () { customElements.defi ne(tagName, MyCustomElement); },
59 'customElements.define must throw a SyntaxError if the tag name is " ' + tagName + '"');
60 }
61
62 }, 'customElements.define must throw with an invalid name');
63
64 test(function () {
65 class SomeCustomElement extends HTMLElement {};
66
67 var calls = [];
68 var OtherCustomElement = new Proxy(class extends HTMLElement {}, {
69 get: function (target, name) {
70 calls.push(name);
71 return target[name];
72 }
73 })
74
75 customElements.define('some-custom-element', SomeCustomElement);
76 assert_throws({'name': 'NotSupportedError'}, function () { customElements.de fine('some-custom-element', OtherCustomElement); },
77 'customElements.define must throw a NotSupportedError if the specified t ag name is already used');
78 assert_array_equals(calls, [], 'customElements.define must validate the cust om element name before getting the prototype of the constructor');
79
80 }, 'customElements.define must throw when there is already a custom element of t he same name');
81
82 test(function () {
83 class AnotherCustomElement extends HTMLElement {};
84
85 customElements.define('another-custom-element', AnotherCustomElement);
86 assert_throws({'name': 'NotSupportedError'}, function () { customElements.de fine('some-other-element', AnotherCustomElement); },
87 'customElements.define must throw a NotSupportedError if the specified c lass already defines an element');
88
89 }, 'customElements.define must throw a NotSupportedError when there is already a custom element with the same class');
90
91 test(function () {
92 var outerCalls = [];
93 var OuterCustomElement = new Proxy(class extends HTMLElement { }, {
94 get: function (target, name) {
95 outerCalls.push(name);
96 customElements.define('inner-custom-element', InnerCustomElement);
97 return target[name];
98 }
99 });
100 var innerCalls = [];
101 var InnerCustomElement = new Proxy(class extends HTMLElement { }, {
102 get: function (target, name) {
103 outerCalls.push(name);
104 return target[name];
105 }
106 });
107
108 assert_throws({'name': 'NotSupportedError'}, function () { customElements.de fine('outer-custom-element', OuterCustomElement); },
109 'customElements.define must throw a NotSupportedError if the specified c lass already defines an element');
110 assert_array_equals(outerCalls, ['prototype'], 'customElements.define must g et "prototype"');
111 assert_array_equals(innerCalls, [],
112 'customElements.define must throw a NotSupportedError when element defin ition is running flag is set'
113 + ' before getting the prototype of the constructor');
114
115 }, 'customElements.define must throw a NotSupportedError when element definition is running flag is set');
116
117 test(function () {
118 var calls = [];
119 var ElementWithBadInnerConstructor = new Proxy(class extends HTMLElement { } , {
120 get: function (target, name) {
121 calls.push(name);
122 customElements.define('inner-custom-element', 1);
123 return target[name];
124 }
125 });
126
127 assert_throws({'name': 'TypeError'}, function () {
128 customElements.define('element-with-bad-inner-constructor', ElementWithB adInnerConstructor);
129 }, 'customElements.define must throw a NotSupportedError if IsConstructor(co nstructor) is false');
130
131 assert_array_equals(calls, ['prototype'], 'customElements.define must get "p rototype"');
132 }, 'customElements.define must check IsConstructor on the constructor before che cking the element definition is running flag');
133
134 test(function () {
135 var calls = [];
136 var ElementWithBadInnerName = new Proxy(class extends HTMLElement { }, {
137 get: function (target, name) {
138 calls.push(name);
139 customElements.define('badname', class extends HTMLElement {});
140 return target[name];
141 }
142 });
143
144 assert_throws({'name': 'SyntaxError'}, function () {
145 customElements.define('element-with-bad-inner-name', ElementWithBadInner Name);
146 }, 'customElements.define must throw a SyntaxError if the specified name is not a valid custom element name');
147
148 assert_array_equals(calls, ['prototype'], 'customElements.define must get "p rototype"');
149 }, 'customElements.define must validate the custom element name before checking the element definition is running flag');
150
151 test(function () {
152 var unresolvedElement = document.createElement('constructor-calls-define');
153 document.body.appendChild(unresolvedElement);
154 var elementUpgradedDuringUpgrade = document.createElement('defined-during-up grade');
155 document.body.appendChild(elementUpgradedDuringUpgrade);
156
157 var DefinedDuringUpgrade = class extends HTMLElement { };
158
159 class ConstructorCallsDefine extends HTMLElement {
160 constructor() {
161 customElements.define('defined-during-upgrade', DefinedDuringUpgrade );
162 assert_false(unresolvedElement instanceof ConstructorCallsDefine);
163 assert_true(elementUpgradedDuringUpgrade instanceof DefinedDuringUpg rade);
164 super();
165 assert_true(unresolvedElement instanceof ConstructorCallsDefine);
166 assert_true(elementUpgradedDuringUpgrade instanceof DefinedDuringUpg rade);
167 }
168 }
169
170 assert_false(unresolvedElement instanceof ConstructorCallsDefine);
171 assert_false(elementUpgradedDuringUpgrade instanceof DefinedDuringUpgrade);
172
173 customElements.define('constructor-calls-define', ConstructorCallsDefine);
174 }, 'customElements.define unset the element definition is running flag before up grading custom elements');
175
176 (function () {
177 var testCase = async_test('customElements.define must not throw'
178 +' when defining another custom element in a different global object dur ing Get(constructor, "prototype")', {timeout: 100});
179
180 var iframe = document.createElement('iframe');
181 iframe.onload = function () {
182 testCase.step(function () {
183 var InnerCustomElement = class extends iframe.contentWindow.HTMLElem ent {};
184 var calls = [];
185 var proxy = new Proxy(class extends HTMLElement { }, {
186 get: function (target, name) {
187 calls.push(name);
188 iframe.contentWindow.customElements.define('another-custom-e lement', InnerCustomElement);
189 return target[name];
190 }
191 })
192 customElements.define('element-with-inner-element-define', proxy);
193 assert_array_equals(calls, ['prototype'], 'customElements.define mus t get "prototype"');
194 assert_true(iframe.contentDocument.createElement('another-custom-ele ment') instanceof InnerCustomElement);
195 });
196 document.body.removeChild(iframe);
197 testCase.done();
198 }
199
200 document.body.appendChild(iframe);
201 })();
202
203 test(function () {
204 var calls = [];
205 var ElementWithBadInnerName = new Proxy(class extends HTMLElement { }, {
206 get: function (target, name) {
207 calls.push(name);
208 customElements.define('badname', class extends HTMLElement {});
209 return target[name];
210 }
211 });
212
213 assert_throws({'name': 'SyntaxError'}, function () {
214 customElements.define('element-with-bad-inner-name', ElementWithBadInner Name);
215 }, 'customElements.define must throw a SyntaxError if the specified name is not a valid custom element name');
216
217 assert_array_equals(calls, ['prototype'], 'customElements.define must get "p rototype"');
218 }, '');
219
220 test(function () {
221 var calls = [];
222 var proxy = new Proxy(class extends HTMLElement { }, {
223 get: function (target, name) {
224 calls.push(name);
225 return target[name];
226 }
227 });
228 customElements.define('proxy-element', proxy);
229 assert_array_equals(calls, ['prototype']);
230 }, 'customElements.define must get "prototype" property of the constructor');
231
232 test(function () {
233 var proxy = new Proxy(class extends HTMLElement { }, {
234 get: function (target, name) {
235 throw {name: 'expectedError'};
236 }
237 });
238 assert_throws({'name': 'expectedError'}, function () { customElements.define ('element-with-string-prototype', proxy); });
239 }, 'customElements.define must rethrow an exception thrown while getting "protot ype" property of the constructor');
240
241 test(function () {
242 var returnedValue;
243 var proxy = new Proxy(class extends HTMLElement { }, {
244 get: function (target, name) { return returnedValue; }
245 });
246
247 returnedValue = null;
248 assert_throws({'name': 'TypeError'}, function () { customElements.define('el ement-with-string-prototype', proxy); },
249 'customElements.define must throw when "prototype" property of the const ructor is null');
250 returnedValue = undefined;
251 assert_throws({'name': 'TypeError'}, function () { customElements.define('el ement-with-string-prototype', proxy); },
252 'customElements.define must throw when "prototype" property of the const ructor is undefined');
253 returnedValue = 'hello';
254 assert_throws({'name': 'TypeError'}, function () { customElements.define('el ement-with-string-prototype', proxy); },
255 'customElements.define must throw when "prototype" property of the const ructor is a string');
256 returnedValue = 1;
257 assert_throws({'name': 'TypeError'}, function () { customElements.define('el ement-with-string-prototype', proxy); },
258 'customElements.define must throw when "prototype" property of the const ructor is a number');
259
260 }, 'customElements.define must throw when "prototype" property of the constructo r is not an object');
261
262 test(function () {
263 var constructor = function () {}
264 var calls = [];
265 constructor.prototype = new Proxy(constructor.prototype, {
266 get: function (target, name) {
267 calls.push(name);
268 return target[name];
269 }
270 });
271 customElements.define('element-with-proxy-prototype', constructor);
272 assert_array_equals(calls, ['connectedCallback', 'disconnectedCallback', 'ad optedCallback', 'attributeChangedCallback']);
273 }, 'customElements.define must get callbacks of the constructor prototype');
274
275 test(function () {
276 var constructor = function () {}
277 var calls = [];
278 constructor.prototype = new Proxy(constructor.prototype, {
279 get: function (target, name) {
280 calls.push(name);
281 if (name == 'disconnectedCallback')
282 throw {name: 'expectedError'};
283 return target[name];
284 }
285 });
286 assert_throws({'name': 'expectedError'}, function () { customElements.define ('element-with-throwing-callback', constructor); });
287 assert_array_equals(calls, ['connectedCallback', 'disconnectedCallback'],
288 'customElements.define must not get callbacks after one of the get throw s');
289 }, 'customElements.define must rethrow an exception thrown while getting callbac ks on the constructor prototype');
290
291 test(function () {
292 var constructor = function () {}
293 var calls = [];
294 constructor.prototype = new Proxy(constructor.prototype, {
295 get: function (target, name) {
296 calls.push(name);
297 if (name == 'adoptedCallback')
298 return 1;
299 return target[name];
300 }
301 });
302 assert_throws({'name': 'TypeError'}, function () { customElements.define('el ement-with-throwing-callback', constructor); });
303 assert_array_equals(calls, ['connectedCallback', 'disconnectedCallback', 'ad optedCallback'],
304 'customElements.define must not get callbacks after one of the conversio n throws');
305 }, 'customElements.define must rethrow an exception thrown while converting a ca llback value to Function callback type');
306
307 test(function () {
308 var constructor = function () {}
309 constructor.prototype.attributeChangedCallback = function () { };
310 var prototypeCalls = [];
311 var callOrder = 0;
312 constructor.prototype = new Proxy(constructor.prototype, {
313 get: function (target, name) {
314 if (name == 'prototype' || name == 'observedAttributes')
315 throw 'Unexpected access to observedAttributes';
316 prototypeCalls.push(callOrder++);
317 prototypeCalls.push(name);
318 return target[name];
319 }
320 });
321 var constructorCalls = [];
322 var proxy = new Proxy(constructor, {
323 get: function (target, name) {
324 constructorCalls.push(callOrder++);
325 constructorCalls.push(name);
326 return target[name];
327 }
328 });
329 customElements.define('element-with-attribute-changed-callback', proxy);
330 assert_array_equals(prototypeCalls, [1, 'connectedCallback', 2, 'disconnecte dCallback', 3, 'adoptedCallback', 4, 'attributeChangedCallback']);
331 assert_array_equals(constructorCalls, [0, 'prototype', 5, 'observedAttribute s']);
332 }, 'customElements.define must get "observedAttributes" property on the construc tor prototype when "attributeChangedCallback" is present');
333
334 test(function () {
335 var constructor = function () {}
336 constructor.prototype.attributeChangedCallback = function () { };
337 var calls = [];
338 var proxy = new Proxy(constructor, {
339 get: function (target, name) {
340 calls.push(name);
341 if (name == 'observedAttributes')
342 throw {name: 'expectedError'};
343 return target[name];
344 }
345 });
346 assert_throws({'name': 'expectedError'}, function () { customElements.define ('element-with-throwing-observed-attributes', proxy); });
347 assert_array_equals(calls, ['prototype', 'observedAttributes'],
348 'customElements.define must get "prototype" and "observedAttributes" on the constructor');
349 }, 'customElements.define must rethrow an exception thrown while getting observe dAttributes on the constructor prototype');
350
351 test(function () {
352 var constructor = function () {}
353 constructor.prototype.attributeChangedCallback = function () { };
354 var calls = [];
355 var proxy = new Proxy(constructor, {
356 get: function (target, name) {
357 calls.push(name);
358 if (name == 'observedAttributes')
359 return 1;
360 return target[name];
361 }
362 });
363 assert_throws({'name': 'TypeError'}, function () { customElements.define('el ement-with-invalid-observed-attributes', proxy); });
364 assert_array_equals(calls, ['prototype', 'observedAttributes'],
365 'customElements.define must get "prototype" and "observedAttributes" on the constructor');
366 }, 'customElements.define must rethrow an exception thrown while converting the value of observedAttributes to sequence<DOMString>');
367
368 test(function () {
369 var constructor = function () {}
370 constructor.prototype.attributeChangedCallback = function () { };
371 constructor.observedAttributes = {[Symbol.iterator]: function *() {
372 yield 'foo';
373 throw {name: 'SomeError'};
374 }};
375 assert_throws({'name': 'SomeError'}, function () { customElements.define('el ement-with-generator-observed-attributes', constructor); });
376 }, 'customElements.define must rethrow an exception thrown while iterating over observedAttributes to sequence<DOMString>');
377
378 test(function () {
379 var constructor = function () {}
380 constructor.prototype.attributeChangedCallback = function () { };
381 constructor.observedAttributes = {[Symbol.iterator]: 1};
382 assert_throws({'name': 'TypeError'}, function () { customElements.define('el ement-with-observed-attributes-with-uncallable-iterator', constructor); });
383 }, 'customElements.define must rethrow an exception thrown while retrieving Symb ol.iterator on observedAttributes');
384
385 test(function () {
386 var constructor = function () {}
387 constructor.observedAttributes = 1;
388 customElements.define('element-without-callback-with-invalid-observed-attrib utes', constructor);
389 }, 'customElements.define must not throw even if "observedAttributes" fails to c onvert if "attributeChangedCallback" is not defined');
390
391 test(function () {
392 class MyCustomElement extends HTMLElement {};
393 customElements.define('my-custom-element', MyCustomElement);
394
395 var instance = new MyCustomElement;
396 assert_true(instance instanceof MyCustomElement,
397 'An instance of a custom HTML element be an instance of the associated i nterface');
398
399 assert_true(instance instanceof HTMLElement,
400 'An instance of a custom HTML element must inherit from HTMLElement');
401
402 assert_equals(instance.localName, 'my-custom-element',
403 'An instance of a custom element must use the associated tag name');
404
405 assert_equals(instance.namespaceURI, 'http://www.w3.org/1999/xhtml',
406 'A custom element HTML must use HTML namespace');
407
408 }, 'customElements.define must define an instantiatable custom element');
409
410 test(function () {
411 var disconnectedElement = document.createElement('some-custom');
412 var connectedElementBeforeShadowHost = document.createElement('some-custom') ;
413 var connectedElementAfterShadowHost = document.createElement('some-custom');
414 var elementInShadowTree = document.createElement('some-custom');
415 var childElementOfShadowHost = document.createElement('some-custom');
416 var customShadowHost = document.createElement('some-custom');
417 var elementInNestedShadowTree = document.createElement('some-custom');
418
419 var container = document.createElement('div');
420 var shadowHost = document.createElement('div');
421 var shadowRoot = shadowHost.attachShadow({mode: 'closed'});
422 container.appendChild(connectedElementBeforeShadowHost);
423 container.appendChild(shadowHost);
424 container.appendChild(connectedElementAfterShadowHost);
425 shadowHost.appendChild(childElementOfShadowHost);
426 shadowRoot.appendChild(elementInShadowTree);
427 shadowRoot.appendChild(customShadowHost);
428
429 var innerShadowRoot = customShadowHost.attachShadow({mode: 'closed'});
430 innerShadowRoot.appendChild(elementInNestedShadowTree);
431
432 var calls = [];
433 class SomeCustomElement extends HTMLElement {
434 constructor() {
435 super();
436 calls.push(this);
437 }
438 };
439
440 document.body.appendChild(container);
441 customElements.define('some-custom', SomeCustomElement);
442 assert_array_equals(calls, [connectedElementBeforeShadowHost, elementInShado wTree, customShadowHost, elementInNestedShadowTree, childElementOfShadowHost, co nnectedElementAfterShadowHost]);
443 }, 'customElements.define must upgrade elements in the shadow-including tree ord er');
444
445 test(function () {
446 assert_true('get' in CustomElementRegistry.prototype, '"get" exists on Custo mElementRegistry.prototype');
447 assert_true('get' in customElements, '"get" exists on window.customElements' );
448 }, 'CustomElementRegistry interface must have get as a method');
449
450 test(function () {
451 assert_equals(customElements.get('a-b'), undefined);
452 }, 'customElements.get must return undefined when the registry does not contain an entry with the given name');
453
454 test(function () {
455 assert_equals(customElements.get('html'), undefined);
456 assert_equals(customElements.get('span'), undefined);
457 assert_equals(customElements.get('div'), undefined);
458 assert_equals(customElements.get('g'), undefined);
459 assert_equals(customElements.get('ab'), undefined);
460 }, 'customElements.get must return undefined when the registry does not contain an entry with the given name even if the name was not a valid custom element nam e');
461
462 test(function () {
463 assert_equals(customElements.get('existing-custom-element'), undefined);
464 class ExistingCustomElement extends HTMLElement {};
465 customElements.define('existing-custom-element', ExistingCustomElement);
466 assert_equals(customElements.get('existing-custom-element'), ExistingCustomE lement);
467 }, 'customElements.get return the constructor of the entry with the given name w hen there is a matching entry.');
468
469 test(function () {
470 assert_true(customElements.whenDefined('some-name') instanceof Promise);
471 }, 'customElements.whenDefined must return a promise for a valid custom element name');
472
473 test(function () {
474 assert_equals(customElements.whenDefined('some-name'), customElements.whenDe fined('some-name'));
475 }, 'customElements.whenDefined must return the same promise each time invoked fo r a valid custom element name which has not been defined');
476
477 promise_test(function () {
478 var resolved = false;
479 var rejected = false;
480 customElements.whenDefined('a-b').then(function () { resolved = true; }, fun ction () { rejected = true; });
481 return Promise.resolve().then(function () {
482 assert_false(resolved, 'The promise returned by "whenDefined" must not b e resolved until a custom element is defined');
483 assert_false(rejected, 'The promise returned by "whenDefined" must not b e rejected until a custom element is defined');
484 });
485 }, 'customElements.whenDefined must return an unresolved promise when the regist ry does not contain the entry with the given name')
486
487 promise_test(function () {
488 var promise = customElements.whenDefined('badname');
489 promise.then(function (value) { promise.resolved = value; }, function (value ) { promise.rejected = value; });
490
491 assert_false('resolved' in promise, 'The promise returned by "whenDefined" m ust not be resolved until the end of the next microtask');
492 assert_false('rejected' in promise, 'The promise returned by "whenDefined" m ust not be rejected until the end of the next microtask');
493
494 return Promise.resolve().then(function () {
495 assert_false('resolved' in promise, 'The promise returned by "whenDefine d" must be resolved when a custom element is defined');
496 assert_true('rejected' in promise, 'The promise returned by "whenDefined " must not be rejected when a custom element is defined');
497 });
498 }, 'customElements.whenDefined must return a rejected promise when the given nam e is not a valid custom element name');
499
500 promise_test(function () {
501 customElements.define('preexisting-custom-element', class extends HTMLElemen t { });
502
503 var promise = customElements.whenDefined('preexisting-custom-element');
504 promise.then(function (value) { promise.resolved = value; }, function (value ) { promise.rejected = value; });
505
506 assert_false('resolved' in promise, 'The promise returned by "whenDefined" m ust not be resolved until the end of the next microtask');
507 assert_false('rejected' in promise, 'The promise returned by "whenDefined" m ust not be rejected until the end of the next microtask');
508
509 return Promise.resolve().then(function () {
510 assert_true('resolved' in promise, 'The promise returned by "whenDefined " must be resolved when a custom element is defined');
511 assert_equals(promise.resolved, undefined,
512 'The promise returned by "whenDefined" must be resolved with "undefi ned" when a custom element is defined');
513 assert_false('rejected' in promise, 'The promise returned by "whenDefine d" must not be rejected when a custom element is defined');
514 });
515 }, 'customElements.whenDefined must return a resolved promise when the registry contains the entry with the given name');
516
517 promise_test(function () {
518 class AnotherExistingCustomElement extends HTMLElement {};
519 customElements.define('another-existing-custom-element', AnotherExistingCust omElement);
520
521 var promise1 = customElements.whenDefined('another-existing-custom-element') ;
522 var promise2 = customElements.whenDefined('another-existing-custom-element') ;
523 promise1.then(function (value) { promise1.resolved = value; }, function (val ue) { promise1.rejected = value; });
524 promise2.then(function (value) { promise2.resolved = value; }, function (val ue) { promise2.rejected = value; });
525
526 assert_not_equals(promise1, promise2);
527 assert_false('resolved' in promise1, 'The promise returned by "whenDefined" must not be resolved until the end of the next microtask');
528 assert_false('resolved' in promise2, 'The promise returned by "whenDefined" must not be resolved until the end of the next microtask');
529 assert_false('rejected' in promise1, 'The promise returned by "whenDefined" must not be rejected until the end of the next microtask');
530 assert_false('rejected' in promise2, 'The promise returned by "whenDefined" must not be rejected until the end of the next microtask');
531
532 return Promise.resolve().then(function () {
533 assert_true('resolved' in promise1, 'The promise returned by "whenDefine d" must be resolved when a custom element is defined');
534 assert_equals(promise1.resolved, undefined, 'The promise returned by "wh enDefined" must be resolved with "undefined" when a custom element is defined');
535 assert_false('rejected' in promise1, 'The promise returned by "whenDefin ed" must not be rejected when a custom element is defined');
536
537 assert_true('resolved' in promise2, 'The promise returned by "whenDefine d" must be resolved when a custom element is defined');
538 assert_equals(promise2.resolved, undefined, 'The promise returned by "wh enDefined" must be resolved with "undefined" when a custom element is defined');
539 assert_false('rejected' in promise2, 'The promise returned by "whenDefin ed" must not be rejected when a custom element is defined');
540 });
541 }, 'customElements.whenDefined must return a new resolved promise each time invo ked when the registry contains the entry with the given name');
542
543 promise_test(function () {
544 var promise = customElements.whenDefined('element-defined-after-whendefined' );
545 promise.then(function (value) { promise.resolved = value; }, function (value ) { promise.rejected = value; });
546
547 assert_false('resolved' in promise, 'The promise returned by "whenDefined" m ust not be resolved until the end of the next microtask');
548 assert_false('rejected' in promise, 'The promise returned by "whenDefined" m ust not be rejected until the end of the next microtask');
549
550 var promiseAfterDefine;
551 return Promise.resolve().then(function () {
552 assert_false('resolved' in promise, 'The promise returned by "whenDefine d" must not be resolved until the element is defined');
553 assert_false('rejected' in promise, 'The promise returned by "whenDefine d" must not be rejected until the element is defined');
554 assert_equals(customElements.whenDefined('element-defined-after-whendefi ned'), promise,
555 '"whenDefined" must return the same unresolved promise before the cu stom element is defined');
556 customElements.define('element-defined-after-whendefined', class extends HTMLElement { });
557 assert_false('resolved' in promise, 'The promise returned by "whenDefine d" must not be resolved until the end of the next microtask');
558 assert_false('rejected' in promise, 'The promise returned by "whenDefine d" must not be rejected until the end of the next microtask');
559
560 promiseAfterDefine = customElements.whenDefined('element-defined-after-w hendefined');
561 promiseAfterDefine.then(function (value) { promiseAfterDefine.resolved = value; }, function (value) { promiseAfterDefine.rejected = value; });
562 assert_not_equals(promiseAfterDefine, promise, '"whenDefined" must retur n a resolved promise once the custom element is defined');
563 assert_false('resolved' in promiseAfterDefine, 'The promise returned by "whenDefined" must not be resolved until the end of the next microtask');
564 assert_false('rejected' in promiseAfterDefine, 'The promise returned by "whenDefined" must not be rejected until the end of the next microtask');
565 }).then(function () {
566 assert_true('resolved' in promise, 'The promise returned by "whenDefined " must be resolved when a custom element is defined');
567 assert_equals(promise.resolved, undefined,
568 'The promise returned by "whenDefined" must be resolved with "undefi ned" when a custom element is defined');
569 assert_false('rejected' in promise, 'The promise returned by "whenDefine d" must not be rejected when a custom element is defined');
570
571 assert_true('resolved' in promiseAfterDefine, 'The promise returned by " whenDefined" must be resolved when a custom element is defined');
572 assert_equals(promiseAfterDefine.resolved, undefined,
573 'The promise returned by "whenDefined" must be resolved with "undefi ned" when a custom element is defined');
574 assert_false('rejected' in promiseAfterDefine, 'The promise returned by "whenDefined" must not be rejected when a custom element is defined');
575 });
576 }, 'A promise returned by customElements.whenDefined must be resolved by "define "');
577
578 </script>
579 </body>
580 </html>
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698