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

Side by Side Diff: Source/core/inspector/InspectorDOMDebuggerAgent.cpp

Issue 320933003: DevTools: Expand protocol to allow setting DOM event breakpoints on a given event target. (Closed) Base URL: svn://svn.chromium.org/blink/trunk
Patch Set: Created 6 years, 6 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 | Annotate | Revision Log
« no previous file with comments | « Source/core/inspector/InspectorDOMDebuggerAgent.h ('k') | Source/devtools/protocol.json » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 /* 1 /*
2 * Copyright (C) 2011 Google Inc. All rights reserved. 2 * Copyright (C) 2011 Google Inc. All rights reserved.
3 * 3 *
4 * Redistribution and use in source and binary forms, with or without 4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions are 5 * modification, are permitted provided that the following conditions are
6 * met: 6 * met:
7 * 7 *
8 * * Redistributions of source code must retain the above copyright 8 * * Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer. 9 * notice, this list of conditions and the following disclaimer.
10 * * Redistributions in binary form must reproduce the above 10 * * Redistributions in binary form must reproduce the above
(...skipping 51 matching lines...) Expand 10 before | Expand all | Expand 10 after
62 static const char setTimerEventName[] = "setTimer"; 62 static const char setTimerEventName[] = "setTimer";
63 static const char clearTimerEventName[] = "clearTimer"; 63 static const char clearTimerEventName[] = "clearTimer";
64 static const char timerFiredEventName[] = "timerFired"; 64 static const char timerFiredEventName[] = "timerFired";
65 static const char customElementCallbackName[] = "customElementCallback"; 65 static const char customElementCallbackName[] = "customElementCallback";
66 static const char webglErrorFiredEventName[] = "webglErrorFired"; 66 static const char webglErrorFiredEventName[] = "webglErrorFired";
67 static const char webglWarningFiredEventName[] = "webglWarningFired"; 67 static const char webglWarningFiredEventName[] = "webglWarningFired";
68 static const char webglErrorNameProperty[] = "webglErrorName"; 68 static const char webglErrorNameProperty[] = "webglErrorName";
69 69
70 namespace DOMDebuggerAgentState { 70 namespace DOMDebuggerAgentState {
71 static const char eventListenerBreakpoints[] = "eventListenerBreakpoints"; 71 static const char eventListenerBreakpoints[] = "eventListenerBreakpoints";
72 static const char eventTargetAny[] = "*";
72 static const char pauseOnAllXHRs[] = "pauseOnAllXHRs"; 73 static const char pauseOnAllXHRs[] = "pauseOnAllXHRs";
73 static const char xhrBreakpoints[] = "xhrBreakpoints"; 74 static const char xhrBreakpoints[] = "xhrBreakpoints";
74 } 75 }
75 76
76 PassOwnPtr<InspectorDOMDebuggerAgent> InspectorDOMDebuggerAgent::create(Inspecto rDOMAgent* domAgent, InspectorDebuggerAgent* debuggerAgent) 77 PassOwnPtr<InspectorDOMDebuggerAgent> InspectorDOMDebuggerAgent::create(Inspecto rDOMAgent* domAgent, InspectorDebuggerAgent* debuggerAgent)
77 { 78 {
78 return adoptPtr(new InspectorDOMDebuggerAgent(domAgent, debuggerAgent)); 79 return adoptPtr(new InspectorDOMDebuggerAgent(domAgent, debuggerAgent));
79 } 80 }
80 81
81 InspectorDOMDebuggerAgent::InspectorDOMDebuggerAgent(InspectorDOMAgent* domAgent , InspectorDebuggerAgent* debuggerAgent) 82 InspectorDOMDebuggerAgent::InspectorDOMDebuggerAgent(InspectorDOMAgent* domAgent , InspectorDebuggerAgent* debuggerAgent)
(...skipping 64 matching lines...) Expand 10 before | Expand all | Expand 10 after
146 { 147 {
147 disable(); 148 disable();
148 } 149 }
149 150
150 void InspectorDOMDebuggerAgent::discardAgent() 151 void InspectorDOMDebuggerAgent::discardAgent()
151 { 152 {
152 m_debuggerAgent->setListener(0); 153 m_debuggerAgent->setListener(0);
153 m_debuggerAgent = 0; 154 m_debuggerAgent = 0;
154 } 155 }
155 156
156 void InspectorDOMDebuggerAgent::setEventListenerBreakpoint(ErrorString* error, c onst String& eventName) 157 void InspectorDOMDebuggerAgent::setEventListenerBreakpoint(ErrorString* error, c onst String& eventName, const String* targetName)
157 { 158 {
158 setBreakpoint(error, String(listenerEventCategoryType) + eventName); 159 setBreakpoint(error, String(listenerEventCategoryType) + eventName, targetNa me);
159 } 160 }
160 161
161 void InspectorDOMDebuggerAgent::setInstrumentationBreakpoint(ErrorString* error, const String& eventName) 162 void InspectorDOMDebuggerAgent::setInstrumentationBreakpoint(ErrorString* error, const String& eventName)
162 { 163 {
163 setBreakpoint(error, String(instrumentationEventCategoryType) + eventName); 164 setBreakpoint(error, String(instrumentationEventCategoryType) + eventName, 0 );
164 } 165 }
165 166
166 void InspectorDOMDebuggerAgent::setBreakpoint(ErrorString* error, const String& eventName) 167 static PassRefPtr<JSONObject> ensurePropertyObject(JSONObject* object, const Str ing& propertyName)
168 {
169 JSONObject::iterator it = object->find(propertyName);
170 if (it != object->end())
171 return it->value->asObject();
172
173 RefPtr<JSONObject> result = JSONObject::create();
174 object->setObject(propertyName, result);
175 return result.release();
176 }
177
178 void InspectorDOMDebuggerAgent::setBreakpoint(ErrorString* error, const String& eventName, const String* targetName)
167 { 179 {
168 if (eventName.isEmpty()) { 180 if (eventName.isEmpty()) {
169 *error = "Event name is empty"; 181 *error = "Event name is empty";
170 return; 182 return;
171 } 183 }
172 184
173 RefPtr<JSONObject> eventListenerBreakpoints = m_state->getObject(DOMDebugger AgentState::eventListenerBreakpoints); 185 RefPtr<JSONObject> eventListenerBreakpoints = m_state->getObject(DOMDebugger AgentState::eventListenerBreakpoints);
174 eventListenerBreakpoints->setBoolean(eventName, true); 186 RefPtr<JSONObject> breakpointsByTarget = ensurePropertyObject(eventListenerB reakpoints.get(), eventName);
175 m_state->setObject(DOMDebuggerAgentState::eventListenerBreakpoints, eventLis tenerBreakpoints); 187 if (!targetName || targetName->isEmpty())
188 breakpointsByTarget->setBoolean(DOMDebuggerAgentState::eventTargetAny, t rue);
189 else
190 breakpointsByTarget->setBoolean(targetName->lower(), true);
191 m_state->setObject(DOMDebuggerAgentState::eventListenerBreakpoints, eventLis tenerBreakpoints.release());
176 } 192 }
177 193
178 void InspectorDOMDebuggerAgent::removeEventListenerBreakpoint(ErrorString* error , const String& eventName) 194 void InspectorDOMDebuggerAgent::removeEventListenerBreakpoint(ErrorString* error , const String& eventName, const String* targetName)
179 { 195 {
180 removeBreakpoint(error, String(listenerEventCategoryType) + eventName); 196 removeBreakpoint(error, String(listenerEventCategoryType) + eventName, targe tName);
181 } 197 }
182 198
183 void InspectorDOMDebuggerAgent::removeInstrumentationBreakpoint(ErrorString* err or, const String& eventName) 199 void InspectorDOMDebuggerAgent::removeInstrumentationBreakpoint(ErrorString* err or, const String& eventName)
184 { 200 {
185 removeBreakpoint(error, String(instrumentationEventCategoryType) + eventName ); 201 removeBreakpoint(error, String(instrumentationEventCategoryType) + eventName , 0);
186 } 202 }
187 203
188 void InspectorDOMDebuggerAgent::removeBreakpoint(ErrorString* error, const Strin g& eventName) 204 void InspectorDOMDebuggerAgent::removeBreakpoint(ErrorString* error, const Strin g& eventName, const String* targetName)
189 { 205 {
190 if (eventName.isEmpty()) { 206 if (eventName.isEmpty()) {
191 *error = "Event name is empty"; 207 *error = "Event name is empty";
192 return; 208 return;
193 } 209 }
194 210
195 RefPtr<JSONObject> eventListenerBreakpoints = m_state->getObject(DOMDebugger AgentState::eventListenerBreakpoints); 211 RefPtr<JSONObject> eventListenerBreakpoints = m_state->getObject(DOMDebugger AgentState::eventListenerBreakpoints);
196 eventListenerBreakpoints->remove(eventName); 212 RefPtr<JSONObject> breakpointsByTarget = ensurePropertyObject(eventListenerB reakpoints.get(), eventName);
197 m_state->setObject(DOMDebuggerAgentState::eventListenerBreakpoints, eventLis tenerBreakpoints); 213 if (!targetName || targetName->isEmpty())
214 breakpointsByTarget->remove(DOMDebuggerAgentState::eventTargetAny);
yurys 2014/06/10 08:49:53 It might make sense to remove all targets if targe
aandrey 2014/06/10 09:14:38 I dont think so. e.g. if we have an option to brea
215 else
216 breakpointsByTarget->remove(targetName->lower());
217 m_state->setObject(DOMDebuggerAgentState::eventListenerBreakpoints, eventLis tenerBreakpoints.release());
198 } 218 }
199 219
200 void InspectorDOMDebuggerAgent::didInvalidateStyleAttr(Node* node) 220 void InspectorDOMDebuggerAgent::didInvalidateStyleAttr(Node* node)
201 { 221 {
202 if (hasBreakpoint(node, AttributeModified)) { 222 if (hasBreakpoint(node, AttributeModified)) {
203 RefPtr<JSONObject> eventData = JSONObject::create(); 223 RefPtr<JSONObject> eventData = JSONObject::create();
204 descriptionForDOMEvent(node, AttributeModified, false, eventData.get()); 224 descriptionForDOMEvent(node, AttributeModified, false, eventData.get());
205 m_debuggerAgent->breakProgram(InspectorFrontend::Debugger::Reason::DOM, eventData.release()); 225 m_debuggerAgent->breakProgram(InspectorFrontend::Debugger::Reason::DOM, eventData.release());
206 } 226 }
207 } 227 }
(...skipping 182 matching lines...) Expand 10 before | Expand all | Expand 10 after
390 void InspectorDOMDebuggerAgent::pauseOnNativeEventIfNeeded(PassRefPtr<JSONObject > eventData, bool synchronous) 410 void InspectorDOMDebuggerAgent::pauseOnNativeEventIfNeeded(PassRefPtr<JSONObject > eventData, bool synchronous)
391 { 411 {
392 if (!eventData) 412 if (!eventData)
393 return; 413 return;
394 if (synchronous) 414 if (synchronous)
395 m_debuggerAgent->breakProgram(InspectorFrontend::Debugger::Reason::Event Listener, eventData); 415 m_debuggerAgent->breakProgram(InspectorFrontend::Debugger::Reason::Event Listener, eventData);
396 else 416 else
397 m_debuggerAgent->schedulePauseOnNextStatement(InspectorFrontend::Debugge r::Reason::EventListener, eventData); 417 m_debuggerAgent->schedulePauseOnNextStatement(InspectorFrontend::Debugge r::Reason::EventListener, eventData);
398 } 418 }
399 419
400 PassRefPtr<JSONObject> InspectorDOMDebuggerAgent::preparePauseOnNativeEventData( bool isDOMEvent, const String& eventName) 420 PassRefPtr<JSONObject> InspectorDOMDebuggerAgent::preparePauseOnNativeEventData( const String& eventName, const AtomicString* targetName)
401 { 421 {
402 String fullEventName = (isDOMEvent ? listenerEventCategoryType : instrumenta tionEventCategoryType) + eventName; 422 String fullEventName = (targetName ? listenerEventCategoryType : instrumenta tionEventCategoryType) + eventName;
403 if (m_pauseInNextEventListener) 423 if (m_pauseInNextEventListener) {
404 m_pauseInNextEventListener = false; 424 m_pauseInNextEventListener = false;
405 else { 425 } else {
406 RefPtr<JSONObject> eventListenerBreakpoints = m_state->getObject(DOMDebu ggerAgentState::eventListenerBreakpoints); 426 RefPtr<JSONObject> eventListenerBreakpoints = m_state->getObject(DOMDebu ggerAgentState::eventListenerBreakpoints);
407 if (eventListenerBreakpoints->find(fullEventName) == eventListenerBreakp oints->end()) 427 JSONObject::iterator it = eventListenerBreakpoints->find(fullEventName);
428 if (it == eventListenerBreakpoints->end())
429 return nullptr;
430 bool match = false;
431 RefPtr<JSONObject> breakpointsByTarget = it->value->asObject();
432 breakpointsByTarget->getBoolean(DOMDebuggerAgentState::eventTargetAny, & match);
433 if (!match && targetName)
434 breakpointsByTarget->getBoolean(targetName->lower(), &match);
435 if (!match)
408 return nullptr; 436 return nullptr;
409 } 437 }
410 438
411 RefPtr<JSONObject> eventData = JSONObject::create(); 439 RefPtr<JSONObject> eventData = JSONObject::create();
412 eventData->setString("eventName", fullEventName); 440 eventData->setString("eventName", fullEventName);
441 if (targetName)
442 eventData->setString("targetName", *targetName);
413 return eventData.release(); 443 return eventData.release();
414 } 444 }
415 445
416 void InspectorDOMDebuggerAgent::didInstallTimer(ExecutionContext*, int, int, boo l) 446 void InspectorDOMDebuggerAgent::didInstallTimer(ExecutionContext*, int, int, boo l)
417 { 447 {
418 pauseOnNativeEventIfNeeded(preparePauseOnNativeEventData(false, setTimerEven tName), true); 448 pauseOnNativeEventIfNeeded(preparePauseOnNativeEventData(setTimerEventName, 0), true);
419 } 449 }
420 450
421 void InspectorDOMDebuggerAgent::didRemoveTimer(ExecutionContext*, int) 451 void InspectorDOMDebuggerAgent::didRemoveTimer(ExecutionContext*, int)
422 { 452 {
423 pauseOnNativeEventIfNeeded(preparePauseOnNativeEventData(false, clearTimerEv entName), true); 453 pauseOnNativeEventIfNeeded(preparePauseOnNativeEventData(clearTimerEventName , 0), true);
424 } 454 }
425 455
426 void InspectorDOMDebuggerAgent::willFireTimer(ExecutionContext*, int) 456 void InspectorDOMDebuggerAgent::willFireTimer(ExecutionContext*, int)
427 { 457 {
428 pauseOnNativeEventIfNeeded(preparePauseOnNativeEventData(false, timerFiredEv entName), false); 458 pauseOnNativeEventIfNeeded(preparePauseOnNativeEventData(timerFiredEventName , 0), false);
429 } 459 }
430 460
431 void InspectorDOMDebuggerAgent::didRequestAnimationFrame(Document*, int) 461 void InspectorDOMDebuggerAgent::didRequestAnimationFrame(Document*, int)
432 { 462 {
433 pauseOnNativeEventIfNeeded(preparePauseOnNativeEventData(false, requestAnima tionFrameEventName), true); 463 pauseOnNativeEventIfNeeded(preparePauseOnNativeEventData(requestAnimationFra meEventName, 0), true);
434 } 464 }
435 465
436 void InspectorDOMDebuggerAgent::didCancelAnimationFrame(Document*, int) 466 void InspectorDOMDebuggerAgent::didCancelAnimationFrame(Document*, int)
437 { 467 {
438 pauseOnNativeEventIfNeeded(preparePauseOnNativeEventData(false, cancelAnimat ionFrameEventName), true); 468 pauseOnNativeEventIfNeeded(preparePauseOnNativeEventData(cancelAnimationFram eEventName, 0), true);
439 } 469 }
440 470
441 void InspectorDOMDebuggerAgent::willFireAnimationFrame(Document*, int) 471 void InspectorDOMDebuggerAgent::willFireAnimationFrame(Document*, int)
442 { 472 {
443 pauseOnNativeEventIfNeeded(preparePauseOnNativeEventData(false, animationFra meFiredEventName), false); 473 pauseOnNativeEventIfNeeded(preparePauseOnNativeEventData(animationFrameFired EventName, 0), false);
444 } 474 }
445 475
446 void InspectorDOMDebuggerAgent::willHandleEvent(EventTarget*, const AtomicString & eventType, EventListener*, bool) 476 void InspectorDOMDebuggerAgent::willHandleEvent(EventTarget* target, const Atomi cString& eventType, EventListener*, bool)
447 { 477 {
448 pauseOnNativeEventIfNeeded(preparePauseOnNativeEventData(true, eventType), f alse); 478 pauseOnNativeEventIfNeeded(preparePauseOnNativeEventData(eventType, &target- >interfaceName()), false);
449 } 479 }
450 480
451 void InspectorDOMDebuggerAgent::willExecuteCustomElementCallback(Element*) 481 void InspectorDOMDebuggerAgent::willExecuteCustomElementCallback(Element*)
452 { 482 {
453 pauseOnNativeEventIfNeeded(preparePauseOnNativeEventData(false, customElemen tCallbackName), false); 483 pauseOnNativeEventIfNeeded(preparePauseOnNativeEventData(customElementCallba ckName, 0), false);
454 } 484 }
455 485
456 void InspectorDOMDebuggerAgent::didFireWebGLError(const String& errorName) 486 void InspectorDOMDebuggerAgent::didFireWebGLError(const String& errorName)
457 { 487 {
458 RefPtr<JSONObject> eventData = preparePauseOnNativeEventData(false, webglErr orFiredEventName); 488 RefPtr<JSONObject> eventData = preparePauseOnNativeEventData(webglErrorFired EventName, 0);
459 if (!eventData) 489 if (!eventData)
460 return; 490 return;
461 if (!errorName.isEmpty()) 491 if (!errorName.isEmpty())
462 eventData->setString(webglErrorNameProperty, errorName); 492 eventData->setString(webglErrorNameProperty, errorName);
463 pauseOnNativeEventIfNeeded(eventData.release(), m_debuggerAgent->canBreakPro gram()); 493 pauseOnNativeEventIfNeeded(eventData.release(), m_debuggerAgent->canBreakPro gram());
464 } 494 }
465 495
466 void InspectorDOMDebuggerAgent::didFireWebGLWarning() 496 void InspectorDOMDebuggerAgent::didFireWebGLWarning()
467 { 497 {
468 pauseOnNativeEventIfNeeded(preparePauseOnNativeEventData(false, webglWarning FiredEventName), m_debuggerAgent->canBreakProgram()); 498 pauseOnNativeEventIfNeeded(preparePauseOnNativeEventData(webglWarningFiredEv entName, 0), m_debuggerAgent->canBreakProgram());
469 } 499 }
470 500
471 void InspectorDOMDebuggerAgent::didFireWebGLErrorOrWarning(const String& message ) 501 void InspectorDOMDebuggerAgent::didFireWebGLErrorOrWarning(const String& message )
472 { 502 {
473 if (message.findIgnoringCase("error") != WTF::kNotFound) 503 if (message.findIgnoringCase("error") != WTF::kNotFound)
474 didFireWebGLError(String()); 504 didFireWebGLError(String());
475 else 505 else
476 didFireWebGLWarning(); 506 didFireWebGLWarning();
477 } 507 }
478 508
479 void InspectorDOMDebuggerAgent::setXHRBreakpoint(ErrorString*, const String& url ) 509 void InspectorDOMDebuggerAgent::setXHRBreakpoint(ErrorString*, const String& url )
480 { 510 {
481 if (url.isEmpty()) { 511 if (url.isEmpty()) {
482 m_state->setBoolean(DOMDebuggerAgentState::pauseOnAllXHRs, true); 512 m_state->setBoolean(DOMDebuggerAgentState::pauseOnAllXHRs, true);
483 return; 513 return;
484 } 514 }
485 515
486 RefPtr<JSONObject> xhrBreakpoints = m_state->getObject(DOMDebuggerAgentState ::xhrBreakpoints); 516 RefPtr<JSONObject> xhrBreakpoints = m_state->getObject(DOMDebuggerAgentState ::xhrBreakpoints);
487 xhrBreakpoints->setBoolean(url, true); 517 xhrBreakpoints->setBoolean(url, true);
488 m_state->setObject(DOMDebuggerAgentState::xhrBreakpoints, xhrBreakpoints); 518 m_state->setObject(DOMDebuggerAgentState::xhrBreakpoints, xhrBreakpoints.rel ease());
489 } 519 }
490 520
491 void InspectorDOMDebuggerAgent::removeXHRBreakpoint(ErrorString*, const String& url) 521 void InspectorDOMDebuggerAgent::removeXHRBreakpoint(ErrorString*, const String& url)
492 { 522 {
493 if (url.isEmpty()) { 523 if (url.isEmpty()) {
494 m_state->setBoolean(DOMDebuggerAgentState::pauseOnAllXHRs, false); 524 m_state->setBoolean(DOMDebuggerAgentState::pauseOnAllXHRs, false);
495 return; 525 return;
496 } 526 }
497 527
498 RefPtr<JSONObject> xhrBreakpoints = m_state->getObject(DOMDebuggerAgentState ::xhrBreakpoints); 528 RefPtr<JSONObject> xhrBreakpoints = m_state->getObject(DOMDebuggerAgentState ::xhrBreakpoints);
499 xhrBreakpoints->remove(url); 529 xhrBreakpoints->remove(url);
500 m_state->setObject(DOMDebuggerAgentState::xhrBreakpoints, xhrBreakpoints); 530 m_state->setObject(DOMDebuggerAgentState::xhrBreakpoints, xhrBreakpoints.rel ease());
501 } 531 }
502 532
503 void InspectorDOMDebuggerAgent::willSendXMLHttpRequest(const String& url) 533 void InspectorDOMDebuggerAgent::willSendXMLHttpRequest(const String& url)
504 { 534 {
505 String breakpointURL; 535 String breakpointURL;
506 if (m_state->getBoolean(DOMDebuggerAgentState::pauseOnAllXHRs)) 536 if (m_state->getBoolean(DOMDebuggerAgentState::pauseOnAllXHRs))
507 breakpointURL = ""; 537 breakpointURL = "";
508 else { 538 else {
509 RefPtr<JSONObject> xhrBreakpoints = m_state->getObject(DOMDebuggerAgentS tate::xhrBreakpoints); 539 RefPtr<JSONObject> xhrBreakpoints = m_state->getObject(DOMDebuggerAgentS tate::xhrBreakpoints);
510 for (JSONObject::iterator it = xhrBreakpoints->begin(); it != xhrBreakpo ints->end(); ++it) { 540 for (JSONObject::iterator it = xhrBreakpoints->begin(); it != xhrBreakpo ints->end(); ++it) {
(...skipping 14 matching lines...) Expand all
525 } 555 }
526 556
527 void InspectorDOMDebuggerAgent::clear() 557 void InspectorDOMDebuggerAgent::clear()
528 { 558 {
529 m_domBreakpoints.clear(); 559 m_domBreakpoints.clear();
530 m_pauseInNextEventListener = false; 560 m_pauseInNextEventListener = false;
531 } 561 }
532 562
533 } // namespace WebCore 563 } // namespace WebCore
534 564
OLDNEW
« no previous file with comments | « Source/core/inspector/InspectorDOMDebuggerAgent.h ('k') | Source/devtools/protocol.json » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698