QV8DebugService: Simplify the service code
[profile/ivi/qtdeclarative.git] / tests / auto / declarative / debugger / qdeclarativedebugjs / tst_qdeclarativedebugjs.cpp
1 /****************************************************************************
2 **
3 ** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
4 ** All rights reserved.
5 ** Contact: Nokia Corporation (qt-info@nokia.com)
6 **
7 ** This file is part of the test suite of the Qt Toolkit.
8 **
9 ** $QT_BEGIN_LICENSE:LGPL$
10 ** GNU Lesser General Public License Usage
11 ** This file may be used under the terms of the GNU Lesser General Public
12 ** License version 2.1 as published by the Free Software Foundation and
13 ** appearing in the file LICENSE.LGPL included in the packaging of this
14 ** file. Please review the following information to ensure the GNU Lesser
15 ** General Public License version 2.1 requirements will be met:
16 ** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
17 **
18 ** In addition, as a special exception, Nokia gives you certain additional
19 ** rights. These rights are described in the Nokia Qt LGPL Exception
20 ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
21 **
22 ** GNU General Public License Usage
23 ** Alternatively, this file may be used under the terms of the GNU General
24 ** Public License version 3.0 as published by the Free Software Foundation
25 ** and appearing in the file LICENSE.GPL included in the packaging of this
26 ** file. Please review the following information to ensure the GNU General
27 ** Public License version 3.0 requirements will be met:
28 ** http://www.gnu.org/copyleft/gpl.html.
29 **
30 ** Other Usage
31 ** Alternatively, this file may be used in accordance with the terms and
32 ** conditions contained in a signed written agreement between you and Nokia.
33 **
34 **
35 **
36 **
37 **
38 ** $QT_END_LICENSE$
39 **
40 ****************************************************************************/
41
42 #include <qtest.h>
43 #include <QtCore/QProcess>
44 #include <QtCore/QTimer>
45 #include <QtCore/QFileInfo>
46 #include <QtCore/QDir>
47 #include <QtCore/QMutex>
48 #include <QtCore/QLibraryInfo>
49 #include <QtDeclarative/private/qdeclarativedebugclient_p.h>
50 #include <QtDeclarative/QJSEngine>
51
52 //QDeclarativeDebugTest
53 #include "../shared/debugutil_p.h"
54 #include "../../../shared/util.h"
55
56 const char *V8REQUEST = "v8request";
57 const char *V8MESSAGE = "v8message";
58 const char *SEQ = "seq";
59 const char *TYPE = "type";
60 const char *COMMAND = "command";
61 const char *ARGUMENTS = "arguments";
62 const char *STEPACTION = "stepaction";
63 const char *STEPCOUNT = "stepcount";
64 const char *EXPRESSION = "expression";
65 const char *FRAME = "frame";
66 const char *GLOBAL = "global";
67 const char *DISABLEBREAK = "disable_break";
68 const char *HANDLES = "handles";
69 const char *INCLUDESOURCE = "includeSource";
70 const char *FROMFRAME = "fromFrame";
71 const char *TOFRAME = "toFrame";
72 const char *BOTTOM = "bottom";
73 const char *NUMBER = "number";
74 const char *FRAMENUMBER = "frameNumber";
75 const char *TYPES = "types";
76 const char *IDS = "ids";
77 const char *FILTER = "filter";
78 const char *FROMLINE = "fromLine";
79 const char *TOLINE = "toLine";
80 const char *TARGET = "target";
81 const char *LINE = "line";
82 const char *COLUMN = "column";
83 const char *ENABLED = "enabled";
84 const char *CONDITION = "condition";
85 const char *IGNORECOUNT = "ignoreCount";
86 const char *BREAKPOINT = "breakpoint";
87 const char *FLAGS = "flags";
88
89 const char *CONTINEDEBUGGING = "continue";
90 const char *EVALUATE = "evaluate";
91 const char *LOOKUP = "lookup";
92 const char *BACKTRACE = "backtrace";
93 const char *SCOPE = "scope";
94 const char *SCOPES = "scopes";
95 const char *SCRIPTS = "scripts";
96 const char *SOURCE = "source";
97 const char *SETBREAKPOINT = "setbreakpoint";
98 const char *CHANGEBREAKPOINT = "changebreakpoint";
99 const char *CLEARBREAKPOINT = "clearbreakpoint";
100 const char *SETEXCEPTIONBREAK = "setexceptionbreak";
101 const char *V8FLAGS = "v8flags";
102 const char *VERSION = "version";
103 const char *DISCONNECT = "disconnect";
104 const char *LISTBREAKPOINTS = "listbreakpoints";
105 const char *GARBAGECOLLECTOR = "gc";
106 //const char *PROFILE = "profile";
107
108 const char *CONNECT = "connect";
109 const char *INTERRUPT = "interrupt";
110
111 const char *REQUEST = "request";
112 const char *IN = "in";
113 const char *NEXT = "next";
114 const char *OUT = "out";
115
116 const char *FUNCTION = "function";
117 const char *SCRIPT = "script";
118 const char *SCRIPTREGEXP = "scriptRegExp";
119 const char *EVENT = "event";
120
121 const char *ALL = "all";
122 const char *UNCAUGHT = "uncaught";
123
124 //const char *PAUSE = "pause";
125 //const char *RESUME = "resume";
126
127 const char *BLOCKMODE = "-qmljsdebugger=port:3771,block";
128 const char *NORMALMODE = "-qmljsdebugger=port:3771";
129 const char *TEST_QMLFILE = "test.qml";
130 const char *TEST_JSFILE = "test.js";
131 const char *TIMER_QMLFILE = "timer.qml";
132 const char *LOADJSFILE_QMLFILE = "loadjsfile.qml";
133 const char *EXCEPTION_QMLFILE = "exception.qml";
134 const char *ONCOMPLETED_QMLFILE = "oncompleted.qml";
135 const char *CREATECOMPONENT_QMLFILE = "createComponent.qml";
136 const char *CONDITION_QMLFILE = "condition.qml";
137 const char *CHANGEBREAKPOINT_QMLFILE = "changeBreakpoint.qml";
138 const char *STEPACTION_QMLFILE = "stepAction.qml";
139 const char *BREAKPOINTRELOCATION_QMLFILE = "breakpointRelocation.qml";
140
141 #define VARIANTMAPINIT \
142     QString obj("{}"); \
143     QJSValue jsonVal = parser.call(QJSValue(), QJSValueList() << obj); \
144     jsonVal.setProperty(SEQ,QJSValue(seq++)); \
145     jsonVal.setProperty(TYPE,REQUEST);
146
147
148 #undef QVERIFY
149 #define QVERIFY(statement) \
150 do {\
151     if (!QTest::qVerify((statement), #statement, "", __FILE__, __LINE__)) {\
152         if (QTest::currentTestFailed()) \
153           qDebug().nospace() << "\nDEBUGGEE OUTPUT:\n" << process->output();\
154         return;\
155     }\
156 } while (0)
157
158
159 class QJSDebugClient;
160
161 class tst_QDeclarativeDebugJS : public QObject
162 {
163     Q_OBJECT
164
165     bool init(const QString &qmlFile = QString(TEST_QMLFILE), bool blockMode = true);
166
167 private slots:
168     void initTestCase();
169     void cleanupTestCase();
170
171     void cleanup();
172
173     void connect();
174     void interrupt();
175     void getVersion();
176     void getVersionWhenAttaching();
177
178     void applyV8Flags();
179
180     void disconnect();
181
182     void gc();
183
184     void listBreakpoints();
185
186     void setBreakpointInScriptOnCompleted();
187     void setBreakpointInScriptOnComponentCreated();
188     void setBreakpointInScriptOnTimerCallback();
189     void setBreakpointInScriptInDifferentFile();
190     void setBreakpointInScriptOnComment();
191     void setBreakpointInScriptOnEmptyLine();
192     void setBreakpointInScriptWithCondition();
193     //void setBreakpointInFunction(); //NOT SUPPORTED
194     void setBreakpointOnEvent();
195     void setBreakpointWhenAttaching();
196
197     void changeBreakpoint();
198     void changeBreakpointOnCondition();
199
200     void clearBreakpoint();
201
202     void setExceptionBreak();
203
204     void stepNext();
205     void stepNextWithCount();
206     void stepIn();
207     void stepOut();
208     void continueDebugging();
209
210     void backtrace();
211
212     void getFrameDetails();
213
214     void getScopeDetails();
215
216     void evaluateInGlobalScope();
217     void evaluateInLocalScope();
218
219     void getScopes();
220
221     void getScripts();
222
223     void getSource();
224
225     //    void profile(); //NOT SUPPORTED
226
227     //    void verifyQMLOptimizerDisabled();
228
229 private:
230     QDeclarativeDebugProcess *process;
231     QJSDebugClient *client;
232     QDeclarativeDebugConnection *connection;
233     QTime t;
234 };
235
236 class QJSDebugClient : public QDeclarativeDebugClient
237 {
238     Q_OBJECT
239 public:
240     enum StepAction
241     {
242         Continue,
243         In,
244         Out,
245         Next
246     };
247
248     enum Exception
249     {
250         All,
251         Uncaught
252     };
253
254 //    enum ProfileCommand
255 //    {
256 //        Pause,
257 //        Resume
258 //    };
259
260     QJSDebugClient(QDeclarativeDebugConnection *connection)
261         : QDeclarativeDebugClient(QLatin1String("V8Debugger"), connection),
262           seq(0)
263     {
264         parser = jsEngine.evaluate(QLatin1String("JSON.parse"));
265         stringify = jsEngine.evaluate(QLatin1String("JSON.stringify"));
266     }
267
268     void connect();
269     void interrupt();
270
271     void continueDebugging(StepAction stepAction, int stepCount = 1);
272     void evaluate(QString expr, bool global = false, bool disableBreak = false, int frame = -1, const QVariantMap &addContext = QVariantMap());
273     void lookup(QList<int> handles, bool includeSource = false);
274     void backtrace(int fromFrame = -1, int toFrame = -1, bool bottom = false);
275     void frame(int number = -1);
276     void scope(int number = -1, int frameNumber = -1);
277     void scopes(int frameNumber = -1);
278     void scripts(int types = 4, QList<int> ids = QList<int>(), bool includeSource = false, QVariant filter = QVariant());
279     void source(int frame = -1, int fromLine = -1, int toLine = -1);
280     void setBreakpoint(QString type, QString target, int line = -1, int column = -1, bool enabled = true, QString condition = QString(), int ignoreCount = -1);
281     void changeBreakpoint(int breakpoint, bool enabled = true, QString condition = QString(), int ignoreCount = -1);
282     void clearBreakpoint(int breakpoint);
283     void setExceptionBreak(Exception type, bool enabled = false);
284     void v8flags(QString flags);
285     void version();
286     //void profile(ProfileCommand command); //NOT SUPPORTED
287     void disconnect();
288     void gc();
289     void listBreakpoints();
290
291 protected:
292     //inherited from QDeclarativeDebugClient
293     void statusChanged(Status status);
294     void messageReceived(const QByteArray &data);
295
296 signals:
297     void enabled();
298     void connected();
299     void interruptRequested();
300     void result();
301     void stopped();
302
303 private:
304     void sendMessage(const QByteArray &);
305     void flushSendBuffer();
306     QByteArray packMessage(const QByteArray &type, const QByteArray &message = QByteArray());
307
308 private:
309     QJSEngine jsEngine;
310     int seq;
311
312     QList<QByteArray> sendBuffer;
313 public:
314     QJSValue parser;
315     QJSValue stringify;
316     QByteArray response;
317
318 };
319
320 void QJSDebugClient::connect()
321 {
322     sendMessage(packMessage(CONNECT));
323 }
324
325 void QJSDebugClient::interrupt()
326 {
327     sendMessage(packMessage(INTERRUPT));
328 }
329
330 void QJSDebugClient::continueDebugging(StepAction action, int count)
331 {
332     //    { "seq"       : <number>,
333     //      "type"      : "request",
334     //      "command"   : "continue",
335     //      "arguments" : { "stepaction" : <"in", "next" or "out">,
336     //                      "stepcount"  : <number of steps (default 1)>
337     //                    }
338     //    }
339     VARIANTMAPINIT;
340     jsonVal.setProperty(QLatin1String(COMMAND),QJSValue(QLatin1String(CONTINEDEBUGGING)));
341
342     if (action != Continue) {
343         QJSValue args = parser.call(QJSValue(), QJSValueList() << obj);
344         switch (action) {
345         case In: args.setProperty(QLatin1String(STEPACTION),QJSValue(QLatin1String(IN)));
346             break;
347         case Out: args.setProperty(QLatin1String(STEPACTION),QJSValue(QLatin1String(OUT)));
348             break;
349         case Next: args.setProperty(QLatin1String(STEPACTION),QJSValue(QLatin1String(NEXT)));
350             break;
351         default:break;
352         }
353         if (args.isValid()) {
354             if (count != 1)
355                 args.setProperty(QLatin1String(STEPCOUNT),QJSValue(count));
356             jsonVal.setProperty(QLatin1String(ARGUMENTS),args);
357         }
358     }
359     QJSValue json = stringify.call(QJSValue(), QJSValueList() << jsonVal);
360     sendMessage(packMessage(V8REQUEST, json.toString().toUtf8()));
361 }
362
363 void QJSDebugClient::evaluate(QString expr, bool global, bool disableBreak, int frame, const QVariantMap &/*addContext*/)
364 {
365     //    { "seq"       : <number>,
366     //      "type"      : "request",
367     //      "command"   : "evaluate",
368     //      "arguments" : { "expression"    : <expression to evaluate>,
369     //                      "frame"         : <number>,
370     //                      "global"        : <boolean>,
371     //                      "disable_break" : <boolean>,
372     //                      "additional_context" : [
373     //                           { "name" : <name1>, "handle" : <handle1> },
374     //                           { "name" : <name2>, "handle" : <handle2> },
375     //                           ...
376     //                      ]
377     //                    }
378     //    }
379     VARIANTMAPINIT;
380     jsonVal.setProperty(QLatin1String(COMMAND),QJSValue(QLatin1String(EVALUATE)));
381
382     QJSValue args = parser.call(QJSValue(), QJSValueList() << obj);
383     args.setProperty(QLatin1String(EXPRESSION),QJSValue(expr));
384
385     if (frame != -1)
386         args.setProperty(QLatin1String(FRAME),QJSValue(frame));
387
388     if (global)
389         args.setProperty(QLatin1String(GLOBAL),QJSValue(global));
390
391     if (disableBreak)
392         args.setProperty(QLatin1String(DISABLEBREAK),QJSValue(disableBreak));
393
394     if (args.isValid()) {
395         jsonVal.setProperty(QLatin1String(ARGUMENTS),args);
396     }
397
398     QJSValue json = stringify.call(QJSValue(), QJSValueList() << jsonVal);
399     sendMessage(packMessage(V8REQUEST, json.toString().toUtf8()));
400 }
401
402 void QJSDebugClient::lookup(QList<int> handles, bool includeSource)
403 {
404     //    { "seq"       : <number>,
405     //      "type"      : "request",
406     //      "command"   : "lookup",
407     //      "arguments" : { "handles"       : <array of handles>,
408     //                      "includeSource" : <boolean indicating whether the source will be included when script objects are returned>,
409     //                    }
410     //    }
411     VARIANTMAPINIT;
412     jsonVal.setProperty(QLatin1String(COMMAND),QJSValue(QLatin1String(LOOKUP)));
413
414     QJSValue args = parser.call(QJSValue(), QJSValueList() << obj);
415
416     QString arr("[]");
417     QJSValue array = parser.call(QJSValue(), QJSValueList() << arr);
418     int index = 0;
419     foreach (int handle, handles) {
420         array.setProperty(index++,QJSValue(handle));
421     }
422     args.setProperty(QLatin1String(HANDLES),array);
423
424     if (includeSource)
425         args.setProperty(QLatin1String(INCLUDESOURCE),QJSValue(includeSource));
426
427     if (args.isValid()) {
428         jsonVal.setProperty(QLatin1String(ARGUMENTS),args);
429     }
430
431     QJSValue json = stringify.call(QJSValue(), QJSValueList() << jsonVal);
432     sendMessage(packMessage(V8REQUEST, json.toString().toUtf8()));
433 }
434
435 void QJSDebugClient::backtrace(int fromFrame, int toFrame, bool bottom)
436 {
437     //    { "seq"       : <number>,
438     //      "type"      : "request",
439     //      "command"   : "backtrace",
440     //      "arguments" : { "fromFrame" : <number>
441     //                      "toFrame" : <number>
442     //                      "bottom" : <boolean, set to true if the bottom of the stack is requested>
443     //                    }
444     //    }
445     VARIANTMAPINIT;
446     jsonVal.setProperty(QLatin1String(COMMAND),QJSValue(QLatin1String(BACKTRACE)));
447
448     QJSValue args = parser.call(QJSValue(), QJSValueList() << obj);
449
450     if (fromFrame != -1)
451         args.setProperty(QLatin1String(FROMFRAME),QJSValue(fromFrame));
452
453     if (toFrame != -1)
454         args.setProperty(QLatin1String(TOFRAME),QJSValue(toFrame));
455
456     if (bottom)
457         args.setProperty(QLatin1String(BOTTOM),QJSValue(bottom));
458
459     if (args.isValid()) {
460         jsonVal.setProperty(QLatin1String(ARGUMENTS),args);
461     }
462
463     QJSValue json = stringify.call(QJSValue(), QJSValueList() << jsonVal);
464     sendMessage(packMessage(V8REQUEST, json.toString().toUtf8()));
465 }
466
467 void QJSDebugClient::frame(int number)
468 {
469     //    { "seq"       : <number>,
470     //      "type"      : "request",
471     //      "command"   : "frame",
472     //      "arguments" : { "number" : <frame number>
473     //                    }
474     //    }
475     VARIANTMAPINIT;
476     jsonVal.setProperty(QLatin1String(COMMAND),QJSValue(QLatin1String(FRAME)));
477
478     if (number != -1) {
479         QJSValue args = parser.call(QJSValue(), QJSValueList() << obj);
480         args.setProperty(QLatin1String(NUMBER),QJSValue(number));
481
482         if (args.isValid()) {
483             jsonVal.setProperty(QLatin1String(ARGUMENTS),args);
484         }
485     }
486
487     QJSValue json = stringify.call(QJSValue(), QJSValueList() << jsonVal);
488     sendMessage(packMessage(V8REQUEST, json.toString().toUtf8()));
489 }
490
491 void QJSDebugClient::scope(int number, int frameNumber)
492 {
493     //    { "seq"       : <number>,
494     //      "type"      : "request",
495     //      "command"   : "scope",
496     //      "arguments" : { "number" : <scope number>
497     //                      "frameNumber" : <frame number, optional uses selected frame if missing>
498     //                    }
499     //    }
500     VARIANTMAPINIT;
501     jsonVal.setProperty(QLatin1String(COMMAND),QJSValue(QLatin1String(SCOPE)));
502
503     if (number != -1) {
504         QJSValue args = parser.call(QJSValue(), QJSValueList() << obj);
505         args.setProperty(QLatin1String(NUMBER),QJSValue(number));
506
507         if (frameNumber != -1)
508             args.setProperty(QLatin1String(FRAMENUMBER),QJSValue(frameNumber));
509
510         if (args.isValid()) {
511             jsonVal.setProperty(QLatin1String(ARGUMENTS),args);
512         }
513     }
514
515     QJSValue json = stringify.call(QJSValue(), QJSValueList() << jsonVal);
516     sendMessage(packMessage(V8REQUEST, json.toString().toUtf8()));
517 }
518
519 void QJSDebugClient::scopes(int frameNumber)
520 {
521     //    { "seq"       : <number>,
522     //      "type"      : "request",
523     //      "command"   : "scopes",
524     //      "arguments" : { "frameNumber" : <frame number, optional uses selected frame if missing>
525     //                    }
526     //    }
527     VARIANTMAPINIT;
528     jsonVal.setProperty(QLatin1String(COMMAND),QJSValue(QLatin1String(SCOPES)));
529
530     if (frameNumber != -1) {
531         QJSValue args = parser.call(QJSValue(), QJSValueList() << obj);
532         args.setProperty(QLatin1String(FRAMENUMBER),QJSValue(frameNumber));
533
534         if (args.isValid()) {
535             jsonVal.setProperty(QLatin1String(ARGUMENTS),args);
536         }
537     }
538
539     QJSValue json = stringify.call(QJSValue(), QJSValueList() << jsonVal);
540     sendMessage(packMessage(V8REQUEST, json.toString().toUtf8()));
541 }
542
543 void QJSDebugClient::scripts(int types, QList<int> ids, bool includeSource, QVariant /*filter*/)
544 {
545     //    { "seq"       : <number>,
546     //      "type"      : "request",
547     //      "command"   : "scripts",
548     //      "arguments" : { "types"         : <types of scripts to retrieve
549     //                                           set bit 0 for native scripts
550     //                                           set bit 1 for extension scripts
551     //                                           set bit 2 for normal scripts
552     //                                         (default is 4 for normal scripts)>
553     //                      "ids"           : <array of id's of scripts to return. If this is not specified all scripts are requrned>
554     //                      "includeSource" : <boolean indicating whether the source code should be included for the scripts returned>
555     //                      "filter"        : <string or number: filter string or script id.
556     //                                         If a number is specified, then only the script with the same number as its script id will be retrieved.
557     //                                         If a string is specified, then only scripts whose names contain the filter string will be retrieved.>
558     //                    }
559     //    }
560     VARIANTMAPINIT;
561     jsonVal.setProperty(QLatin1String(COMMAND),QJSValue(QLatin1String(SCRIPTS)));
562
563     QJSValue args = parser.call(QJSValue(), QJSValueList() << obj);
564     args.setProperty(QLatin1String(TYPES),QJSValue(types));
565
566     if (ids.count()) {
567         QString arr("[]");
568         QJSValue array = parser.call(QJSValue(), QJSValueList() << arr);
569         int index = 0;
570         foreach (int id, ids) {
571             array.setProperty(index++,QJSValue(id));
572         }
573         args.setProperty(QLatin1String(IDS),array);
574     }
575
576     if (includeSource)
577         args.setProperty(QLatin1String(INCLUDESOURCE),QJSValue(includeSource));
578
579     if (args.isValid()) {
580         jsonVal.setProperty(QLatin1String(ARGUMENTS),args);
581     }
582
583     QJSValue json = stringify.call(QJSValue(), QJSValueList() << jsonVal);
584     sendMessage(packMessage(V8REQUEST, json.toString().toUtf8()));
585 }
586
587 void QJSDebugClient::source(int frame, int fromLine, int toLine)
588 {
589     //    { "seq"       : <number>,
590     //      "type"      : "request",
591     //      "command"   : "source",
592     //      "arguments" : { "frame"    : <frame number (default selected frame)>
593     //                      "fromLine" : <from line within the source default is line 0>
594     //                      "toLine"   : <to line within the source this line is not included in
595     //                                    the result default is the number of lines in the script>
596     //                    }
597     //    }
598     VARIANTMAPINIT;
599     jsonVal.setProperty(QLatin1String(COMMAND),QJSValue(QLatin1String(SOURCE)));
600
601     QJSValue args = parser.call(QJSValue(), QJSValueList() << obj);
602
603     if (frame != -1)
604         args.setProperty(QLatin1String(FRAME),QJSValue(frame));
605
606     if (fromLine != -1)
607         args.setProperty(QLatin1String(FROMLINE),QJSValue(fromLine));
608
609     if (toLine != -1)
610         args.setProperty(QLatin1String(TOLINE),QJSValue(toLine));
611
612     if (args.isValid()) {
613         jsonVal.setProperty(QLatin1String(ARGUMENTS),args);
614     }
615
616     QJSValue json = stringify.call(QJSValue(), QJSValueList() << jsonVal);
617     sendMessage(packMessage(V8REQUEST, json.toString().toUtf8()));
618 }
619
620 void QJSDebugClient::setBreakpoint(QString type, QString target, int line, int column, bool enabled, QString condition, int ignoreCount)
621 {
622     //    { "seq"       : <number>,
623     //      "type"      : "request",
624     //      "command"   : "setbreakpoint",
625     //      "arguments" : { "type"        : <"function" or "script" or "scriptId" or "scriptRegExp">
626     //                      "target"      : <function expression or script identification>
627     //                      "line"        : <line in script or function>
628     //                      "column"      : <character position within the line>
629     //                      "enabled"     : <initial enabled state. True or false, default is true>
630     //                      "condition"   : <string with break point condition>
631     //                      "ignoreCount" : <number specifying the number of break point hits to ignore, default value is 0>
632     //                    }
633     //    }
634
635     if (type == QLatin1String(EVENT)) {
636         QByteArray reply;
637         QDataStream rs(&reply, QIODevice::WriteOnly);
638         rs <<  target.toUtf8() << enabled;
639         sendMessage(packMessage(QByteArray("breakonsignal"), reply));
640
641     } else {
642         VARIANTMAPINIT;
643         jsonVal.setProperty(QLatin1String(COMMAND),QJSValue(QLatin1String(SETBREAKPOINT)));
644
645         QJSValue args = parser.call(QJSValue(), QJSValueList() << obj);
646
647         args.setProperty(QLatin1String(TYPE),QJSValue(type));
648         args.setProperty(QLatin1String(TARGET),QJSValue(target));
649
650         if (line != -1)
651             args.setProperty(QLatin1String(LINE),QJSValue(line));
652
653         if (column != -1)
654             args.setProperty(QLatin1String(COLUMN),QJSValue(column));
655
656         args.setProperty(QLatin1String(ENABLED),QJSValue(enabled));
657
658         if (!condition.isEmpty())
659             args.setProperty(QLatin1String(CONDITION),QJSValue(condition));
660
661         if (ignoreCount != -1)
662             args.setProperty(QLatin1String(IGNORECOUNT),QJSValue(ignoreCount));
663
664         if (args.isValid()) {
665             jsonVal.setProperty(QLatin1String(ARGUMENTS),args);
666         }
667
668         QJSValue json = stringify.call(QJSValue(), QJSValueList() << jsonVal);
669         sendMessage(packMessage(V8REQUEST, json.toString().toUtf8()));
670     }
671 }
672
673 void QJSDebugClient::changeBreakpoint(int breakpoint, bool enabled, QString condition, int ignoreCount)
674 {
675     //    { "seq"       : <number>,
676     //      "type"      : "request",
677     //      "command"   : "changebreakpoint",
678     //      "arguments" : { "breakpoint"  : <number of the break point to clear>
679     //                      "enabled"     : <initial enabled state. True or false, default is true>
680     //                      "condition"   : <string with break point condition>
681     //                      "ignoreCount" : <number specifying the number of break point hits            }
682     //    }
683     VARIANTMAPINIT;
684     jsonVal.setProperty(QLatin1String(COMMAND),QJSValue(QLatin1String(CHANGEBREAKPOINT)));
685
686     QJSValue args = parser.call(QJSValue(), QJSValueList() << obj);
687
688     args.setProperty(QLatin1String(BREAKPOINT),QJSValue(breakpoint));
689
690     args.setProperty(QLatin1String(ENABLED),QJSValue(enabled));
691
692     if (!condition.isEmpty())
693         args.setProperty(QLatin1String(CONDITION),QJSValue(condition));
694
695     if (ignoreCount != -1)
696         args.setProperty(QLatin1String(IGNORECOUNT),QJSValue(ignoreCount));
697
698     if (args.isValid()) {
699         jsonVal.setProperty(QLatin1String(ARGUMENTS),args);
700     }
701
702     QJSValue json = stringify.call(QJSValue(), QJSValueList() << jsonVal);
703     sendMessage(packMessage(V8REQUEST, json.toString().toUtf8()));
704 }
705
706 void QJSDebugClient::clearBreakpoint(int breakpoint)
707 {
708     //    { "seq"       : <number>,
709     //      "type"      : "request",
710     //      "command"   : "clearbreakpoint",
711     //      "arguments" : { "breakpoint" : <number of the break point to clear>
712     //                    }
713     //    }
714     VARIANTMAPINIT;
715     jsonVal.setProperty(QLatin1String(COMMAND),QJSValue(QLatin1String(CLEARBREAKPOINT)));
716
717     QJSValue args = parser.call(QJSValue(), QJSValueList() << obj);
718
719     args.setProperty(QLatin1String(BREAKPOINT),QJSValue(breakpoint));
720
721     if (args.isValid()) {
722         jsonVal.setProperty(QLatin1String(ARGUMENTS),args);
723     }
724
725     QJSValue json = stringify.call(QJSValue(), QJSValueList() << jsonVal);
726     sendMessage(packMessage(V8REQUEST, json.toString().toUtf8()));
727 }
728
729 void QJSDebugClient::setExceptionBreak(Exception type, bool enabled)
730 {
731     //    { "seq"       : <number>,
732     //      "type"      : "request",
733     //      "command"   : "setexceptionbreak",
734     //      "arguments" : { "type"    : <string: "all", or "uncaught">,
735     //                      "enabled" : <optional bool: enables the break type if true>
736     //                    }
737     //    }
738     VARIANTMAPINIT;
739     jsonVal.setProperty(QLatin1String(COMMAND),QJSValue(QLatin1String(SETEXCEPTIONBREAK)));
740
741     QJSValue args = parser.call(QJSValue(), QJSValueList() << obj);
742
743     if (type == All)
744         args.setProperty(QLatin1String(TYPE),QJSValue(QLatin1String(ALL)));
745     else if (type == Uncaught)
746         args.setProperty(QLatin1String(TYPE),QJSValue(QLatin1String(UNCAUGHT)));
747
748     if (enabled)
749         args.setProperty(QLatin1String(ENABLED),QJSValue(enabled));
750
751     if (args.isValid()) {
752         jsonVal.setProperty(QLatin1String(ARGUMENTS),args);
753     }
754
755     QJSValue json = stringify.call(QJSValue(), QJSValueList() << jsonVal);
756     sendMessage(packMessage(V8REQUEST, json.toString().toUtf8()));
757 }
758
759 void QJSDebugClient::v8flags(QString flags)
760 {
761     //    { "seq"       : <number>,
762     //      "type"      : "request",
763     //      "command"   : "v8flags",
764     //      "arguments" : { "flags" : <string: a sequence of v8 flags just like those used on the command line>
765     //                    }
766     //    }
767     VARIANTMAPINIT;
768     jsonVal.setProperty(QLatin1String(COMMAND),QJSValue(QLatin1String(V8FLAGS)));
769
770     QJSValue args = parser.call(QJSValue(), QJSValueList() << obj);
771
772     args.setProperty(QLatin1String(FLAGS),QJSValue(flags));
773
774     if (args.isValid()) {
775         jsonVal.setProperty(QLatin1String(ARGUMENTS),args);
776     }
777
778     QJSValue json = stringify.call(QJSValue(), QJSValueList() << jsonVal);
779     sendMessage(packMessage(V8REQUEST, json.toString().toUtf8()));
780 }
781
782 void QJSDebugClient::version()
783 {
784     //    { "seq"       : <number>,
785     //      "type"      : "request",
786     //      "command"   : "version",
787     //    }
788     VARIANTMAPINIT;
789     jsonVal.setProperty(QLatin1String(COMMAND),QJSValue(QLatin1String(VERSION)));
790
791     QJSValue json = stringify.call(QJSValue(), QJSValueList() << jsonVal);
792     sendMessage(packMessage(V8REQUEST, json.toString().toUtf8()));
793 }
794
795 //void QJSDebugClient::profile(ProfileCommand command)
796 //{
797 ////    { "seq"       : <number>,
798 ////      "type"      : "request",
799 ////      "command"   : "profile",
800 ////      "arguments" : { "command"  : "resume" or "pause" }
801 ////    }
802 //    VARIANTMAPINIT;
803 //    jsonVal.setProperty(QLatin1String(COMMAND),QJSValue(QLatin1String(PROFILE)));
804
805 //    QJSValue args = parser.call(QJSValue(), QJSValueList() << obj);
806
807 //    if (command == Resume)
808 //        args.setProperty(QLatin1String(COMMAND),QJSValue(QLatin1String(RESUME)));
809 //    else
810 //        args.setProperty(QLatin1String(COMMAND),QJSValue(QLatin1String(PAUSE)));
811
812 //    args.setProperty(QLatin1String("modules"),QJSValue(1));
813 //    if (args.isValid()) {
814 //        jsonVal.setProperty(QLatin1String(ARGUMENTS),args);
815 //    }
816
817 //    QJSValue json = stringify.call(QJSValue(), QJSValueList() << jsonVal);
818 //    sendMessage(packMessage(V8REQUEST, json.toString().toUtf8()));
819 //}
820
821 void QJSDebugClient::disconnect()
822 {
823     //    { "seq"     : <number>,
824     //      "type"    : "request",
825     //      "command" : "disconnect",
826     //    }
827     VARIANTMAPINIT;
828     jsonVal.setProperty(QLatin1String(COMMAND),QJSValue(QLatin1String(DISCONNECT)));
829
830     QJSValue json = stringify.call(QJSValue(), QJSValueList() << jsonVal);
831     sendMessage(packMessage(DISCONNECT, json.toString().toUtf8()));
832 }
833
834 void QJSDebugClient::gc()
835 {
836     //    { "seq"       : <number>,
837     //      "type"      : "request",
838     //      "command"   : "gc",
839     //      "arguments" : { "type" : <string: "all">,
840     //                    }
841     //    }
842     VARIANTMAPINIT;
843     jsonVal.setProperty(QLatin1String(COMMAND),QJSValue(QLatin1String(GARBAGECOLLECTOR)));
844
845     QJSValue args = parser.call(QJSValue(), QJSValueList() << obj);
846
847     args.setProperty(QLatin1String(TYPE),QJSValue(QLatin1String(ALL)));
848
849     if (args.isValid()) {
850         jsonVal.setProperty(QLatin1String(ARGUMENTS),args);
851     }
852
853     QJSValue json = stringify.call(QJSValue(), QJSValueList() << jsonVal);
854     sendMessage(packMessage(V8REQUEST, json.toString().toUtf8()));
855 }
856
857 void QJSDebugClient::listBreakpoints()
858 {
859     //    { "seq"       : <number>,
860     //      "type"      : "request",
861     //      "command"   : "listbreakpoints",
862     //    }
863     VARIANTMAPINIT;
864     jsonVal.setProperty(QLatin1String(COMMAND),QJSValue(QLatin1String(LISTBREAKPOINTS)));
865
866     QJSValue json = stringify.call(QJSValue(), QJSValueList() << jsonVal);
867     sendMessage(packMessage(V8REQUEST, json.toString().toUtf8()));
868 }
869
870 void QJSDebugClient::statusChanged(Status status)
871 {
872     if (status == Enabled) {
873         flushSendBuffer();
874         emit enabled();
875     }
876 }
877
878 void QJSDebugClient::messageReceived(const QByteArray &data)
879 {
880     QDataStream ds(data);
881     QByteArray command;
882     ds >> command;
883
884     if (command == "V8DEBUG") {
885         QByteArray type;
886         ds >> type >> response;
887
888         if (type == CONNECT) {
889             emit connected();
890
891         } else if (type == INTERRUPT) {
892             emit interruptRequested();
893
894         } else if (type == V8MESSAGE) {
895             QString jsonString(response);
896             QVariantMap value = parser.call(QJSValue(), QJSValueList() << QJSValue(jsonString)).toVariant().toMap();
897             QString type = value.value("type").toString();
898
899             if (type == "response") {
900
901                 if (!value.value("success").toBool()) {
902 //                    qDebug() << "Error: The test case will fail since no signal is emitted";
903                     return;
904                 }
905
906                 QString debugCommand(value.value("command").toString());
907                 if (debugCommand == "backtrace" ||
908                         debugCommand == "lookup" ||
909                         debugCommand == "setbreakpoint" ||
910                         debugCommand == "evaluate" ||
911                         debugCommand == "listbreakpoints" ||
912                         debugCommand == "version" ||
913                         debugCommand == "v8flags" ||
914                         debugCommand == "disconnect" ||
915                         debugCommand == "gc" ||
916                         debugCommand == "changebreakpoint" ||
917                         debugCommand == "clearbreakpoint" ||
918                         debugCommand == "frame" ||
919                         debugCommand == "scope" ||
920                         debugCommand == "scopes" ||
921                         debugCommand == "scripts" ||
922                         debugCommand == "source" ||
923                         debugCommand == "setexceptionbreak" /*||
924                         debugCommand == "profile"*/) {
925                     emit result();
926
927                 } else {
928                     // DO NOTHING
929                 }
930
931             } else if (type == QLatin1String(EVENT)) {
932                 QString event(value.value(QLatin1String(EVENT)).toString());
933
934                 if (event == "break" ||
935                         event == "exception")
936                     emit stopped();
937                 }
938         }
939     }
940 }
941
942 void QJSDebugClient::sendMessage(const QByteArray &msg)
943 {
944     if (status() == Enabled) {
945         QDeclarativeDebugClient::sendMessage(msg);
946     } else {
947         sendBuffer.append(msg);
948     }
949 }
950
951 void QJSDebugClient::flushSendBuffer()
952 {
953     foreach (const QByteArray &msg, sendBuffer)
954         QDeclarativeDebugClient::sendMessage(msg);
955     sendBuffer.clear();
956 }
957
958 QByteArray QJSDebugClient::packMessage(const QByteArray &type, const QByteArray &message)
959 {
960     QByteArray reply;
961     QDataStream rs(&reply, QIODevice::WriteOnly);
962     QByteArray cmd = "V8DEBUG";
963     rs << cmd << type << message;
964     return reply;
965 }
966
967 void tst_QDeclarativeDebugJS::initTestCase()
968 {
969     t.start();
970     process = 0;
971     client = 0;
972     connection = 0;
973 }
974
975 void tst_QDeclarativeDebugJS::cleanupTestCase()
976 {
977     if (process) {
978         process->stop();
979         delete process;
980     }
981
982     if (client)
983         delete client;
984
985     if (connection)
986         delete connection;
987
988 //    qDebug() << "Time Elapsed:" << t.elapsed();
989 }
990
991 bool tst_QDeclarativeDebugJS::init(const QString &qmlFile, bool blockMode)
992 {
993     connection = new QDeclarativeDebugConnection();
994     process = new QDeclarativeDebugProcess(QLibraryInfo::location(QLibraryInfo::BinariesPath) + "/qmlscene");
995     client = new QJSDebugClient(connection);
996
997     QStringList systemEnvironment = QProcess::systemEnvironment();
998     systemEnvironment << "QML_DISABLE_OPTIMIZER=1";
999     process->setEnvironment(systemEnvironment);
1000     if (blockMode)
1001         process->start(QStringList() << QLatin1String(BLOCKMODE) << TESTDATA(qmlFile));
1002     else
1003         process->start(QStringList() << QLatin1String(NORMALMODE) << TESTDATA(qmlFile));
1004
1005     if (!process->waitForSessionStart()) {
1006         return false;
1007     }
1008
1009     connection->connectToHost("127.0.0.1", 3771);
1010     if (!connection->waitForConnected())
1011         return false;
1012
1013     return QDeclarativeDebugTest::waitForSignal(client, SIGNAL(enabled()));
1014 }
1015
1016 void tst_QDeclarativeDebugJS::cleanup()
1017 {
1018     if (process) {
1019         process->stop();
1020         delete process;
1021     }
1022
1023     if (client)
1024         delete client;
1025
1026     if (connection)
1027         delete connection;
1028
1029     process = 0;
1030     client = 0;
1031     connection = 0;
1032 }
1033
1034 void tst_QDeclarativeDebugJS::connect()
1035 {
1036     //void connect()
1037
1038     QVERIFY(init());
1039     client->connect();
1040     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(connected())));
1041 }
1042
1043 void tst_QDeclarativeDebugJS::interrupt()
1044 {
1045     //void connect()
1046
1047     QVERIFY(init());
1048     client->connect();
1049
1050     client->interrupt();
1051     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(interruptRequested())));
1052 }
1053
1054 void tst_QDeclarativeDebugJS::getVersion()
1055 {
1056     //void version()
1057
1058     QVERIFY(init());
1059     client->connect();
1060     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(connected())));
1061
1062     client->version();
1063     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(result())));
1064 }
1065
1066 void tst_QDeclarativeDebugJS::getVersionWhenAttaching()
1067 {
1068     //void version()
1069
1070     QVERIFY(init(QLatin1String(TIMER_QMLFILE), false));
1071     client->connect();
1072
1073     client->version();
1074     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(result())));
1075 }
1076
1077 void tst_QDeclarativeDebugJS::applyV8Flags()
1078 {
1079     //void v8flags(QString flags)
1080
1081     QVERIFY(init());
1082     client->connect();
1083
1084     client->v8flags(QString());
1085     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(result())));
1086 }
1087
1088 void tst_QDeclarativeDebugJS::disconnect()
1089 {
1090     //void disconnect()
1091
1092     QVERIFY(init());
1093     client->connect();
1094
1095     client->disconnect();
1096     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(result())));
1097 }
1098
1099 void tst_QDeclarativeDebugJS::gc()
1100 {
1101     //void gc()
1102
1103     QVERIFY(init());
1104     client->connect();
1105
1106     client->gc();
1107     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(result())));
1108 }
1109
1110 void tst_QDeclarativeDebugJS::listBreakpoints()
1111 {
1112     //void listBreakpoints()
1113
1114     int sourceLine1 = 47;
1115     int sourceLine2 = 48;
1116     int sourceLine3 = 49;
1117
1118     QVERIFY(init());
1119     client->connect();
1120
1121     client->setBreakpoint(QLatin1String(SCRIPTREGEXP), QLatin1String(TEST_QMLFILE), sourceLine1, -1, true);
1122     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(result())));
1123     client->setBreakpoint(QLatin1String(SCRIPTREGEXP), QLatin1String(TEST_QMLFILE), sourceLine2, -1, true);
1124     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(result())));
1125     client->setBreakpoint(QLatin1String(SCRIPTREGEXP), QLatin1String(TEST_QMLFILE), sourceLine3, -1, true);
1126     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(result())));
1127     client->listBreakpoints();
1128     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(result())));
1129
1130     QString jsonString(client->response);
1131     QVariantMap value = client->parser.call(QJSValue(), QJSValueList() << QJSValue(jsonString)).toVariant().toMap();
1132
1133     QList<QVariant> breakpoints = value.value("body").toMap().value("breakpoints").toList();
1134
1135     QCOMPARE(breakpoints.count(), 3);
1136 }
1137
1138 void tst_QDeclarativeDebugJS::setBreakpointInScriptOnCompleted()
1139 {
1140     //void setBreakpoint(QString type, QString target, int line = -1, int column = -1, bool enabled = false, QString condition = QString(), int ignoreCount = -1)
1141
1142     int sourceLine = 47;
1143     QVERIFY(init(ONCOMPLETED_QMLFILE));
1144
1145     client->setBreakpoint(QLatin1String(SCRIPTREGEXP), QLatin1String(ONCOMPLETED_QMLFILE), sourceLine, -1, true);
1146     client->connect();
1147     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1148
1149     QString jsonString(client->response);
1150     QVariantMap value = client->parser.call(QJSValue(), QJSValueList() << QJSValue(jsonString)).toVariant().toMap();
1151
1152     QVariantMap body = value.value("body").toMap();
1153
1154     QCOMPARE(body.value("sourceLine").toInt(), sourceLine);
1155     QCOMPARE(QFileInfo(body.value("script").toMap().value("name").toString()).fileName(), QLatin1String(ONCOMPLETED_QMLFILE));
1156 }
1157
1158 void tst_QDeclarativeDebugJS::setBreakpointInScriptOnComponentCreated()
1159 {
1160     //void setBreakpoint(QString type, QString target, int line = -1, int column = -1, bool enabled = false, QString condition = QString(), int ignoreCount = -1)
1161
1162     int sourceLine = 47;
1163     QVERIFY(init(CREATECOMPONENT_QMLFILE));
1164
1165     client->setBreakpoint(QLatin1String(SCRIPTREGEXP), QLatin1String(ONCOMPLETED_QMLFILE), sourceLine, -1, true);
1166     client->connect();
1167     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1168
1169     QString jsonString(client->response);
1170     QVariantMap value = client->parser.call(QJSValue(), QJSValueList() << QJSValue(jsonString)).toVariant().toMap();
1171
1172     QVariantMap body = value.value("body").toMap();
1173
1174     QCOMPARE(body.value("sourceLine").toInt(), sourceLine);
1175     QCOMPARE(QFileInfo(body.value("script").toMap().value("name").toString()).fileName(), QLatin1String(ONCOMPLETED_QMLFILE));
1176 }
1177
1178 void tst_QDeclarativeDebugJS::setBreakpointInScriptOnTimerCallback()
1179 {
1180     int sourceLine = 48;
1181     QVERIFY(init(TIMER_QMLFILE));
1182
1183     client->connect();
1184
1185     client->setBreakpoint(QLatin1String(SCRIPTREGEXP), QLatin1String(TIMER_QMLFILE), sourceLine, -1, true);
1186     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1187
1188     QString jsonString(client->response);
1189     QVariantMap value = client->parser.call(QJSValue(), QJSValueList() << QJSValue(jsonString)).toVariant().toMap();
1190
1191     QVariantMap body = value.value("body").toMap();
1192
1193     QCOMPARE(body.value("sourceLine").toInt(), sourceLine);
1194     QCOMPARE(QFileInfo(body.value("script").toMap().value("name").toString()).fileName(), QLatin1String(TIMER_QMLFILE));
1195 }
1196
1197 void tst_QDeclarativeDebugJS::setBreakpointInScriptInDifferentFile()
1198 {
1199     //void setBreakpoint(QString type, QString target, int line = -1, int column = -1, bool enabled = false, QString condition = QString(), int ignoreCount = -1)
1200
1201     int sourceLine = 43;
1202     QVERIFY(init(LOADJSFILE_QMLFILE));
1203
1204     client->connect();
1205     client->setBreakpoint(QLatin1String(SCRIPTREGEXP), QLatin1String(TEST_JSFILE), sourceLine, -1, true);
1206     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1207
1208     QString jsonString(client->response);
1209     QVariantMap value = client->parser.call(QJSValue(), QJSValueList() << QJSValue(jsonString)).toVariant().toMap();
1210
1211     QVariantMap body = value.value("body").toMap();
1212
1213     QCOMPARE(body.value("sourceLine").toInt(), sourceLine);
1214     QCOMPARE(QFileInfo(body.value("script").toMap().value("name").toString()).fileName(), QLatin1String(TEST_JSFILE));
1215 }
1216
1217 void tst_QDeclarativeDebugJS::setBreakpointInScriptOnComment()
1218 {
1219     //void setBreakpoint(QString type, QString target, int line = -1, int column = -1, bool enabled = false, QString condition = QString(), int ignoreCount = -1)
1220
1221     int sourceLine = 47;
1222     int actualLine = 49;
1223     QVERIFY(init(BREAKPOINTRELOCATION_QMLFILE));
1224
1225     client->connect();
1226     client->setBreakpoint(QLatin1String(SCRIPTREGEXP), QLatin1String(BREAKPOINTRELOCATION_QMLFILE), sourceLine, -1, true);
1227     QEXPECT_FAIL("", "Relocation of breakpoints is disabled right now", Abort);
1228     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped()), 1));
1229
1230     QString jsonString(client->response);
1231     QVariantMap value = client->parser.call(QJSValue(), QJSValueList() << QJSValue(jsonString)).toVariant().toMap();
1232
1233     QVariantMap body = value.value("body").toMap();
1234
1235     QCOMPARE(body.value("sourceLine").toInt(), actualLine);
1236     QCOMPARE(QFileInfo(body.value("script").toMap().value("name").toString()).fileName(), QLatin1String(BREAKPOINTRELOCATION_QMLFILE));
1237 }
1238
1239 void tst_QDeclarativeDebugJS::setBreakpointInScriptOnEmptyLine()
1240 {
1241     //void setBreakpoint(QString type, QString target, int line = -1, int column = -1, bool enabled = false, QString condition = QString(), int ignoreCount = -1)
1242
1243     int sourceLine = 48;
1244     int actualLine = 49;
1245     QVERIFY(init(BREAKPOINTRELOCATION_QMLFILE));
1246
1247     client->connect();
1248     client->setBreakpoint(QLatin1String(SCRIPTREGEXP), QLatin1String(BREAKPOINTRELOCATION_QMLFILE), sourceLine, -1, true);
1249     QEXPECT_FAIL("", "Relocation of breakpoints is disabled right now", Abort);
1250     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped()), 1));
1251
1252     QString jsonString(client->response);
1253     QVariantMap value = client->parser.call(QJSValue(), QJSValueList() << QJSValue(jsonString)).toVariant().toMap();
1254
1255     QVariantMap body = value.value("body").toMap();
1256
1257     QCOMPARE(body.value("sourceLine").toInt(), actualLine);
1258     QCOMPARE(QFileInfo(body.value("script").toMap().value("name").toString()).fileName(), QLatin1String(BREAKPOINTRELOCATION_QMLFILE));
1259 }
1260
1261 void tst_QDeclarativeDebugJS::setBreakpointInScriptWithCondition()
1262 {
1263     //void setBreakpoint(QString type, QString target, int line = -1, int column = -1, bool enabled = false, QString condition = QString(), int ignoreCount = -1)
1264
1265     int out = 10;
1266     int sourceLine = 50;
1267     QVERIFY(init(CONDITION_QMLFILE));
1268
1269     client->connect();
1270     client->setBreakpoint(QLatin1String(SCRIPTREGEXP), QLatin1String(CONDITION_QMLFILE), sourceLine, 1, true, QLatin1String("a > 10"));
1271     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1272
1273     //Get the frame index
1274     QString jsonString = client->response;
1275     QVariantMap value = client->parser.call(QJSValue(), QJSValueList() << QJSValue(jsonString)).toVariant().toMap();
1276
1277     QVariantMap body = value.value("body").toMap();
1278
1279     int frameIndex = body.value("index").toInt();
1280
1281     //Verify the value of 'result'
1282     client->evaluate(QLatin1String("a"),frameIndex);
1283
1284     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(result())));
1285
1286     jsonString = client->response;
1287     value = client->parser.call(QJSValue(), QJSValueList() << QJSValue(jsonString)).toVariant().toMap();
1288
1289     body = value.value("body").toMap();
1290
1291     QVERIFY(body.value("value").toInt() > out);
1292 }
1293
1294 void tst_QDeclarativeDebugJS::setBreakpointWhenAttaching()
1295 {
1296     int sourceLine = 49;
1297     QVERIFY(init(QLatin1String(TIMER_QMLFILE), false));
1298
1299     client->connect();
1300     client->setBreakpoint(QLatin1String(SCRIPTREGEXP), QLatin1String(TIMER_QMLFILE), sourceLine);
1301     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1302 }
1303
1304 //void tst_QDeclarativeDebugJS::setBreakpointInFunction()
1305 //{
1306 //    //void setBreakpoint(QString type, QString target, int line = -1, int column = -1, bool enabled = false, QString condition = QString(), int ignoreCount = -1)
1307
1308 //    int actualLine = 31;
1309
1310 //    client->connect();
1311 //    client->setBreakpoint(QLatin1String(FUNCTION), QLatin1String("doSomethingElse"), -1, -1, true);
1312
1313 //    QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1314
1315 //    QString jsonString(client->response);
1316 //    QVariantMap value = client->parser.call(QJSValue(), QJSValueList() << QJSValue(jsonString)).toVariant().toMap();
1317
1318 //    QVariantMap body = value.value("body").toMap();
1319
1320 //    QCOMPARE(body.value("sourceLine").toInt(), actualLine);
1321 //    QCOMPARE(QFileInfo(body.value("script").toMap().value("name").toString()).fileName(), QLatin1String(QMLFILE));
1322 //}
1323
1324 void tst_QDeclarativeDebugJS::setBreakpointOnEvent()
1325 {
1326     //void setBreakpoint(QString type, QString target, int line = -1, int column = -1, bool enabled = false, QString condition = QString(), int ignoreCount = -1)
1327
1328     QVERIFY(init(TIMER_QMLFILE));
1329
1330     client->connect();
1331
1332     client->setBreakpoint(QLatin1String(EVENT), QLatin1String("triggered"), -1, -1, true);
1333     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1334
1335     QString jsonString(client->response);
1336     QVariantMap value = client->parser.call(QJSValue(), QJSValueList() << QJSValue(jsonString)).toVariant().toMap();
1337
1338     QVariantMap body = value.value("body").toMap();
1339
1340     QCOMPARE(QFileInfo(body.value("script").toMap().value("name").toString()).fileName(), QLatin1String(TIMER_QMLFILE));
1341 }
1342
1343
1344 void tst_QDeclarativeDebugJS::changeBreakpoint()
1345 {
1346     //void changeBreakpoint(int breakpoint, bool enabled = false, QString condition = QString(), int ignoreCount = -1)
1347
1348     int sourceLine1 = 50;
1349     int sourceLine2 = 51;
1350     QVERIFY(init(CHANGEBREAKPOINT_QMLFILE));
1351
1352     client->connect();
1353     client->setBreakpoint(QLatin1String(SCRIPTREGEXP), QLatin1String(CHANGEBREAKPOINT_QMLFILE), sourceLine2, -1, true);
1354     client->setBreakpoint(QLatin1String(SCRIPTREGEXP), QLatin1String(CHANGEBREAKPOINT_QMLFILE), sourceLine1, -1, true);
1355
1356     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1357
1358     //Will hit 1st brakpoint, change this breakpoint enable = false
1359     QString jsonString(client->response);
1360     QVariantMap value = client->parser.call(QJSValue(), QJSValueList() << QJSValue(jsonString)).toVariant().toMap();
1361
1362     QVariantMap body = value.value("body").toMap();
1363     QList<QVariant> breakpointsHit = body.value("breakpoints").toList();
1364
1365     int breakpoint = breakpointsHit.at(0).toInt();
1366     client->changeBreakpoint(breakpoint,false);
1367
1368     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(result())));
1369
1370     //Continue with debugging
1371     client->continueDebugging(QJSDebugClient::Continue);
1372     //Hit 2nd breakpoint
1373     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1374
1375     //Continue with debugging
1376     client->continueDebugging(QJSDebugClient::Continue);
1377     //Should stop at 2nd breakpoint
1378     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1379
1380     jsonString = client->response;
1381     value = client->parser.call(QJSValue(), QJSValueList() << QJSValue(jsonString)).toVariant().toMap();
1382
1383     body = value.value("body").toMap();
1384
1385     QCOMPARE(body.value("sourceLine").toInt(), sourceLine2);
1386 }
1387
1388 void tst_QDeclarativeDebugJS::changeBreakpointOnCondition()
1389 {
1390     //void changeBreakpoint(int breakpoint, bool enabled = false, QString condition = QString(), int ignoreCount = -1)
1391
1392     int sourceLine1 = 50;
1393     int sourceLine2 = 51;
1394
1395     QVERIFY(init(CHANGEBREAKPOINT_QMLFILE));
1396
1397     client->connect();
1398     client->setBreakpoint(QLatin1String(SCRIPTREGEXP), QLatin1String(CHANGEBREAKPOINT_QMLFILE), sourceLine1, -1, true);
1399     client->setBreakpoint(QLatin1String(SCRIPTREGEXP), QLatin1String(CHANGEBREAKPOINT_QMLFILE), sourceLine2, -1, true);
1400
1401     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1402
1403     //Will hit 1st brakpoint, change this breakpoint enable = false
1404     QString jsonString(client->response);
1405     QVariantMap value = client->parser.call(QJSValue(), QJSValueList() << QJSValue(jsonString)).toVariant().toMap();
1406
1407     QVariantMap body = value.value("body").toMap();
1408     QList<QVariant> breakpointsHit = body.value("breakpoints").toList();
1409
1410     int breakpoint = breakpointsHit.at(0).toInt();
1411     client->changeBreakpoint(breakpoint, false, QLatin1String("d == 0"));
1412
1413     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(result())));
1414
1415     //Continue with debugging
1416     client->continueDebugging(QJSDebugClient::Continue);
1417     //Hit 2nd breakpoint
1418     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1419
1420     //Continue with debugging
1421     client->continueDebugging(QJSDebugClient::Continue);
1422     //Should stop at 2nd breakpoint
1423     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1424
1425     jsonString = client->response;
1426     value = client->parser.call(QJSValue(), QJSValueList() << QJSValue(jsonString)).toVariant().toMap();
1427
1428     body = value.value("body").toMap();
1429
1430     QCOMPARE(body.value("sourceLine").toInt(), sourceLine2);
1431
1432 }
1433
1434 void tst_QDeclarativeDebugJS::clearBreakpoint()
1435 {
1436     //void clearBreakpoint(int breakpoint);
1437
1438     int sourceLine1 = 50;
1439     int sourceLine2 = 51;
1440     QVERIFY(init(CHANGEBREAKPOINT_QMLFILE));
1441
1442     client->connect();
1443     client->setBreakpoint(QLatin1String(SCRIPTREGEXP), QLatin1String(CHANGEBREAKPOINT_QMLFILE), sourceLine1, -1, true);
1444     client->setBreakpoint(QLatin1String(SCRIPTREGEXP), QLatin1String(CHANGEBREAKPOINT_QMLFILE), sourceLine2, -1, true);
1445
1446     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1447
1448     //Will hit 1st brakpoint, change this breakpoint enable = false
1449     QString jsonString(client->response);
1450     QVariantMap value = client->parser.call(QJSValue(), QJSValueList() << QJSValue(jsonString)).toVariant().toMap();
1451
1452     QVariantMap body = value.value("body").toMap();
1453     QList<QVariant> breakpointsHit = body.value("breakpoints").toList();
1454
1455     int breakpoint = breakpointsHit.at(0).toInt();
1456     client->clearBreakpoint(breakpoint);
1457
1458     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(result())));
1459
1460     //Continue with debugging
1461     client->continueDebugging(QJSDebugClient::Continue);
1462     //Hit 2nd breakpoint
1463     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1464
1465     //Continue with debugging
1466     client->continueDebugging(QJSDebugClient::Continue);
1467     //Should stop at 2nd breakpoint
1468     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1469
1470     jsonString = client->response;
1471     value = client->parser.call(QJSValue(), QJSValueList() << QJSValue(jsonString)).toVariant().toMap();
1472
1473     body = value.value("body").toMap();
1474
1475     QCOMPARE(body.value("sourceLine").toInt(), sourceLine2);
1476 }
1477
1478 void tst_QDeclarativeDebugJS::setExceptionBreak()
1479 {
1480     //void setExceptionBreak(QString type, bool enabled = false);
1481
1482     QVERIFY(init(EXCEPTION_QMLFILE));
1483     client->setExceptionBreak(QJSDebugClient::All,true);
1484     client->connect();
1485     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1486 }
1487
1488 void tst_QDeclarativeDebugJS::stepNext()
1489 {
1490     //void continueDebugging(StepAction stepAction, int stepCount = 1);
1491
1492     int sourceLine = 50;
1493     QVERIFY(init(STEPACTION_QMLFILE));
1494
1495     client->setBreakpoint(QLatin1String(SCRIPTREGEXP), QLatin1String(STEPACTION_QMLFILE), sourceLine, -1, true);
1496     client->connect();
1497     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1498
1499     client->continueDebugging(QJSDebugClient::Next);
1500     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1501
1502     QString jsonString(client->response);
1503     QVariantMap value = client->parser.call(QJSValue(), QJSValueList() << QJSValue(jsonString)).toVariant().toMap();
1504
1505     QVariantMap body = value.value("body").toMap();
1506
1507     QCOMPARE(body.value("sourceLine").toInt(), sourceLine + 1);
1508     QCOMPARE(QFileInfo(body.value("script").toMap().value("name").toString()).fileName(), QLatin1String(STEPACTION_QMLFILE));
1509 }
1510
1511 void tst_QDeclarativeDebugJS::stepNextWithCount()
1512 {
1513     //void continueDebugging(StepAction stepAction, int stepCount = 1);
1514
1515     int sourceLine = 50;
1516     QVERIFY(init(STEPACTION_QMLFILE));
1517
1518     client->connect();
1519     client->setBreakpoint(QLatin1String(SCRIPTREGEXP), QLatin1String(STEPACTION_QMLFILE), sourceLine, -1, true);
1520     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1521
1522     client->continueDebugging(QJSDebugClient::Next, 2);
1523     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1524
1525     QString jsonString(client->response);
1526     QVariantMap value = client->parser.call(QJSValue(), QJSValueList() << QJSValue(jsonString)).toVariant().toMap();
1527
1528     QVariantMap body = value.value("body").toMap();
1529
1530     QCOMPARE(body.value("sourceLine").toInt(), sourceLine + 2);
1531     QCOMPARE(QFileInfo(body.value("script").toMap().value("name").toString()).fileName(), QLatin1String(STEPACTION_QMLFILE));
1532 }
1533
1534 void tst_QDeclarativeDebugJS::stepIn()
1535 {
1536     //void continueDebugging(StepAction stepAction, int stepCount = 1);
1537
1538     int sourceLine = 54;
1539     int actualLine = 50;
1540     QVERIFY(init(STEPACTION_QMLFILE));
1541
1542     client->connect();
1543     client->setBreakpoint(QLatin1String(SCRIPTREGEXP), QLatin1String(STEPACTION_QMLFILE), sourceLine, 1, true);
1544     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1545
1546     client->continueDebugging(QJSDebugClient::In);
1547     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1548
1549     QString jsonString(client->response);
1550     QVariantMap value = client->parser.call(QJSValue(), QJSValueList() << QJSValue(jsonString)).toVariant().toMap();
1551
1552     QVariantMap body = value.value("body").toMap();
1553
1554     QCOMPARE(body.value("sourceLine").toInt(), actualLine);
1555     QCOMPARE(QFileInfo(body.value("script").toMap().value("name").toString()).fileName(), QLatin1String(STEPACTION_QMLFILE));
1556 }
1557
1558 void tst_QDeclarativeDebugJS::stepOut()
1559 {
1560     //void continueDebugging(StepAction stepAction, int stepCount = 1);
1561
1562     int sourceLine = 50;
1563     int actualLine = 54;
1564     QVERIFY(init(STEPACTION_QMLFILE));
1565
1566     client->connect();
1567     client->setBreakpoint(QLatin1String(SCRIPTREGEXP), QLatin1String(STEPACTION_QMLFILE), sourceLine, -1, true);
1568     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1569
1570     client->continueDebugging(QJSDebugClient::Out);
1571     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1572
1573     QString jsonString(client->response);
1574     QVariantMap value = client->parser.call(QJSValue(), QJSValueList() << QJSValue(jsonString)).toVariant().toMap();
1575
1576     QVariantMap body = value.value("body").toMap();
1577
1578     QCOMPARE(body.value("sourceLine").toInt(), actualLine);
1579     QCOMPARE(QFileInfo(body.value("script").toMap().value("name").toString()).fileName(), QLatin1String(STEPACTION_QMLFILE));
1580 }
1581
1582 void tst_QDeclarativeDebugJS::continueDebugging()
1583 {
1584     //void continueDebugging(StepAction stepAction, int stepCount = 1);
1585
1586     int sourceLine1 = 54;
1587     int sourceLine2 = 51;
1588     QVERIFY(init(STEPACTION_QMLFILE));
1589
1590     client->connect();
1591     client->setBreakpoint(QLatin1String(SCRIPTREGEXP), QLatin1String(STEPACTION_QMLFILE), sourceLine1, -1, true);
1592     client->setBreakpoint(QLatin1String(SCRIPTREGEXP), QLatin1String(STEPACTION_QMLFILE), sourceLine2, -1, true);
1593     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1594
1595     client->continueDebugging(QJSDebugClient::Continue);
1596     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1597
1598     QString jsonString(client->response);
1599     QVariantMap value = client->parser.call(QJSValue(), QJSValueList() << QJSValue(jsonString)).toVariant().toMap();
1600
1601     QVariantMap body = value.value("body").toMap();
1602
1603     QCOMPARE(body.value("sourceLine").toInt(), sourceLine2);
1604     QCOMPARE(QFileInfo(body.value("script").toMap().value("name").toString()).fileName(), QLatin1String(STEPACTION_QMLFILE));
1605 }
1606
1607 void tst_QDeclarativeDebugJS::backtrace()
1608 {
1609     //void backtrace(int fromFrame = -1, int toFrame = -1, bool bottom = false);
1610
1611     int sourceLine = 47;
1612     QVERIFY(init(ONCOMPLETED_QMLFILE));
1613
1614     client->setBreakpoint(QLatin1String(SCRIPTREGEXP), QLatin1String(ONCOMPLETED_QMLFILE), sourceLine, -1, true);
1615     client->connect();
1616     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1617
1618     client->backtrace();
1619     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(result())));
1620 }
1621
1622 void tst_QDeclarativeDebugJS::getFrameDetails()
1623 {
1624     //void frame(int number = -1);
1625
1626     int sourceLine = 47;
1627     QVERIFY(init(ONCOMPLETED_QMLFILE));
1628
1629     client->setBreakpoint(QLatin1String(SCRIPTREGEXP), QLatin1String(ONCOMPLETED_QMLFILE), sourceLine, -1, true);
1630     client->connect();
1631     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1632
1633     client->frame();
1634     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(result())));
1635 }
1636
1637 void tst_QDeclarativeDebugJS::getScopeDetails()
1638 {
1639     //void scope(int number = -1, int frameNumber = -1);
1640
1641     int sourceLine = 47;
1642     QVERIFY(init(ONCOMPLETED_QMLFILE));
1643
1644     client->setBreakpoint(QLatin1String(SCRIPTREGEXP), QLatin1String(ONCOMPLETED_QMLFILE), sourceLine, -1, true);
1645     client->connect();
1646     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1647
1648     client->scope();
1649     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(result())));
1650 }
1651
1652 void tst_QDeclarativeDebugJS::evaluateInGlobalScope()
1653 {
1654     //void evaluate(QString expr, bool global = false, bool disableBreak = false, int frame = -1, const QVariantMap &addContext = QVariantMap());
1655
1656     QVERIFY(init());
1657
1658     client->connect();
1659     client->evaluate(QLatin1String("print('Hello World')"), true);
1660     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(result())));
1661
1662     //Verify the value of 'print'
1663     QString jsonString(client->response);
1664     QVariantMap value = client->parser.call(QJSValue(), QJSValueList() << QJSValue(jsonString)).toVariant().toMap();
1665
1666     QVariantMap body = value.value("body").toMap();
1667
1668     QCOMPARE(body.value("text").toString(),QLatin1String("undefined"));
1669 }
1670
1671 void tst_QDeclarativeDebugJS::evaluateInLocalScope()
1672 {
1673     //void evaluate(QString expr, bool global = false, bool disableBreak = false, int frame = -1, const QVariantMap &addContext = QVariantMap());
1674
1675     int sourceLine = 47;
1676     QVERIFY(init(ONCOMPLETED_QMLFILE));
1677
1678     client->setBreakpoint(QLatin1String(SCRIPTREGEXP), QLatin1String(ONCOMPLETED_QMLFILE), sourceLine, -1, true);
1679     client->connect();
1680     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1681
1682     client->frame();
1683     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(result())));
1684
1685     //Get the frame index
1686     QString jsonString(client->response);
1687     QVariantMap value = client->parser.call(QJSValue(), QJSValueList() << QJSValue(jsonString)).toVariant().toMap();
1688
1689     QVariantMap body = value.value("body").toMap();
1690
1691     int frameIndex = body.value("index").toInt();
1692
1693     client->evaluate(QLatin1String("root.a"), frameIndex);
1694     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(result())));
1695
1696     //Verify the value of 'timer.interval'
1697     jsonString = client->response;
1698     value = client->parser.call(QJSValue(), QJSValueList() << QJSValue(jsonString)).toVariant().toMap();
1699
1700     body = value.value("body").toMap();
1701
1702     QCOMPARE(body.value("value").toInt(),10);
1703 }
1704
1705 void tst_QDeclarativeDebugJS::getScopes()
1706 {
1707     //void scopes(int frameNumber = -1);
1708
1709     int sourceLine = 47;
1710     QVERIFY(init(ONCOMPLETED_QMLFILE));
1711
1712     client->setBreakpoint(QLatin1String(SCRIPTREGEXP), QLatin1String(ONCOMPLETED_QMLFILE), sourceLine, -1, true);
1713     client->connect();
1714     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1715
1716     client->scopes();
1717     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(result())));
1718 }
1719
1720 void tst_QDeclarativeDebugJS::getScripts()
1721 {
1722     //void scripts(int types = -1, QList<int> ids = QList<int>(), bool includeSource = false, QVariant filter = QVariant());
1723
1724     QVERIFY(init());
1725
1726     client->connect();
1727
1728     client->scripts();
1729     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(result())));
1730     QString jsonString(client->response);
1731     QVariantMap value = client->parser.call(QJSValue(),
1732                                             QJSValueList()
1733                                             << QJSValue(jsonString)).toVariant().toMap();
1734
1735     QList<QVariant> scripts = value.value("body").toList();
1736
1737     QCOMPARE(scripts.count(), 2);
1738 }
1739
1740 void tst_QDeclarativeDebugJS::getSource()
1741 {
1742     //void source(int frame = -1, int fromLine = -1, int toLine = -1);
1743
1744     int sourceLine = 47;
1745     QVERIFY(init(ONCOMPLETED_QMLFILE));
1746
1747     client->setBreakpoint(QLatin1String(SCRIPTREGEXP), QLatin1String(ONCOMPLETED_QMLFILE), sourceLine, -1, true);
1748     client->connect();
1749     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(stopped())));
1750
1751     client->source();
1752     QVERIFY(QDeclarativeDebugTest::waitForSignal(client, SIGNAL(result())));
1753 }
1754
1755 QTEST_MAIN(tst_QDeclarativeDebugJS)
1756
1757 #include "tst_qdeclarativedebugjs.moc"
1758