PageRenderTime 8ms CodeModel.GetById 8ms app.highlight 98ms RepoModel.GetById 1ms app.codeStats 1ms

/tests/auto/qjsonrpcserver/tst_qjsonrpcserver.cpp

https://bitbucket.org/mgodshall/qjsonrpc
C++ | 1011 lines | 780 code | 151 blank | 80 comment | 40 complexity | 94f18b17c813624c2e3acea3756c40f5 MD5 | raw file
   1/*
   2 * Copyright (C) 2012-2013 Matt Broadstone
   3 * Contact: http://bitbucket.org/devonit/qjsonrpc
   4 *
   5 * This file is part of the QJsonRpc Library.
   6 *
   7 * This library is free software; you can redistribute it and/or
   8 * modify it under the terms of the GNU Lesser General Public
   9 * License as published by the Free Software Foundation; either
  10 * version 2.1 of the License, or (at your option) any later version.
  11 *
  12 * This library is distributed in the hope that it will be useful,
  13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
  14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
  15 * Lesser General Public License for more details.
  16 */
  17#include <QLocalSocket>
  18#include <QTcpSocket>
  19
  20#include <QtCore/QEventLoop>
  21#include <QtCore/QVariant>
  22#include <QtTest/QtTest>
  23
  24#include "json/qjsondocument.h"
  25#include "qjsonrpcservice.h"
  26#include "qjsonrpcmessage.h"
  27
  28class TestQJsonRpcServer: public QObject
  29{
  30    Q_OBJECT
  31private Q_SLOTS:
  32    void initTestCase();
  33    void cleanupTestCase();
  34    void init();
  35    void cleanup();
  36
  37    // Local Server
  38    void testLocalNoParameter();
  39    void testLocalSingleParameter();
  40    void testLocalMultiparameter();
  41    void testLocalVariantParameter();
  42    void testLocalVariantListParameter();
  43    void testLocalVariantResult();
  44    void testLocalInvalidArgs();
  45    void testLocalMethodNotFound();
  46    void testLocalInvalidRequest();
  47    void testLocalNotifyConnectedClients();
  48    void testLocalNumberParameters();
  49    void testLocalHugeResponse();
  50    void testLocalComplexMethod();
  51    void testLocalDefaultParameters();
  52    void testLocalNotifyServiceSocket();
  53    void testLocalNoWhitespace();
  54    void testLocalOverloadedMethod();
  55    void testLocalQVariantMapInvalidParam();
  56
  57
  58    // TCP Server
  59    void testTcpNoParameter();
  60    void testTcpSingleParameter();
  61    void testTcpMultiparameter();
  62    void testTcpVariantParameter();
  63    void testTcpInvalidArgs();
  64    void testTcpMethodNotFound();
  65    void testTcpInvalidRequest();
  66    void testTcpNotifyConnectedClients();
  67    void testTcpNumberParameters();
  68    void testTcpHugeResponse();
  69
  70private:
  71    // fix later
  72    void testLocalListOfInts();
  73
  74};
  75
  76class TestService : public QJsonRpcService
  77{
  78    Q_OBJECT
  79    Q_CLASSINFO("serviceName", "service")
  80public:
  81    TestService(QObject *parent = 0)
  82        : QJsonRpcService(parent),
  83          m_called(0)
  84    {}
  85
  86    void resetCount() { m_called = 0; }
  87    int callCount() const {
  88        return m_called;
  89    }
  90
  91public Q_SLOTS:
  92    void noParam() const {}
  93    QString singleParam(const QString &string) const { return string; }
  94    QString multipleParam(const QString &first,
  95                          const QString &second,
  96                          const QString &third) const
  97    {
  98        return first + second + third;
  99    }
 100
 101    void numberParameters(int intParam, double doubleParam, float floatParam)
 102    {
 103        Q_UNUSED(intParam)
 104        Q_UNUSED(doubleParam)
 105        Q_UNUSED(floatParam)
 106    }
 107
 108    bool variantParameter(const QVariant &variantParam) const
 109    {
 110        return variantParam.toBool();
 111    }
 112
 113    QVariantList variantListParameter(const QVariantList &data) {
 114        return data;
 115    }
 116
 117    QVariant variantStringResult() {
 118        return "hello";
 119    }
 120
 121    QVariantList variantListResult() {
 122        return QVariantList() << "one" << 2 << 3.0;
 123    }
 124
 125    QVariantMap variantMapResult() {
 126        QVariantMap result;
 127        result["one"] = 1;
 128        result["two"] = 2.0;
 129        return result;
 130    }
 131
 132    void increaseCalled() {
 133        m_called++;
 134    }
 135
 136    bool methodWithListOfInts(const QList<int> &list) {
 137        if (list.size() < 3)
 138            return false;
 139
 140        if (list.at(0) != 300)
 141            return false;
 142        if (list.at(1) != 30)
 143            return false;
 144        if (list.at(2) != 3)
 145            return false;
 146        return true;
 147    }
 148
 149    QString variantMapInvalidParam(const QVariantMap &map) {
 150        return map["foo"].toString();
 151    }
 152
 153    bool overloadedMethod(int input) { Q_UNUSED(input) return true; }
 154    bool overloadedMethod(const QString &input) { Q_UNUSED(input) return false; }
 155
 156private:
 157    int m_called;
 158};
 159
 160void TestQJsonRpcServer::initTestCase()
 161{
 162    qRegisterMetaType<QJsonRpcMessage>("QJsonRpcMessage");
 163}
 164
 165void TestQJsonRpcServer::cleanupTestCase()
 166{
 167}
 168
 169void TestQJsonRpcServer::init()
 170{
 171}
 172
 173void TestQJsonRpcServer::cleanup()
 174{
 175}
 176
 177void TestQJsonRpcServer::testLocalNoParameter()
 178{
 179    // Initialize the service provider.
 180    QJsonRpcLocalServer serviceProvider;
 181    serviceProvider.addService(new TestService);
 182    QVERIFY(serviceProvider.listen("test"));
 183
 184    // Connect to the socket.
 185    QLocalSocket socket;
 186    socket.connectToServer("test");
 187    QVERIFY(socket.waitForConnected(1000));
 188    QJsonRpcSocket serviceSocket(&socket, this);
 189    QSignalSpy spyMessageReceived(&serviceSocket,
 190                                  SIGNAL(messageReceived(QJsonRpcMessage)));
 191
 192    QJsonRpcMessage request = QJsonRpcMessage::createRequest("service.noParam");
 193    QJsonRpcMessage response = serviceSocket.sendMessageBlocking(request);
 194    QCOMPARE(spyMessageReceived.count(), 1);
 195    QVERIFY(response.errorCode() == QJsonRpc::NoError);
 196    QCOMPARE(request.id(), response.id());
 197}
 198
 199void TestQJsonRpcServer::testLocalSingleParameter()
 200{
 201    // Initialize the service provider.
 202    QJsonRpcLocalServer serviceProvider;
 203    serviceProvider.addService(new TestService);
 204    QVERIFY(serviceProvider.listen("test"));
 205
 206    // Connect to the socket.
 207    QLocalSocket socket;
 208    socket.connectToServer("test");
 209    QVERIFY(socket.waitForConnected());
 210    QJsonRpcSocket serviceSocket(&socket, this);
 211    QSignalSpy spyMessageReceived(&serviceSocket, SIGNAL(messageReceived(QJsonRpcMessage)));
 212    QJsonRpcMessage request = QJsonRpcMessage::createRequest("service.singleParam", QString("single"));
 213    QJsonRpcMessage response = serviceSocket.sendMessageBlocking(request);
 214    QCOMPARE(spyMessageReceived.count(), 1);
 215    QVERIFY(response.errorCode() == QJsonRpc::NoError);
 216    QCOMPARE(request.id(), response.id());
 217    QCOMPARE(response.result().toString(), QLatin1String("single"));
 218}
 219
 220void TestQJsonRpcServer::testLocalOverloadedMethod()
 221{
 222    // Initialize the service provider.
 223    QJsonRpcLocalServer serviceProvider;
 224    serviceProvider.addService(new TestService);
 225    QVERIFY(serviceProvider.listen("test"));
 226
 227    // Connect to the socket.
 228    QLocalSocket socket;
 229    socket.connectToServer("test");
 230    QVERIFY(socket.waitForConnected());
 231    QJsonRpcSocket serviceSocket(&socket, this);
 232    QSignalSpy spyMessageReceived(&serviceSocket,
 233                                  SIGNAL(messageReceived(QJsonRpcMessage)));
 234
 235    QJsonRpcMessage stringRequest = QJsonRpcMessage::createRequest("service.overloadedMethod", QString("single"));
 236    QJsonRpcMessage stringResponse = serviceSocket.sendMessageBlocking(stringRequest);
 237    QCOMPARE(spyMessageReceived.count(), 1);
 238    QVERIFY(stringResponse.errorCode() == QJsonRpc::NoError);
 239    QCOMPARE(stringRequest.id(), stringResponse.id());
 240    QCOMPARE(stringResponse.result().toBool(), false);
 241
 242    QJsonRpcMessage intRequest = QJsonRpcMessage::createRequest("service.overloadedMethod", 10);
 243    QJsonRpcMessage intResponse = serviceSocket.sendMessageBlocking(intRequest);
 244    QCOMPARE(spyMessageReceived.count(), 2);
 245    QVERIFY(intResponse.errorCode() == QJsonRpc::NoError);
 246    QCOMPARE(intRequest.id(), intResponse.id());
 247    QCOMPARE(intResponse.result().toBool(), true);
 248
 249    QVariantMap testMap;
 250    testMap["one"] = 1;
 251    testMap["two"] = 2;
 252    testMap["three"] = 3;
 253    QJsonRpcMessage mapRequest =
 254        QJsonRpcMessage::createRequest("service.overloadedMethod", testMap);
 255    QJsonRpcMessage mapResponse = serviceSocket.sendMessageBlocking(mapRequest);
 256    QCOMPARE(spyMessageReceived.count(), 3);
 257    QVERIFY(mapResponse.errorCode() == QJsonRpc::InvalidParams);
 258    QCOMPARE(mapRequest.id(), mapResponse.id());
 259}
 260
 261void TestQJsonRpcServer::testLocalMultiparameter()
 262{
 263    // Initialize the service provider.
 264    QJsonRpcLocalServer serviceProvider;
 265    serviceProvider.addService(new TestService);
 266    QVERIFY(serviceProvider.listen("test"));
 267
 268    // Connect to the socket.
 269    QLocalSocket socket;
 270    socket.connectToServer("test");
 271    QVERIFY(socket.waitForConnected());
 272    QJsonRpcSocket serviceSocket(&socket, this);
 273    QSignalSpy spyMessageReceived(&serviceSocket,
 274                                  SIGNAL(messageReceived(QJsonRpcMessage)));
 275
 276    QJsonRpcMessage request = QJsonRpcMessage::createRequest("service.multipleParam",
 277                                                             QVariantList() << QVariant(QString("a"))
 278                                                                            << QVariant(QString("b"))
 279                                                                            << QVariant(QString("c")));
 280    QJsonRpcMessage response = serviceSocket.sendMessageBlocking(request);
 281    QCOMPARE(spyMessageReceived.count(), 1);
 282    QVERIFY(response.errorCode() == QJsonRpc::NoError);
 283    QCOMPARE(request.id(), response.id());
 284    QCOMPARE(response.result().toString(), QLatin1String("abc"));
 285}
 286
 287void TestQJsonRpcServer::testLocalVariantParameter()
 288{
 289    // Initialize the service provider.
 290    QJsonRpcLocalServer serviceProvider;
 291    serviceProvider.addService(new TestService);
 292    QVERIFY(serviceProvider.listen("test"));
 293
 294    // Connect to the socket.
 295    QLocalSocket socket;
 296    socket.connectToServer("test");
 297    QVERIFY(socket.waitForConnected());
 298    QJsonRpcSocket serviceSocket(&socket, this);
 299    QSignalSpy spyMessageReceived(&serviceSocket,
 300                                  SIGNAL(messageReceived(QJsonRpcMessage)));
 301
 302    QJsonRpcMessage request = QJsonRpcMessage::createRequest("service.variantParameter",
 303                                                             QVariantList() << QVariant(true));
 304    QJsonRpcMessage response = serviceSocket.sendMessageBlocking(request);
 305    QCOMPARE(spyMessageReceived.count(), 1);
 306    QVERIFY(response.errorCode() == QJsonRpc::NoError);
 307    QCOMPARE(request.id(), response.id());
 308    QVERIFY(response.result() == true);
 309}
 310
 311void TestQJsonRpcServer::testLocalVariantListParameter()
 312{
 313    // Initialize the service provider.
 314    QJsonRpcLocalServer serviceProvider;
 315    serviceProvider.addService(new TestService);
 316    QVERIFY(serviceProvider.listen("test"));
 317
 318    // Connect to the socket.
 319    QLocalSocket socket;
 320    socket.connectToServer("test");
 321    QVERIFY(socket.waitForConnected());
 322    QJsonRpcSocket serviceSocket(&socket, this);
 323    QSignalSpy spyMessageReceived(&serviceSocket,
 324                                  SIGNAL(messageReceived(QJsonRpcMessage)));
 325
 326    QVariantList data;
 327    data << 1 << 20 << "hello" << false;
 328    QJsonRpcMessage request = QJsonRpcMessage::createRequest("service.variantListParameter",
 329                                                             QVariantList() << QVariant(data));
 330    QJsonRpcMessage response = serviceSocket.sendMessageBlocking(request);
 331    QCOMPARE(spyMessageReceived.count(), 1);
 332    QVERIFY(response.errorCode() == QJsonRpc::NoError);
 333    QCOMPARE(request.id(), response.id());
 334    QCOMPARE(response.result().toList(), data);
 335}
 336
 337void TestQJsonRpcServer::testLocalVariantResult()
 338{
 339    // Initialize the service provider.
 340    QJsonRpcLocalServer serviceProvider;
 341    serviceProvider.addService(new TestService);
 342    QVERIFY(serviceProvider.listen("test"));
 343
 344    // Connect to the socket.
 345    QLocalSocket socket;
 346    socket.connectToServer("test");
 347    QVERIFY(socket.waitForConnected());
 348    QJsonRpcSocket serviceSocket(&socket, this);
 349
 350
 351    QJsonRpcMessage response = serviceSocket.invokeRemoteMethodBlocking("service.variantStringResult");
 352    QVERIFY(response.errorCode() == QJsonRpc::NoError);
 353    QString stringResult = response.result().toString();
 354    QCOMPARE(stringResult, QLatin1String("hello"));
 355}
 356
 357void TestQJsonRpcServer::testLocalInvalidArgs()
 358{
 359    // Initialize the service provider.
 360    QJsonRpcLocalServer serviceProvider;
 361    serviceProvider.addService(new TestService);
 362    QVERIFY(serviceProvider.listen("test"));
 363
 364    // Connect to the socket.
 365    QLocalSocket socket;
 366    socket.connectToServer("test");
 367    QVERIFY(socket.waitForConnected());
 368    QJsonRpcSocket serviceSocket(&socket, this);
 369    QSignalSpy spyMessageReceived(&serviceSocket,
 370                                  SIGNAL(messageReceived(QJsonRpcMessage)));
 371
 372    QJsonRpcMessage request = QJsonRpcMessage::createRequest("service.noParam",
 373                                                             QVariantList() << false);
 374    serviceSocket.sendMessageBlocking(request);
 375    QCOMPARE(spyMessageReceived.count(), 1);
 376    QVariant message = spyMessageReceived.takeFirst().at(0);
 377    QJsonRpcMessage error = message.value<QJsonRpcMessage>();
 378    QCOMPARE(request.id(), error.id());
 379    QVERIFY(error.errorCode() == QJsonRpc::InvalidParams);
 380}
 381
 382void TestQJsonRpcServer::testLocalMethodNotFound()
 383{
 384    // Initialize the service provider.
 385    QJsonRpcLocalServer serviceProvider;
 386    serviceProvider.addService(new TestService);
 387    QVERIFY(serviceProvider.listen("test"));
 388
 389    // Connect to the socket.
 390    QLocalSocket socket;
 391    socket.connectToServer("test");
 392    QVERIFY(socket.waitForConnected());
 393    QJsonRpcSocket serviceSocket(&socket, this);
 394    QSignalSpy spyMessageReceived(&serviceSocket,
 395                                  SIGNAL(messageReceived(QJsonRpcMessage)));
 396
 397    QJsonRpcMessage request = QJsonRpcMessage::createRequest("service.doesNotExist");
 398    QJsonRpcMessage response = serviceSocket.sendMessageBlocking(request);
 399    QCOMPARE(spyMessageReceived.count(), 1);
 400    QVERIFY(response.isValid());
 401    QVariant message = spyMessageReceived.takeFirst().at(0);
 402    QJsonRpcMessage error = message.value<QJsonRpcMessage>();
 403    QCOMPARE(request.id(), error.id());
 404    QVERIFY(error.errorCode() == QJsonRpc::MethodNotFound);
 405}
 406
 407void TestQJsonRpcServer::testLocalInvalidRequest()
 408{
 409    // Initialize the service provider.
 410    QJsonRpcLocalServer serviceProvider;
 411    serviceProvider.addService(new TestService);
 412    QVERIFY(serviceProvider.listen("test"));
 413
 414    // Connect to the socket.
 415    QLocalSocket socket;
 416    socket.connectToServer("test");
 417    QVERIFY(socket.waitForConnected());
 418    QJsonRpcSocket serviceSocket(&socket, this);
 419    QSignalSpy spyMessageReceived(&serviceSocket,
 420                                  SIGNAL(messageReceived(QJsonRpcMessage)));
 421
 422    QJsonRpcMessage request("{\"jsonrpc\": \"2.0\", \"id\": 666}");
 423    serviceSocket.sendMessageBlocking(request);
 424
 425    QCOMPARE(spyMessageReceived.count(), 1);
 426    QVariant message = spyMessageReceived.takeFirst().at(0);
 427    QJsonRpcMessage error = message.value<QJsonRpcMessage>();
 428    QCOMPARE(request.id(), error.id());
 429    QVERIFY(error.errorCode() == QJsonRpc::InvalidRequest);
 430}
 431
 432void TestQJsonRpcServer::testLocalNoWhitespace()
 433{
 434    // Initialize the service provider.
 435    QJsonRpcLocalServer serviceProvider;
 436    TestService *service = new TestService;
 437    serviceProvider.addService(service);
 438    QVERIFY(serviceProvider.listen("test"));
 439
 440    // Connect to the socket.
 441    QLocalSocket socket;
 442    socket.connectToServer("test");
 443    QVERIFY(socket.waitForConnected());
 444
 445    QByteArray singleNoWhite("{\"jsonrpc\":\"2.0\",\"method\":\"service.increaseCalled\"}");
 446    QCOMPARE(socket.write(singleNoWhite), (qint64)singleNoWhite.size());
 447    QTest::qWait(200);
 448    QCOMPARE(service->callCount(), 1);
 449
 450    service->resetCount();
 451    QByteArray multipleNoWhite("{\"jsonrpc\":\"2.0\",\"method\":\"service.increaseCalled\"}{\"jsonrpc\":\"2.0\",\"method\":\"service.increaseCalled\"}{\"jsonrpc\":\"2.0\",\"method\":\"service.increaseCalled\"}");
 452    QCOMPARE(socket.write(multipleNoWhite), (qint64)multipleNoWhite.size());
 453    QTest::qWait(200);
 454    QCOMPARE(service->callCount(), 3);
 455}
 456
 457void TestQJsonRpcServer::testLocalQVariantMapInvalidParam()
 458{
 459    QJsonRpcLocalServer serviceProvider;
 460    TestService *service = new TestService;
 461    serviceProvider.addService(service);
 462    QVERIFY(serviceProvider.listen("test"));
 463
 464    QLocalSocket socket;
 465    socket.connectToServer("test");
 466    QVERIFY(socket.waitForConnected());
 467    QJsonRpcSocket serviceSocket(&socket, this);
 468    QSignalSpy spyMessageReceived(&serviceSocket,
 469                                  SIGNAL(messageReceived(QJsonRpcMessage)));
 470
 471    const char *invalid = "{\"jsonrpc\": \"2.0\", \"id\": 0, \"method\": \"service.variantMapInvalidParam\",\"params\": [[{\"foo\":\"bar\",\"baz\":\"quux\"}, {\"foo\":\"bar\"}]]}";
 472    QJsonRpcMessage request(invalid);
 473    serviceSocket.sendMessageBlocking(request);
 474
 475    QCOMPARE(spyMessageReceived.count(), 1);
 476    QVariant message = spyMessageReceived.takeFirst().at(0);
 477    QJsonRpcMessage error = message.value<QJsonRpcMessage>();
 478    QCOMPARE(request.id(), error.id());
 479    QVERIFY(error.errorCode() == QJsonRpc::InvalidParams);
 480}
 481
 482class ServerNotificationHelper : public QObject
 483{
 484    Q_OBJECT
 485public:
 486    ServerNotificationHelper(const QJsonRpcMessage &message, QJsonRpcServer *provider)
 487        : m_provider(provider),
 488          m_notification(message) {}
 489
 490public Q_SLOTS:
 491    void activate() {
 492        m_provider->notifyConnectedClients(m_notification);
 493    }
 494
 495private:
 496    QJsonRpcServer *m_provider;
 497    QJsonRpcMessage m_notification;
 498
 499};
 500
 501void TestQJsonRpcServer::testLocalNotifyConnectedClients()
 502{
 503    // Initialize the service provider.
 504    QEventLoop firstLoop;
 505    QJsonRpcLocalServer serviceProvider;
 506    QVERIFY(serviceProvider.listen("test"));
 507    serviceProvider.addService(new TestService);
 508
 509    // first client
 510    QLocalSocket first;
 511    first.connectToServer("test");
 512    QVERIFY(first.waitForConnected());
 513    QJsonRpcSocket firstClient(&first, this);
 514    QSignalSpy firstSpyMessageReceived(&firstClient,
 515                                  SIGNAL(messageReceived(QJsonRpcMessage)));
 516
 517    // send notification
 518    QJsonRpcMessage notification = QJsonRpcMessage::createNotification("testNotification");
 519    connect(&firstClient, SIGNAL(messageReceived(QJsonRpcMessage)), &firstLoop, SLOT(quit()));
 520    ServerNotificationHelper helper(notification, &serviceProvider);
 521    QTimer::singleShot(100, &helper, SLOT(activate()));
 522    firstLoop.exec();
 523
 524    QCOMPARE(firstSpyMessageReceived.count(), 1);
 525    QVariant firstMessage = firstSpyMessageReceived.takeFirst().at(0);
 526    QJsonRpcMessage firstNotification = firstMessage.value<QJsonRpcMessage>();
 527    QCOMPARE(firstNotification, notification);
 528}
 529
 530
 531class TestNumberParamsService : public QJsonRpcService
 532{
 533    Q_OBJECT
 534    Q_CLASSINFO("serviceName", "service")
 535public:
 536    TestNumberParamsService(QObject *parent = 0)
 537        : QJsonRpcService(parent), m_called(0) {}
 538
 539    int callCount() const { return m_called; }
 540
 541public Q_SLOTS:
 542    void numberParameters(int intParam, double doubleParam)
 543    {
 544        if (intParam == 10 && doubleParam == 3.14159)
 545            m_called++;
 546    }
 547
 548private:
 549    int m_called;
 550
 551};
 552
 553void TestQJsonRpcServer::testLocalNumberParameters()
 554{
 555    // Initialize the service provider.
 556    QEventLoop loop;
 557    TestNumberParamsService *service = new TestNumberParamsService;
 558    QJsonRpcLocalServer serviceProvider;
 559    serviceProvider.addService(service);
 560    QVERIFY(serviceProvider.listen("test"));
 561
 562    // Connect to the socket.
 563    QLocalSocket socket;
 564    socket.connectToServer("test");
 565    QVERIFY(socket.waitForConnected());
 566    QJsonRpcSocket serviceSocket(&socket, this);
 567    QJsonRpcMessage request = QJsonRpcMessage::createRequest("service.numberParameters", QVariantList() << 10 << 3.14159);
 568    serviceSocket.sendMessageBlocking(request);
 569    QCOMPARE(service->callCount(), 1);
 570}
 571
 572class TestHugeResponseService : public QJsonRpcService
 573{
 574    Q_OBJECT
 575    Q_CLASSINFO("serviceName", "service")
 576public:
 577    TestHugeResponseService(QObject *parent = 0)
 578        : QJsonRpcService(parent) {}
 579
 580public Q_SLOTS:
 581    QVariantMap hugeResponse()
 582    {
 583        QVariantMap result;
 584        for (int i = 0; i < 1000; i++) {
 585            QString key = QString("testKeyForHugeResponse%1").arg(i);
 586            result[key] = "some sample data to make the response larger";
 587        }
 588        return result;
 589    }
 590};
 591
 592void TestQJsonRpcServer::testLocalHugeResponse()
 593{
 594    // Initialize the service provider.
 595    QJsonRpcLocalServer serviceProvider;
 596    serviceProvider.addService(new TestHugeResponseService);
 597    QVERIFY(serviceProvider.listen("test"));
 598
 599    // Connect to the socket.
 600    QLocalSocket socket;
 601    socket.connectToServer("test");
 602    QVERIFY(socket.waitForConnected());
 603    QJsonRpcSocket serviceSocket(&socket, this);
 604    QSignalSpy spyMessageReceived(&serviceSocket,
 605                                  SIGNAL(messageReceived(QJsonRpcMessage)));
 606
 607    QJsonRpcMessage request = QJsonRpcMessage::createRequest("service.hugeResponse");
 608    QJsonRpcMessage response = serviceSocket.sendMessageBlocking(request);
 609    QCOMPARE(spyMessageReceived.count(), 1);
 610    QVERIFY(response.isValid());
 611}
 612
 613class TestComplexMethodService : public QJsonRpcService
 614{
 615    Q_OBJECT
 616    Q_CLASSINFO("serviceName", "service.complex.prefix.for")
 617public:
 618    TestComplexMethodService(QObject *parent = 0)
 619        : QJsonRpcService(parent) {}
 620
 621public Q_SLOTS:
 622    void testMethod() {}
 623};
 624
 625void TestQJsonRpcServer::testLocalComplexMethod()
 626{
 627    // Initialize the service provider.
 628    QEventLoop loop;
 629    QJsonRpcLocalServer serviceProvider;
 630    serviceProvider.addService(new TestComplexMethodService);
 631    QVERIFY(serviceProvider.listen("test"));
 632
 633    // Connect to the socket.
 634    QLocalSocket socket;
 635    socket.connectToServer("test");
 636    QVERIFY(socket.waitForConnected());
 637    QJsonRpcSocket serviceSocket(&socket, this);
 638    QSignalSpy spyMessageReceived(&serviceSocket,
 639                                  SIGNAL(messageReceived(QJsonRpcMessage)));
 640
 641    QJsonRpcMessage request = QJsonRpcMessage::createRequest("service.complex.prefix.for.testMethod");
 642    QJsonRpcMessage response = serviceSocket.sendMessageBlocking(request);
 643    QCOMPARE(spyMessageReceived.count(), 1);
 644    QVERIFY(response.errorCode() == QJsonRpc::NoError);
 645    QCOMPARE(request.id(), response.id());
 646}
 647
 648class TestDefaultParametersService : public QJsonRpcService
 649{
 650    Q_OBJECT
 651    Q_CLASSINFO("serviceName", "service")
 652public:
 653    TestDefaultParametersService(QObject *parent = 0)
 654        : QJsonRpcService(parent) {}
 655
 656public Q_SLOTS:
 657    QString testMethod(const QString &name = QString()) {
 658        if (name.isEmpty())
 659            return "empty string";
 660        return QString("hello %1").arg(name);
 661    }
 662
 663    QString testMethod2(const QString &name = QString(), int year = 2012)
 664    {
 665        return QString("%1%2").arg(name).arg(year);
 666    }
 667};
 668
 669void TestQJsonRpcServer::testLocalDefaultParameters()
 670{
 671    // Initialize the service provider.
 672    QEventLoop loop;
 673    QJsonRpcLocalServer serviceProvider;
 674    serviceProvider.addService(new TestDefaultParametersService);
 675    QVERIFY(serviceProvider.listen("test"));
 676
 677    // Connect to the socket.
 678    QLocalSocket socket;
 679    socket.connectToServer("test");
 680    QVERIFY(socket.waitForConnected());
 681    QJsonRpcSocket serviceSocket(&socket, this);
 682
 683    // test without name
 684    QJsonRpcMessage noNameRequest = QJsonRpcMessage::createRequest("service.testMethod");
 685    QJsonRpcMessage response = serviceSocket.sendMessageBlocking(noNameRequest);
 686    QVERIFY(response.type() != QJsonRpcMessage::Error);
 687    QCOMPARE(response.result().toString(), QLatin1String("empty string"));
 688
 689    // test with name
 690    QJsonRpcMessage nameRequest = QJsonRpcMessage::createRequest("service.testMethod", QLatin1String("matt"));
 691    response = serviceSocket.sendMessageBlocking(nameRequest);
 692    QVERIFY(response.type() != QJsonRpcMessage::Error);
 693    QCOMPARE(response.result().toString(), QLatin1String("hello matt"));
 694
 695    // test multiparameter
 696    QJsonRpcMessage konyRequest = QJsonRpcMessage::createRequest("service.testMethod2", QLatin1String("KONY"));
 697    response = serviceSocket.sendMessageBlocking(konyRequest);
 698    QVERIFY(response.type() != QJsonRpcMessage::Error);
 699    QCOMPARE(response.result().toString(), QLatin1String("KONY2012"));
 700}
 701
 702class TestNotifyService : public QJsonRpcService
 703{
 704    Q_OBJECT
 705    Q_CLASSINFO("serviceName", "service")
 706public:
 707    TestNotifyService(QObject *parent = 0)
 708        : QJsonRpcService(parent)
 709    {
 710    }
 711
 712public Q_SLOTS:
 713    void testMethod() { qDebug() << "text"; }
 714};
 715
 716void TestQJsonRpcServer::testLocalNotifyServiceSocket()
 717{
 718    // Initialize the service provider.
 719    QJsonRpcLocalServer serviceProvider;
 720    QVERIFY(serviceProvider.listen("test"));
 721
 722    // Connect to the socket.
 723    QLocalSocket socket;
 724    socket.connectToServer("test");
 725    QVERIFY(socket.waitForConnected());
 726
 727    QJsonRpcServiceSocket serviceSocket(&socket);
 728    TestNumberParamsService *service = new TestNumberParamsService;
 729    serviceSocket.addService(service);
 730    QCOMPARE(service->callCount(), 0);
 731
 732    QEventLoop test;
 733    QTimer::singleShot(10, &test, SLOT(quit()));
 734    test.exec();
 735    serviceProvider.notifyConnectedClients("service.numberParameters", QVariantList() << 10 << 3.14159);
 736    QTimer::singleShot(10, &test, SLOT(quit()));
 737    test.exec();
 738
 739    QCOMPARE(service->callCount(), 1);
 740}
 741
 742Q_DECLARE_METATYPE(QList<int>)
 743void TestQJsonRpcServer::testLocalListOfInts()
 744{
 745    // Initialize the service provider.
 746    QEventLoop loop;
 747    QJsonRpcLocalServer serviceProvider;
 748    serviceProvider.addService(new TestService);
 749    QVERIFY(serviceProvider.listen("test"));
 750
 751    // Connect to the socket.
 752    QLocalSocket socket;
 753    socket.connectToServer("test");
 754    QVERIFY(socket.waitForConnected());
 755    QJsonRpcSocket serviceSocket(&socket, this);
 756
 757    qRegisterMetaType<QList<int> >("QList<int>");
 758    QList<int> intList = QList<int>() << 300 << 30 << 3;
 759    QVariant variant = QVariant::fromValue(intList);
 760
 761    QJsonRpcMessage intRequest = QJsonRpcMessage::createRequest("service.methodWithListOfInts", variant);
 762    QJsonRpcMessage response = serviceSocket.sendMessageBlocking(intRequest);
 763    QVERIFY(response.type() != QJsonRpcMessage::Error);
 764    QVERIFY(response.result().toBool());
 765}
 766
 767
 768
 769
 770
 771
 772
 773void TestQJsonRpcServer::testTcpNoParameter()
 774{
 775    // Initialize the service provider.
 776    QJsonRpcTcpServer serviceProvider;
 777    serviceProvider.addService(new TestService);
 778    QVERIFY(serviceProvider.listen(QHostAddress::LocalHost, 5555));
 779
 780    // Connect to the socket.
 781    QTcpSocket socket;
 782    socket.connectToHost(QHostAddress::LocalHost, 5555);
 783    QVERIFY(socket.waitForConnected());
 784
 785    QJsonRpcSocket serviceSocket(&socket, this);
 786    QSignalSpy spyMessageReceived(&serviceSocket,
 787                                  SIGNAL(messageReceived(QJsonRpcMessage)));
 788
 789    QJsonRpcMessage request = QJsonRpcMessage::createRequest("service.noParam");
 790    QJsonRpcMessage response = serviceSocket.sendMessageBlocking(request);
 791    QCOMPARE(spyMessageReceived.count(), 1);
 792    QVERIFY(response.errorCode() == QJsonRpc::NoError);
 793    QCOMPARE(request.id(), response.id());
 794}
 795
 796void TestQJsonRpcServer::testTcpSingleParameter()
 797{
 798    // Initialize the service provider.
 799    QJsonRpcTcpServer serviceProvider;
 800    serviceProvider.addService(new TestService);
 801    QVERIFY(serviceProvider.listen(QHostAddress::LocalHost, 5555));
 802
 803    // Connect to the socket.
 804    QTcpSocket socket;
 805    socket.connectToHost(QHostAddress::LocalHost, 5555);
 806    QVERIFY(socket.waitForConnected());
 807    QJsonRpcSocket serviceSocket(&socket, this);
 808    QSignalSpy spyMessageReceived(&serviceSocket,
 809                                  SIGNAL(messageReceived(QJsonRpcMessage)));
 810
 811    QJsonRpcMessage request = QJsonRpcMessage::createRequest("service.singleParam", QString("single"));
 812    QJsonRpcMessage response = serviceSocket.sendMessageBlocking(request);
 813    QCOMPARE(spyMessageReceived.count(), 1);
 814    QVERIFY(response.errorCode() == QJsonRpc::NoError);
 815    QCOMPARE(request.id(), response.id());
 816    QCOMPARE(response.result().toString(), QLatin1String("single"));
 817}
 818
 819void TestQJsonRpcServer::testTcpMultiparameter()
 820{
 821    // Initialize the service provider.
 822    QJsonRpcTcpServer serviceProvider;
 823    serviceProvider.addService(new TestService);
 824    QVERIFY(serviceProvider.listen(QHostAddress::LocalHost, 5555));
 825
 826    // Connect to the socket.
 827    QTcpSocket socket;
 828    socket.connectToHost(QHostAddress::LocalHost, 5555);
 829    QVERIFY(socket.waitForConnected());
 830    QJsonRpcSocket serviceSocket(&socket, this);
 831    QSignalSpy spyMessageReceived(&serviceSocket,
 832                                  SIGNAL(messageReceived(QJsonRpcMessage)));
 833
 834    QJsonRpcMessage request = QJsonRpcMessage::createRequest("service.multipleParam",
 835                                                             QVariantList() << QVariant(QString("a"))
 836                                                                            << QVariant(QString("b"))
 837                                                                            << QVariant(QString("c")));
 838    QJsonRpcMessage response = serviceSocket.sendMessageBlocking(request);
 839    QCOMPARE(spyMessageReceived.count(), 1);
 840    QVERIFY(response.errorCode() == QJsonRpc::NoError);
 841    QCOMPARE(request.id(), response.id());
 842    QCOMPARE(response.result().toString(), QLatin1String("abc"));
 843}
 844
 845void TestQJsonRpcServer::testTcpVariantParameter()
 846{
 847    // Initialize the service provider.
 848    QJsonRpcTcpServer serviceProvider;
 849    serviceProvider.addService(new TestService);
 850    QVERIFY(serviceProvider.listen(QHostAddress::LocalHost, 5555));
 851
 852    // Connect to the socket.
 853    QTcpSocket socket;
 854    socket.connectToHost(QHostAddress::LocalHost, 5555);
 855    QVERIFY(socket.waitForConnected());
 856    QJsonRpcSocket serviceSocket(&socket, this);
 857    QSignalSpy spyMessageReceived(&serviceSocket,
 858                                  SIGNAL(messageReceived(QJsonRpcMessage)));
 859
 860    QJsonRpcMessage request = QJsonRpcMessage::createRequest("service.variantParameter",
 861                                                             QVariantList() << QVariant(true));
 862    QJsonRpcMessage response = serviceSocket.sendMessageBlocking(request);
 863    QCOMPARE(spyMessageReceived.count(), 1);
 864    QVERIFY(response.errorCode() == QJsonRpc::NoError);
 865    QCOMPARE(request.id(), response.id());
 866    QVERIFY(response.result() == true);
 867}
 868
 869void TestQJsonRpcServer::testTcpInvalidArgs()
 870{
 871    // Initialize the service provider.
 872    QJsonRpcTcpServer serviceProvider;
 873    serviceProvider.addService(new TestService);
 874    QVERIFY(serviceProvider.listen(QHostAddress::LocalHost, 5555));
 875
 876    // Connect to the socket.
 877    QTcpSocket socket;
 878    socket.connectToHost(QHostAddress::LocalHost, 5555);
 879    QVERIFY(socket.waitForConnected());
 880    QJsonRpcSocket serviceSocket(&socket, this);
 881    QSignalSpy spyMessageReceived(&serviceSocket,
 882                                  SIGNAL(messageReceived(QJsonRpcMessage)));
 883
 884    QJsonRpcMessage request = QJsonRpcMessage::createRequest("service.noParam",
 885                                                             QVariantList() << false);
 886    serviceSocket.sendMessageBlocking(request);
 887    QCOMPARE(spyMessageReceived.count(), 1);
 888    QVariant message = spyMessageReceived.takeFirst().at(0);
 889    QJsonRpcMessage error = message.value<QJsonRpcMessage>();
 890    QCOMPARE(request.id(), error.id());
 891    QVERIFY(error.errorCode() == QJsonRpc::InvalidParams);
 892}
 893
 894void TestQJsonRpcServer::testTcpMethodNotFound()
 895{
 896    // Initialize the service provider.
 897    QJsonRpcTcpServer serviceProvider;
 898    serviceProvider.addService(new TestService);
 899    QVERIFY(serviceProvider.listen(QHostAddress::LocalHost, 5555));
 900
 901    // Connect to the socket.
 902    QTcpSocket socket;
 903    socket.connectToHost(QHostAddress::LocalHost, 5555);
 904    QVERIFY(socket.waitForConnected());
 905    QJsonRpcSocket serviceSocket(&socket, this);
 906    QSignalSpy spyMessageReceived(&serviceSocket,
 907                                  SIGNAL(messageReceived(QJsonRpcMessage)));
 908
 909    QJsonRpcMessage request = QJsonRpcMessage::createRequest("service.doesNotExist");
 910    serviceSocket.sendMessageBlocking(request);
 911    QCOMPARE(spyMessageReceived.count(), 1);
 912    QVariant message = spyMessageReceived.takeFirst().at(0);
 913    QJsonRpcMessage error = message.value<QJsonRpcMessage>();
 914    QCOMPARE(request.id(), error.id());
 915    QVERIFY(error.errorCode() == QJsonRpc::MethodNotFound);
 916}
 917
 918void TestQJsonRpcServer::testTcpInvalidRequest()
 919{
 920    // Initialize the service provider.
 921    QJsonRpcTcpServer serviceProvider;
 922    serviceProvider.addService(new TestService);
 923    QVERIFY(serviceProvider.listen(QHostAddress::LocalHost, 5555));
 924
 925    // Connect to the socket.
 926    QTcpSocket socket;
 927    socket.connectToHost(QHostAddress::LocalHost, 5555);
 928    QVERIFY(socket.waitForConnected());
 929    QJsonRpcSocket serviceSocket(&socket, this);
 930    QSignalSpy spyMessageReceived(&serviceSocket,
 931                                  SIGNAL(messageReceived(QJsonRpcMessage)));
 932
 933    QJsonRpcMessage request("{\"jsonrpc\": \"2.0\", \"id\": 666}");
 934    serviceSocket.sendMessageBlocking(request);
 935    QCOMPARE(spyMessageReceived.count(), 1);
 936    QVariant message = spyMessageReceived.takeFirst().at(0);
 937    QJsonRpcMessage error = message.value<QJsonRpcMessage>();
 938    QCOMPARE(request.id(), error.id());
 939    QVERIFY(error.errorCode() == QJsonRpc::InvalidRequest);
 940}
 941
 942void TestQJsonRpcServer::testTcpNotifyConnectedClients()
 943{
 944    // Initialize the service provider.
 945    QEventLoop firstLoop;
 946    QJsonRpcTcpServer serviceProvider;
 947    serviceProvider.addService(new TestService);
 948    QVERIFY(serviceProvider.listen(QHostAddress::LocalHost, 5555));
 949
 950    // first client
 951    QTcpSocket first;
 952    first.connectToHost(QHostAddress::LocalHost, 5555);
 953    QVERIFY(first.waitForConnected());
 954    QJsonRpcSocket firstClient(&first, this);
 955    QSignalSpy firstSpyMessageReceived(&firstClient,
 956                                  SIGNAL(messageReceived(QJsonRpcMessage)));
 957
 958    // send notification
 959    QJsonRpcMessage notification = QJsonRpcMessage::createNotification("testNotification");
 960    connect(&firstClient, SIGNAL(messageReceived(QJsonRpcMessage)), &firstLoop, SLOT(quit()));
 961    ServerNotificationHelper helper(notification, &serviceProvider);
 962    QTimer::singleShot(100, &helper, SLOT(activate()));
 963    firstLoop.exec();
 964
 965    QCOMPARE(firstSpyMessageReceived.count(), 1);
 966    QVariant firstMessage = firstSpyMessageReceived.takeFirst().at(0);
 967    QJsonRpcMessage firstNotification = firstMessage.value<QJsonRpcMessage>();
 968    QCOMPARE(firstNotification, notification);
 969}
 970
 971void TestQJsonRpcServer::testTcpNumberParameters()
 972{
 973    // Initialize the service provider.
 974    TestNumberParamsService *service = new TestNumberParamsService;
 975    QJsonRpcTcpServer serviceProvider;
 976    serviceProvider.addService(service);
 977    QVERIFY(serviceProvider.listen(QHostAddress::LocalHost, 5555));
 978
 979    // Connect to the socket.
 980    QTcpSocket socket;
 981    socket.connectToHost(QHostAddress::LocalHost, 5555);
 982    QVERIFY(socket.waitForConnected());
 983    QJsonRpcSocket serviceSocket(&socket, this);
 984    QJsonRpcMessage request = QJsonRpcMessage::createRequest("service.numberParameters", QVariantList() << 10 << 3.14159);
 985    serviceSocket.sendMessageBlocking(request);
 986    QCOMPARE(service->callCount(), 1);
 987}
 988
 989void TestQJsonRpcServer::testTcpHugeResponse()
 990{
 991    // Initialize the service provider.
 992    QJsonRpcTcpServer serviceProvider;
 993    serviceProvider.addService(new TestHugeResponseService(this));
 994    QVERIFY(serviceProvider.listen(QHostAddress::LocalHost, 5555));
 995
 996    // Connect to the socket.
 997    QTcpSocket socket;
 998    socket.connectToHost(QHostAddress::LocalHost, 5555);
 999    QVERIFY(socket.waitForConnected());
1000    QJsonRpcSocket serviceSocket(&socket, this);
1001    QSignalSpy spyMessageReceived(&serviceSocket,
1002                                  SIGNAL(messageReceived(QJsonRpcMessage)));
1003
1004    QJsonRpcMessage request = QJsonRpcMessage::createRequest("service.hugeResponse");
1005    QJsonRpcMessage response = serviceSocket.sendMessageBlocking(request);
1006    QCOMPARE(spyMessageReceived.count(), 1);
1007    QVERIFY(response.isValid());
1008}
1009
1010QTEST_MAIN(TestQJsonRpcServer)
1011#include "tst_qjsonrpcserver.moc"