Changeset 204551 in webkit
- Timestamp:
- Aug 16, 2016 8:17:04 PM (8 years ago)
- Location:
- trunk
- Files:
-
- 2 added
- 2 deleted
- 12 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/LayoutTests/ChangeLog
r204543 r204551 1 2016-08-16 Commit Queue <commit-queue@webkit.org> 2 3 Unreviewed, rolling out r204540, r204545, and r204547. 4 https://bugs.webkit.org/show_bug.cgi?id=160932 5 6 Broke Windows builds (Requested by rniwa on #webkit). 7 8 Reverted changesets: 9 10 "customElements.define should retrieve lifecycle callbacks" 11 https://bugs.webkit.org/show_bug.cgi?id=160797 12 http://trac.webkit.org/changeset/204540 13 14 "Windows build fix attempt after r204540." 15 http://trac.webkit.org/changeset/204545 16 17 "Another Windows build fix attempt. The error message doesn't 18 make any sense to me." 19 http://trac.webkit.org/changeset/204547 20 1 21 2016-08-16 Chris Dumez <cdumez@apple.com> 2 22 -
trunk/LayoutTests/fast/custom-elements/attribute-changed-callback-expected.txt
r204540 r204551 4 4 PASS setAttributeNode and removeAttributeNS must enqueue and invoke attributeChangedCallback 5 5 PASS setAttributeNode and removeAttributeNS must enqueue and invoke attributeChangedCallback 6 PASS Mutating attributeChangedCallback after calling customElements.define must not affect the callback being invoked7 PASS attributedChangedCallback must not be invoked when the observed attributes does not contain the attribute.8 PASS Mutating observedAttributes after calling customElements.define must not affect the set of attributes for which attributedChangedCallback is invoked9 PASS attributedChangedCallback must be enqueued for attributes specified in a non-Array iterable observedAttributes10 6 -
trunk/LayoutTests/fast/custom-elements/attribute-changed-callback.html
r204540 r204551 20 20 } 21 21 } 22 MyCustomElement.observedAttributes = ['title', 'id', 'r'];23 22 customElements.define('my-custom-element', MyCustomElement); 24 23 … … 98 97 assert_equals(argumentList[1].value, null); 99 98 assert_array_equals(argumentList[1].arguments, ['r', '100', null, 'http://www.w3.org/2000/svg']); 99 100 100 }, 'setAttributeNode and removeAttributeNS must enqueue and invoke attributeChangedCallback'); 101 102 test(function () {103 var callsToOld = [];104 var callsToNew = [];105 class CustomElement extends HTMLElement { }106 CustomElement.prototype.attributeChangedCallback = function () {107 callsToOld.push(Array.from(arguments));108 }109 CustomElement.observedAttributes = ['title'];110 customElements.define('element-with-mutated-attribute-changed-callback', CustomElement);111 CustomElement.prototype.attributeChangedCallback = function () {112 callsToNew.push(Array.from(arguments));113 }114 115 var instance = document.createElement('element-with-mutated-attribute-changed-callback');116 instance.setAttribute('title', 'hi');117 assert_equals(instance.getAttribute('title'), 'hi');118 assert_array_equals(callsToNew, []);119 assert_equals(callsToOld.length, 1);120 assert_array_equals(callsToOld[0], ['title', null, 'hi', null]);121 }, 'Mutating attributeChangedCallback after calling customElements.define must not affect the callback being invoked');122 123 test(function () {124 var calls = [];125 class CustomElement extends HTMLElement {126 attributeChangedCallback() {127 calls.push(Array.from(arguments));128 }129 }130 CustomElement.observedAttributes = ['title'];131 customElements.define('element-not-observing-id-attribute', CustomElement);132 133 var instance = document.createElement('element-not-observing-id-attribute');134 instance.setAttribute('title', 'hi');135 assert_equals(calls.length, 1);136 assert_array_equals(calls[0], ['title', null, 'hi', null]);137 instance.setAttribute('id', 'some');138 assert_equals(calls.length, 1);139 }, 'attributedChangedCallback must not be invoked when the observed attributes does not contain the attribute.');140 141 test(function () {142 var calls = [];143 class CustomElement extends HTMLElement { }144 CustomElement.prototype.attributeChangedCallback = function () {145 calls.push(Array.from(arguments));146 }147 CustomElement.observedAttributes = ['title', 'lang'];148 customElements.define('element-with-mutated-observed-attributes', CustomElement);149 CustomElement.observedAttributes = ['title', 'id'];150 151 var instance = document.createElement('element-with-mutated-observed-attributes');152 instance.setAttribute('title', 'hi');153 assert_equals(calls.length, 1);154 assert_array_equals(calls[0], ['title', null, 'hi', null]);155 156 instance.setAttribute('id', 'some');157 assert_equals(calls.length, 1);158 159 instance.setAttribute('lang', 'en');160 assert_equals(calls.length, 2);161 assert_array_equals(calls[0], ['title', null, 'hi', null]);162 assert_array_equals(calls[1], ['lang', null, 'en', null]);163 }, 'Mutating observedAttributes after calling customElements.define must not affect the set of attributes for which attributedChangedCallback is invoked');164 165 test(function () {166 var calls = [];167 class CustomElement extends HTMLElement { }168 CustomElement.prototype.attributeChangedCallback = function () {169 calls.push(Array.from(arguments));170 }171 CustomElement.observedAttributes = { [Symbol.iterator]: function *() { yield 'lang'; yield 'style'; } };172 customElements.define('element-with-generator-observed-attributes', CustomElement);173 174 var instance = document.createElement('element-with-generator-observed-attributes');175 instance.setAttribute('lang', 'en');176 assert_equals(calls.length, 1);177 assert_array_equals(calls[0], ['lang', null, 'en', null]);178 179 instance.setAttribute('lang', 'ja');180 assert_equals(calls.length, 2);181 assert_array_equals(calls[1], ['lang', 'en', 'ja', null]);182 183 instance.setAttribute('title', 'hello');184 assert_equals(calls.length, 2);185 186 instance.setAttribute('style', 'font-size: 2rem');187 assert_equals(calls.length, 3);188 assert_array_equals(calls[2], ['style', null, 'font-size: 2rem', null]);189 }, 'attributedChangedCallback must be enqueued for attributes specified in a non-Array iterable observedAttributes');190 101 191 102 </script> -
trunk/LayoutTests/fast/custom-elements/lifecycle-callback-timing.html
r204540 r204551 21 21 handler() { } 22 22 } 23 MyCustomElement.observedAttributes = ['data-title', 'title'];24 23 customElements.define('my-custom-element', MyCustomElement); 25 24 -
trunk/Source/WebCore/ChangeLog
r204550 r204551 1 2016-08-16 Commit Queue <commit-queue@webkit.org> 2 3 Unreviewed, rolling out r204540, r204545, and r204547. 4 https://bugs.webkit.org/show_bug.cgi?id=160932 5 6 Broke Windows builds (Requested by rniwa on #webkit). 7 8 Reverted changesets: 9 10 "customElements.define should retrieve lifecycle callbacks" 11 https://bugs.webkit.org/show_bug.cgi?id=160797 12 http://trac.webkit.org/changeset/204540 13 14 "Windows build fix attempt after r204540." 15 http://trac.webkit.org/changeset/204545 16 17 "Another Windows build fix attempt. The error message doesn't 18 make any sense to me." 19 http://trac.webkit.org/changeset/204547 20 1 21 2016-08-16 Hunseop Jeong <hs85.jeong@samsung.com> 2 22 -
trunk/Source/WebCore/bindings/js/JSBindingsAllInOne.cpp
r204545 r204551 47 47 #include "JSCommandLineAPIHostCustom.cpp" 48 48 #include "JSCryptoCustom.cpp" 49 #include "JSCustomElementsRegistryCustom.cpp"50 49 #include "JSCustomEventCustom.cpp" 51 50 #include "JSCustomSQLStatementErrorCallback.cpp" -
trunk/Source/WebCore/bindings/js/JSCustomElementInterface.cpp
r204540 r204551 152 152 } 153 153 154 void JSCustomElementInterface::setAttributeChangedCallback(JSC::JSObject* callback, const Vector<String>& observedAttributes)155 {156 m_attributeChangedCallback = callback;157 m_observedAttributes.clear();158 for (auto& name : observedAttributes)159 m_observedAttributes.add(name);160 }161 162 154 void JSCustomElementInterface::attributeChanged(Element& element, const QualifiedName& attributeName, const AtomicString& oldValue, const AtomicString& newValue) 163 155 { … … 179 171 JSObject* jsElement = asObject(toJS(state, globalObject, element)); 180 172 173 PropertyName attributeChanged(Identifier::fromString(state, "attributeChangedCallback")); 174 JSValue callback = jsElement->get(state, attributeChanged); 181 175 CallData callData; 182 CallType callType = m_attributeChangedCallback->methodTable()->getCallData(m_attributeChangedCallback.get(), callData); 183 ASSERT(callType != CallType::None); 176 CallType callType = getCallData(callback, callData); 177 if (callType == CallType::None) 178 return; 184 179 185 180 const AtomicString& namespaceURI = attributeName.namespaceURI(); … … 193 188 194 189 NakedPtr<Exception> exception; 195 JSMainThreadExecState::call(state, m_attributeChangedCallback.get(), callType, callData, jsElement, args, exception);190 JSMainThreadExecState::call(state, callback, callType, callData, jsElement, args, exception); 196 191 197 192 InspectorInstrumentation::didCallFunction(cookie, context); -
trunk/Source/WebCore/bindings/js/JSCustomElementInterface.h
r204540 r204551 38 38 #include <wtf/RefCounted.h> 39 39 #include <wtf/RefPtr.h> 40 #include <wtf/text/AtomicStringHash.h>41 40 42 41 namespace JSC { … … 67 66 void upgradeElement(Element&); 68 67 69 void setAttributeChangedCallback(JSC::JSObject* callback, const Vector<String>& observedAttributes);70 bool observesAttribute(const AtomicString& name) const { return m_observedAttributes.contains(name); }71 68 void attributeChanged(Element&, const QualifiedName&, const AtomicString& oldValue, const AtomicString& newValue); 72 69 … … 87 84 QualifiedName m_name; 88 85 mutable JSC::Weak<JSC::JSObject> m_constructor; 89 mutable JSC::Weak<JSC::JSObject> m_attributeChangedCallback;90 86 RefPtr<DOMWrapperWorld> m_isolatedWorld; 91 87 Vector<RefPtr<Element>, 1> m_constructionStack; 92 HashSet<AtomicString> m_observedAttributes;93 88 }; 94 89 -
trunk/Source/WebCore/bindings/js/JSCustomElementsRegistryCustom.cpp
r204547 r204551 32 32 #include "JSCustomElementInterface.h" 33 33 #include "JSDOMBinding.h" 34 #include "JSDOMConvert.h"35 34 36 35 using namespace JSC; … … 38 37 namespace WebCore { 39 38 39 40 40 #if ENABLE(CUSTOM_ELEMENTS) 41 42 static JSObject* getLifecycleCallback(ExecState& state, JSObject& prototype, const Identifier& id)43 {44 JSValue callback = prototype.get(&state, id);45 if (state.hadException())46 return nullptr;47 if (callback.isUndefined())48 return nullptr;49 if (!callback.isFunction()) {50 throwTypeError(&state, ASCIILiteral("A lifecycle callback must be a function"));51 return nullptr;52 }53 return callback.getObject();54 }55 56 // https://html.spec.whatwg.org/#dom-customelementsregistry-define57 41 JSValue JSCustomElementsRegistry::define(ExecState& state) 58 42 { … … 70 54 71 55 // FIXME: Throw a TypeError if constructor doesn't inherit from HTMLElement. 72 // https://github.com/w3c/webcomponents/issues/54173 56 74 57 switch (Document::validateCustomElementName(localName)) { … … 83 66 } 84 67 85 // FIXME: Check re-entrancy here.86 // https://github.com/w3c/webcomponents/issues/54587 88 68 CustomElementsRegistry& registry = wrapped(); 89 69 if (registry.findInterface(localName)) { … … 97 77 } 98 78 99 auto& vm = globalObject()->vm(); 100 JSValue prototypeValue = constructor->get(&state, vm.propertyNames->prototype); 101 if (state.hadException()) 102 return jsUndefined(); 103 if (!prototypeValue.isObject()) 104 return throwTypeError(&state, ASCIILiteral("Custom element constructor's prototype must be an object")); 105 JSObject& prototypeObject = *asObject(prototypeValue); 79 // FIXME: 10. Let prototype be Get(constructor, "prototype"). Rethrow any exceptions. 80 // FIXME: 11. If Type(prototype) is not Object, throw a TypeError exception. 81 // FIXME: 12. Let attachedCallback be Get(prototype, "attachedCallback"). Rethrow any exceptions. 82 // FIXME: 13. Let detachedCallback be Get(prototype, "detachedCallback"). Rethrow any exceptions. 83 // FIXME: 14. Let attributeChangedCallback be Get(prototype, "attributeChangedCallback"). Rethrow any exceptions. 106 84 107 // FIXME: Add the support for connectedCallback. 108 getLifecycleCallback(state, prototypeObject, Identifier::fromString(&vm, "connectedCallback")); 109 if (state.hadException()) 110 return jsUndefined(); 111 112 // FIXME: Add the support for disconnectedCallback. 113 getLifecycleCallback(state, prototypeObject, Identifier::fromString(&vm, "disconnectedCallback")); 114 if (state.hadException()) 115 return jsUndefined(); 116 117 // FIXME: Add the support for adoptedCallback. 118 getLifecycleCallback(state, prototypeObject, Identifier::fromString(&vm, "adoptedCallback")); 119 if (state.hadException()) 120 return jsUndefined(); 85 PrivateName uniquePrivateName; 86 globalObject()->putDirect(globalObject()->vm(), uniquePrivateName, constructor); 121 87 122 88 QualifiedName name(nullAtom, localName, HTMLNames::xhtmlNamespaceURI); 123 Ref<JSCustomElementInterface> interface = JSCustomElementInterface::create(name, constructor, globalObject()); 124 125 auto* attributeChangedCallback = getLifecycleCallback(state, prototypeObject, Identifier::fromString(&vm, "attributeChangedCallback")); 126 if (state.hadException()) 127 return jsUndefined(); 128 if (attributeChangedCallback) { 129 auto value = convertOptional<Vector<String>>(state, constructor->get(&state, Identifier::fromString(&state, "observedAttributes"))); 130 if (state.hadException()) 131 return jsUndefined(); 132 if (value) 133 interface->setAttributeChangedCallback(attributeChangedCallback, *value); 134 } 135 136 PrivateName uniquePrivateName; 137 globalObject()->putDirect(vm, uniquePrivateName, constructor); 138 139 registry.addElementDefinition(WTFMove(interface)); 89 registry.addElementDefinition(JSCustomElementInterface::create(name, constructor, globalObject())); 140 90 141 91 // FIXME: 17. Let map be registry's upgrade candidates map. 142 92 // FIXME: 18. Upgrade a newly-defined element given map and definition. 143 // FIXME: 19. Resolve whenDefined promise.144 93 145 94 return jsUndefined(); -
trunk/Source/WebCore/dom/Element.cpp
r204543 r204551 1291 1291 1292 1292 #if ENABLE(CUSTOM_ELEMENTS) 1293 if (UNLIKELY(isCustomElement())) 1294 LifecycleCallbackQueue::enqueueAttributeChangedCallbackIfNeeded(*this, name, oldValue, newValue); 1293 if (UNLIKELY(isCustomElement())) { 1294 if (auto* window = document().domWindow()) { 1295 if (auto* registry = window->customElementsRegistry()) { 1296 auto* elementInterface = registry->findInterface(tagQName()); 1297 RELEASE_ASSERT(elementInterface); 1298 LifecycleCallbackQueue::enqueueAttributeChangedCallback(*this, *elementInterface, name, oldValue, newValue); 1299 } 1300 } 1301 } 1295 1302 #endif 1296 1303 -
trunk/Source/WebCore/dom/LifecycleCallbackQueue.cpp
r204540 r204551 29 29 #if ENABLE(CUSTOM_ELEMENTS) 30 30 31 #include "CustomElementsRegistry.h"32 #include "DOMWindow.h"33 31 #include "Document.h" 34 32 #include "Element.h" … … 99 97 } 100 98 101 void LifecycleCallbackQueue::enqueueAttributeChangedCallbackIfNeeded(Element& element, const QualifiedName& attributeName, const AtomicString& oldValue, const AtomicString& newValue) 99 void LifecycleCallbackQueue::enqueueAttributeChangedCallback(Element& element, JSCustomElementInterface& elementInterface, 100 const QualifiedName& attributeName, const AtomicString& oldValue, const AtomicString& newValue) 102 101 { 103 ASSERT(element.isCustomElement());104 auto* window = element.document().domWindow();105 if (!window)106 return;107 108 auto* registry = window->customElementsRegistry();109 if (!registry)110 return;111 112 auto* elementInterface = registry->findInterface(element.tagQName());113 if (!elementInterface->observesAttribute(attributeName.localName()))114 return;115 116 102 if (auto* queue = CustomElementLifecycleProcessingStack::ensureCurrentQueue()) 117 queue->m_items.append(LifecycleQueueItem(element, *elementInterface, attributeName, oldValue, newValue));103 queue->m_items.append(LifecycleQueueItem(element, elementInterface, attributeName, oldValue, newValue)); 118 104 } 119 105 -
trunk/Source/WebCore/dom/LifecycleCallbackQueue.h
r204540 r204551 24 24 */ 25 25 26 #pragma once 26 #ifndef LifecycleCallbackQueue_h 27 #define LifecycleCallbackQueue_h 27 28 28 29 #if ENABLE(CUSTOM_ELEMENTS) … … 47 48 48 49 static void enqueueElementUpgrade(Element&, JSCustomElementInterface&); 49 static void enqueueAttributeChangedCallbackIfNeeded(Element&, const QualifiedName&, const AtomicString& oldValue, const AtomicString& newValue); 50 51 static void enqueueAttributeChangedCallback(Element&, JSCustomElementInterface&, 52 const QualifiedName&, const AtomicString& oldValue, const AtomicString& newValue); 50 53 51 54 void invokeAll(); … … 87 90 88 91 #endif 92 93 #endif // LifecycleCallbackQueue_h
Note: See TracChangeset
for help on using the changeset viewer.