diff --git a/plugins/deviceplugins/mock/devicepluginmock.cpp b/plugins/deviceplugins/mock/devicepluginmock.cpp index d30479db..83d088e8 100644 --- a/plugins/deviceplugins/mock/devicepluginmock.cpp +++ b/plugins/deviceplugins/mock/devicepluginmock.cpp @@ -56,6 +56,11 @@ DeviceManager::DeviceError DevicePluginMock::discoverDevices(const DeviceClassId m_discoveredDeviceCount = params.paramValue("resultCount").toInt(); QTimer::singleShot(1000, this, SLOT(emitPushButtonDevicesDiscovered())); return DeviceManager::DeviceErrorAsync; + } else if (deviceClassId == mockDisplayPinDeviceClassId) { + qCDebug(dcMockDevice) << "starting mock display pin discovery:" << params; + m_discoveredDeviceCount = params.paramValue("resultCount").toInt(); + QTimer::singleShot(1000, this, SLOT(emitDisplayPinDevicesDiscovered())); + return DeviceManager::DeviceErrorAsync; } return DeviceManager::DeviceErrorDeviceClassNotFound; } @@ -94,7 +99,11 @@ DeviceManager::DeviceSetupStatus DevicePluginMock::setupDevice(Device *device) } else if (device->deviceClassId() == mockPushButtonDeviceClassId) { qCDebug(dcMockDevice) << "Setup PushButton Mock device" << device->params(); return DeviceManager::DeviceSetupStatusSuccess; + } else if (device->deviceClassId() == mockDisplayPinDeviceClassId) { + qCDebug(dcMockDevice) << "Setup DisplayPin Mock device" << device->params(); + return DeviceManager::DeviceSetupStatusSuccess; } + return DeviceManager::DeviceSetupStatusFailure; } @@ -133,18 +142,37 @@ DeviceManager::DeviceSetupStatus DevicePluginMock::confirmPairing(const PairingT qCDebug(dcMockDevice) << "Confirm pairing"; - if (deviceClassId != mockPushButtonDeviceClassId) { - qCWarning(dcMockDevice) << "Invalid deviceclassId -> no pairing possible with this device"; - return DeviceManager::DeviceSetupStatusFailure; - } - if (!m_pushbuttonPressed) { - qCDebug(dcMockDevice) << "PushButton not pressed yet!"; - return DeviceManager::DeviceSetupStatusFailure; + if (deviceClassId == mockPushButtonDeviceClassId) { + if (!m_pushbuttonPressed) { + qCDebug(dcMockDevice) << "PushButton not pressed yet!"; + return DeviceManager::DeviceSetupStatusFailure; + } + + m_pairingId = pairingTransactionId; + QTimer::singleShot(1000, this, SLOT(onPushButtonPairingFinished())); + return DeviceManager::DeviceSetupStatusAsync; + } else if (deviceClassId == mockDisplayPinDeviceClassId) { + if (secret != "243681") { + qCWarning(dcMockDevice) << "Invalid pin:" << secret; + return DeviceManager::DeviceSetupStatusFailure; + } + m_pairingId = pairingTransactionId; + QTimer::singleShot(500, this, SLOT(onDisplayPinPairingFinished())); + return DeviceManager::DeviceSetupStatusAsync; } - m_pairingId = pairingTransactionId; - QTimer::singleShot(1000, this, SLOT(onPushButtonPairingFinished())); - return DeviceManager::DeviceSetupStatusAsync; + qCWarning(dcMockDevice) << "Invalid deviceclassId -> no pairing possible with this device"; + return DeviceManager::DeviceSetupStatusFailure; +} + +DeviceManager::DeviceError DevicePluginMock::displayPin(const PairingTransactionId &pairingTransactionId, const DeviceDescriptor &deviceDescriptor) +{ + Q_UNUSED(pairingTransactionId) + Q_UNUSED(deviceDescriptor) + + qCDebug(dcMockDevice) << "Display pin!! The pin is 243681"; + + return DeviceManager::DeviceErrorNoError; } QList DevicePluginMock::configurationDescription() const @@ -177,7 +205,7 @@ DeviceManager::DeviceError DevicePluginMock::executeAction(Device *device, const m_daemons.value(device)->actionExecuted(action.actionTypeId()); return DeviceManager::DeviceErrorNoError; - } else if (device->deviceClassId() == mockPushButtonDeviceClassId) { + } else if (device->deviceClassId() == mockPushButtonDeviceClassId || device->deviceClassId() == mockDisplayPinDeviceClassId) { if (action.actionTypeId() == colorActionTypeId) { QString colorString = action.param("color").value().toString(); QColor color(colorString); @@ -259,7 +287,7 @@ void DevicePluginMock::emitPushButtonDevicesDiscovered() QList deviceDescriptors; if (m_discoveredDeviceCount > 0) { - DeviceDescriptor d1(mockDeviceClassId, "Mock Device (Push Button)", "1"); + DeviceDescriptor d1(mockPushButtonDeviceClassId, "Mock Device (Push Button)", "1"); ParamList params; Param name("name", "PushButton Mock Device 1"); params.append(name); @@ -268,7 +296,7 @@ void DevicePluginMock::emitPushButtonDevicesDiscovered() } if (m_discoveredDeviceCount > 1) { - DeviceDescriptor d2(mockDeviceClassId, "Mock Device (Push Button)", "2"); + DeviceDescriptor d2(mockPushButtonDeviceClassId, "Mock Device (Push Button)", "2"); ParamList params; Param name("name", "PushButton Mock Device 2"); params.append(name); @@ -280,7 +308,31 @@ void DevicePluginMock::emitPushButtonDevicesDiscovered() m_pushbuttonPressed = false; QTimer::singleShot(3000, this, SLOT(onPushButtonPressed())); qDebug() << "Start PushButton timer (will be pressed in 3 second)"; +} +void DevicePluginMock::emitDisplayPinDevicesDiscovered() +{ + QList deviceDescriptors; + + if (m_discoveredDeviceCount > 0) { + DeviceDescriptor d1(mockDisplayPinDeviceClassId, "Mock Device (Display Pin)", "1"); + ParamList params; + Param name("name", "DisplayPin Mock Device 1"); + params.append(name); + d1.setParams(params); + deviceDescriptors.append(d1); + } + + if (m_discoveredDeviceCount > 1) { + DeviceDescriptor d2(mockDisplayPinDeviceClassId, "Mock Device (Display Pin)", "2"); + ParamList params; + Param name("name", "DisplayPin Mock Device 2"); + params.append(name); + d2.setParams(params); + deviceDescriptors.append(d2); + } + + emit devicesDiscovered(mockDisplayPinDeviceClassId, deviceDescriptors); } void DevicePluginMock::onPushButtonPressed() @@ -316,3 +368,9 @@ void DevicePluginMock::onPushButtonPairingFinished() qCDebug(dcMockDevice) << "Pairing PushButton Device finished"; emit pairingFinished(m_pairingId, DeviceManager::DeviceSetupStatusSuccess); } + +void DevicePluginMock::onDisplayPinPairingFinished() +{ + qCDebug(dcMockDevice) << "Pairing DisplayPin Device finished"; + emit pairingFinished(m_pairingId, DeviceManager::DeviceSetupStatusSuccess); +} diff --git a/plugins/deviceplugins/mock/devicepluginmock.h b/plugins/deviceplugins/mock/devicepluginmock.h index e3c8ee87..08ac1cd0 100644 --- a/plugins/deviceplugins/mock/devicepluginmock.h +++ b/plugins/deviceplugins/mock/devicepluginmock.h @@ -48,6 +48,7 @@ public: void startMonitoringAutoDevices() override; DeviceManager::DeviceSetupStatus confirmPairing(const PairingTransactionId &pairingTransactionId, const DeviceClassId &deviceClassId, const ParamList ¶ms, const QString &secret) override; + DeviceManager::DeviceError displayPin(const PairingTransactionId &pairingTransactionId, const DeviceDescriptor &deviceDescriptor) override; QList configurationDescription() const override; @@ -59,11 +60,13 @@ private slots: void triggerEvent(const EventTypeId &id); void emitDevicesDiscovered(); void emitPushButtonDevicesDiscovered(); + void emitDisplayPinDevicesDiscovered(); void emitDeviceSetupFinished(); void emitActionExecuted(); void onPushButtonPressed(); void onPushButtonPairingFinished(); + void onDisplayPinPairingFinished(); private: QHash m_daemons; diff --git a/plugins/deviceplugins/mock/devicepluginmock.json b/plugins/deviceplugins/mock/devicepluginmock.json index f8ff02e4..ec7631ba 100644 --- a/plugins/deviceplugins/mock/devicepluginmock.json +++ b/plugins/deviceplugins/mock/devicepluginmock.json @@ -269,6 +269,80 @@ "name": "Timout action" } ] + }, + { + "deviceClassId": "296f1fd4-e893-46b2-8a42-50d1bceb8730", + "idName": "mockDisplayPin", + "name": "Mock Device (Display Pin)", + "createMethods": ["discovery"], + "setupMethod": "displayPin", + "pairingInfo": "Please enter the secret which normaly will be displayed on the device. For the mockdevice the pin is 243681.", + "discoveryParamTypes": [ + { + "name": "resultCount", + "type": "int", + "defaultValue": 2, + "allowedValues": [1, 2] + } + ], + "paramTypes": [ + { + "name": "name", + "type": "QString", + "inputType": "TextLine", + "defaultValue": "Mock device", + "readOnly": true + }, + { + "name": "pin", + "type": "QString", + "inputType": "TextLine", + "defaultValue": "243681", + "readOnly": true + } + ], + "stateTypes": [ + { + "id": "20dc7c22-c50e-42db-837c-2bbced939f8e", + "idName": "color", + "name": "color", + "type": "QColor", + "defaultValue": "#000000", + "writable": true + }, + { + "id": "72981c04-267a-4ba0-a59e-9921d2f3af9c", + "idName": "percentage", + "name": "percentage", + "type": "int", + "unit": "Percentage", + "defaultValue": 0, + "minValue": 0, + "maxValue": 100, + "writable": true + }, + { + "id": "05f63f9c-f61e-4dcf-ad55-3f13fde2765b", + "idName": "allowedValues", + "name": "allowed values", + "type": "QString", + "defaultValue": "String value 1", + "possibleValues": [ + "String value 1", + "String value 2", + "String value 3", + "String value 4" + ], + "writable": true + } + ], + "actionTypes": [ + { + "id": "54646e7c-bc54-4895-81a2-590d72d120f9", + "idName": "timeout", + "name": "Timout action" + } + ] } ] } diff --git a/tests/auto/devices/testdevices.cpp b/tests/auto/devices/testdevices.cpp index 5a86a9dd..b9eb236a 100644 --- a/tests/auto/devices/testdevices.cpp +++ b/tests/auto/devices/testdevices.cpp @@ -64,6 +64,9 @@ private slots: void addPushButtonDevices_data(); void addPushButtonDevices(); + void addDisplayPinDevices_data(); + void addDisplayPinDevices(); + void getActionTypes_data(); void getActionTypes(); @@ -466,6 +469,69 @@ void TestDevices::addPushButtonDevices() } } +void TestDevices::addDisplayPinDevices_data() +{ + QTest::addColumn("deviceClassId"); + QTest::addColumn("error"); + QTest::addColumn("secret"); + + QTest::newRow("Valid: Add DisplayPin device") << mockDisplayPinDeviceClassId << DeviceManager::DeviceErrorNoError << "243681"; + QTest::newRow("Invalid: Add DisplayPin device (wrong pin)") << mockDisplayPinDeviceClassId << DeviceManager::DeviceErrorSetupFailed << "243682"; +} + +void TestDevices::addDisplayPinDevices() +{ + QFETCH(DeviceClassId, deviceClassId); + QFETCH(DeviceManager::DeviceError, error); + QFETCH(QString, secret); + + // Discover device + QVariantList discoveryParams; + QVariantMap resultCountParam; + resultCountParam.insert("name", "resultCount"); + resultCountParam.insert("value", 1); + discoveryParams.append(resultCountParam); + + QVariantMap params; + params.insert("deviceClassId", deviceClassId); + params.insert("discoveryParams", discoveryParams); + QVariant response = injectAndWait("Devices.GetDiscoveredDevices", params); + + verifyDeviceError(response, DeviceManager::DeviceErrorNoError); + QCOMPARE(response.toMap().value("params").toMap().value("deviceDescriptors").toList().count(), 1); + + // Pair device + DeviceDescriptorId descriptorId = DeviceDescriptorId(response.toMap().value("params").toMap().value("deviceDescriptors").toList().first().toMap().value("id").toString()); + params.clear(); + params.insert("deviceClassId", deviceClassId); + params.insert("deviceDescriptorId", descriptorId.toString()); + response = injectAndWait("Devices.PairDevice", params); + + verifyDeviceError(response); + + PairingTransactionId pairingTransactionId(response.toMap().value("params").toMap().value("pairingTransactionId").toString()); + QString displayMessage = response.toMap().value("params").toMap().value("displayMessage").toString(); + + //qDebug() << "displayMessage" << displayMessage; + + params.clear(); + params.insert("pairingTransactionId", pairingTransactionId.toString()); + params.insert("secret", secret); + response = injectAndWait("Devices.ConfirmPairing", params); + + verifyDeviceError(response, error); + + if (error == DeviceManager::DeviceErrorNoError) { + DeviceId deviceId(response.toMap().value("params").toMap().value("deviceId").toString()); + params.clear(); + params.insert("deviceId", deviceId.toString()); + response = injectAndWait("Devices.RemoveConfiguredDevice", params); + verifyDeviceError(response); + } + + +} + void TestDevices::getActionTypes_data() { QTest::addColumn("deviceClassId"); diff --git a/tests/auto/guhtestbase.cpp b/tests/auto/guhtestbase.cpp index 1c652337..5102f3fb 100644 --- a/tests/auto/guhtestbase.cpp +++ b/tests/auto/guhtestbase.cpp @@ -42,6 +42,7 @@ VendorId guhVendorId = VendorId("2062d64d-3232-433c-88bc-0d33c0ba2ba6"); DeviceClassId mockDeviceClassId = DeviceClassId("753f0d32-0468-4d08-82ed-1964aab03298"); DeviceClassId mockDeviceAutoClassId = DeviceClassId("ab4257b3-7548-47ee-9bd4-7dc3004fd197"); DeviceClassId mockPushButtonDeviceClassId = DeviceClassId("9e03144c-e436-4eea-82d9-ccb33ef778db"); +DeviceClassId mockDisplayPinDeviceClassId = DeviceClassId("296f1fd4-e893-46b2-8a42-50d1bceb8730"); DeviceClassId mockDeviceDiscoveryClassId = DeviceClassId("1bbaf751-36b7-4d3d-b05a-58dab2a3be8c"); DeviceClassId mockDeviceAsyncSetupClassId = DeviceClassId("c08a8b27-8200-413d-b96b-4cff78b864d9"); DeviceClassId mockDeviceBrokenClassId = DeviceClassId("ba5fb404-c9ce-4db4-8cd4-f48c61c24b13"); diff --git a/tests/auto/guhtestbase.h b/tests/auto/guhtestbase.h index 746dadbf..1902e63c 100644 --- a/tests/auto/guhtestbase.h +++ b/tests/auto/guhtestbase.h @@ -37,6 +37,7 @@ extern DeviceClassId mockDeviceClassId; extern DeviceClassId mockDeviceAutoClassId; extern DeviceClassId mockPushButtonDeviceClassId; +extern DeviceClassId mockDisplayPinDeviceClassId; extern DeviceClassId mockDeviceDiscoveryClassId; extern DeviceClassId mockDeviceAsyncSetupClassId; extern DeviceClassId mockDeviceBrokenClassId; diff --git a/tests/auto/restdevices/testrestdevices.cpp b/tests/auto/restdevices/testrestdevices.cpp index bc08517b..da5aa4d6 100644 --- a/tests/auto/restdevices/testrestdevices.cpp +++ b/tests/auto/restdevices/testrestdevices.cpp @@ -50,6 +50,9 @@ private slots: void addPushButtonDevices_data(); void addPushButtonDevices(); + void addDisplayPinDevices_data(); + void addDisplayPinDevices(); + void executeAction_data(); void executeAction(); @@ -335,6 +338,118 @@ void TestRestDevices::addPushButtonDevices() nam->deleteLater(); } +void TestRestDevices::addDisplayPinDevices_data() +{ + QTest::addColumn("deviceClassId"); + QTest::addColumn("expectedStatusCode"); + QTest::addColumn("secret"); + + QTest::newRow("Valid: Add DisplayPin device") << mockDisplayPinDeviceClassId << 200 << "243681"; + QTest::newRow("Invalid: Add DisplayPin device (wrong pin)") << mockDisplayPinDeviceClassId << 500 << "243682"; +} + +void TestRestDevices::addDisplayPinDevices() +{ + QFETCH(DeviceClassId, deviceClassId); + QFETCH(int, expectedStatusCode); + QFETCH(QString, secret); + + // Discover device + QVariantList discoveryParams; + QVariantMap resultCountParam; + resultCountParam.insert("name", "resultCount"); + resultCountParam.insert("value", 1); + discoveryParams.append(resultCountParam); + + // Discover + QVariantMap params; + params.insert("deviceClassId", deviceClassId); + params.insert("discoveryParams", discoveryParams); + + QNetworkAccessManager *nam = new QNetworkAccessManager(this); + QSignalSpy clientSpy(nam, SIGNAL(finished(QNetworkReply*))); + + QUrl url(QString("http://localhost:3333/api/v1/deviceclasses/%1/discover").arg(deviceClassId.toString())); + + QUrlQuery query; + query.addQueryItem("params", QJsonDocument::fromVariant(discoveryParams).toJson(QJsonDocument::Compact)); + url.setQuery(query); + + clientSpy.clear(); + QNetworkRequest request(url); + QNetworkReply *reply = nam->get(request); + clientSpy.wait(); + QCOMPARE(clientSpy.count(), 1); + int statusCode = reply->attribute(QNetworkRequest::HttpStatusCodeAttribute).toInt(); + QCOMPARE(statusCode, 200); + QByteArray data = reply->readAll(); + reply->deleteLater(); + + // check response + QJsonParseError error; + QJsonDocument jsonDoc = QJsonDocument::fromJson(data, &error); + QCOMPARE(error.error, QJsonParseError::NoError); + QVariantList foundDevices = jsonDoc.toVariant().toList(); + QCOMPARE(foundDevices.count(), 1); + + DeviceDescriptorId deviceDescriptoId(foundDevices.first().toMap().value("id").toString()); + + // Pair + params.clear(); + params.insert("deviceClassId", deviceClassId.toString()); + params.insert("deviceDescriptorId", deviceDescriptoId); + + QNetworkRequest pairRequest(QUrl("http://localhost:3333/api/v1/devices/pair")); + clientSpy.clear(); + reply = nam->post(pairRequest, QJsonDocument::fromVariant(params).toJson(QJsonDocument::Compact)); + clientSpy.wait(); + QCOMPARE(clientSpy.count(), 1); + statusCode = reply->attribute(QNetworkRequest::HttpStatusCodeAttribute).toInt(); + QCOMPARE(statusCode, 200); + data = reply->readAll(); + reply->deleteLater(); + + // check response + jsonDoc = QJsonDocument::fromJson(data, &error); + QCOMPARE(error.error, QJsonParseError::NoError); + PairingTransactionId pairingTransactionId(jsonDoc.toVariant().toMap().value("pairingTransactionId").toString()); + QString displayMessage = jsonDoc.toVariant().toMap().value("displayMessage").toString(); + + qDebug() << "displayMessage" << displayMessage; + + // Confirm pairing + params.clear(); + params.insert("pairingTransactionId", pairingTransactionId.toString()); + params.insert("secret", secret); + + QNetworkRequest confirmPairingRequest(QUrl("http://localhost:3333/api/v1/devices/confirmpairing")); + clientSpy.clear(); + reply = nam->post(confirmPairingRequest, QJsonDocument::fromVariant(params).toJson(QJsonDocument::Compact)); + clientSpy.wait(); + QCOMPARE(clientSpy.count(), 1); + statusCode = reply->attribute(QNetworkRequest::HttpStatusCodeAttribute).toInt(); + QCOMPARE(statusCode, expectedStatusCode); + data = reply->readAll(); + reply->deleteLater(); + + if (expectedStatusCode == 200) { + jsonDoc = QJsonDocument::fromJson(data, &error); + QCOMPARE(error.error, QJsonParseError::NoError); + + DeviceId deviceId(jsonDoc.toVariant().toMap().value("id").toString()); + // delete it + request.setUrl(QUrl(QString("http://localhost:3333/api/v1/devices/%1").arg(deviceId.toString()))); + clientSpy.clear(); + reply = nam->deleteResource(request); + clientSpy.wait(); + QCOMPARE(clientSpy.count(), 1); + statusCode = reply->attribute(QNetworkRequest::HttpStatusCodeAttribute).toInt(); + reply->deleteLater(); + QCOMPARE(statusCode, 200); + } + nam->deleteLater(); +} + void TestRestDevices::executeAction_data() { QTest::addColumn("deviceId");