From 6193a0421abd4ce65e3b568f67183564282b4331 Mon Sep 17 00:00:00 2001 From: GPrathap Date: Wed, 22 Jun 2016 18:43:11 +0530 Subject: [PATCH] removing older sample: doormanager --- .../doormanager/component/analytics/build.xml | 34 - .../doormanager/component/analytics/pom.xml | 87 -- .../component/analytics/src/assembly/src.xml | 37 - .../EventReceiver_smartLock.xml | 27 - .../artifact.xml | 22 - .../Eventstore_smartLock_1.0.0/artifact.xml | 22 - .../org_wso2_iot_devices_smartLock.xml | 62 - .../Eventstream_smartLock_1.0.0/artifact.xml | 23 - .../org.wso2.iot.devices.smartLock_1.0.0.json | 33 - .../smartLock/Sparkscripts_1.0.0/artifact.xml | 22 - .../Sparkscripts_1.0.0/smartLock_Script.xml | 35 - .../carbonapps/smartLock/artifacts.xml | 27 - .../samples/doormanager/component/api/pom.xml | 257 ---- .../api/DoorManagerControllerService.java | 93 -- .../api/DoorManagerControllerServiceImpl.java | 233 ---- .../api/DoorManagerManagerService.java | 65 - .../api/DoorManagerManagerServiceImpl.java | 251 ---- .../doormanager/api/dto/DeviceJSON.java | 38 - .../doormanager/api/dto/UserInfo.java | 36 - .../api/exception/DoorManagerException.java | 64 - .../transport/DoorManagerMQTTConnector.java | 236 ---- .../doormanager/api/util/APIUtil.java | 81 -- .../api/util/DoorManagerServiceUtils.java | 68 - .../doormanager/api/util/ResponsePayload.java | 108 -- .../src/main/webapp/META-INF/permissions.xml | 101 -- .../webapp/META-INF/webapp-classloading.xml | 34 - .../src/main/webapp/WEB-INF/cxf-servlet.xml | 45 - .../api/src/main/webapp/WEB-INF/web.xml | 61 - .../doormanager/component/plugin/pom.xml | 183 --- .../constants/DoorManagerConstants.java | 34 - .../DoorManagerDeviceMgtPluginException.java | 56 - .../doormanager/plugin/impl/DoorManager.java | 299 ---- .../plugin/impl/DoorManagerService.java | 108 -- .../plugin/impl/dao/DoorLockSafe.java | 92 -- .../plugin/impl/dao/DoorManagerDAOUtil.java | 132 -- .../plugin/impl/dao/impl/DoorManagerDAO.java | 474 ------- .../impl/dao/util/DoorManagerUtils.java | 86 -- ...DoorManagerManagementServiceComponent.java | 74 - modules/samples/doormanager/component/pom.xml | 56 - .../samples/doormanager/component/ui/pom.xml | 56 - .../component/ui/src/assembly/src.xml | 36 - .../device-view.hbs | 94 -- .../device-view.js | 37 - .../device-view.json | 4 - .../public/images/doormanager-icon.png | Bin 6697 -> 0 bytes .../public/images/thumb.png | Bin 6697 -> 0 bytes .../public/images/doormanager-icon.png | Bin 6697 -> 0 bytes .../public/images/myDevices_analytics.png | Bin 45802 -> 0 bytes .../public/images/schematicsGuide.png | Bin 178935 -> 0 bytes .../public/images/thumb.png | Bin 6697 -> 0 bytes .../public/js/download.js | 242 ---- .../public/js/jquery.validate.js | 1220 ----------------- .../type-view.hbs | 321 ----- .../type-view.json | 20 - .../doormanager/feature/feature/pom.xml | 209 --- .../resources/agent/deviceConfig.properties | 30 - .../main/resources/agent/sketch.properties | 3 - .../resources/agent/src/DoorManagerAgent.log | 0 .../resources/agent/src/DoorManagerAgent.py | 194 --- .../src/main/resources/agent/src/MFRC522.py | 396 ------ .../main/resources/agent/src/MQTTHandler.py | 131 -- .../main/resources/agent/src/RFIDReader.py | 170 --- .../src/main/resources/agent/src/iotUtils.py | 69 - .../src/main/resources/agent/startService.sh | 59 - .../src/main/resources/build.properties | 18 - .../main/resources/configs/doormanager.json | 31 - .../main/resources/configs/doormanager.xml | 24 - .../resources/database/doormanagerDM_DB.h2.db | Bin 18432 -> 0 bytes .../datasources/doormanager-datasources.xml | 47 - .../src/main/resources/dbscripts/h2.sql | 29 - .../src/main/resources/dbscripts/mysql.sql | 12 - .../feature/feature/src/main/resources/p2.inf | 28 - modules/samples/doormanager/feature/pom.xml | 35 - modules/samples/doormanager/pom.xml | 518 ------- 74 files changed, 7829 deletions(-) delete mode 100644 modules/samples/doormanager/component/analytics/build.xml delete mode 100644 modules/samples/doormanager/component/analytics/pom.xml delete mode 100644 modules/samples/doormanager/component/analytics/src/assembly/src.xml delete mode 100644 modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Eventreceiver_smartLock_1.0.0/EventReceiver_smartLock.xml delete mode 100644 modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Eventreceiver_smartLock_1.0.0/artifact.xml delete mode 100644 modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Eventstore_smartLock_1.0.0/artifact.xml delete mode 100644 modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Eventstore_smartLock_1.0.0/org_wso2_iot_devices_smartLock.xml delete mode 100644 modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Eventstream_smartLock_1.0.0/artifact.xml delete mode 100644 modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Eventstream_smartLock_1.0.0/org.wso2.iot.devices.smartLock_1.0.0.json delete mode 100644 modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Sparkscripts_1.0.0/artifact.xml delete mode 100644 modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Sparkscripts_1.0.0/smartLock_Script.xml delete mode 100644 modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/artifacts.xml delete mode 100644 modules/samples/doormanager/component/api/pom.xml delete mode 100644 modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/DoorManagerControllerService.java delete mode 100644 modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/DoorManagerControllerServiceImpl.java delete mode 100644 modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/DoorManagerManagerService.java delete mode 100644 modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/DoorManagerManagerServiceImpl.java delete mode 100644 modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/dto/DeviceJSON.java delete mode 100644 modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/dto/UserInfo.java delete mode 100644 modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/exception/DoorManagerException.java delete mode 100644 modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/transport/DoorManagerMQTTConnector.java delete mode 100644 modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/util/APIUtil.java delete mode 100644 modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/util/DoorManagerServiceUtils.java delete mode 100644 modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/util/ResponsePayload.java delete mode 100644 modules/samples/doormanager/component/api/src/main/webapp/META-INF/permissions.xml delete mode 100644 modules/samples/doormanager/component/api/src/main/webapp/META-INF/webapp-classloading.xml delete mode 100644 modules/samples/doormanager/component/api/src/main/webapp/WEB-INF/cxf-servlet.xml delete mode 100644 modules/samples/doormanager/component/api/src/main/webapp/WEB-INF/web.xml delete mode 100644 modules/samples/doormanager/component/plugin/pom.xml delete mode 100644 modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/constants/DoorManagerConstants.java delete mode 100644 modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/exception/DoorManagerDeviceMgtPluginException.java delete mode 100644 modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/impl/DoorManager.java delete mode 100644 modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/impl/DoorManagerService.java delete mode 100644 modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/impl/dao/DoorLockSafe.java delete mode 100644 modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/impl/dao/DoorManagerDAOUtil.java delete mode 100644 modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/impl/dao/impl/DoorManagerDAO.java delete mode 100644 modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/impl/dao/util/DoorManagerUtils.java delete mode 100644 modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/internal/DoorManagerManagementServiceComponent.java delete mode 100644 modules/samples/doormanager/component/pom.xml delete mode 100644 modules/samples/doormanager/component/ui/pom.xml delete mode 100644 modules/samples/doormanager/component/ui/src/assembly/src.xml delete mode 100644 modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.device-view/device-view.hbs delete mode 100644 modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.device-view/device-view.js delete mode 100644 modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.device-view/device-view.json delete mode 100644 modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.device-view/public/images/doormanager-icon.png delete mode 100644 modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.device-view/public/images/thumb.png delete mode 100644 modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.type-view/public/images/doormanager-icon.png delete mode 100644 modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.type-view/public/images/myDevices_analytics.png delete mode 100644 modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.type-view/public/images/schematicsGuide.png delete mode 100644 modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.type-view/public/images/thumb.png delete mode 100644 modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.type-view/public/js/download.js delete mode 100644 modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.type-view/public/js/jquery.validate.js delete mode 100644 modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.type-view/type-view.hbs delete mode 100644 modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.type-view/type-view.json delete mode 100644 modules/samples/doormanager/feature/feature/pom.xml delete mode 100644 modules/samples/doormanager/feature/feature/src/main/resources/agent/deviceConfig.properties delete mode 100644 modules/samples/doormanager/feature/feature/src/main/resources/agent/sketch.properties delete mode 100644 modules/samples/doormanager/feature/feature/src/main/resources/agent/src/DoorManagerAgent.log delete mode 100644 modules/samples/doormanager/feature/feature/src/main/resources/agent/src/DoorManagerAgent.py delete mode 100644 modules/samples/doormanager/feature/feature/src/main/resources/agent/src/MFRC522.py delete mode 100644 modules/samples/doormanager/feature/feature/src/main/resources/agent/src/MQTTHandler.py delete mode 100644 modules/samples/doormanager/feature/feature/src/main/resources/agent/src/RFIDReader.py delete mode 100644 modules/samples/doormanager/feature/feature/src/main/resources/agent/src/iotUtils.py delete mode 100755 modules/samples/doormanager/feature/feature/src/main/resources/agent/startService.sh delete mode 100644 modules/samples/doormanager/feature/feature/src/main/resources/build.properties delete mode 100644 modules/samples/doormanager/feature/feature/src/main/resources/configs/doormanager.json delete mode 100644 modules/samples/doormanager/feature/feature/src/main/resources/configs/doormanager.xml delete mode 100644 modules/samples/doormanager/feature/feature/src/main/resources/database/doormanagerDM_DB.h2.db delete mode 100644 modules/samples/doormanager/feature/feature/src/main/resources/datasources/doormanager-datasources.xml delete mode 100644 modules/samples/doormanager/feature/feature/src/main/resources/dbscripts/h2.sql delete mode 100644 modules/samples/doormanager/feature/feature/src/main/resources/dbscripts/mysql.sql delete mode 100644 modules/samples/doormanager/feature/feature/src/main/resources/p2.inf delete mode 100644 modules/samples/doormanager/feature/pom.xml delete mode 100644 modules/samples/doormanager/pom.xml diff --git a/modules/samples/doormanager/component/analytics/build.xml b/modules/samples/doormanager/component/analytics/build.xml deleted file mode 100644 index 6a72f27e..00000000 --- a/modules/samples/doormanager/component/analytics/build.xml +++ /dev/null @@ -1,34 +0,0 @@ - - - - - - - - - - - - - - - - - - diff --git a/modules/samples/doormanager/component/analytics/pom.xml b/modules/samples/doormanager/component/analytics/pom.xml deleted file mode 100644 index f2935ab4..00000000 --- a/modules/samples/doormanager/component/analytics/pom.xml +++ /dev/null @@ -1,87 +0,0 @@ - - - - - org.homeautomation - doormanager-component - 1.0.0-SNAPSHOT - ../pom.xml - - 4.0.0 - org.homeautomation.doormanager.analytics - 1.0.0-SNAPSHOT - pom - org.homeautomation.doormanager.analytics - http://wso2.org - - - - maven-clean-plugin - ${maven-clean-plugin.version} - - - auto-clean - initialize - - clean - - - - - - maven-antrun-plugin - ${wso2.maven.compiler.source} - - - process-resources - - - - - - - run - - - - - - maven-assembly-plugin - 2.5.5 - - org.homeautomation.doormanager.analytics-1.0.0-SNAPSHOT - false - - src/assembly/src.xml - - - - - create-archive - package - - single - - - - - - - \ No newline at end of file diff --git a/modules/samples/doormanager/component/analytics/src/assembly/src.xml b/modules/samples/doormanager/component/analytics/src/assembly/src.xml deleted file mode 100644 index 5469255f..00000000 --- a/modules/samples/doormanager/component/analytics/src/assembly/src.xml +++ /dev/null @@ -1,37 +0,0 @@ - - - - - src - - zip - - false - ${basedir}/src - - - ${basedir}/target/carbonapps - / - true - - - \ No newline at end of file diff --git a/modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Eventreceiver_smartLock_1.0.0/EventReceiver_smartLock.xml b/modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Eventreceiver_smartLock_1.0.0/EventReceiver_smartLock.xml deleted file mode 100644 index 1a53d098..00000000 --- a/modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Eventreceiver_smartLock_1.0.0/EventReceiver_smartLock.xml +++ /dev/null @@ -1,27 +0,0 @@ - - - - - - false - - - - diff --git a/modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Eventreceiver_smartLock_1.0.0/artifact.xml b/modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Eventreceiver_smartLock_1.0.0/artifact.xml deleted file mode 100644 index 8fb0293e..00000000 --- a/modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Eventreceiver_smartLock_1.0.0/artifact.xml +++ /dev/null @@ -1,22 +0,0 @@ - - - - - EventReceiver_smartLock.xml - diff --git a/modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Eventstore_smartLock_1.0.0/artifact.xml b/modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Eventstore_smartLock_1.0.0/artifact.xml deleted file mode 100644 index c039213e..00000000 --- a/modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Eventstore_smartLock_1.0.0/artifact.xml +++ /dev/null @@ -1,22 +0,0 @@ - - - - - org_wso2_iot_devices_smartLock.xml - diff --git a/modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Eventstore_smartLock_1.0.0/org_wso2_iot_devices_smartLock.xml b/modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Eventstore_smartLock_1.0.0/org_wso2_iot_devices_smartLock.xml deleted file mode 100644 index e177b155..00000000 --- a/modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Eventstore_smartLock_1.0.0/org_wso2_iot_devices_smartLock.xml +++ /dev/null @@ -1,62 +0,0 @@ - - - - - - org.wso2.iot.devices.smartLock:1.0.0 - - EVENT_STORE - - - meta_owner - true - true - false - STRING - - - meta_deviceType - true - true - false - STRING - - - meta_deviceId - true - true - false - STRING - - - meta_time - true - true - false - LONG - - - smartLock - false - false - false - FLOAT - - - \ No newline at end of file diff --git a/modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Eventstream_smartLock_1.0.0/artifact.xml b/modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Eventstream_smartLock_1.0.0/artifact.xml deleted file mode 100644 index 67da309f..00000000 --- a/modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Eventstream_smartLock_1.0.0/artifact.xml +++ /dev/null @@ -1,23 +0,0 @@ - - - - - org.wso2.iot.devices.smartLock_1.0.0.json - - diff --git a/modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Eventstream_smartLock_1.0.0/org.wso2.iot.devices.smartLock_1.0.0.json b/modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Eventstream_smartLock_1.0.0/org.wso2.iot.devices.smartLock_1.0.0.json deleted file mode 100644 index fa4e05d6..00000000 --- a/modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Eventstream_smartLock_1.0.0/org.wso2.iot.devices.smartLock_1.0.0.json +++ /dev/null @@ -1,33 +0,0 @@ -{ - "name": "org.wso2.iot.devices.smartLock", - "version": "1.0.0", - "nickName": "smartLock", - "description": "smartLock data received from the Device", - "metaData": [ - { - "name": "owner", - "type": "STRING" - }, - { - "name": "deviceType", - "type": "STRING" - }, - { - "name": "deviceId", - "type": "STRING" - }, - { - "name": "time", - "type": "LONG" - } - ], - "payloadData": [ - { - "name": "smartLock", - "type": "FLOAT" - } - ] -} - - - diff --git a/modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Sparkscripts_1.0.0/artifact.xml b/modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Sparkscripts_1.0.0/artifact.xml deleted file mode 100644 index f7da0d0c..00000000 --- a/modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Sparkscripts_1.0.0/artifact.xml +++ /dev/null @@ -1,22 +0,0 @@ - - - - - smartLock_Script.xml - diff --git a/modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Sparkscripts_1.0.0/smartLock_Script.xml b/modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Sparkscripts_1.0.0/smartLock_Script.xml deleted file mode 100644 index 848ef9e7..00000000 --- a/modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/Sparkscripts_1.0.0/smartLock_Script.xml +++ /dev/null @@ -1,35 +0,0 @@ - - - - - IoTServer_smartLock_Script - - 0 * * * * ? - diff --git a/modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/artifacts.xml b/modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/artifacts.xml deleted file mode 100644 index 4385705f..00000000 --- a/modules/samples/doormanager/component/analytics/src/main/resources/carbonapps/smartLock/artifacts.xml +++ /dev/null @@ -1,27 +0,0 @@ - - - - - - - - - - - diff --git a/modules/samples/doormanager/component/api/pom.xml b/modules/samples/doormanager/component/api/pom.xml deleted file mode 100644 index 7ca2ce6d..00000000 --- a/modules/samples/doormanager/component/api/pom.xml +++ /dev/null @@ -1,257 +0,0 @@ - - - - org.homeautomation - doormanager-component - 1.0.0-SNAPSHOT - ../pom.xml - - 4.0.0 - org.homeautomation.doormanager.api - war - 1.0.0-SNAPSHOT - org.homeautomation.doormanager.api - http://wso2.org - - ${basedir}/src/main/java - - - org.apache.maven.plugins - maven-compiler-plugin - ${maven-compiler-plugin.version} - - UTF-8 - ${wso2.maven.compiler.source} - ${wso2.maven.compiler.target} - - - - maven-war-plugin - ${maven-war-plugin.version} - - org.homeautomation.doormanager.manager_mgt - - - - - - - org.eclipse.paho - org.eclipse.paho.client.mqttv3 - - - org.homeautomation - org.homeautomation.doormanager.plugin - - - org.wso2.carbon.devicemgt - org.wso2.carbon.device.mgt.common - - - org.wso2.carbon.devicemgt - org.wso2.carbon.device.mgt.core - - - org.apache.axis2.wso2 - axis2-client - - - - - - org.wso2.carbon.devicemgt - org.wso2.carbon.device.mgt.analytics.data.publisher - - - org.apache.axis2.wso2 - axis2-client - - - - - - org.wso2.carbon.devicemgt - org.wso2.carbon.certificate.mgt.core - - - commons-codec.wso2 - commons-codec - - - - - - - org.apache.cxf - cxf-rt-frontend-jaxws - - - org.apache.cxf - cxf-rt-frontend-jaxrs - - - org.apache.cxf - cxf-rt-transports-http - - - - org.apache.httpcomponents - httpasyncclient - - - org.wso2.carbon.devicemgt-plugins - org.wso2.carbon.device.mgt.iot - - - - org.codehaus.jackson - jackson-core-asl - - - org.codehaus.jackson - jackson-jaxrs - - - javax - javaee-web-api - - - javax.ws.rs - jsr311-api - - - commons-httpclient.wso2 - commons-httpclient - - - org.wso2.carbon - org.wso2.carbon.utils - - - org.bouncycastle.wso2 - bcprov-jdk15on - - - org.wso2.carbon - org.wso2.carbon.user.api - - - org.wso2.carbon - org.wso2.carbon.queuing - - - org.wso2.carbon - org.wso2.carbon.base - - - org.apache.axis2.wso2 - axis2 - - - org.igniterealtime.smack.wso2 - smack - - - org.igniterealtime.smack.wso2 - smackx - - - jaxen - jaxen - - - commons-fileupload.wso2 - commons-fileupload - - - org.apache.ant.wso2 - ant - - - org.apache.ant.wso2 - ant - - - commons-httpclient.wso2 - commons-httpclient - - - org.eclipse.equinox - javax.servlet - - - org.wso2.carbon - org.wso2.carbon.registry.api - - - - - commons-codec - commons-codec - - - commons-io - commons-io - - - - org.igniterealtime.smack.wso2 - smack - - - org.igniterealtime.smack.wso2 - smackx - - - org.wso2.carbon.devicemgt - org.wso2.carbon.apimgt.annotations - - - org.wso2.carbon.devicemgt - org.wso2.carbon.apimgt.webapp.publisher - - - com.googlecode.json-simple.wso2 - json-simple - 1.1.wso2v1 - - - com.google.code.gson - gson - 2.2.4 - - - org.wso2.carbon.devicemgt - org.wso2.carbon.device.mgt.extensions - - - org.wso2.carbon.devicemgt - org.wso2.carbon.apimgt.application.extension - - - org.wso2.carbon.devicemgt - org.wso2.carbon.identity.jwt.client.extension - - - org.wso2.carbon - org.wso2.carbon.user.api - - - \ No newline at end of file diff --git a/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/DoorManagerControllerService.java b/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/DoorManagerControllerService.java deleted file mode 100644 index 39d22998..00000000 --- a/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/DoorManagerControllerService.java +++ /dev/null @@ -1,93 +0,0 @@ -/* - * Copyright (c) 2016, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. - * - * WSO2 Inc. licenses this file to you under the Apache License, - * Version 2.0 (the "License"); you may not use this file except - * in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -package org.homeautomation.doormanager.api; - -import org.homeautomation.doormanager.api.dto.UserInfo; -import org.wso2.carbon.apimgt.annotations.api.API; -import org.wso2.carbon.device.mgt.extensions.feature.mgt.annotations.DeviceType; -import org.wso2.carbon.device.mgt.extensions.feature.mgt.annotations.Feature; - -import javax.ws.rs.Consumes; -import javax.ws.rs.FormParam; -import javax.ws.rs.GET; -import javax.ws.rs.HeaderParam; -import javax.ws.rs.POST; -import javax.ws.rs.Path; -import javax.ws.rs.Produces; -import javax.ws.rs.core.MediaType; -import javax.ws.rs.core.Response; - -@SuppressWarnings("NonJaxWsWebServices") -@API(name = "doormanager", version = "1.0.0", context = "/doormanager", tags = {"doormanager"}) -@DeviceType(value = "doormanager") -public interface DoorManagerControllerService { - - /** - * Assign new user to lock - * - * @param owner owner of the device - * @param deviceId unique identifier for given device - * @param protocol transport protocol which is being using here MQTT - * @param cardNumber RFID card number - * @param userName user name of RFID card owner - * @param emailAddress email address of RFID card owner - */ - @Path("device/assign-user") - @POST - @Feature(code = "assign_user", name = "Assign new user to lock", type = "operation", - description = "Add new access card to user to control the lock ") - Response assignUserToLock(@HeaderParam("owner") String owner, - @HeaderParam("deviceId") String deviceId, - @HeaderParam("protocol") String protocol, - @FormParam("cardNumber") String cardNumber, - @FormParam("userName") String userName, - @FormParam("emailAddress") String emailAddress); - - - /** - * Change status of door lock safe: LOCK/UNLOCK - * - * @param owner owner of the device - * @param deviceId unique identifier for given device - * @param protocol transport protocol which is being using here MQTT - * @param state status of lock safe: lock/unlock - */ - @Path("device/change-status") - @POST - @Feature(code = "change-status", name = "Change status of door lock safe: LOCK/UNLOCK", type = "operation", - description = "Change status of door lock safe: LOCK/UNLOCK") - Response changeStatusOfDoorLockSafe(@HeaderParam("owner") String owner, - @HeaderParam("deviceId") String deviceId, - @HeaderParam("protocol") String protocol, - @FormParam("state") String state); - - /** - * @param userInfo user information which are required to test given user is authorized to open requested door - * @return if user is authorized open the the door allow to open it - */ - @GET - @Path("device/get-user-info") - @Produces(MediaType.APPLICATION_JSON) - @Consumes(MediaType.APPLICATION_JSON) - @SuppressWarnings("unchecked") - //This is to avoid unchecked call to put(k, v) into jsonObject. org.json.simple - // library uses raw type collections internally. - Response get_user_info(final UserInfo userInfo); - -} diff --git a/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/DoorManagerControllerServiceImpl.java b/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/DoorManagerControllerServiceImpl.java deleted file mode 100644 index 3b7def7b..00000000 --- a/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/DoorManagerControllerServiceImpl.java +++ /dev/null @@ -1,233 +0,0 @@ -/* - * Copyright (c) 2016, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. - * - * WSO2 Inc. licenses this file to you under the Apache License, - * Version 2.0 (the "License"); you may not use this file except - * in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -package org.homeautomation.doormanager.api; - -import org.apache.commons.logging.Log; -import org.apache.commons.logging.LogFactory; -import org.homeautomation.doormanager.api.exception.DoorManagerException; -import org.homeautomation.doormanager.api.transport.DoorManagerMQTTConnector; -import org.homeautomation.doormanager.api.dto.UserInfo; -import org.homeautomation.doormanager.api.util.APIUtil; -import org.homeautomation.doormanager.plugin.constants.DoorManagerConstants; -import org.homeautomation.doormanager.plugin.exception.DoorManagerDeviceMgtPluginException; -import org.homeautomation.doormanager.plugin.impl.DoorManager; -import org.homeautomation.doormanager.plugin.impl.dao.DoorLockSafe; -import org.json.simple.JSONObject; -import org.wso2.carbon.apimgt.annotations.api.API; -import org.wso2.carbon.apimgt.application.extension.APIManagementProviderService; -import org.wso2.carbon.apimgt.application.extension.dto.ApiApplicationKey; -import org.wso2.carbon.apimgt.application.extension.exception.APIManagerException; -import org.wso2.carbon.context.PrivilegedCarbonContext; -import org.wso2.carbon.device.mgt.common.DeviceManagementException; -import org.wso2.carbon.device.mgt.extensions.feature.mgt.annotations.DeviceType; -import org.wso2.carbon.device.mgt.iot.controlqueue.mqtt.MqttConfig; -import org.wso2.carbon.device.mgt.iot.exception.DeviceControllerException; -import org.wso2.carbon.device.mgt.iot.service.IoTServerStartupListener; -import org.wso2.carbon.identity.jwt.client.extension.JWTClient; -import org.wso2.carbon.identity.jwt.client.extension.dto.AccessTokenInfo; -import org.wso2.carbon.identity.jwt.client.extension.exception.JWTClientException; -import org.wso2.carbon.user.api.UserStoreException; -import org.wso2.carbon.user.api.UserStoreManager; - -import javax.ws.rs.Consumes; -import javax.ws.rs.FormParam; -import javax.ws.rs.GET; -import javax.ws.rs.HeaderParam; -import javax.ws.rs.POST; -import javax.ws.rs.Path; -import javax.ws.rs.Produces; -import javax.ws.rs.core.MediaType; -import javax.ws.rs.core.Response; -import java.util.Calendar; -import java.util.HashMap; -import java.util.Map; - -public class DoorManagerControllerServiceImpl implements DoorManagerControllerService { - - private static Log log = LogFactory.getLog(DoorManagerControllerServiceImpl.class); - private static String CURRENT_STATUS = "doorLockerCurrentStatus"; - private DoorManager doorManager; - private DoorManagerMQTTConnector doorManagerMQTTConnector; - private static final String KEY_TYPE = "PRODUCTION"; - private static ApiApplicationKey apiApplicationKey; - - DoorManagerControllerServiceImpl() { - doorManager = new DoorManager(); - } - - private boolean waitForServerStartup() { - while (!IoTServerStartupListener.isServerReady()) { - try { - Thread.sleep(1000); - } catch (InterruptedException e) { - return true; - } - } - return false; - } - - public DoorManagerMQTTConnector getDoorManagerMQTTConnector() { - return doorManagerMQTTConnector; - } - - public void setDoorManagerMQTTConnector(final DoorManagerMQTTConnector MQTTConnector) { - Runnable connector = new Runnable() { - public void run() { - if (waitForServerStartup()) { - return; - } - DoorManagerControllerServiceImpl.this.doorManagerMQTTConnector = MQTTConnector; - if (MqttConfig.getInstance().isEnabled()) { - doorManagerMQTTConnector.connect(); - } else { - log.warn("MQTT disabled in 'devicemgt-config.xml'. Hence, DoorManagerMQTTConnector" + - " not started."); - } - } - }; - Thread connectorThread = new Thread(connector); - connectorThread.setDaemon(true); - connectorThread.start(); - } - - @Path("device/assign-user") - @POST - public Response assignUserToLock(@HeaderParam("owner") String owner, - @HeaderParam("deviceId") String deviceId, - @HeaderParam("protocol") String protocol, - @FormParam("cardNumber") String cardNumber, - @FormParam("userName") String userName, - @FormParam("emailAddress") String emailAddress) { - - if (userName != null && cardNumber != null && deviceId != null) { - try { - UserStoreManager userStoreManager = doorManager.getUserStoreManager(); - DoorLockSafe doorLockSafe = new DoorLockSafe(); - if (userStoreManager.isExistingUser(userName)) { - if (apiApplicationKey == null) { - String applicationUsername = PrivilegedCarbonContext.getThreadLocalCarbonContext().getUserRealm().getRealmConfiguration() - .getAdminUserName(); - APIManagementProviderService apiManagementProviderService = APIUtil.getAPIManagementProviderService(); - String[] tags = {DoorManagerConstants.DEVICE_TYPE}; - apiApplicationKey = apiManagementProviderService.generateAndRetrieveApplicationKeys( - DoorManagerConstants.DEVICE_TYPE, tags, KEY_TYPE, applicationUsername, true); - } - JWTClient jwtClient = APIUtil.getJWTClientManagerService().getJWTClient(); - String scopes = "device_type_" + DoorManagerConstants.DEVICE_TYPE + " device_" + deviceId; - AccessTokenInfo accessTokenInfo = jwtClient.getAccessToken(apiApplicationKey.getConsumerKey(), - apiApplicationKey.getConsumerSecret(), owner, scopes); - String accessToken = accessTokenInfo.getAccessToken(); - if (accessToken == null) { - return Response.status(Response.Status.UNAUTHORIZED.getStatusCode()).build(); - } - Map claims = new HashMap<>(); - claims.put(DoorManagerConstants.DEVICE_CLAIMS_ACCESS_TOKEN, accessToken); - claims.put(DoorManagerConstants.DEVICE_CLAIMS_REFRESH_TOKEN, - accessTokenInfo.getRefreshToken()); - claims.put(DoorManagerConstants.DEVICE_CLAIMS_CARD_NUMBER, cardNumber); - userStoreManager.setUserClaimValues(userName, claims, null); - doorLockSafe.setAccessToken(accessTokenInfo.getAccessToken()); - doorLockSafe.setRefreshToken(accessTokenInfo.getRefreshToken()); - doorLockSafe.setDeviceId(deviceId); - doorLockSafe.setOwner(owner); - doorLockSafe.setEmailAddress(emailAddress); - doorLockSafe.setUIDofUser(cardNumber); - doorLockSafe.setSerialNumber(deviceId); - if (doorManager.assignUserToLock(doorLockSafe)) { - return Response.ok().build(); - } else { - return Response.status(Response.Status.BAD_REQUEST.getStatusCode()).build(); - } - } else { - return Response.status(Response.Status.NOT_FOUND.getStatusCode()).build(); - } - } catch (UserStoreException e) { - return Response.status(Response.Status.UNAUTHORIZED.getStatusCode()).build(); - } catch (JWTClientException e) { - return Response.status(Response.Status.INTERNAL_SERVER_ERROR.getStatusCode()).build(); - } catch (APIManagerException e) { - return Response.status(Response.Status.INTERNAL_SERVER_ERROR.getStatusCode()).build(); - } catch (DoorManagerDeviceMgtPluginException e) { - return Response.status(Response.Status.INTERNAL_SERVER_ERROR.getStatusCode()).build(); - } - } else { - return Response.status(Response.Status.BAD_REQUEST.getStatusCode()).build(); - } - } - - @Path("device/change-status") - @POST - public Response changeStatusOfDoorLockSafe(@HeaderParam("owner") String owner, - @HeaderParam("deviceId") String deviceId, - @HeaderParam("protocol") String protocol, - @FormParam("state") String state) { - try { - int lockerCurrentState; - if (state.toUpperCase().equals("LOCK")) { - lockerCurrentState = 0; - } else { - lockerCurrentState = 1; - } - doorManagerMQTTConnector.sendCommandViaMQTT(owner, deviceId, "DoorManager:", state.toUpperCase()); - return Response.ok().build(); - } catch (DeviceManagementException e) { - return Response.status(Response.Status.UNAUTHORIZED.getStatusCode()).build(); - } catch (DoorManagerException e) { - return Response.status(Response.Status.INTERNAL_SERVER_ERROR.getStatusCode()).build(); - } - } - - @GET - @Path("device/get-user-info") - @Produces(MediaType.APPLICATION_JSON) - @Consumes(MediaType.APPLICATION_JSON) - @SuppressWarnings("unchecked") - public Response get_user_info(final UserInfo userInfo) { - if (userInfo.userName != null && userInfo.cardNumber != null && userInfo.deviceId != null) { - try { - UserStoreManager userStoreManager = doorManager.getUserStoreManager(); - if (userStoreManager.isExistingUser(userInfo.userName)) { - String accessToken = userStoreManager.getUserClaimValue(userInfo.userName, - DoorManagerConstants.DEVICE_CLAIMS_ACCESS_TOKEN, null); - String cardNumber = userStoreManager.getUserClaimValue(userInfo.userName, - DoorManagerConstants.DEVICE_CLAIMS_CARD_NUMBER, null); - if (cardNumber != null) { - if (cardNumber.equals(userInfo.cardNumber)) { - if (accessToken != null) { - JSONObject credentials = new JSONObject(); - credentials.put(DoorManagerConstants.DEVICE_PLUGIN_PROPERTY_ACCESS_TOKEN, accessToken); - //return Response.ok(credentials, MediaType.APPLICATION_JSON_TYPE).build(); - return Response.status(Response.Status.OK).build(); - } - } - return Response.status(Response.Status.UNAUTHORIZED).build(); - } - - } else { - return Response.status(Response.Status.UNAUTHORIZED).build(); - } - } catch (UserStoreException e) { - log.error(e); - return Response.status(Response.Status.INTERNAL_SERVER_ERROR).build(); - } - } - return Response.status(Response.Status.BAD_REQUEST).build(); - } - -} diff --git a/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/DoorManagerManagerService.java b/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/DoorManagerManagerService.java deleted file mode 100644 index 0f7e39c6..00000000 --- a/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/DoorManagerManagerService.java +++ /dev/null @@ -1,65 +0,0 @@ -/* - * Copyright (c) 2016, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. - * - * WSO2 Inc. licenses this file to you under the Apache License, - * Version 2.0 (the "License"); you may not use this file except - * in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -package org.homeautomation.doormanager.api; - -import org.wso2.carbon.apimgt.annotations.api.API; -import org.wso2.carbon.device.mgt.extensions.feature.mgt.annotations.DeviceType; - -import javax.ws.rs.Consumes; -import javax.ws.rs.DELETE; -import javax.ws.rs.GET; -import javax.ws.rs.PUT; -import javax.ws.rs.Path; -import javax.ws.rs.PathParam; -import javax.ws.rs.Produces; -import javax.ws.rs.QueryParam; -import javax.ws.rs.core.MediaType; -import javax.ws.rs.core.Response; - -@Path("enrollment") -@SuppressWarnings("NonJaxWsWebServices") -@DeviceType(value = "doormanager") -@API(name = "doormanager_mgt", version = "1.0.0", context = "/doormanager_mgt" , tags = {"doormanager"}) -public interface DoorManagerManagerService { - - @Path("devices/{device_id}") - @DELETE - Response removeDevice(@PathParam("device_id") String deviceId); - - @Path("devices/{device_id}") - @PUT - Response updateDevice(@PathParam("device_id") String deviceId, @QueryParam("name") String name); - - @Path("devices/{device_id}") - @GET - @Consumes(MediaType.APPLICATION_JSON) - @Produces(MediaType.APPLICATION_JSON) - Response getDevice(@PathParam("device_id") String deviceId); - - @Path("devices/download") - @GET - @Produces(MediaType.APPLICATION_JSON) - Response downloadSketch(@QueryParam("deviceName") String deviceName); - - - @Path("devices/generate_link") - @GET - Response generateSketchLink(@QueryParam("deviceName") String deviceName); - -} diff --git a/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/DoorManagerManagerServiceImpl.java b/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/DoorManagerManagerServiceImpl.java deleted file mode 100644 index 399279d3..00000000 --- a/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/DoorManagerManagerServiceImpl.java +++ /dev/null @@ -1,251 +0,0 @@ -/* - * Copyright (c) 2016, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. - * - * WSO2 Inc. licenses this file to you under the Apache License, - * Version 2.0 (the "License"); you may not use this file except - * in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -package org.homeautomation.doormanager.api; - -import org.apache.commons.io.FileUtils; -import org.apache.commons.logging.Log; -import org.apache.commons.logging.LogFactory; -import org.homeautomation.doormanager.api.util.APIUtil; -import org.homeautomation.doormanager.plugin.constants.DoorManagerConstants; -import org.wso2.carbon.apimgt.annotations.api.API; -import org.wso2.carbon.apimgt.application.extension.APIManagementProviderService; -import org.wso2.carbon.apimgt.application.extension.dto.ApiApplicationKey; -import org.wso2.carbon.apimgt.application.extension.exception.APIManagerException; -import org.wso2.carbon.context.PrivilegedCarbonContext; -import org.wso2.carbon.device.mgt.common.Device; -import org.wso2.carbon.device.mgt.common.DeviceIdentifier; -import org.wso2.carbon.device.mgt.common.DeviceManagementException; -import org.wso2.carbon.device.mgt.common.EnrolmentInfo; -import org.wso2.carbon.device.mgt.extensions.feature.mgt.annotations.DeviceType; -import org.wso2.carbon.device.mgt.iot.exception.DeviceControllerException; -import org.wso2.carbon.device.mgt.iot.util.ZipArchive; -import org.wso2.carbon.device.mgt.iot.util.ZipUtil; -import org.wso2.carbon.identity.jwt.client.extension.JWTClient; -import org.wso2.carbon.identity.jwt.client.extension.dto.AccessTokenInfo; -import org.wso2.carbon.identity.jwt.client.extension.exception.JWTClientException; -import org.wso2.carbon.user.api.UserStoreException; - -import javax.servlet.http.HttpServletResponse; -import javax.ws.rs.core.Response; -import javax.ws.rs.Consumes; -import javax.ws.rs.DELETE; -import javax.ws.rs.GET; -import javax.ws.rs.PUT; -import javax.ws.rs.Path; -import javax.ws.rs.PathParam; -import javax.ws.rs.Produces; -import javax.ws.rs.QueryParam; -import javax.ws.rs.core.MediaType; - -import java.io.IOException; -import java.nio.ByteBuffer; -import java.nio.charset.StandardCharsets; -import java.util.Date; -import java.util.UUID; - -@Path("enrollment") -public class DoorManagerManagerServiceImpl implements DoorManagerManagerService { - - private static Log log = LogFactory.getLog(DoorManagerManagerServiceImpl.class); - private static ApiApplicationKey apiApplicationKey; - private static final String KEY_TYPE = "PRODUCTION"; - - @Path("devices/{device_id}") - @DELETE - public Response removeDevice(@PathParam("device_id") String deviceId) { - try { - DeviceIdentifier deviceIdentifier = new DeviceIdentifier(); - deviceIdentifier.setId(deviceId); - deviceIdentifier.setType(DoorManagerConstants.DEVICE_TYPE); - boolean removed = APIUtil.getDeviceManagementService().disenrollDevice( - deviceIdentifier); - if (removed) { - return Response.ok().build(); - } else { - return Response.status(Response.Status.NOT_ACCEPTABLE.getStatusCode()).build(); - } - } catch (DeviceManagementException e) { - return Response.status(Response.Status.INTERNAL_SERVER_ERROR.getStatusCode()).build(); - } - } - - @Path("devices/{device_id}") - @PUT - public Response updateDevice(@PathParam("device_id") String deviceId, @QueryParam("name") String name) { - try { - DeviceIdentifier deviceIdentifier = new DeviceIdentifier(); - deviceIdentifier.setId(deviceId); - deviceIdentifier.setType(DoorManagerConstants.DEVICE_TYPE); - Device device = APIUtil.getDeviceManagementService().getDevice(deviceIdentifier); - device.setDeviceIdentifier(deviceId); - device.getEnrolmentInfo().setDateOfLastUpdate(new Date().getTime()); - device.setName(name); - device.setType(DoorManagerConstants.DEVICE_TYPE); - boolean updated = APIUtil.getDeviceManagementService().modifyEnrollment(device); - if (updated) { - return Response.ok().build(); - } else { - return Response.status(Response.Status.NOT_ACCEPTABLE.getStatusCode()).build(); - } - } catch (DeviceManagementException e) { - return Response.status(Response.Status.INTERNAL_SERVER_ERROR.getStatusCode()).build(); - } - } - - @Path("devices/{device_id}") - @GET - @Consumes(MediaType.APPLICATION_JSON) - @Produces(MediaType.APPLICATION_JSON) - public Response getDevice(@PathParam("device_id") String deviceId) { - try { - DeviceIdentifier deviceIdentifier = new DeviceIdentifier(); - deviceIdentifier.setId(deviceId); - deviceIdentifier.setType(DoorManagerConstants.DEVICE_TYPE); - Device device = APIUtil.getDeviceManagementService().getDevice(deviceIdentifier); - return Response.ok().entity(device).build(); - } catch (DeviceManagementException e) { - return Response.status(Response.Status.INTERNAL_SERVER_ERROR.getStatusCode()).build(); - } - } - - @Path("devices/download") - @GET - @Produces(MediaType.APPLICATION_JSON) - public Response downloadSketch(@QueryParam("deviceName") String deviceName) { - try { - ZipArchive zipFile = createDownloadFile(APIUtil.getAuthenticatedUser(), deviceName); - Response.ResponseBuilder response = Response.ok(FileUtils.readFileToByteArray(zipFile.getZipFile())); - response.type("application/zip"); - response.header("Content-Disposition", "attachment; filename=\"" + zipFile.getFileName() + "\""); - return response.build(); - } catch (IllegalArgumentException ex) { - return Response.status(400).entity(ex.getMessage()).build();//bad request - } catch (DeviceManagementException ex) { - return Response.status(500).entity(ex.getMessage()).build(); - } catch (JWTClientException ex) { - return Response.status(500).entity(ex.getMessage()).build(); - } catch (APIManagerException ex) { - return Response.status(500).entity(ex.getMessage()).build(); - } catch (DeviceControllerException ex) { - return Response.status(500).entity(ex.getMessage()).build(); - } catch (IOException ex) { - return Response.status(500).entity(ex.getMessage()).build(); - } catch (UserStoreException ex) { - return Response.status(500).entity(ex.getMessage()).build(); - } - } - - @Path("devices/generate_link") - @GET - public Response generateSketchLink(@QueryParam("deviceName") String deviceName){ - try { - ZipArchive zipFile = createDownloadFile(APIUtil.getAuthenticatedUser(), deviceName); - Response.ResponseBuilder rb = Response.ok(zipFile.getDeviceId()); - return rb.build(); - } catch (IllegalArgumentException ex) { - return Response.status(400).entity(ex.getMessage()).build();//bad request - } catch (DeviceManagementException ex) { - return Response.status(500).entity(ex.getMessage()).build(); - } catch (JWTClientException ex) { - return Response.status(500).entity(ex.getMessage()).build(); - } catch (APIManagerException ex) { - return Response.status(500).entity(ex.getMessage()).build(); - } catch (DeviceControllerException ex) { - return Response.status(500).entity(ex.getMessage()).build(); - } catch (UserStoreException ex) { - return Response.status(500).entity(ex.getMessage()).build(); - } - } - - private ZipArchive createDownloadFile(String owner, String deviceName) - throws DeviceManagementException, JWTClientException, DeviceControllerException, APIManagerException, - UserStoreException { - if (owner == null) { - throw new IllegalArgumentException("Error on createDownloadFile() Owner is null!"); - } - //create new device id - String deviceId = shortUUID(); - String applicationUsername = - PrivilegedCarbonContext.getThreadLocalCarbonContext().getUserRealm().getRealmConfiguration() - .getAdminUserName(); - if (apiApplicationKey == null) { - APIManagementProviderService apiManagementProviderService = APIUtil.getAPIManagementProviderService(); - String[] tags = {DoorManagerConstants.DEVICE_TYPE}; - apiApplicationKey = apiManagementProviderService.generateAndRetrieveApplicationKeys( - DoorManagerConstants.DEVICE_TYPE, tags, KEY_TYPE, applicationUsername, true); - } - JWTClient jwtClient = APIUtil.getJWTClientManagerService().getJWTClient(); - String scopes = "device_type_" + DoorManagerConstants.DEVICE_TYPE + " device_" + deviceId; - AccessTokenInfo accessTokenInfo = jwtClient.getAccessToken(apiApplicationKey.getConsumerKey(), - apiApplicationKey.getConsumerSecret(), owner, - scopes); - //create token - String accessToken = accessTokenInfo.getAccessToken(); - String refreshToken = accessTokenInfo.getRefreshToken(); - //Register the device with CDMF - boolean status = register(deviceId, deviceName); - if (!status) { - String msg = "Error occurred while registering the device with " + "id: " + deviceId + " owner:" + owner; - throw new DeviceManagementException(msg); - } - ZipUtil ziputil = new ZipUtil(); - ZipArchive zipFile = ziputil.createZipFile(owner, APIUtil.getTenantDomainOftheUser(), - DoorManagerConstants.DEVICE_TYPE, deviceId, - deviceName, accessToken, refreshToken); - zipFile.setDeviceId(deviceId); - return zipFile; - } - - /** - * Generate UUID - * - * @return generated UUID - */ - private static String shortUUID() { - UUID uuid = UUID.randomUUID(); - long l = ByteBuffer.wrap(uuid.toString().getBytes(StandardCharsets.UTF_8)).getLong(); - return Long.toString(l, Character.MAX_RADIX); - } - - private boolean register(String deviceId, String name) { - try { - DeviceIdentifier deviceIdentifier = new DeviceIdentifier(); - deviceIdentifier.setId(deviceId); - deviceIdentifier.setType(DoorManagerConstants.DEVICE_TYPE); - if (APIUtil.getDeviceManagementService().isEnrolled(deviceIdentifier)) { - return false; - } - Device device = new Device(); - device.setDeviceIdentifier(deviceId); - EnrolmentInfo enrolmentInfo = new EnrolmentInfo(); - enrolmentInfo.setDateOfEnrolment(new Date().getTime()); - enrolmentInfo.setDateOfLastUpdate(new Date().getTime()); - enrolmentInfo.setStatus(EnrolmentInfo.Status.ACTIVE); - device.setName(name); - device.setType(DoorManagerConstants.DEVICE_TYPE); - enrolmentInfo.setOwner(APIUtil.getAuthenticatedUser()); - device.setEnrolmentInfo(enrolmentInfo); - boolean added = APIUtil.getDeviceManagementService().enrollDevice(device); - return added; - } catch (DeviceManagementException e) { - return false; - } - } - -} diff --git a/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/dto/DeviceJSON.java b/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/dto/DeviceJSON.java deleted file mode 100644 index bf97492e..00000000 --- a/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/dto/DeviceJSON.java +++ /dev/null @@ -1,38 +0,0 @@ -/* - * Copyright (c) 2015, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. - * - * WSO2 Inc. licenses this file to you under the Apache License, - * Version 2.0 (the "License"); you may not use this file except - * in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -package org.homeautomation.doormanager.api.dto; - -import org.codehaus.jackson.annotate.JsonIgnoreProperties; - -import javax.xml.bind.annotation.XmlElement; -import javax.xml.bind.annotation.XmlRootElement; - -@XmlRootElement - -@JsonIgnoreProperties(ignoreUnknown = true) -public class DeviceJSON { - @XmlElement(required = true) - public String owner; - @XmlElement(required = true) - public String deviceId; - @XmlElement(required = true) - public String UIDofUser; - @XmlElement(required = true) - public String serialNumber; -} diff --git a/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/dto/UserInfo.java b/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/dto/UserInfo.java deleted file mode 100644 index 1438bbc8..00000000 --- a/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/dto/UserInfo.java +++ /dev/null @@ -1,36 +0,0 @@ -/* - * Copyright (c) 2015, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. - * - * WSO2 Inc. licenses this file to you under the Apache License, - * Version 2.0 (the "License"); you may not use this file except - * in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -package org.homeautomation.doormanager.api.dto; - -import org.codehaus.jackson.annotate.JsonIgnoreProperties; - -import javax.xml.bind.annotation.XmlElement; -import javax.xml.bind.annotation.XmlRootElement; - -@XmlRootElement - -@JsonIgnoreProperties(ignoreUnknown = true) -public class UserInfo { - @XmlElement(required = true) - public String deviceId; - @XmlElement(required = true) - public String cardNumber; - @XmlElement(required = true) - public String userName; -} diff --git a/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/exception/DoorManagerException.java b/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/exception/DoorManagerException.java deleted file mode 100644 index fc828f82..00000000 --- a/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/exception/DoorManagerException.java +++ /dev/null @@ -1,64 +0,0 @@ -/* - * Copyright (c) 2016, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. - * - * WSO2 Inc. licenses this file to you under the Apache License, - * Version 2.0 (the "License"); you may not use this file except - * in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -package org.homeautomation.doormanager.api.exception; - -public class DoorManagerException extends Exception { - - private static final long serialVersionUID = 2736466230451105441L; - - private String errorMessage; - - @SuppressWarnings("unused") - public DoorManagerException(String msg, DoorManagerException nestedEx) { - super(msg, nestedEx); - setErrorMessage(msg); - } - - public DoorManagerException(String message, Throwable cause) { - super(message, cause); - setErrorMessage(message); - } - - @SuppressWarnings("unused") - public DoorManagerException(String msg) { - super(msg); - setErrorMessage(msg); - } - - @SuppressWarnings("unused") - public DoorManagerException() { - super(); - } - - @SuppressWarnings("unused") - public DoorManagerException(Throwable cause) { - super(cause); - } - - @SuppressWarnings("unused") - public String getErrorMessage() { - return errorMessage; - } - - public void setErrorMessage(String errorMessage) { - this.errorMessage = errorMessage; - } - - -} diff --git a/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/transport/DoorManagerMQTTConnector.java b/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/transport/DoorManagerMQTTConnector.java deleted file mode 100644 index cff9d4d8..00000000 --- a/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/transport/DoorManagerMQTTConnector.java +++ /dev/null @@ -1,236 +0,0 @@ -/* - * Copyright (c) 2016, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. - * - * WSO2 Inc. licenses this file to you under the Apache License, - * Version 2.0 (the "License"); you may not use this file except - * in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -package org.homeautomation.doormanager.api.transport; - -import org.apache.commons.logging.Log; -import org.apache.commons.logging.LogFactory; -import org.eclipse.paho.client.mqttv3.MqttException; -import org.eclipse.paho.client.mqttv3.MqttMessage; -import org.homeautomation.doormanager.api.exception.DoorManagerException; -import org.homeautomation.doormanager.api.util.DoorManagerServiceUtils; -import org.homeautomation.doormanager.plugin.constants.DoorManagerConstants; -import org.wso2.carbon.device.mgt.analytics.data.publisher.exception.DataPublisherConfigurationException; -import org.wso2.carbon.device.mgt.common.DeviceManagementException; -import org.wso2.carbon.device.mgt.iot.controlqueue.mqtt.MqttConfig; -import org.wso2.carbon.device.mgt.iot.transport.TransportHandlerException; -import org.wso2.carbon.device.mgt.iot.transport.mqtt.MQTTTransportHandler; - -import java.io.File; -import java.util.Calendar; -import java.util.UUID; - -/** - * MQTT is used as transport protocol. So this will provide basic functional requirement in order to communicate over - * MQTT - */ -@SuppressWarnings("no JAX-WS annotation") -public class DoorManagerMQTTConnector extends MQTTTransportHandler { - - private static Log log = LogFactory.getLog(DoorManagerMQTTConnector.class); - private static String PUBLISHER_CONTEXT = "publisher"; - private static String SUBCRIBER_TOPIC = "wso2/" + DoorManagerConstants.DEVICE_TYPE + "/+/publisher"; - private static String PUBLISHER_TOPIC = "wso2/"+ DoorManagerConstants.DEVICE_TYPE + "/%s/subscriber"; - private static String SUBSCRIBER = UUID.randomUUID().toString().substring(0, 5); - - private DoorManagerMQTTConnector() { - super(SUBSCRIBER, DoorManagerConstants.DEVICE_TYPE, - MqttConfig.getInstance().getMqttQueueEndpoint(), SUBCRIBER_TOPIC); - } - - /** - * This method will initialize connection with message broker - */ - @Override - public void connect() { - Runnable connector = new Runnable() { - public void run() { - while (!isConnected()) { - try { - String brokerUsername = MqttConfig.getInstance().getMqttQueueUsername(); - String brokerPassword = MqttConfig.getInstance().getMqttQueuePassword(); - setUsernameAndPassword(brokerUsername, brokerPassword); - connectToQueue(); - } catch (TransportHandlerException e) { - log.error("Connection to MQTT Broker at: " + mqttBrokerEndPoint + " failed", e); - try { - Thread.sleep(timeoutInterval); - } catch (InterruptedException ex) { - log.error("MQTT-Connector: Thread Sleep Interrupt Exception.", ex); - } - } - try { - subscribeToQueue(); - } catch (TransportHandlerException e) { - log.warn("Subscription to MQTT Broker at: " + mqttBrokerEndPoint + " failed", e); - } - } - } - }; - Thread connectorThread = new Thread(connector); - connectorThread.setDaemon(true); - connectorThread.start(); - } - - /** - * This callback function will be called by message broker when some messages available to subscribed topic - * - * @param message mqtt message which is coming form agent side - * @param messageParams metadata of mqtt message - */ - @Override - public void processIncomingMessage(MqttMessage message, String... messageParams) { - String topic = messageParams[0]; - String ownerAndId = topic.replace("wso2" + File.separator + "iot" + File.separator, ""); - ownerAndId = ownerAndId.replace(File.separator + DoorManagerConstants.DEVICE_TYPE - + File.separator, ":"); - ownerAndId = ownerAndId.replace(File.separator + PUBLISHER_CONTEXT, ""); - String owner = ownerAndId.split(":")[0]; - String deviceId = ownerAndId.split(":")[1]; - log.warn(deviceId); - String[] messageData = message.toString().split(":"); - if (log.isDebugEnabled()) { - log.debug("Received MQTT message for: [OWNER-" + owner + "] & [DEVICE.ID-" + deviceId + "]"); - } - if (messageData.length == 2) { - String lockerCurrentState = messageData[1]; - float lockerStatus; - if (lockerCurrentState.equals("LOCKED")) { - lockerStatus = 0; - } else { - lockerStatus = 1; - } - try { - if (!DoorManagerServiceUtils.publishToDASLockerStatus(owner, deviceId, lockerStatus)) { - log.warn("An error occurred while trying to publish with ID [" + deviceId + "] of owner [" - + owner + "]"); - } - } catch (Exception e) { - log.error(e); - } - } - } - - /** - * Publish a MQTT message to device through message broker - * - * @param topic mqtt topic which will be used to uniquely identify who are the subscribers to this topic - * @param payLoad message is to be published - * @param qos level of qos(quality of service):1,2,3 - * @param retained klkkl - * @throws TransportHandlerException - */ - private void publishToAutomaticDoorLocker(String topic, String payLoad, int qos, boolean retained) - throws TransportHandlerException { - if (log.isDebugEnabled()) { - log.debug("Publishing message [" + payLoad + "to topic [" + topic + "]."); - } - publishToQueue(topic, payLoad, qos, retained); - } - - /** - * Publish a MQTT message to device through message broker - * - * @param deviceOwner person who own the device - * @param deviceId unique identifier for each device - * @param operation command is to executed at agent side e.g: off, on - * @param param additional payload - * @throws DeviceManagementException - * @throws DoorManagerException - */ - public void sendCommandViaMQTT(String deviceOwner, String deviceId, String operation, String param) - throws DeviceManagementException, DoorManagerException { - String topic = String.format(PUBLISHER_TOPIC, deviceOwner, deviceId); - String payload = operation + param; - try { - publishToAutomaticDoorLocker(topic, payload, 2, false); - if (param.toUpperCase().equals("LOCK")) { - if (!DoorManagerServiceUtils.publishToDASLockerStatus(deviceOwner, deviceId, 0)) { - log.warn("An error occurred whilst trying to publish with ID [" + deviceId + "] of owner [" + - deviceOwner + "]"); - } - } else if (param.toUpperCase().equals("UNLOCK")) { - if (!DoorManagerServiceUtils.publishToDASLockerStatus(deviceOwner, deviceId, 1)) { - log.warn("An error occurred whilst trying to publish with ID [" + deviceId + "] of owner [" + - deviceOwner + "]"); - } - } - } catch (TransportHandlerException e) { - String errorMessage = "Error publishing data to device with ID " + deviceId; - throw new DoorManagerException(errorMessage, e); - } catch (DataPublisherConfigurationException e) { - String errorMessage = "Error publishing data to DAS with ID " + deviceId; - throw new DoorManagerException(errorMessage, e); - } - } - - /** - * Connection with message broker can be terminated - */ - @Override - public void disconnect() { - Runnable stopConnection = new Runnable() { - public void run() { - while (isConnected()) { - try { - closeConnection(); - } catch (MqttException e) { - if (log.isDebugEnabled()) { - log.warn("Unable to 'STOP' MQTT connection at broker at: " + mqttBrokerEndPoint); - } - try { - Thread.sleep(timeoutInterval); - } catch (InterruptedException e1) { - log.error("MQTT-Terminator: Thread Sleep Interrupt Exception"); - } - } - } - } - }; - Thread terminatorThread = new Thread(stopConnection); - terminatorThread.setDaemon(true); - terminatorThread.start(); - } - - - @Override - public void publishDeviceData() throws TransportHandlerException { - - } - - @Override - public void publishDeviceData(MqttMessage publishData) throws TransportHandlerException { - - } - - @Override - public void publishDeviceData(String... publishData) throws TransportHandlerException { - - } - - @Override - public void processIncomingMessage() { - - } - - @Override - public void processIncomingMessage(MqttMessage message) throws TransportHandlerException { - - } - -} diff --git a/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/util/APIUtil.java b/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/util/APIUtil.java deleted file mode 100644 index 6e403b65..00000000 --- a/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/util/APIUtil.java +++ /dev/null @@ -1,81 +0,0 @@ -/* -* Copyright (c) 2016, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. -* -* WSO2 Inc. licenses this file to you under the Apache License, -* Version 2.0 (the "License"); you may not use this file except -* in compliance with the License. -* You may obtain a copy of the License at -* -* http://www.apache.org/licenses/LICENSE-2.0 -* -* Unless required by applicable law or agreed to in writing, -* software distributed under the License is distributed on an -* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY -* KIND, either express or implied. See the License for the -* specific language governing permissions and limitations -* under the License. -*/ - -package org.homeautomation.doormanager.api.util; - -import org.wso2.carbon.apimgt.application.extension.APIManagementProviderService; -import org.wso2.carbon.context.PrivilegedCarbonContext; -import org.wso2.carbon.device.mgt.core.service.DeviceManagementProviderService; -import org.wso2.carbon.identity.jwt.client.extension.service.JWTClientManagerService; - -/** - * This class provides utility functions used by REST-API. - */ -public class APIUtil { - - - public static String getAuthenticatedUser() { - PrivilegedCarbonContext threadLocalCarbonContext = PrivilegedCarbonContext.getThreadLocalCarbonContext(); - String username = threadLocalCarbonContext.getUsername(); - String tenantDomain = threadLocalCarbonContext.getTenantDomain(); - if (username.endsWith(tenantDomain)) { - return username.substring(0, username.lastIndexOf("@")); - } - return username; - } - - public static String getTenantDomainOftheUser() { - PrivilegedCarbonContext threadLocalCarbonContext = PrivilegedCarbonContext.getThreadLocalCarbonContext(); - String tenantDomain = threadLocalCarbonContext.getTenantDomain(); - return tenantDomain; - } - - public static DeviceManagementProviderService getDeviceManagementService() { - PrivilegedCarbonContext ctx = PrivilegedCarbonContext.getThreadLocalCarbonContext(); - DeviceManagementProviderService deviceManagementProviderService = - (DeviceManagementProviderService) ctx.getOSGiService(DeviceManagementProviderService.class, null); - if (deviceManagementProviderService == null) { - String msg = "Device Management service has not initialized."; - throw new IllegalStateException(msg); - } - return deviceManagementProviderService; - } - - public static APIManagementProviderService getAPIManagementProviderService() { - PrivilegedCarbonContext ctx = PrivilegedCarbonContext.getThreadLocalCarbonContext(); - APIManagementProviderService apiManagementProviderService = - (APIManagementProviderService) ctx.getOSGiService(DeviceManagementProviderService.class, null); - if (apiManagementProviderService == null) { - String msg = "API management provider service has not initialized."; - throw new IllegalStateException(msg); - } - return apiManagementProviderService; - } - - public static JWTClientManagerService getJWTClientManagerService() { - PrivilegedCarbonContext ctx = PrivilegedCarbonContext.getThreadLocalCarbonContext(); - JWTClientManagerService jwtClientManagerService = - (JWTClientManagerService) ctx.getOSGiService(JWTClientManagerService.class, null); - if (jwtClientManagerService == null) { - String msg = "JWT Client manager service has not initialized."; - throw new IllegalStateException(msg); - } - return jwtClientManagerService; - } - -} diff --git a/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/util/DoorManagerServiceUtils.java b/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/util/DoorManagerServiceUtils.java deleted file mode 100644 index 876ff33c..00000000 --- a/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/util/DoorManagerServiceUtils.java +++ /dev/null @@ -1,68 +0,0 @@ -/* - * Copyright (c) 2016, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. - * - * WSO2 Inc. licenses this file to you under the Apache License, - * Version 2.0 (the "License"); you may not use this file except - * in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -package org.homeautomation.doormanager.api.util; - -import org.apache.commons.logging.Log; -import org.apache.commons.logging.LogFactory; -import org.homeautomation.doormanager.plugin.constants.DoorManagerConstants; -import org.wso2.carbon.context.PrivilegedCarbonContext; -import org.wso2.carbon.device.mgt.analytics.data.publisher.exception.DataPublisherConfigurationException; -import org.wso2.carbon.device.mgt.analytics.data.publisher.service.EventsPublisherService; - -public class DoorManagerServiceUtils { - - private static final Log log = LogFactory.getLog(DoorManagerServiceUtils.class); - private static final String STREAM_DEFINITION = "org.wso2.iot.devices.smartLock"; - private static final String STREAM_DEFINITION_VERSION = "1.0.0"; - - /** - * Publish door locker current status to DAS - * - * @param owner owner of the device - * @param deviceId unique identifier of device - * @param status current status of lock:- 1: open, 0: close - * @return status - */ - public static boolean publishToDASLockerStatus(String owner, String deviceId, float status) - throws DataPublisherConfigurationException { - Object payloadCurrent[] = {status}; - return publishToDAS(owner, deviceId, payloadCurrent, STREAM_DEFINITION); - } - - private static boolean publishToDAS(String owner, String deviceId, Object[] payloadCurrent, - String definition) { - PrivilegedCarbonContext.startTenantFlow(); - PrivilegedCarbonContext ctx = PrivilegedCarbonContext.getThreadLocalCarbonContext(); - ctx.setUsername(owner); - if (ctx.getTenantDomain(true) == null) { - ctx.setTenantDomain("carbon.super", true); - } - EventsPublisherService deviceAnalyticsService = (EventsPublisherService) ctx.getOSGiService( - EventsPublisherService.class, null); - Object metaData[] = {owner, DoorManagerConstants.DEVICE_TYPE, deviceId, System.currentTimeMillis()}; - try { - deviceAnalyticsService.publishEvent(definition, STREAM_DEFINITION_VERSION, metaData, - new Object[0], payloadCurrent); - } catch (DataPublisherConfigurationException e) { - log.error(e); - return false; - } - return true; - } -} diff --git a/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/util/ResponsePayload.java b/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/util/ResponsePayload.java deleted file mode 100644 index 5b3d1542..00000000 --- a/modules/samples/doormanager/component/api/src/main/java/org/homeautomation/doormanager/api/util/ResponsePayload.java +++ /dev/null @@ -1,108 +0,0 @@ -/* - * Copyright (c) 2016, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. - * - * WSO2 Inc. licenses this file to you under the Apache License, - * Version 2.0 (the "License"); you may not use this file except - * in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -package org.homeautomation.doormanager.api.util; - -import javax.xml.bind.annotation.XmlElement; -import javax.xml.bind.annotation.XmlRootElement; - -@XmlRootElement -public class ResponsePayload { - - private int statusCode; - private String messageFromServer; - private Object responseContent; - - public static ResponsePayload.ResponsePayloadBuilder statusCode(int statusCode) { - ResponsePayload message = new ResponsePayload(); - return message.getBuilder().statusCode(statusCode); - } - - public static ResponsePayload.ResponsePayloadBuilder messageFromServer( - String messageFromServer) { - ResponsePayload message = new ResponsePayload(); - return message.getBuilder().messageFromServer(messageFromServer); - } - - public static ResponsePayload.ResponsePayloadBuilder responseContent(String responseContent) { - ResponsePayload message = new ResponsePayload(); - return message.getBuilder().responseContent(responseContent); - } - - @XmlElement - public int getStatusCode() { - return statusCode; - } - - public void setStatusCode(int statusCode) { - this.statusCode = statusCode; - } - - @XmlElement - public String getMessageFromServer() { - return messageFromServer; - } - - public void setMessageFromServer(String messageFromServer) { - this.messageFromServer = messageFromServer; - } - - @XmlElement - public Object getResponseContent() { - return responseContent; - } - - public void setResponseContent(Object responseContent) { - this.responseContent = responseContent; - } - - private ResponsePayload.ResponsePayloadBuilder getBuilder() { - return new ResponsePayload.ResponsePayloadBuilder(); - } - - public class ResponsePayloadBuilder { - - private int statusCode; - private String messageFromServer; - private Object responseContent; - - public ResponsePayloadBuilder statusCode(int statusCode) { - this.statusCode = statusCode; - return this; - } - - public ResponsePayloadBuilder messageFromServer(String messageFromServer) { - this.messageFromServer = messageFromServer; - return this; - } - - public ResponsePayloadBuilder responseContent(String responseContent) { - this.responseContent = responseContent; - return this; - } - - public ResponsePayload build() { - ResponsePayload payload = new ResponsePayload(); - payload.setStatusCode(statusCode); - payload.setMessageFromServer(messageFromServer); - payload.setResponseContent(responseContent); - return payload; - } - } - -} diff --git a/modules/samples/doormanager/component/api/src/main/webapp/META-INF/permissions.xml b/modules/samples/doormanager/component/api/src/main/webapp/META-INF/permissions.xml deleted file mode 100644 index d1a85ab4..00000000 --- a/modules/samples/doormanager/component/api/src/main/webapp/META-INF/permissions.xml +++ /dev/null @@ -1,101 +0,0 @@ - - - - - - - - - - Get device - /device-mgt/user/devices/list - /devices/* - GET - emm_admin,emm_user - - - Add device - /device-mgt/user/devices/add - /devices/register - PUT - emm_admin,emm_user - - - Download device - /device-mgt/user/devices/add - /devices/doormanager/download - GET - emm_admin,emm_user - - - Generate link to download - /device-mgt/user/devices/add - /devices/doormanager/generate_link - GET - emm_admin,emm_user - - - Update device - /device-mgt/user/devices/update - /devices/update/* - POST - emm_admin,emm_user - - - Remove device - /device-mgt/user/devices/remove - /devices/remove/* - DELETE - emm_admin,emm_user - - - Assign user - /device-mgt/user/device/assign-user - /device/assign-user - POST - emm_admin,emm_user - - - Change status - /device-mgt/user/device/change-status - /device/change-status - POST - emm_admin,emm_user - - - Get current status - /device-mgt/user/device/ - /device/current-status - GET - emm_admin,emm_user - - - Get user Info - /device-mgt/user/device/ - /device/get-user-info - GET - emm_admin,emm_user - - \ No newline at end of file diff --git a/modules/samples/doormanager/component/api/src/main/webapp/META-INF/webapp-classloading.xml b/modules/samples/doormanager/component/api/src/main/webapp/META-INF/webapp-classloading.xml deleted file mode 100644 index 01f27b48..00000000 --- a/modules/samples/doormanager/component/api/src/main/webapp/META-INF/webapp-classloading.xml +++ /dev/null @@ -1,34 +0,0 @@ - - - - - - - - false - - - CXF,Carbon - diff --git a/modules/samples/doormanager/component/api/src/main/webapp/WEB-INF/cxf-servlet.xml b/modules/samples/doormanager/component/api/src/main/webapp/WEB-INF/cxf-servlet.xml deleted file mode 100644 index eb4f1bc2..00000000 --- a/modules/samples/doormanager/component/api/src/main/webapp/WEB-INF/cxf-servlet.xml +++ /dev/null @@ -1,45 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - diff --git a/modules/samples/doormanager/component/api/src/main/webapp/WEB-INF/web.xml b/modules/samples/doormanager/component/api/src/main/webapp/WEB-INF/web.xml deleted file mode 100644 index 8f029527..00000000 --- a/modules/samples/doormanager/component/api/src/main/webapp/WEB-INF/web.xml +++ /dev/null @@ -1,61 +0,0 @@ - - - - Sample-Webapp-Controller - - - CXFServlet - org.apache.cxf.transport.servlet.CXFServlet - 1 - - - CXFServlet - /* - - - isAdminService - false - - - doAuthentication - true - - - isSharedWithAllTenants - true - - - providerTenantDomain - carbon.super - - - - - managed-api-enabled - true - - - managed-api-owner - admin - - - diff --git a/modules/samples/doormanager/component/plugin/pom.xml b/modules/samples/doormanager/component/plugin/pom.xml deleted file mode 100644 index 57d70d57..00000000 --- a/modules/samples/doormanager/component/plugin/pom.xml +++ /dev/null @@ -1,183 +0,0 @@ - - - - org.homeautomation - doormanager-component - 1.0.0-SNAPSHOT - ../pom.xml - - 4.0.0 - 1.0.0-SNAPSHOT - org.homeautomation.doormanager.plugin - bundle - org.homeautomation.doormanager.plugin - http://wso2.org - - - - org.apache.felix - maven-scr-plugin - - - org.apache.maven.plugins - maven-compiler-plugin - ${maven-compiler-plugin.version} - - UTF-8 - ${wso2.maven.compiler.source} - ${wso2.maven.compiler.target} - - - - org.apache.felix - maven-bundle-plugin - ${org.apache.felix.version} - true - - - org.homeautomation.doormanager.plugin - org.homeautomation.doormanager.plugin - 1.0.0-SNAPSHOT - IoT Server Impl Bundle - org.homeautomation.doormanager.plugin.internal - - org.osgi.framework, - org.osgi.service.component, - org.apache.commons.logging, - javax.naming, - javax.sql, - javax.xml.parsers, - javax.net, - javax.net.ssl, - org.w3c.dom, - org.wso2.carbon.device.mgt.common.*, - org.wso2.carbon.device.mgt.common, - org.wso2.carbon.context.*, - org.wso2.carbon.ndatasource.core, - org.wso2.carbon.device.mgt.iot.*, - org.wso2.carbon.user.api.*, - org.wso2.carbon.user.core.service.* - - - !org.homeautomation.doormanager.plugin.internal, - org.homeautomation.doormanager.plugin.* - - - - - - - - - org.eclipse.osgi - org.eclipse.osgi - - - org.eclipse.osgi - org.eclipse.osgi.services - - - org.wso2.carbon - org.wso2.carbon.logging - - - org.wso2.carbon.devicemgt - org.wso2.carbon.device.mgt.common - - - org.wso2.carbon - org.wso2.carbon.ndatasource.core - - - org.wso2.carbon.devicemgt-plugins - org.wso2.carbon.device.mgt.iot - - - org.wso2.carbon - org.wso2.carbon.user.core - - - org.wso2.carbon - org.wso2.carbon.user.api - - - org.wso2.carbon - org.wso2.carbon.utils - - - org.bouncycastle.wso2 - bcprov-jdk15on - - - org.wso2.carbon - org.wso2.carbon.user.api - - - org.wso2.carbon - org.wso2.carbon.queuing - - - org.wso2.carbon - org.wso2.carbon.base - - - org.apache.axis2.wso2 - axis2 - - - org.igniterealtime.smack.wso2 - smack - - - org.igniterealtime.smack.wso2 - smackx - - - jaxen - jaxen - - - commons-fileupload.wso2 - commons-fileupload - - - org.apache.ant.wso2 - ant - - - org.apache.ant.wso2 - ant - - - commons-httpclient.wso2 - commons-httpclient - - - org.eclipse.equinox - javax.servlet - - - org.wso2.carbon - org.wso2.carbon.registry.api - - - - - \ No newline at end of file diff --git a/modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/constants/DoorManagerConstants.java b/modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/constants/DoorManagerConstants.java deleted file mode 100644 index 8f6ec4e0..00000000 --- a/modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/constants/DoorManagerConstants.java +++ /dev/null @@ -1,34 +0,0 @@ -/* - * Copyright (c) 2015, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. - * - * WSO2 Inc. licenses this file to you under the Apache License, - * Version 2.0 (the "License"); you may not use this file except - * in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -package org.homeautomation.doormanager.plugin.constants; - -public class DoorManagerConstants { - public final static String DEVICE_TYPE = "doormanager"; - public final static String DEVICE_PLUGIN_DEVICE_NAME = "DEVICE_NAME"; - public final static String DEVICE_PLUGIN_DEVICE_ID = "doormanager_DEVICE_ID"; - public final static String DEVICE_PLUGIN_DEVICE_SERIAL_NUMBER = "SERIAL_NUMBER"; - public final static String DEVICE_PLUGIN_DEVICE_UID_OF_USER = "UID_of_USER"; - public static final String DATA_SOURCE_NAME = "jdbc/doormanagerDM_DB"; - public final static String DEVICE_PLUGIN_PROPERTY_ACCESS_TOKEN = "ACCESS_TOKEN"; - public final static String DEVICE_PLUGIN_PROPERTY_REFRESH_TOKEN = "REFRESH_TOKEN"; - public final static String DEVICE_CLAIMS_ACCESS_TOKEN = "http://wso2.org/claims/lock/accesstoken"; - public final static String DEVICE_CLAIMS_REFRESH_TOKEN = "http://wso2.org/claims/lock/refreshtoken"; - public final static String DEVICE_CLAIMS_CARD_NUMBER = "http://wso2.org/claims/lock/cardnumber"; - -} diff --git a/modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/exception/DoorManagerDeviceMgtPluginException.java b/modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/exception/DoorManagerDeviceMgtPluginException.java deleted file mode 100644 index 78dd8484..00000000 --- a/modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/exception/DoorManagerDeviceMgtPluginException.java +++ /dev/null @@ -1,56 +0,0 @@ -/* - * Copyright (c) 2015, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. - * - * WSO2 Inc. licenses this file to you under the Apache License, - * Version 2.0 (the "License"); you may not use this file except - * in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ -package org.homeautomation.doormanager.plugin.exception; - - -public class DoorManagerDeviceMgtPluginException extends Exception { - - private String errorMessage; - - public DoorManagerDeviceMgtPluginException(String msg, Exception nestedEx) { - super(msg, nestedEx); - setErrorMessage(msg); - } - - public DoorManagerDeviceMgtPluginException(String message, Throwable cause) { - super(message, cause); - setErrorMessage(message); - } - - public DoorManagerDeviceMgtPluginException(String msg) { - super(msg); - setErrorMessage(msg); - } - - public DoorManagerDeviceMgtPluginException() { - super(); - } - - public DoorManagerDeviceMgtPluginException(Throwable cause) { - super(cause); - } - - public String getErrorMessage() { - return errorMessage; - } - - public void setErrorMessage(String errorMessage) { - this.errorMessage = errorMessage; - } - -} diff --git a/modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/impl/DoorManager.java b/modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/impl/DoorManager.java deleted file mode 100644 index c6083466..00000000 --- a/modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/impl/DoorManager.java +++ /dev/null @@ -1,299 +0,0 @@ -/* - * Copyright (c) 2015, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. - * - * WSO2 Inc. licenses this file to you under the Apache License, - * Version 2.0 (the "License"); you may not use this file except - * in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -package org.homeautomation.doormanager.plugin.impl; - - -import org.apache.commons.logging.Log; -import org.apache.commons.logging.LogFactory; -import org.homeautomation.doormanager.plugin.exception.DoorManagerDeviceMgtPluginException; -import org.homeautomation.doormanager.plugin.impl.dao.DoorLockSafe; -import org.homeautomation.doormanager.plugin.impl.dao.DoorManagerDAOUtil; -import org.wso2.carbon.context.CarbonContext; -import org.wso2.carbon.context.PrivilegedCarbonContext; -import org.wso2.carbon.device.mgt.common.*; -import org.wso2.carbon.device.mgt.common.configuration.mgt.TenantConfiguration; -import org.wso2.carbon.device.mgt.common.license.mgt.License; -import org.wso2.carbon.device.mgt.common.license.mgt.LicenseManagementException; -import org.wso2.carbon.user.api.UserStoreException; -import org.wso2.carbon.user.api.UserStoreManager; -import org.wso2.carbon.user.core.service.RealmService; - -import java.util.List; - -public class DoorManager implements DeviceManager { - - private static final Log log = LogFactory.getLog(DoorManager.class); - private static final DoorManagerDAOUtil DOOR_MANAGER_DAO = new DoorManagerDAOUtil(); - private PrivilegedCarbonContext ctx; - - @Override - public FeatureManager getFeatureManager() { - return null; - } - - @Override - public boolean saveConfiguration(TenantConfiguration tenantConfiguration) - throws DeviceManagementException { - return false; - } - - @Override - public TenantConfiguration getConfiguration() throws DeviceManagementException { - return null; - } - - @Override - public boolean enrollDevice(Device device) throws DeviceManagementException { - boolean status; - try { - if (log.isDebugEnabled()) { - log.debug("Enrolling a new Automatic Door Locker device : " + device.getDeviceIdentifier()); - } - DoorManagerDAOUtil.beginTransaction(); - status = DOOR_MANAGER_DAO.getAutomaticDoorLockerDeviceDAO().addDevice(device); - DoorManagerDAOUtil.commitTransaction(); - } catch (DoorManagerDeviceMgtPluginException e) { - try { - DoorManagerDAOUtil.rollbackTransaction(); - } catch (DoorManagerDeviceMgtPluginException e1) { - e1.printStackTrace(); - } - String msg = "Error while enrolling the Automatic Door Locker device : " + device.getDeviceIdentifier(); - log.error(msg, e); - throw new DeviceManagementException(msg, e); - } - return status; - } - - @Override - public boolean modifyEnrollment(Device device) throws DeviceManagementException { - boolean status; - try { - if (log.isDebugEnabled()) { - log.debug("Modifying the Automatic Door Locker device enrollment data"); - } - DoorManagerDAOUtil.beginTransaction(); - status = DOOR_MANAGER_DAO.getAutomaticDoorLockerDeviceDAO().updateDevice(device); - DoorManagerDAOUtil.commitTransaction(); - } catch (DoorManagerDeviceMgtPluginException e) { - try { - DoorManagerDAOUtil.rollbackTransaction(); - } catch (DoorManagerDeviceMgtPluginException e1) { - e1.printStackTrace(); - } - String msg = "Error while updating the enrollment of the Automatic Door Locker device : " + - device.getDeviceIdentifier(); - log.error(msg, e); - throw new DeviceManagementException(msg, e); - } - return status; - } - - @Override - public boolean disenrollDevice(DeviceIdentifier deviceId) throws DeviceManagementException { - boolean status; - try { - if (log.isDebugEnabled()) { - log.debug("Dis-enrolling Automatic Door Locker device : " + deviceId); - } - DoorManagerDAOUtil.beginTransaction(); - status = DOOR_MANAGER_DAO.getAutomaticDoorLockerDeviceDAO().deleteDevice(deviceId.getId()); - DoorManagerDAOUtil.commitTransaction(); - } catch (DoorManagerDeviceMgtPluginException e) { - try { - DoorManagerDAOUtil.rollbackTransaction(); - } catch (DoorManagerDeviceMgtPluginException e1) { - e1.printStackTrace(); - } - String msg = "Error while removing the Automatic Door Locker device : " + deviceId.getId(); - log.error(msg, e); - throw new DeviceManagementException(msg, e); - } - return status; - } - - @Override - public boolean isEnrolled(DeviceIdentifier deviceId) throws DeviceManagementException { - boolean isEnrolled = false; - try { - if (log.isDebugEnabled()) { - log.debug("Checking the enrollment of Automatic Door Locker device : " + deviceId.getId()); - } - Device iotDevice = DOOR_MANAGER_DAO.getAutomaticDoorLockerDeviceDAO().getDevice(deviceId.getId()); - if (iotDevice != null) { - isEnrolled = true; - } - } catch (DoorManagerDeviceMgtPluginException e) { - String msg = "Error while checking the enrollment status of Automatic Door Locker device : " + - deviceId.getId(); - log.error(msg, e); - throw new DeviceManagementException(msg, e); - } - return isEnrolled; - } - - @Override - public boolean isActive(DeviceIdentifier deviceId) throws DeviceManagementException { - return true; - } - - @Override - public boolean setActive(DeviceIdentifier deviceId, boolean status) - throws DeviceManagementException { - return true; - } - - @Override - public Device getDevice(DeviceIdentifier deviceId) throws DeviceManagementException { - Device device; - try { - if (log.isDebugEnabled()) { - log.debug("Getting the details of Automatic Door Locker device : " + deviceId.getId()); - } - device = DOOR_MANAGER_DAO.getAutomaticDoorLockerDeviceDAO().getDevice(deviceId.getId()); - - } catch (DoorManagerDeviceMgtPluginException e) { - String msg = "Error while fetching the Automatic Door Locker device : " + deviceId.getId(); - log.error(msg, e); - throw new DeviceManagementException(msg, e); - } - return device; - } - - @Override - public boolean setOwnership(DeviceIdentifier deviceId, String ownershipType) - throws DeviceManagementException { - return true; - } - - public boolean isClaimable(DeviceIdentifier deviceIdentifier) throws DeviceManagementException { - return false; - } - - @Override - public boolean setStatus(DeviceIdentifier deviceId, String currentOwner, - EnrolmentInfo.Status status) throws DeviceManagementException { - return false; - } - - @Override - public License getLicense(String s) throws LicenseManagementException { - return null; - } - - @Override - public void addLicense(License license) throws LicenseManagementException { - - } - - @Override - public boolean requireDeviceAuthorization() { - return false; - } - - @Override - public boolean updateDeviceInfo(DeviceIdentifier deviceIdentifier, Device device) throws DeviceManagementException { - boolean status; - try { - if (log.isDebugEnabled()) { - log.debug( - "updating the details of Automatic Door Locker device : " + deviceIdentifier); - } - DoorManagerDAOUtil.beginTransaction(); - status = DOOR_MANAGER_DAO.getAutomaticDoorLockerDeviceDAO().updateDevice(device); - DoorManagerDAOUtil.commitTransaction(); - } catch (DoorManagerDeviceMgtPluginException e) { - try { - DoorManagerDAOUtil.rollbackTransaction(); - } catch (DoorManagerDeviceMgtPluginException iotDAOEx) { - String msg = "Error occurred while roll back the update device info transaction :" + device.toString(); - log.warn(msg, iotDAOEx); - } - String msg = - "Error while updating the Automatic Door Locker device : " + deviceIdentifier; - log.error(msg, e); - throw new DeviceManagementException(msg, e); - } - return status; - } - - @Override - public List getAllDevices() throws DeviceManagementException { - List devices; - try { - if (log.isDebugEnabled()) { - log.debug("Fetching the details of all Automatic Door Locker devices"); - } - devices = DOOR_MANAGER_DAO.getAutomaticDoorLockerDeviceDAO().getAllDevices(); - } catch (DoorManagerDeviceMgtPluginException e) { - String msg = "Error while fetching all Automatic Door Locker devices."; - log.error(msg, e); - throw new DeviceManagementException(msg, e); - } - return devices; - } - - /** - * Get userStore manager - * - * @return - * @throws UserStoreException - */ - public UserStoreManager getUserStoreManager() throws UserStoreException { - String tenantDomain = CarbonContext.getThreadLocalCarbonContext().getTenantDomain(); - PrivilegedCarbonContext.startTenantFlow(); - ctx = PrivilegedCarbonContext.getThreadLocalCarbonContext(); - ctx.setTenantDomain(tenantDomain, true); - if (log.isDebugEnabled()) { - log.debug("Getting thread local carbon context for tenant domain: " + tenantDomain); - } - RealmService realmService = (RealmService) ctx.getOSGiService(RealmService.class, null); - return realmService.getTenantUserRealm(ctx.getTenantId()).getUserStoreManager(); - } - - public boolean assignUserToLock(DoorLockSafe doorLockSafe) throws DoorManagerDeviceMgtPluginException { - boolean status; - try { - DoorManagerDAOUtil.beginTransaction(); - status = DOOR_MANAGER_DAO.getAutomaticDoorLockerDeviceDAO().registerDoorLockSafe(doorLockSafe); - DoorManagerDAOUtil.commitTransaction(); - return status; - } catch (DoorManagerDeviceMgtPluginException e) { - try { - DoorManagerDAOUtil.rollbackTransaction(); - throw new DoorManagerDeviceMgtPluginException(e); - } catch (DoorManagerDeviceMgtPluginException e1) { - String msg = "Error while adding new access card to user to control the lock " - + doorLockSafe.getOwner(); - log.error(msg, e); - throw new DoorManagerDeviceMgtPluginException(msg, e); - } - } - } - - public boolean checkCardDoorAssociation(String cardNumber, String deviceId) - throws DoorManagerDeviceMgtPluginException { - boolean status; - DoorManagerDAOUtil.beginTransaction(); - status = DOOR_MANAGER_DAO.getAutomaticDoorLockerDeviceDAO().checkCardDoorAssociation(cardNumber, deviceId); - DoorManagerDAOUtil.commitTransaction(); - return status; - } - -} \ No newline at end of file diff --git a/modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/impl/DoorManagerService.java b/modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/impl/DoorManagerService.java deleted file mode 100644 index 108f9dc2..00000000 --- a/modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/impl/DoorManagerService.java +++ /dev/null @@ -1,108 +0,0 @@ -/* - * Copyright (c) 2016, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. - * - * WSO2 Inc. licenses this file to you under the Apache License, - * Version 2.0 (the "License"); you may not use this file except - * in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -package org.homeautomation.doormanager.plugin.impl; - -import org.homeautomation.doormanager.plugin.constants.DoorManagerConstants; -import org.wso2.carbon.device.mgt.common.DeviceIdentifier; -import org.wso2.carbon.device.mgt.common.DeviceManagementException; -import org.wso2.carbon.device.mgt.common.DeviceManager; -import org.wso2.carbon.device.mgt.common.app.mgt.Application; -import org.wso2.carbon.device.mgt.common.app.mgt.ApplicationManagementException; -import org.wso2.carbon.device.mgt.common.app.mgt.ApplicationManager; -import org.wso2.carbon.device.mgt.common.operation.mgt.Operation; -import org.wso2.carbon.device.mgt.common.spi.DeviceManagementService; - -import java.util.List; - -public class DoorManagerService implements DeviceManagementService { - private DeviceManager deviceManager; - - @Override - public String getType() { - return DoorManagerConstants.DEVICE_TYPE; - } - - - @Override - public String getProviderTenantDomain() { - return "carbon.super"; - } - - @Override - public boolean isSharedWithAllTenants() { - return true; - } - - @Override - public void init() throws DeviceManagementException { - this.deviceManager = new DoorManager(); - } - - @Override - public DeviceManager getDeviceManager() { - return deviceManager; - } - - @Override - public ApplicationManager getApplicationManager() { - return null; - } - - @Override - public void notifyOperationToDevices(Operation operation, List deviceIds) - throws DeviceManagementException { - - } - - @Override - public Application[] getApplications(String domain, int pageNumber, int size) - throws ApplicationManagementException { - return new Application[0]; - } - - @Override - public void updateApplicationStatus(DeviceIdentifier deviceId, Application application, - String status) throws ApplicationManagementException { - - } - - @Override - public String getApplicationStatus(DeviceIdentifier deviceId, Application application) - throws ApplicationManagementException { - return null; - } - - @Override - public void installApplicationForDevices(Operation operation, List deviceIdentifiers) - throws ApplicationManagementException { - - } - - @Override - public void installApplicationForUsers(Operation operation, List userNameList) - throws ApplicationManagementException { - - } - - @Override - public void installApplicationForUserRoles(Operation operation, List userRoleList) - throws ApplicationManagementException { - - } -} diff --git a/modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/impl/dao/DoorLockSafe.java b/modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/impl/dao/DoorLockSafe.java deleted file mode 100644 index 2e7fa720..00000000 --- a/modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/impl/dao/DoorLockSafe.java +++ /dev/null @@ -1,92 +0,0 @@ -/*~ Copyright (c) 2016 WSO2 Inc. (http://www.wso2.org) All Rights Reserved. - ~ - ~ WSO2 Inc. licenses this file to you under the Apache License, - ~ Version 2.0 (the "License"); you may not use this file except - ~ in compliance with the License. - ~ You may obtain a copy of the License at - ~ - ~ http://www.apache.org/licenses/LICENSE-2.0 - ~ - ~ Unless required by applicable law or agreed to in writing, - ~ software distributed under the License is distributed on an - ~ "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - ~ KIND, either express or implied. See the License for the - ~ specific language governing permissions and limitations - ~ under the License.*/ - -package org.homeautomation.doormanager.plugin.impl.dao; - -public class DoorLockSafe { - private String owner; - private String deviceId; - private String UIDofUser; - private String serialNumber; - private String policy; - private String emailAddress; - private String accessToken; - private String refreshToken; - - public String getOwner() { - return owner; - } - - public void setOwner(String owner) { - this.owner = owner; - } - - public String getDeviceId() { - return deviceId; - } - - public void setDeviceId(String deviceId) { - this.deviceId = deviceId; - } - - public String getUIDofUser() { - return UIDofUser; - } - - public void setUIDofUser(String UIDofUser) { - this.UIDofUser = UIDofUser; - } - - public String getSerialNumber() { - return serialNumber; - } - - public void setSerialNumber(String serialNumber) { - this.serialNumber = serialNumber; - } - - public String getPolicy() { - return policy; - } - - public void setPolicy(String policy) { - this.policy = policy; - } - - public String getEmailAddress() { - return emailAddress; - } - - public void setEmailAddress(String emailAddress) { - this.emailAddress = emailAddress; - } - - public String getAccessToken() { - return accessToken; - } - - public void setAccessToken(String accessToken) { - this.accessToken = accessToken; - } - - public String getRefreshToken() { - return refreshToken; - } - - public void setRefreshToken(String refreshToken) { - this.refreshToken = refreshToken; - } -} diff --git a/modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/impl/dao/DoorManagerDAOUtil.java b/modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/impl/dao/DoorManagerDAOUtil.java deleted file mode 100644 index ecaec9db..00000000 --- a/modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/impl/dao/DoorManagerDAOUtil.java +++ /dev/null @@ -1,132 +0,0 @@ -/* - * Copyright (c) 2015, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. - * - * WSO2 Inc. licenses this file to you under the Apache License, - * Version 2.0 (the "License"); you may not use this file except - * in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -package org.homeautomation.doormanager.plugin.impl.dao; - -import org.apache.commons.logging.Log; -import org.apache.commons.logging.LogFactory; -import org.homeautomation.doormanager.plugin.constants.DoorManagerConstants; -import org.homeautomation.doormanager.plugin.exception.DoorManagerDeviceMgtPluginException; -import org.homeautomation.doormanager.plugin.impl.dao.impl.DoorManagerDAO; - -import javax.naming.Context; -import javax.naming.InitialContext; -import javax.naming.NamingException; -import javax.sql.DataSource; -import java.sql.Connection; -import java.sql.SQLException; - -public class DoorManagerDAOUtil { - - private static final Log log = LogFactory.getLog(DoorManagerDAOUtil.class); - static DataSource dataSource; - private static ThreadLocal currentConnection = new ThreadLocal(); - - public DoorManagerDAOUtil() { - initAutomaticDoorLOckerDAO(); - } - - public static void initAutomaticDoorLOckerDAO() { - try { - Context ctx = new InitialContext(); - dataSource = (DataSource) ctx.lookup(DoorManagerConstants.DATA_SOURCE_NAME); - } catch (NamingException e) { - log.error("Error while looking up the data source: " + - DoorManagerConstants.DATA_SOURCE_NAME); - } - - } - - public static void beginTransaction() throws DoorManagerDeviceMgtPluginException { - try { - Connection conn = dataSource.getConnection(); - conn.setAutoCommit(false); - currentConnection.set(conn); - } catch (SQLException e) { - throw new DoorManagerDeviceMgtPluginException( - "Error occurred while retrieving datasource connection", e); - } - } - - public static Connection getConnection() throws DoorManagerDeviceMgtPluginException { - if (currentConnection.get() == null) { - try { - currentConnection.set(dataSource.getConnection()); - } catch (SQLException e) { - throw new DoorManagerDeviceMgtPluginException( - "Error occurred while retrieving data source connection", e); - } - } - return currentConnection.get(); - } - - public static void commitTransaction() throws DoorManagerDeviceMgtPluginException { - try { - Connection conn = currentConnection.get(); - if (conn != null) { - conn.commit(); - } else { - if (log.isDebugEnabled()) { - log.debug("Datasource connection associated with the current thread is null, " + - "hence commit has not been attempted"); - } - } - } catch (SQLException e) { - throw new DoorManagerDeviceMgtPluginException( - "Error occurred while committing the transaction", e); - } finally { - closeConnection(); - } - } - - public static void closeConnection() throws DoorManagerDeviceMgtPluginException { - - Connection con = currentConnection.get(); - if (con != null) { - try { - con.close(); - } catch (SQLException e) { - log.error("Error occurred while close the connection"); - } - } - currentConnection.remove(); - } - - public static void rollbackTransaction() throws DoorManagerDeviceMgtPluginException { - try { - Connection conn = currentConnection.get(); - if (conn != null) { - conn.rollback(); - } else { - if (log.isDebugEnabled()) { - log.debug( - "Datasource connection associated with the current thread is null, " + - "hence rollback has not been attempted"); - } - } - } catch (SQLException e) { - throw new DoorManagerDeviceMgtPluginException("Error occurred while rollback the transaction", e); - } finally { - closeConnection(); - } - } - - public DoorManagerDAO getAutomaticDoorLockerDeviceDAO() { - return new DoorManagerDAO(); - } -} \ No newline at end of file diff --git a/modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/impl/dao/impl/DoorManagerDAO.java b/modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/impl/dao/impl/DoorManagerDAO.java deleted file mode 100644 index 6d0bbcab..00000000 --- a/modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/impl/dao/impl/DoorManagerDAO.java +++ /dev/null @@ -1,474 +0,0 @@ -/* - * Copyright (c) 2015, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. - * - * WSO2 Inc. licenses this file to you under the Apache License, - * Version 2.0 (the "License"); you may not use this file except - * in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -package org.homeautomation.doormanager.plugin.impl.dao.impl; - -import org.apache.commons.logging.Log; -import org.apache.commons.logging.LogFactory; -import org.homeautomation.doormanager.plugin.constants.DoorManagerConstants; -import org.homeautomation.doormanager.plugin.exception.DoorManagerDeviceMgtPluginException; -import org.homeautomation.doormanager.plugin.impl.dao.DoorLockSafe; -import org.homeautomation.doormanager.plugin.impl.dao.DoorManagerDAOUtil; -import org.homeautomation.doormanager.plugin.impl.dao.util.DoorManagerUtils; -import org.wso2.carbon.device.mgt.common.Device; - -import java.sql.Connection; -import java.sql.PreparedStatement; -import java.sql.ResultSet; -import java.sql.SQLException; -import java.util.ArrayList; -import java.util.List; - -/** - * Device Dao for automatic door locker Devices. - */ -public class DoorManagerDAO { - - - private static final Log log = LogFactory.getLog(DoorManagerDAO.class); - - public Device getDevice(String deviceId) throws DoorManagerDeviceMgtPluginException { - Connection conn = null; - PreparedStatement stmt = null; - Device automaticDoorLockerDevice = null; - ResultSet resultSet = null; - try { - conn = DoorManagerDAOUtil.getConnection(); - String selectDBQuery = - "SELECT doormanager_DEVICE_ID, DEVICE_NAME" + - " FROM doormanager_DEVICE WHERE doormanager_DEVICE_ID = ?"; - stmt = conn.prepareStatement(selectDBQuery); - stmt.setString(1, deviceId); - resultSet = stmt.executeQuery(); - if (resultSet.next()) { - automaticDoorLockerDevice = new Device(); - automaticDoorLockerDevice.setName(resultSet.getString( - DoorManagerConstants.DEVICE_PLUGIN_DEVICE_NAME)); - List properties = new ArrayList<>(); - automaticDoorLockerDevice.setProperties(properties); - if (log.isDebugEnabled()) { - log.debug("Locker Manager service " + deviceId + " data has been fetched from" + - "Locker Manager database."); - } - } - } catch (SQLException e) { - String msg = "Error occurred while fetching Locker Manager device : '" + deviceId + "'"; - log.error(msg, e); - throw new DoorManagerDeviceMgtPluginException(msg, e); - } finally { - DoorManagerUtils.cleanupResources(stmt, resultSet); - DoorManagerDAOUtil.closeConnection(); - } - return automaticDoorLockerDevice; - } - - - public boolean addDevice(Device automaticDoorLOcker) throws DoorManagerDeviceMgtPluginException { - boolean status = false; - Connection conn = null; - PreparedStatement stmt = null; - try { - conn = DoorManagerDAOUtil.getConnection(); - String createDBQuery = - "INSERT INTO doormanager_DEVICE(doormanager_DEVICE_ID, DEVICE_NAME, ACCESS_TOKEN, REFRESH_TOKEN) VALUES (?, ?, ?, ?)"; - - stmt = conn.prepareStatement(createDBQuery); - stmt.setString(1, automaticDoorLOcker.getDeviceIdentifier()); - stmt.setString(2, automaticDoorLOcker.getName()); - stmt.setString(3, DoorManagerUtils.getDeviceProperty( - automaticDoorLOcker.getProperties(), - DoorManagerConstants.DEVICE_PLUGIN_PROPERTY_ACCESS_TOKEN)); - stmt.setString(4, DoorManagerUtils.getDeviceProperty( - automaticDoorLOcker.getProperties(), - DoorManagerConstants.DEVICE_PLUGIN_PROPERTY_REFRESH_TOKEN)); - int rows = stmt.executeUpdate(); - if (rows > 0) { - status = true; - if (log.isDebugEnabled()) { - log.debug("Locker Manager device " + automaticDoorLOcker.getDeviceIdentifier() + - " data has been added to the Locker Manager database."); - } - } - } catch (SQLException e) { - String msg = "Error occurred while adding the Locker Manager device '" + - automaticDoorLOcker.getDeviceIdentifier() + "' to the Locker Manager db."; - log.error(msg, e); - throw new DoorManagerDeviceMgtPluginException(msg, e); - } finally { - DoorManagerUtils.cleanupResources(stmt, null); - } - return status; - } - - public boolean registerDoorLockSafe(DoorLockSafe automaticDoorLOcker) throws DoorManagerDeviceMgtPluginException { - boolean status = false; - Connection conn = null; - PreparedStatement stmt = null; - try { - conn = DoorManagerDAOUtil.getConnection(); - String createDBQuery = - "INSERT INTO REGISTERED_DOORLOCK_SAFE(doormanager_DEVICE_ID, SERIAL_NUMBER, UID_of_USER, POLICY, " + - "EMAIL_ADDRESS, ACCESS_TOKEN, REFRESH_TOKEN) VALUES (?, ?, ?, ?, ?, ?, ?)"; - stmt = conn.prepareStatement(createDBQuery); - stmt.setString(1, automaticDoorLOcker.getDeviceId()); - stmt.setString(2, automaticDoorLOcker.getSerialNumber()); - stmt.setString(3, automaticDoorLOcker.getUIDofUser()); - stmt.setString(4, automaticDoorLOcker.getPolicy()); - stmt.setString(5, automaticDoorLOcker.getEmailAddress()); - stmt.setString(6, automaticDoorLOcker.getAccessToken()); - stmt.setString(7, automaticDoorLOcker.getRefreshToken()); - int rows = stmt.executeUpdate(); - if (rows > 0) { - status = true; - if (log.isDebugEnabled()) { - log.debug("Locker Manager device " + automaticDoorLOcker.getOwner() + - " data has been added to the Locker Manager database."); - } - } - } catch (SQLException e) { - String msg = "Error occurred while adding the Locker Manager device '" + - automaticDoorLOcker.getOwner() + "' to the Locker Manager db."; - log.error(msg, e); - throw new DoorManagerDeviceMgtPluginException(msg, e); - } finally { - DoorManagerUtils.cleanupResources(stmt, null); - } - return status; - } - - public boolean isDoorLockSafeRegistered(String serialNumber, String deviceId) throws DoorManagerDeviceMgtPluginException { - - Connection conn = null; - PreparedStatement stmt = null; - ResultSet resultSet = null; - try { - conn = DoorManagerDAOUtil.getConnection(); - String selectDBQuery = - "SELECT SERIAL_NUMBER FROM REGISTERED_DOORLOCK_SAFE WHERE SERIAL_NUMBER = ? AND doormanager_DEVICE_ID = ?"; - stmt = conn.prepareStatement(selectDBQuery); - stmt.setString(1, serialNumber); - stmt.setString(2, deviceId); - resultSet = stmt.executeQuery(); - if (resultSet.next()) { - String result = resultSet.getString(DoorManagerConstants.DEVICE_PLUGIN_DEVICE_SERIAL_NUMBER); - log.warn(result); - return true; - } else { - return false; - } - - } catch (SQLException e) { - String msg = "Error occurred while fetching all Automatic Door Locker device data'"; - log.error(msg, e); - throw new DoorManagerDeviceMgtPluginException(msg, e); - } finally { - DoorManagerUtils.cleanupResources(stmt, resultSet); - DoorManagerDAOUtil.closeConnection(); - } - - } - - public boolean isUserAllowed(String serialNumber, String UIDofUser, String deviceId) throws DoorManagerDeviceMgtPluginException { - Connection conn = null; - PreparedStatement stmt = null; - ResultSet resultSet = null; - try { - conn = DoorManagerDAOUtil.getConnection(); - String selectDBQuery = - "SELECT UID_OF_USER FROM REGISTERED_DOORLOCK_SAFE WHERE SERIAL_NUMBER = ? AND DOORMANAGER_DEVICE_ID = ?"; - stmt = conn.prepareStatement(selectDBQuery); - stmt.setString(1, serialNumber); - stmt.setString(2, deviceId); - resultSet = stmt.executeQuery(); - String result; - if (resultSet.next()) { - result = resultSet.getString(DoorManagerConstants.DEVICE_PLUGIN_DEVICE_UID_OF_USER); - log.warn(result); - return true; - } else { - selectDBQuery = - "SELECT UID_OF_USER FROM SHARED_DOORLOCK_SAFE WHERE SERIAL_NUMBER = ? AND DOORMANAGER_DEVICE_ID = ? AND UID_OF_USER = ?"; - stmt = conn.prepareStatement(selectDBQuery); - stmt.setString(1, serialNumber); - stmt.setString(2, deviceId); - stmt.setString(3, UIDofUser); - resultSet = stmt.executeQuery(); - if (resultSet.next()) { - result = resultSet.getString(DoorManagerConstants.DEVICE_PLUGIN_DEVICE_UID_OF_USER); - log.warn(result); - return true; - } - return false; - } - } catch (SQLException e) { - String msg = "Error occurred while validating: whether user is registered or not"; - log.error(msg, e); - throw new DoorManagerDeviceMgtPluginException(msg, e); - } finally { - DoorManagerUtils.cleanupResources(stmt, resultSet); - DoorManagerDAOUtil.closeConnection(); - } - - } - - - public boolean shareDoorLockSafe(DoorLockSafe automaticDoorLOcker) throws DoorManagerDeviceMgtPluginException { - boolean status = false; - Connection conn = null; - PreparedStatement stmt = null; - try { - conn = DoorManagerDAOUtil.getConnection(); - String createDBQuery = - "INSERT INTO SHARED_DOORLOCK_SAFE(doormanager_DEVICE_ID, SERIAL_NUMBER, UID_of_USER, POLICY) VALUES (?, ?, ?, ?)"; - stmt = conn.prepareStatement(createDBQuery); - stmt.setString(1, automaticDoorLOcker.getDeviceId()); - stmt.setString(2, automaticDoorLOcker.getSerialNumber()); - stmt.setString(3, automaticDoorLOcker.getUIDofUser()); - stmt.setString(4, automaticDoorLOcker.getPolicy()); - int rows = stmt.executeUpdate(); - if (rows > 0) { - status = true; - if (log.isDebugEnabled()) { - log.debug("Locker Manager device " + automaticDoorLOcker.getOwner() + - " data has been added to the Locker Manager database."); - } - } - } catch (SQLException e) { - String msg = "Error occurred while adding the Locker Manager device '" + - automaticDoorLOcker.getOwner() + "' to the Locker Manager db."; - log.error(msg, e); - throw new DoorManagerDeviceMgtPluginException(msg, e); - } finally { - DoorManagerUtils.cleanupResources(stmt, null); - } - return status; - } - - public boolean checkCardDoorAssociation(String cardNum, String deviceID) throws DoorManagerDeviceMgtPluginException { - Connection conn; - PreparedStatement stmt = null; - ResultSet resultSet = null; - try { - conn = DoorManagerDAOUtil.getConnection(); - String selectDBQuery = "SELECT * FROM REGISTERED_DOORLOCK_SAFE WHERE UID_of_USER = ? AND doormanager_DEVICE_ID = ?"; - stmt = conn.prepareStatement(selectDBQuery); - stmt.setString(1, cardNum); - stmt.setString(2, deviceID); - resultSet = stmt.executeQuery(); - String result; - if (resultSet.next()) { - return true; - } else { - return false; - } - } catch (SQLException e) { - String msg = "No associations were found between lock : " + deviceID + " and card : " + cardNum; - throw new DoorManagerDeviceMgtPluginException(msg, e); - } finally { - DoorManagerUtils.cleanupResources(stmt, null); - } - } - - - public String getUserEmailAddress(String cardNum) throws DoorManagerDeviceMgtPluginException { - Connection conn; - PreparedStatement stmt = null; - ResultSet resultSet = null; - String email; - try { - conn = DoorManagerDAOUtil.getConnection(); - String selectDBQuery = "SELECT EMAIL_ADDRESS FROM REGISTERED_DOORLOCK_SAFE WHERE UID_of_USER = ?"; - stmt = conn.prepareStatement(selectDBQuery); - stmt.setString(1, cardNum); - resultSet = stmt.executeQuery(); - if (resultSet.next()) { - email = resultSet.getString("EMAIL_ADDRESS"); - log.warn(email); - return email; - } - return null; - } catch (SQLException e) { - String msg = "No email found for the and card : " + cardNum; - throw new DoorManagerDeviceMgtPluginException(msg, e); - } finally { - DoorManagerUtils.cleanupResources(stmt, null); - } - } - - public List getUserCredentials(String deviceId, String UIDofUser) throws DoorManagerDeviceMgtPluginException { - - Connection conn = null; - PreparedStatement stmt = null; - ResultSet resultSet = null; - List userCredentials = new ArrayList<>(); - try { - conn = DoorManagerDAOUtil.getConnection(); - String selectDBQuery = - "SELECT ACCESS_TOKEN, REFRESH_TOKEN FROM REGISTERED_DOORLOCK_SAFE WHERE DOORMANAGER_DEVICE_ID = ? AND UID_OF_USER = ?"; - stmt = conn.prepareStatement(selectDBQuery); - stmt.setString(1, deviceId); - stmt.setString(2, UIDofUser); - resultSet = stmt.executeQuery(); - if (log.isDebugEnabled()) { - log.debug("Get user credentials from Automatic Door Locker database."); - } - log.warn("getting user credentials"); - if (resultSet.next()) { - String accessToken = resultSet.getString(DoorManagerConstants.DEVICE_PLUGIN_PROPERTY_ACCESS_TOKEN); - String refreshToken = resultSet.getString(DoorManagerConstants.DEVICE_PLUGIN_PROPERTY_REFRESH_TOKEN); - log.warn(accessToken); - userCredentials.add(accessToken); - userCredentials.add(refreshToken); - } - return userCredentials; - } catch (SQLException e) { - String msg = "Error occurred while getting user credentials"; - log.error(msg, e); - throw new DoorManagerDeviceMgtPluginException(msg, e); - } finally { - DoorManagerUtils.cleanupResources(stmt, resultSet); - DoorManagerDAOUtil.closeConnection(); - } - - } - - public List getRegisteredDoorLocks(String deviceId) throws DoorManagerDeviceMgtPluginException { - - Connection conn = null; - PreparedStatement stmt = null; - ResultSet resultSet = null; - List doorLockSafes = new ArrayList<>(); - try { - conn = DoorManagerDAOUtil.getConnection(); - String selectDBQuery = - "SELECT SERIAL_NUMBER FROM REGISTERED_DOORLOCK_SAFE WHERE doormanager_DEVICE_ID = ?"; - stmt = conn.prepareStatement(selectDBQuery); - stmt.setString(1, deviceId); - resultSet = stmt.executeQuery(); - while (resultSet.next()) { - doorLockSafes.add(resultSet.getString(DoorManagerConstants.DEVICE_PLUGIN_DEVICE_SERIAL_NUMBER)); - } - if (log.isDebugEnabled()) { - log.debug("All Locker Manager device details have fetched from Automatic Door Locker database."); - } - return doorLockSafes; - } catch (SQLException e) { - String msg = "Error occurred while fetching all Automatic Door Locker device data'"; - log.error(msg, e); - throw new DoorManagerDeviceMgtPluginException(msg, e); - } finally { - DoorManagerUtils.cleanupResources(stmt, resultSet); - DoorManagerDAOUtil.closeConnection(); - } - } - - public boolean updateDevice(Device automaticDoorLocker) throws DoorManagerDeviceMgtPluginException { - boolean status = false; - Connection conn = null; - PreparedStatement stmt = null; - try { - conn = DoorManagerDAOUtil.getConnection(); - String updateDBQuery = - "UPDATE doormanager_DEVICE SET DEVICE_NAME = ? WHERE doormanager_DEVICE_ID = ?"; - stmt = conn.prepareStatement(updateDBQuery); - if (automaticDoorLocker.getProperties() == null) { - automaticDoorLocker.setProperties(new ArrayList()); - } - stmt.setString(1, automaticDoorLocker.getName()); - stmt.setString(2, automaticDoorLocker.getDeviceIdentifier()); - int rows = stmt.executeUpdate(); - if (rows > 0) { - status = true; - if (log.isDebugEnabled()) { - log.debug("Locker Manager device " + automaticDoorLocker.getDeviceIdentifier() + - " data has been modified."); - } - } - } catch (SQLException e) { - String msg = "Error occurred while modifying the Locker Manager device '" + - automaticDoorLocker.getDeviceIdentifier() + "' data."; - log.error(msg, e); - throw new DoorManagerDeviceMgtPluginException(msg, e); - } finally { - DoorManagerUtils.cleanupResources(stmt, null); - } - return status; - } - - public boolean deleteDevice(String deviceId) throws DoorManagerDeviceMgtPluginException { - boolean status = false; - Connection conn = null; - PreparedStatement stmt = null; - try { - conn = DoorManagerDAOUtil.getConnection(); - String deleteDBQuery = - "DELETE FROM doormanager_DEVICE WHERE doormanager_DEVICE_ID = ?"; - stmt = conn.prepareStatement(deleteDBQuery); - stmt.setString(1, deviceId); - int rows = stmt.executeUpdate(); - if (rows > 0) { - status = true; - if (log.isDebugEnabled()) { - log.debug("Automatic Door Locker device " + deviceId + " data has deleted" + - " from the Automatic Door Locker database."); - } - } - } catch (SQLException e) { - String msg = "Error occurred while deleting Automatic Door Locker device " + deviceId; - log.error(msg, e); - throw new DoorManagerDeviceMgtPluginException(msg, e); - } finally { - DoorManagerUtils.cleanupResources(stmt, null); - } - return status; - } - - public List getAllDevices() throws DoorManagerDeviceMgtPluginException { - - Connection conn = null; - PreparedStatement stmt = null; - ResultSet resultSet = null; - Device connectedCupDevice; - List iotDevices = new ArrayList<>(); - try { - conn = DoorManagerDAOUtil.getConnection(); - String selectDBQuery = - "SELECT doormanager_DEVICE_ID, DEVICE_NAME FROM doormanager_DEVICE"; - stmt = conn.prepareStatement(selectDBQuery); - resultSet = stmt.executeQuery(); - while (resultSet.next()) { - connectedCupDevice = new Device(); - connectedCupDevice.setDeviceIdentifier(resultSet.getString( - DoorManagerConstants.DEVICE_PLUGIN_DEVICE_ID)); - connectedCupDevice.setName(resultSet.getString( - DoorManagerConstants.DEVICE_PLUGIN_DEVICE_NAME)); - } - if (log.isDebugEnabled()) { - log.debug("All Locker Manager device details have fetched from Automatic Door Locker database."); - } - return iotDevices; - } catch (SQLException e) { - String msg = "Error occurred while fetching all Automatic Door Locker device data'"; - log.error(msg, e); - throw new DoorManagerDeviceMgtPluginException(msg, e); - } finally { - DoorManagerUtils.cleanupResources(stmt, resultSet); - DoorManagerDAOUtil.closeConnection(); - } - } -} \ No newline at end of file diff --git a/modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/impl/dao/util/DoorManagerUtils.java b/modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/impl/dao/util/DoorManagerUtils.java deleted file mode 100644 index eaafe0ea..00000000 --- a/modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/impl/dao/util/DoorManagerUtils.java +++ /dev/null @@ -1,86 +0,0 @@ -/* - * Copyright (c) 2015, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. - * - * WSO2 Inc. licenses this file to you under the Apache License, - * Version 2.0 (the "License"); you may not use this file except - * in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -package org.homeautomation.doormanager.plugin.impl.dao.util; - -import org.apache.commons.logging.Log; -import org.apache.commons.logging.LogFactory; -import org.wso2.carbon.device.mgt.common.Device; - -import java.sql.Connection; -import java.sql.PreparedStatement; -import java.sql.ResultSet; -import java.sql.SQLException; -import java.util.List; - -/** - * Contains utility methods used by Automatic Door Locker - */ -public class DoorManagerUtils { - - private static Log log = LogFactory.getLog(DoorManagerUtils.class); - - public static String getDeviceProperty(List deviceProperties, String propertyKey) { - String deviceProperty = ""; - for (Device.Property property : deviceProperties) { - if (propertyKey.equals(property.getName())) { - deviceProperty = property.getValue(); - } - } - return deviceProperty; - } - - public static Device.Property getProperty(String property, String value) { - if (property != null) { - Device.Property prop = new Device.Property(); - prop.setName(property); - prop.setValue(value); - return prop; - } - return null; - } - - public static void cleanupResources(Connection conn, PreparedStatement stmt, ResultSet rs) { - if (rs != null) { - try { - rs.close(); - } catch (SQLException e) { - log.warn("Error occurred while closing result set", e); - } - } - if (stmt != null) { - try { - stmt.close(); - } catch (SQLException e) { - log.warn("Error occurred while closing prepared statement", e); - } - } - if (conn != null) { - try { - conn.close(); - } catch (SQLException e) { - log.warn("Error occurred while closing database connection", e); - } - } - } - - public static void cleanupResources(PreparedStatement stmt, ResultSet rs) { - cleanupResources(null, stmt, rs); - } - -} diff --git a/modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/internal/DoorManagerManagementServiceComponent.java b/modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/internal/DoorManagerManagementServiceComponent.java deleted file mode 100644 index 3363bf41..00000000 --- a/modules/samples/doormanager/component/plugin/src/main/java/org.homeautomation/doormanager/plugin/internal/DoorManagerManagementServiceComponent.java +++ /dev/null @@ -1,74 +0,0 @@ -/* - * Copyright (c) 2016, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. - * - * WSO2 Inc. licenses this file to you under the Apache License, - * Version 2.0 (the "License"); you may not use this file except - * in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -package org.homeautomation.doormanager.plugin.internal; - -import org.apache.commons.logging.Log; -import org.apache.commons.logging.LogFactory; -import org.homeautomation.doormanager.plugin.impl.DoorManagerService; -import org.osgi.framework.BundleContext; -import org.osgi.framework.ServiceRegistration; -import org.osgi.service.component.ComponentContext; -import org.wso2.carbon.device.mgt.common.spi.DeviceManagementService; - - -/** - * @scr.component name="org.homeautomation.doormanager.plugin.internal.DoorManagerManagementServiceComponent" - * immediate="true" - */ -public class DoorManagerManagementServiceComponent { - - private static final Log log = LogFactory.getLog(DoorManagerManagementServiceComponent.class); - private ServiceRegistration automaticDoorLocker; - - protected void activate(ComponentContext ctx) { - if (log.isDebugEnabled()) { - log.debug("Activating Door Opener Device Management Service Component"); - } - try { - BundleContext bundleContext = ctx.getBundleContext(); - automaticDoorLocker = - bundleContext.registerService(DeviceManagementService.class.getName(), - new DoorManagerService(), null); - if (log.isDebugEnabled()) { - log.debug("DoorOpener Device Management Service Component has been successfully activated"); - } - } catch (Throwable e) { - log.error("Error occurred while activating DoorOpener Device Management Service Component", e); - } - } - - protected void deactivate(ComponentContext ctx) { - if (log.isDebugEnabled()) { - log.debug("De-activating Door Opener Device Management Service Component"); - } - try { - if (automaticDoorLocker != null) { - automaticDoorLocker.unregister(); - } - if (log.isDebugEnabled()) { - log.debug( - "Door Opener Device Management Service Component has been successfully de-activated"); - } - } catch (Throwable e) { - log.error( - "Error occurred while de-activating Door Locker Device Management bundle", e); - } - } - -} diff --git a/modules/samples/doormanager/component/pom.xml b/modules/samples/doormanager/component/pom.xml deleted file mode 100644 index 5e8bd5d8..00000000 --- a/modules/samples/doormanager/component/pom.xml +++ /dev/null @@ -1,56 +0,0 @@ - - - - - org.homeautomation - doormanager - 1.0.0-SNAPSHOT - ../pom.xml - - 4.0.0 - 1.0.0-SNAPSHOT - doormanager-component - pom - - - - - org.apache.felix - maven-scr-plugin - ${maven-scr-plugin.version} - - - generate-scr-scrdescriptor - - scr - - - - - - - - - plugin - api - analytics - ui - - diff --git a/modules/samples/doormanager/component/ui/pom.xml b/modules/samples/doormanager/component/ui/pom.xml deleted file mode 100644 index d618b978..00000000 --- a/modules/samples/doormanager/component/ui/pom.xml +++ /dev/null @@ -1,56 +0,0 @@ - - - - - org.homeautomation - doormanager-component - 1.0.0-SNAPSHOT - ../pom.xml - - 4.0.0 - org.homeautomation.doormanager.ui - org.homeautomation.doormanager.ui - pom - - - - maven-assembly-plugin - 2.5.5 - - org.homeautomation.doormanager.ui-1.0.0-SNAPSHOT - false - - src/assembly/src.xml - - - - - create-archive - package - - single - - - - - - - \ No newline at end of file diff --git a/modules/samples/doormanager/component/ui/src/assembly/src.xml b/modules/samples/doormanager/component/ui/src/assembly/src.xml deleted file mode 100644 index 5e2e656a..00000000 --- a/modules/samples/doormanager/component/ui/src/assembly/src.xml +++ /dev/null @@ -1,36 +0,0 @@ - - - - src - - zip - - false - ${basedir}/src - - - ${basedir}/src/main/resources/jaggeryapps/ - / - true - - - \ No newline at end of file diff --git a/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.device-view/device-view.hbs b/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.device-view/device-view.hbs deleted file mode 100644 index 4a037a61..00000000 --- a/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.device-view/device-view.hbs +++ /dev/null @@ -1,94 +0,0 @@ - -{{#zone "topCss"}} - -{{/zone}} - -{{#zone "device-thumbnail"}} - -{{/zone}} - -{{#zone "operation-status"}} - -{{/zone}} - -{{#zone "device-opetations"}} -
- Operations -
-
- {{unit "iot.unit.device.operation-bar" device=device}} -
-{{/zone}} - -{{#zone "device-detail-properties"}} -
- - -
-
-
-
Device Statistics
- {{unit "iot.unit.device.stats" device=device}} -
-
-
Operations Log
-
- -
-
- Not available yet -
-
-
-
-
-
-
-
-{{/zone}} - - - diff --git a/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.device-view/device-view.js b/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.device-view/device-view.js deleted file mode 100644 index 9e6e6747..00000000 --- a/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.device-view/device-view.js +++ /dev/null @@ -1,37 +0,0 @@ -/* - * Copyright (c) 2016, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. - * - * WSO2 Inc. licenses this file to you under the Apache License, - * Version 2.0 (the "License"); you may not use this file except - * in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -function onRequest(context) { - - var log = new Log("device-view.js"); - var deviceType = context.uriParams.deviceType; - var deviceId = request.getParameter("id"); - - var getProperty = require("process").getProperty; - var port = getProperty("carbon.https.port"); - var host = getProperty("carbon.local.ip"); - var sessionId = session.getId(); - if (deviceType != null && deviceType != undefined && deviceId != null && deviceId != undefined) { - var deviceModule = require("/app/modules/device.js").deviceModule; - var device = deviceModule.viewDevice(deviceType, deviceId); - if (device && device.status != "error") { - log.info(device); - return {"device": device, "port": port, "host": host, "sessionId": sessionId}; - } - } -} \ No newline at end of file diff --git a/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.device-view/device-view.json b/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.device-view/device-view.json deleted file mode 100644 index 3c9e4e4c..00000000 --- a/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.device-view/device-view.json +++ /dev/null @@ -1,4 +0,0 @@ - -{ - "version": "1.0.0" -} \ No newline at end of file diff --git a/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.device-view/public/images/doormanager-icon.png b/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.device-view/public/images/doormanager-icon.png deleted file mode 100644 index a44f50fc48a55fdae888184ecb9133e7ff3f057f..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 6697 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 bATa1N>A@I+6Bf1q=Z)TFBkht)_Ba0rw^AMC diff --git a/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.device-view/public/images/thumb.png b/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.device-view/public/images/thumb.png deleted file mode 100644 index a44f50fc48a55fdae888184ecb9133e7ff3f057f..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 6697 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 bATa1N>A@I+6Bf1q=Z)TFBkht)_Ba0rw^AMC diff --git a/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.type-view/public/images/doormanager-icon.png b/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.type-view/public/images/doormanager-icon.png deleted file mode 100644 index a44f50fc48a55fdae888184ecb9133e7ff3f057f..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 6697 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 bATa1N>A@I+6Bf1q=Z)TFBkht)_Ba0rw^AMC diff --git a/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.type-view/public/images/myDevices_analytics.png b/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.type-view/public/images/myDevices_analytics.png deleted file mode 100644 index dc5f9a7d99446d847c118055650139302719e710..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 45802 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
ABby(s=LJO21V_>RLT6jLL^ z=4SUR0FdeO+Wy_(Y5B{Kv|3EnSaqzql4X&@7TM?A4eoMs7t_~mrbitCRt(p^{VBswjBJHoh27agFV*uvFv_Yx@3n#LYjBK~|Qi#RGHHfFD z@)|RoHt8x9w-P@R>%Lx=c0OoYIQk_Pa;}z9OzLt3y>bbsW4ftJ(prMDrMIq=QKgMdU^bfjGFEvi*NbJn@P!$MKxUFwR>lX%bI8n##=+PO+|Ujr%&!0R>FDfi6m;Q^FDTrn9Y@jAsefHY z1M-3K9bK6(a-r6b(iJo*NQ9^Fl3VulWfj-me#y{O^Hi+$Fm#@8wsf#5X!?o>6 z!1_@;8BfQgcmFY^6qjcBrSWg(J~stx(^l1kh7Z z6h>@y08FFS?1AZ(-Y*RX-0j_IO8Eq|W-;9|C#JQEdXl53z$*hiKa`jW8|{bZdO3C@ z4-jOK(Iep7|e3uEW2! zPwARrCLZSB*JQ3*6v6(J=mQ&dIdhvK-!kN&;Gw`ib9iunUWL#i1w)uVRZIq5MY$wbGOi(XvIQLkQX@ZH$5fGpP2BH(;sTYF03Po} ze2~Qe>45?8%lP`4O~hiz-LOms8Z}@SqV1kNKMTgE{t1T~YVZb^glebkkos3>RtC>6 z1$;t*m+4j#s344ZV)#1rW%qe~PI&z~vskoE$n$}A~v*n_4(-MO8x^eB= zxb9TpJ>3aDnLȯ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 G{(k^OIp?eZ diff --git a/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.type-view/public/images/thumb.png b/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.type-view/public/images/thumb.png deleted file mode 100644 index a44f50fc48a55fdae888184ecb9133e7ff3f057f..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 6697 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 bATa1N>A@I+6Bf1q=Z)TFBkht)_Ba0rw^AMC diff --git a/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.type-view/public/js/download.js b/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.type-view/public/js/download.js deleted file mode 100644 index faefdefb..00000000 --- a/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.type-view/public/js/download.js +++ /dev/null @@ -1,242 +0,0 @@ -/* - * Copyright (c) 2015, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - * - * - */ - -var modalPopup = ".wr-modalpopup"; -var modalPopupContainer = modalPopup + " .modalpopup-container"; -var modalPopupContent = modalPopup + " .modalpopup-content"; -var body = "body"; - -/* - * set popup maximum height function. - */ -function setPopupMaxHeight() { - $(modalPopupContent).css('max-height', ($(body).height() - ($(body).height() / 100 * 30))); - $(modalPopupContainer).css('margin-top', (-($(modalPopupContainer).height() / 2))); -} - -/* - * show popup function. - */ -function showPopup() { - $(modalPopup).show(); - setPopupMaxHeight(); - $('#downloadForm').validate({ - rules: { - deviceName: { - minlength: 4, - required: true - } - }, - highlight: function (element) { - $(element).closest('.control-group').removeClass('success').addClass('error'); - }, - success: function (element) { - $(element).closest('.control-group').removeClass('error').addClass('success'); - $('label[for=deviceName]').remove(); - } - }); - var deviceType = ""; - $('.deviceType').each(function () { - if (this.value != "") { - deviceType = this.value; - } - }); -} - -/* - * hide popup function. - */ -function hidePopup() { - $('label[for=deviceName]').remove(); - $('.control-group').removeClass('success').removeClass('error'); - $(modalPopupContent).html(''); - $(modalPopup).hide(); -} - -/* - * DOM ready functions. - */ -$(document).ready(function () { - attachEvents(); -}); - -function attachEvents() { - /** - * Following click function would execute - * when a user clicks on "Download" link - * on Device Management page in WSO2 DC Console. - */ - $("a.download-link").click(function () { - var sketchType = $(this).data("sketchtype"); - var deviceType = $(this).data("devicetype"); - var downloadDeviceAPI = "/devicemgt/api/devices/sketch/generate_link"; - var payload = {"sketchType": sketchType, "deviceType": deviceType}; - $(modalPopupContent).html($('#download-device-modal-content').html()); - showPopup(); - var deviceName; - $("a#download-device-download-link").click(function () { - $('.new-device-name').each(function () { - if (this.value != "") { - deviceName = this.value; - } - }); - $('label[for=deviceName]').remove(); - if (deviceName && deviceName.length >= 4) { - payload.deviceName = deviceName; - invokerUtil.post( - downloadDeviceAPI, - payload, - function (data, textStatus, jqxhr) { - doAction(data); - }, - function (data) { - doAction(data); - } - ); - } else if (deviceName) { - $('.controls').append(''); - $('.control-group').removeClass('success').addClass('error'); - } else { - $('.controls').append(''); - $('.control-group').removeClass('success').addClass('error'); - } - }); - - $("a#download-device-cancel-link").click(function () { - hidePopup(); - }); - - }); -} - -function downloadAgent() { - - /*var $inputs = $('#downloadForm :input'); - var values = {}; - $inputs.each(function() { - values[this.name] = $(this).val(); - }); - var payload = {}; - payload.name = $inputs[0].value; - //payload.owner = $inputs[3].value; - payload.serialNumber = $inputs[1].value; - - var doorManagerRegisterURL = "/doormanager_mgt/manager/device/register?" + - "name=" + encodeURI(payload.name) + "&deviceId=" + payload.serialNumber; - - invokerUtil.post( - doorManagerRegisterURL, - payload, - function (data, textStatus, jqxhr) { - hidePopup(); - }, - function (data) { - hidePopup(); - } - ); - var deviceName; - $('.new-device-name').each(function () { - if (this.value != "") { - deviceName = this.value; - } - }); - if (deviceName && deviceName.length >= 4) { - setTimeout(function () { - hidePopup(); - }, 1000); - }*/ - var deviceName = ""; - $('.new-device-name').each(function () { - if (this.value != "") { - deviceName = this.value; - } - }); - var deviceType = ""; - $('.deviceType').each(function () { - if (this.value != "") { - deviceType = this.value; - } - }); - var sketchType = ""; - $('.sketchType').each(function () { - if (this.value != "") { - sketchType = this.value; - } - }); - /*var serialNumber = ""; - $('.device-serial-number').each(function () { - if (this.value != "") { - serialNumber = this.value; - } - });*/ - var deviceNameFormat = /^[^~?!#$:;%^*`+={}\[\]\\()|<>,'"]{1,30}$/; - if (deviceName && deviceNameFormat.test(deviceName)) { - $(modalPopupContent).html($('#device-agent-downloading-content').html()); - var successCallback = function (data) { - data = JSON.parse(data); - hidePopup(); - window.location = "/devicemgt/api/devices/sketch/download/" + data.responseContent; - }; - var generateLink = "/" + deviceType + "_mgt/manager/device/" + sketchType - + "/generate_link?deviceName=" + deviceName; - console.log("generated link"+ generateLink); - invokerUtil.get(generateLink, successCallback, function (message) { - console.log(message.content); - hidePopup(); - doAction(data); - }); - } else { - $("#invalid-username-error-msg span").text("Invalid device name"); - $("#invalid-username-error-msg").removeClass("hidden"); - } -} - -function doAction(data) { - if (data.status == null) { - document.write(data); - } - if (data.status == "200") { - $(modalPopupContent).html($('#download-device-modal-content-links').html()); - $("input#download-device-url").val(data.responseText); - $("input#download-device-url").focus(function () { - $(this).select(); - }); - showPopup(); - } else if (data.status == "401") { - $(modalPopupContent).html($('#device-401-content').html()); - $("#device-401-link").click(function () { - window.location = "/devicemgt/login"; - }); - showPopup(); - } else if (data == "403") { - $(modalPopupContent).html($('#device-403-content').html()); - $("#device-403-link").click(function () { - window.location = "/devicemgt/login"; - }); - showPopup(); - } else { - $(modalPopupContent).html($('#device-unexpected-error-content').html()); - $("a#device-unexpected-error-link").click(function () { - hidePopup(); - }); - } -} \ No newline at end of file diff --git a/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.type-view/public/js/jquery.validate.js b/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.type-view/public/js/jquery.validate.js deleted file mode 100644 index 3c1ebb04..00000000 --- a/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.type-view/public/js/jquery.validate.js +++ /dev/null @@ -1,1220 +0,0 @@ -/** - * jQuery Validation Plugin 1.11.0pre - * - * http://bassistance.de/jquery-plugins/jquery-plugin-validation/ - * http://docs.jquery.com/Plugins/Validation - * - * Copyright 2013 Jörn Zaefferer - * Released under the MIT license: - * http://www.opensource.org/licenses/mit-license.php - */ - -(function($) { - -$.extend($.fn, { - // http://docs.jquery.com/Plugins/Validation/validate - validate: function( options ) { - - // if nothing is selected, return nothing; can't chain anyway - if ( !this.length ) { - if ( options && options.debug && window.console ) { - console.warn( "Nothing selected, can't validate, returning nothing." ); - } - return; - } - - // check if a validator for this form was already created - var validator = $.data( this[0], "validator" ); - if ( validator ) { - return validator; - } - - // Add novalidate tag if HTML5. - this.attr( "novalidate", "novalidate" ); - - validator = new $.validator( options, this[0] ); - $.data( this[0], "validator", validator ); - - if ( validator.settings.onsubmit ) { - - this.validateDelegate( ":submit", "click", function( event ) { - if ( validator.settings.submitHandler ) { - validator.submitButton = event.target; - } - // allow suppressing validation by adding a cancel class to the submit button - if ( $(event.target).hasClass("cancel") ) { - validator.cancelSubmit = true; - } - }); - - // validate the form on submit - this.submit( function( event ) { - if ( validator.settings.debug ) { - // prevent form submit to be able to see console output - event.preventDefault(); - } - function handle() { - var hidden; - if ( validator.settings.submitHandler ) { - if ( validator.submitButton ) { - // insert a hidden input as a replacement for the missing submit button - hidden = $("").attr("name", validator.submitButton.name).val(validator.submitButton.value).appendTo(validator.currentForm); - } - validator.settings.submitHandler.call( validator, validator.currentForm, event ); - if ( validator.submitButton ) { - // and clean up afterwards; thanks to no-block-scope, hidden can be referenced - hidden.remove(); - } - return false; - } - return true; - } - - // prevent submit for invalid forms or custom submit handlers - if ( validator.cancelSubmit ) { - validator.cancelSubmit = false; - return handle(); - } - if ( validator.form() ) { - if ( validator.pendingRequest ) { - validator.formSubmitted = true; - return false; - } - return handle(); - } else { - validator.focusInvalid(); - return false; - } - }); - } - - return validator; - }, - // http://docs.jquery.com/Plugins/Validation/valid - valid: function() { - if ( $(this[0]).is("form")) { - return this.validate().form(); - } else { - var valid = true; - var validator = $(this[0].form).validate(); - this.each(function() { - valid &= validator.element(this); - }); - return valid; - } - }, - // attributes: space seperated list of attributes to retrieve and remove - removeAttrs: function( attributes ) { - var result = {}, - $element = this; - $.each(attributes.split(/\s/), function( index, value ) { - result[value] = $element.attr(value); - $element.removeAttr(value); - }); - return result; - }, - // http://docs.jquery.com/Plugins/Validation/rules - rules: function( command, argument ) { - var element = this[0]; - - if ( command ) { - var settings = $.data(element.form, "validator").settings; - var staticRules = settings.rules; - var existingRules = $.validator.staticRules(element); - switch(command) { - case "add": - $.extend(existingRules, $.validator.normalizeRule(argument)); - staticRules[element.name] = existingRules; - if ( argument.messages ) { - settings.messages[element.name] = $.extend( settings.messages[element.name], argument.messages ); - } - break; - case "remove": - if ( !argument ) { - delete staticRules[element.name]; - return existingRules; - } - var filtered = {}; - $.each(argument.split(/\s/), function( index, method ) { - filtered[method] = existingRules[method]; - delete existingRules[method]; - }); - return filtered; - } - } - - var data = $.validator.normalizeRules( - $.extend( - {}, - $.validator.classRules(element), - $.validator.attributeRules(element), - $.validator.dataRules(element), - $.validator.staticRules(element) - ), element); - - // make sure required is at front - if ( data.required ) { - var param = data.required; - delete data.required; - data = $.extend({required: param}, data); - } - - return data; - } -}); - -// Custom selectors -$.extend($.expr[":"], { - // http://docs.jquery.com/Plugins/Validation/blank - blank: function( a ) { return !$.trim("" + a.value); }, - // http://docs.jquery.com/Plugins/Validation/filled - filled: function( a ) { return !!$.trim("" + a.value); }, - // http://docs.jquery.com/Plugins/Validation/unchecked - unchecked: function( a ) { return !a.checked; } -}); - -// constructor for validator -$.validator = function( options, form ) { - this.settings = $.extend( true, {}, $.validator.defaults, options ); - this.currentForm = form; - this.init(); -}; - -$.validator.format = function( source, params ) { - if ( arguments.length === 1 ) { - return function() { - var args = $.makeArray(arguments); - args.unshift(source); - return $.validator.format.apply( this, args ); - }; - } - if ( arguments.length > 2 && params.constructor !== Array ) { - params = $.makeArray(arguments).slice(1); - } - if ( params.constructor !== Array ) { - params = [ params ]; - } - $.each(params, function( i, n ) { - source = source.replace( new RegExp("\\{" + i + "\\}", "g"), function() { - return n; - }); - }); - return source; -}; - -$.extend($.validator, { - - defaults: { - messages: {}, - groups: {}, - rules: {}, - errorClass: "error", - validClass: "valid", - errorElement: "label", - focusInvalid: true, - errorContainer: $([]), - errorLabelContainer: $([]), - onsubmit: true, - ignore: ":hidden", - ignoreTitle: false, - onfocusin: function( element, event ) { - this.lastActive = element; - - // hide error label and remove error class on focus if enabled - if ( this.settings.focusCleanup && !this.blockFocusCleanup ) { - if ( this.settings.unhighlight ) { - this.settings.unhighlight.call( this, element, this.settings.errorClass, this.settings.validClass ); - } - this.addWrapper(this.errorsFor(element)).hide(); - } - }, - onfocusout: function( element, event ) { - if ( !this.checkable(element) && (element.name in this.submitted || !this.optional(element)) ) { - this.element(element); - } - }, - onkeyup: function( element, event ) { - if ( event.which === 9 && this.elementValue(element) === "" ) { - return; - } else if ( element.name in this.submitted || element === this.lastElement ) { - this.element(element); - } - }, - onclick: function( element, event ) { - // click on selects, radiobuttons and checkboxes - if ( element.name in this.submitted ) { - this.element(element); - } - // or option elements, check parent select in that case - else if ( element.parentNode.name in this.submitted ) { - this.element(element.parentNode); - } - }, - highlight: function( element, errorClass, validClass ) { - if ( element.type === "radio" ) { - this.findByName(element.name).addClass(errorClass).removeClass(validClass); - } else { - $(element).addClass(errorClass).removeClass(validClass); - } - }, - unhighlight: function( element, errorClass, validClass ) { - if ( element.type === "radio" ) { - this.findByName(element.name).removeClass(errorClass).addClass(validClass); - } else { - $(element).removeClass(errorClass).addClass(validClass); - } - } - }, - - // http://docs.jquery.com/Plugins/Validation/Validator/setDefaults - setDefaults: function( settings ) { - $.extend( $.validator.defaults, settings ); - }, - - messages: { - required: "This field is required.", - remote: "Please fix this field.", - email: "Please enter a valid email address.", - url: "Please enter a valid URL.", - date: "Please enter a valid date.", - dateISO: "Please enter a valid date (ISO).", - number: "Please enter a valid number.", - digits: "Please enter only digits.", - creditcard: "Please enter a valid credit card number.", - equalTo: "Please enter the same value again.", - maxlength: $.validator.format("Please enter no more than {0} characters."), - minlength: $.validator.format("Please enter at least {0} characters."), - rangelength: $.validator.format("Please enter a value between {0} and {1} characters long."), - range: $.validator.format("Please enter a value between {0} and {1}."), - max: $.validator.format("Please enter a value less than or equal to {0}."), - min: $.validator.format("Please enter a value greater than or equal to {0}.") - }, - - autoCreateRanges: false, - - prototype: { - - init: function() { - this.labelContainer = $(this.settings.errorLabelContainer); - this.errorContext = this.labelContainer.length && this.labelContainer || $(this.currentForm); - this.containers = $(this.settings.errorContainer).add( this.settings.errorLabelContainer ); - this.submitted = {}; - this.valueCache = {}; - this.pendingRequest = 0; - this.pending = {}; - this.invalid = {}; - this.reset(); - - var groups = (this.groups = {}); - $.each(this.settings.groups, function( key, value ) { - if ( typeof value === "string" ) { - value = value.split(/\s/); - } - $.each(value, function( index, name ) { - groups[name] = key; - }); - }); - var rules = this.settings.rules; - $.each(rules, function( key, value ) { - rules[key] = $.validator.normalizeRule(value); - }); - - function delegate(event) { - var validator = $.data(this[0].form, "validator"), - eventType = "on" + event.type.replace(/^validate/, ""); - if ( validator.settings[eventType] ) { - validator.settings[eventType].call(validator, this[0], event); - } - } - $(this.currentForm) - .validateDelegate(":text, [type='password'], [type='file'], select, textarea, " + - "[type='number'], [type='search'] ,[type='tel'], [type='url'], " + - "[type='email'], [type='datetime'], [type='date'], [type='month'], " + - "[type='week'], [type='time'], [type='datetime-local'], " + - "[type='range'], [type='color'] ", - "focusin focusout keyup", delegate) - .validateDelegate("[type='radio'], [type='checkbox'], select, option", "click", delegate); - - if ( this.settings.invalidHandler ) { - $(this.currentForm).bind("invalid-form.validate", this.settings.invalidHandler); - } - }, - - // http://docs.jquery.com/Plugins/Validation/Validator/form - form: function() { - this.checkForm(); - $.extend(this.submitted, this.errorMap); - this.invalid = $.extend({}, this.errorMap); - if ( !this.valid() ) { - $(this.currentForm).triggerHandler("invalid-form", [this]); - } - this.showErrors(); - return this.valid(); - }, - - checkForm: function() { - this.prepareForm(); - for ( var i = 0, elements = (this.currentElements = this.elements()); elements[i]; i++ ) { - this.check( elements[i] ); - } - return this.valid(); - }, - - // http://docs.jquery.com/Plugins/Validation/Validator/element - element: function( element ) { - element = this.validationTargetFor( this.clean( element ) ); - this.lastElement = element; - this.prepareElement( element ); - this.currentElements = $(element); - var result = this.check( element ) !== false; - if ( result ) { - delete this.invalid[element.name]; - } else { - this.invalid[element.name] = true; - } - if ( !this.numberOfInvalids() ) { - // Hide error containers on last error - this.toHide = this.toHide.add( this.containers ); - } - this.showErrors(); - return result; - }, - - // http://docs.jquery.com/Plugins/Validation/Validator/showErrors - showErrors: function( errors ) { - if ( errors ) { - // add items to error list and map - $.extend( this.errorMap, errors ); - this.errorList = []; - for ( var name in errors ) { - this.errorList.push({ - message: errors[name], - element: this.findByName(name)[0] - }); - } - // remove items from success list - this.successList = $.grep( this.successList, function( element ) { - return !(element.name in errors); - }); - } - if ( this.settings.showErrors ) { - this.settings.showErrors.call( this, this.errorMap, this.errorList ); - } else { - this.defaultShowErrors(); - } - }, - - // http://docs.jquery.com/Plugins/Validation/Validator/resetForm - resetForm: function() { - if ( $.fn.resetForm ) { - $(this.currentForm).resetForm(); - } - this.submitted = {}; - this.lastElement = null; - this.prepareForm(); - this.hideErrors(); - this.elements().removeClass( this.settings.errorClass ).removeData( "previousValue" ); - }, - - numberOfInvalids: function() { - return this.objectLength(this.invalid); - }, - - objectLength: function( obj ) { - var count = 0; - for ( var i in obj ) { - count++; - } - return count; - }, - - hideErrors: function() { - this.addWrapper( this.toHide ).hide(); - }, - - valid: function() { - return this.size() === 0; - }, - - size: function() { - return this.errorList.length; - }, - - focusInvalid: function() { - if ( this.settings.focusInvalid ) { - try { - $(this.findLastActive() || this.errorList.length && this.errorList[0].element || []) - .filter(":visible") - .focus() - // manually trigger focusin event; without it, focusin handler isn't called, findLastActive won't have anything to find - .trigger("focusin"); - } catch(e) { - // ignore IE throwing errors when focusing hidden elements - } - } - }, - - findLastActive: function() { - var lastActive = this.lastActive; - return lastActive && $.grep(this.errorList, function( n ) { - return n.element.name === lastActive.name; - }).length === 1 && lastActive; - }, - - elements: function() { - var validator = this, - rulesCache = {}; - - // select all valid inputs inside the form (no submit or reset buttons) - return $(this.currentForm) - .find("input, select, textarea") - .not(":submit, :reset, :image, [disabled]") - .not( this.settings.ignore ) - .filter(function() { - if ( !this.name ) { - if ( window.console ) { - console.error( "%o has no name assigned", this ); - } - throw new Error( "Failed to validate, found an element with no name assigned. See console for element reference." ); - } - - // select only the first element for each name, and only those with rules specified - if ( this.name in rulesCache || !validator.objectLength($(this).rules()) ) { - return false; - } - - rulesCache[this.name] = true; - return true; - }); - }, - - clean: function( selector ) { - return $(selector)[0]; - }, - - errors: function() { - var errorClass = this.settings.errorClass.replace(" ", "."); - return $(this.settings.errorElement + "." + errorClass, this.errorContext); - }, - - reset: function() { - this.successList = []; - this.errorList = []; - this.errorMap = {}; - this.toShow = $([]); - this.toHide = $([]); - this.currentElements = $([]); - }, - - prepareForm: function() { - this.reset(); - this.toHide = this.errors().add( this.containers ); - }, - - prepareElement: function( element ) { - this.reset(); - this.toHide = this.errorsFor(element); - }, - - elementValue: function( element ) { - var type = $(element).attr("type"), - val = $(element).val(); - - if ( type === "radio" || type === "checkbox" ) { - return $("input[name='" + $(element).attr("name") + "']:checked").val(); - } - - if ( typeof val === "string" ) { - return val.replace(/\r/g, ""); - } - return val; - }, - - check: function( element ) { - element = this.validationTargetFor( this.clean( element ) ); - - var rules = $(element).rules(); - var dependencyMismatch = false; - var val = this.elementValue(element); - var result; - - for (var method in rules ) { - var rule = { method: method, parameters: rules[method] }; - try { - - result = $.validator.methods[method].call( this, val, element, rule.parameters ); - - // if a method indicates that the field is optional and therefore valid, - // don't mark it as valid when there are no other rules - if ( result === "dependency-mismatch" ) { - dependencyMismatch = true; - continue; - } - dependencyMismatch = false; - - if ( result === "pending" ) { - this.toHide = this.toHide.not( this.errorsFor(element) ); - return; - } - - if ( !result ) { - this.formatAndAdd( element, rule ); - return false; - } - } catch(e) { - if ( this.settings.debug && window.console ) { - console.log( "Exception occured when checking element " + element.id + ", check the '" + rule.method + "' method.", e ); - } - throw e; - } - } - if ( dependencyMismatch ) { - return; - } - if ( this.objectLength(rules) ) { - this.successList.push(element); - } - return true; - }, - - // return the custom message for the given element and validation method - // specified in the element's HTML5 data attribute - customDataMessage: function( element, method ) { - return $(element).data("msg-" + method.toLowerCase()) || (element.attributes && $(element).attr("data-msg-" + method.toLowerCase())); - }, - - // return the custom message for the given element name and validation method - customMessage: function( name, method ) { - var m = this.settings.messages[name]; - return m && (m.constructor === String ? m : m[method]); - }, - - // return the first defined argument, allowing empty strings - findDefined: function() { - for(var i = 0; i < arguments.length; i++) { - if ( arguments[i] !== undefined ) { - return arguments[i]; - } - } - return undefined; - }, - - defaultMessage: function( element, method ) { - return this.findDefined( - this.customMessage( element.name, method ), - this.customDataMessage( element, method ), - // title is never undefined, so handle empty string as undefined - !this.settings.ignoreTitle && element.title || undefined, - $.validator.messages[method], - "Warning: No message defined for " + element.name + "" - ); - }, - - formatAndAdd: function( element, rule ) { - var message = this.defaultMessage( element, rule.method ), - theregex = /\$?\{(\d+)\}/g; - if ( typeof message === "function" ) { - message = message.call(this, rule.parameters, element); - } else if (theregex.test(message)) { - message = $.validator.format(message.replace(theregex, "{$1}"), rule.parameters); - } - this.errorList.push({ - message: message, - element: element - }); - - this.errorMap[element.name] = message; - this.submitted[element.name] = message; - }, - - addWrapper: function( toToggle ) { - if ( this.settings.wrapper ) { - toToggle = toToggle.add( toToggle.parent( this.settings.wrapper ) ); - } - return toToggle; - }, - - defaultShowErrors: function() { - var i, elements; - for ( i = 0; this.errorList[i]; i++ ) { - var error = this.errorList[i]; - if ( this.settings.highlight ) { - this.settings.highlight.call( this, error.element, this.settings.errorClass, this.settings.validClass ); - } - this.showLabel( error.element, error.message ); - } - if ( this.errorList.length ) { - this.toShow = this.toShow.add( this.containers ); - } - if ( this.settings.success ) { - for ( i = 0; this.successList[i]; i++ ) { - this.showLabel( this.successList[i] ); - } - } - if ( this.settings.unhighlight ) { - for ( i = 0, elements = this.validElements(); elements[i]; i++ ) { - this.settings.unhighlight.call( this, elements[i], this.settings.errorClass, this.settings.validClass ); - } - } - this.toHide = this.toHide.not( this.toShow ); - this.hideErrors(); - this.addWrapper( this.toShow ).show(); - }, - - validElements: function() { - return this.currentElements.not(this.invalidElements()); - }, - - invalidElements: function() { - return $(this.errorList).map(function() { - return this.element; - }); - }, - - showLabel: function( element, message ) { - var label = this.errorsFor( element ); - if ( label.length ) { - // refresh error/success class - label.removeClass( this.settings.validClass ).addClass( this.settings.errorClass ); - - // check if we have a generated label, replace the message then - if ( label.attr("generated") ) { - label.html(message); - } - } else { - // create label - label = $("<" + this.settings.errorElement + "/>") - .attr({"for": this.idOrName(element), generated: true}) - .addClass(this.settings.errorClass) - .html(message || ""); - if ( this.settings.wrapper ) { - // make sure the element is visible, even in IE - // actually showing the wrapped element is handled elsewhere - label = label.hide().show().wrap("<" + this.settings.wrapper + "/>").parent(); - } - if ( !this.labelContainer.append(label).length ) { - if ( this.settings.errorPlacement ) { - this.settings.errorPlacement(label, $(element) ); - } else { - label.insertAfter(element); - } - } - } - if ( !message && this.settings.success ) { - label.text(""); - if ( typeof this.settings.success === "string" ) { - label.addClass( this.settings.success ); - } else { - this.settings.success( label, element ); - } - } - this.toShow = this.toShow.add(label); - }, - - errorsFor: function( element ) { - var name = this.idOrName(element); - return this.errors().filter(function() { - return $(this).attr("for") === name; - }); - }, - - idOrName: function( element ) { - return this.groups[element.name] || (this.checkable(element) ? element.name : element.id || element.name); - }, - - validationTargetFor: function( element ) { - // if radio/checkbox, validate first element in group instead - if ( this.checkable(element) ) { - element = this.findByName( element.name ).not(this.settings.ignore)[0]; - } - return element; - }, - - checkable: function( element ) { - return (/radio|checkbox/i).test(element.type); - }, - - findByName: function( name ) { - return $(this.currentForm).find("[name='" + name + "']"); - }, - - getLength: function( value, element ) { - switch( element.nodeName.toLowerCase() ) { - case "select": - return $("option:selected", element).length; - case "input": - if ( this.checkable( element) ) { - return this.findByName(element.name).filter(":checked").length; - } - } - return value.length; - }, - - depend: function( param, element ) { - return this.dependTypes[typeof param] ? this.dependTypes[typeof param](param, element) : true; - }, - - dependTypes: { - "boolean": function( param, element ) { - return param; - }, - "string": function( param, element ) { - return !!$(param, element.form).length; - }, - "function": function( param, element ) { - return param(element); - } - }, - - optional: function( element ) { - var val = this.elementValue(element); - return !$.validator.methods.required.call(this, val, element) && "dependency-mismatch"; - }, - - startRequest: function( element ) { - if ( !this.pending[element.name] ) { - this.pendingRequest++; - this.pending[element.name] = true; - } - }, - - stopRequest: function( element, valid ) { - this.pendingRequest--; - // sometimes synchronization fails, make sure pendingRequest is never < 0 - if ( this.pendingRequest < 0 ) { - this.pendingRequest = 0; - } - delete this.pending[element.name]; - if ( valid && this.pendingRequest === 0 && this.formSubmitted && this.form() ) { - $(this.currentForm).submit(); - this.formSubmitted = false; - } else if (!valid && this.pendingRequest === 0 && this.formSubmitted) { - $(this.currentForm).triggerHandler("invalid-form", [this]); - this.formSubmitted = false; - } - }, - - previousValue: function( element ) { - return $.data(element, "previousValue") || $.data(element, "previousValue", { - old: null, - valid: true, - message: this.defaultMessage( element, "remote" ) - }); - } - - }, - - classRuleSettings: { - required: {required: true}, - email: {email: true}, - url: {url: true}, - date: {date: true}, - dateISO: {dateISO: true}, - number: {number: true}, - digits: {digits: true}, - creditcard: {creditcard: true} - }, - - addClassRules: function( className, rules ) { - if ( className.constructor === String ) { - this.classRuleSettings[className] = rules; - } else { - $.extend(this.classRuleSettings, className); - } - }, - - classRules: function( element ) { - var rules = {}; - var classes = $(element).attr("class"); - if ( classes ) { - $.each(classes.split(" "), function() { - if ( this in $.validator.classRuleSettings ) { - $.extend(rules, $.validator.classRuleSettings[this]); - } - }); - } - return rules; - }, - - attributeRules: function( element ) { - var rules = {}; - var $element = $(element); - - for (var method in $.validator.methods) { - var value; - - // support for in both html5 and older browsers - if ( method === "required" ) { - value = $element.get(0).getAttribute(method); - // Some browsers return an empty string for the required attribute - // and non-HTML5 browsers might have required="" markup - if ( value === "" ) { - value = true; - } - // force non-HTML5 browsers to return bool - value = !!value; - } else { - value = $element.attr(method); - } - - if ( value ) { - rules[method] = value; - } else if ( $element[0].getAttribute("type") === method ) { - rules[method] = true; - } - } - - // maxlength may be returned as -1, 2147483647 (IE) and 524288 (safari) for text inputs - if ( rules.maxlength && /-1|2147483647|524288/.test(rules.maxlength) ) { - delete rules.maxlength; - } - - return rules; - }, - - dataRules: function( element ) { - var method, value, - rules = {}, $element = $(element); - for (method in $.validator.methods) { - value = $element.data("rule-" + method.toLowerCase()); - if ( value !== undefined ) { - rules[method] = value; - } - } - return rules; - }, - - staticRules: function( element ) { - var rules = {}; - var validator = $.data(element.form, "validator"); - if ( validator.settings.rules ) { - rules = $.validator.normalizeRule(validator.settings.rules[element.name]) || {}; - } - return rules; - }, - - normalizeRules: function( rules, element ) { - // handle dependency check - $.each(rules, function( prop, val ) { - // ignore rule when param is explicitly false, eg. required:false - if ( val === false ) { - delete rules[prop]; - return; - } - if ( val.param || val.depends ) { - var keepRule = true; - switch (typeof val.depends) { - case "string": - keepRule = !!$(val.depends, element.form).length; - break; - case "function": - keepRule = val.depends.call(element, element); - break; - } - if ( keepRule ) { - rules[prop] = val.param !== undefined ? val.param : true; - } else { - delete rules[prop]; - } - } - }); - - // evaluate parameters - $.each(rules, function( rule, parameter ) { - rules[rule] = $.isFunction(parameter) ? parameter(element) : parameter; - }); - - // clean number parameters - $.each(["minlength", "maxlength", "min", "max"], function() { - if ( rules[this] ) { - rules[this] = Number(rules[this]); - } - }); - $.each(["rangelength", "range"], function() { - var parts; - if ( rules[this] ) { - if ( $.isArray(rules[this]) ) { - rules[this] = [Number(rules[this][0]), Number(rules[this][1])]; - } else if ( typeof rules[this] === "string" ) { - parts = rules[this].split(/[\s,]+/); - rules[this] = [Number(parts[0]), Number(parts[1])]; - } - } - }); - - if ( $.validator.autoCreateRanges ) { - // auto-create ranges - if ( rules.min && rules.max ) { - rules.range = [rules.min, rules.max]; - delete rules.min; - delete rules.max; - } - if ( rules.minlength && rules.maxlength ) { - rules.rangelength = [rules.minlength, rules.maxlength]; - delete rules.minlength; - delete rules.maxlength; - } - } - - return rules; - }, - - // Converts a simple string to a {string: true} rule, e.g., "required" to {required:true} - normalizeRule: function( data ) { - if ( typeof data === "string" ) { - var transformed = {}; - $.each(data.split(/\s/), function() { - transformed[this] = true; - }); - data = transformed; - } - return data; - }, - - // http://docs.jquery.com/Plugins/Validation/Validator/addMethod - addMethod: function( name, method, message ) { - $.validator.methods[name] = method; - $.validator.messages[name] = message !== undefined ? message : $.validator.messages[name]; - if ( method.length < 3 ) { - $.validator.addClassRules(name, $.validator.normalizeRule(name)); - } - }, - - methods: { - - // http://docs.jquery.com/Plugins/Validation/Methods/required - required: function( value, element, param ) { - // check if dependency is met - if ( !this.depend(param, element) ) { - return "dependency-mismatch"; - } - if ( element.nodeName.toLowerCase() === "select" ) { - // could be an array for select-multiple or a string, both are fine this way - var val = $(element).val(); - return val && val.length > 0; - } - if ( this.checkable(element) ) { - return this.getLength(value, element) > 0; - } - return $.trim(value).length > 0; - }, - - // http://docs.jquery.com/Plugins/Validation/Methods/remote - remote: function( value, element, param ) { - if ( this.optional(element) ) { - return "dependency-mismatch"; - } - - var previous = this.previousValue(element); - if (!this.settings.messages[element.name] ) { - this.settings.messages[element.name] = {}; - } - previous.originalMessage = this.settings.messages[element.name].remote; - this.settings.messages[element.name].remote = previous.message; - - param = typeof param === "string" && {url:param} || param; - - if ( previous.old === value ) { - return previous.valid; - } - - previous.old = value; - var validator = this; - this.startRequest(element); - var data = {}; - data[element.name] = value; - $.ajax($.extend(true, { - url: param, - mode: "abort", - port: "validate" + element.name, - dataType: "json", - data: data, - success: function( response ) { - validator.settings.messages[element.name].remote = previous.originalMessage; - var valid = response === true || response === "true"; - if ( valid ) { - var submitted = validator.formSubmitted; - validator.prepareElement(element); - validator.formSubmitted = submitted; - validator.successList.push(element); - delete validator.invalid[element.name]; - validator.showErrors(); - } else { - var errors = {}; - var message = response || validator.defaultMessage( element, "remote" ); - errors[element.name] = previous.message = $.isFunction(message) ? message(value) : message; - validator.invalid[element.name] = true; - validator.showErrors(errors); - } - previous.valid = valid; - validator.stopRequest(element, valid); - } - }, param)); - return "pending"; - }, - - // http://docs.jquery.com/Plugins/Validation/Methods/minlength - minlength: function( value, element, param ) { - var length = $.isArray( value ) ? value.length : this.getLength($.trim(value), element); - return this.optional(element) || length >= param; - }, - - // http://docs.jquery.com/Plugins/Validation/Methods/maxlength - maxlength: function( value, element, param ) { - var length = $.isArray( value ) ? value.length : this.getLength($.trim(value), element); - return this.optional(element) || length <= param; - }, - - // http://docs.jquery.com/Plugins/Validation/Methods/rangelength - rangelength: function( value, element, param ) { - var length = $.isArray( value ) ? value.length : this.getLength($.trim(value), element); - return this.optional(element) || ( length >= param[0] && length <= param[1] ); - }, - - // http://docs.jquery.com/Plugins/Validation/Methods/min - min: function( value, element, param ) { - return this.optional(element) || value >= param; - }, - - // http://docs.jquery.com/Plugins/Validation/Methods/max - max: function( value, element, param ) { - return this.optional(element) || value <= param; - }, - - // http://docs.jquery.com/Plugins/Validation/Methods/range - range: function( value, element, param ) { - return this.optional(element) || ( value >= param[0] && value <= param[1] ); - }, - - // http://docs.jquery.com/Plugins/Validation/Methods/email - email: function( value, element ) { - // contributed by Scott Gonzalez: http://projects.scottsplayground.com/email_address_validation/ - return this.optional(element) || /^((([a-z]|\d|[!#\$%&'\*\+\-\/=\?\^_`{\|}~]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])+(\.([a-z]|\d|[!#\$%&'\*\+\-\/=\?\^_`{\|}~]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])+)*)|((\x22)((((\x20|\x09)*(\x0d\x0a))?(\x20|\x09)+)?(([\x01-\x08\x0b\x0c\x0e-\x1f\x7f]|\x21|[\x23-\x5b]|[\x5d-\x7e]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(\\([\x01-\x09\x0b\x0c\x0d-\x7f]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF]))))*(((\x20|\x09)*(\x0d\x0a))?(\x20|\x09)+)?(\x22)))@((([a-z]|\d|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(([a-z]|\d|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])*([a-z]|\d|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])))\.)+(([a-z]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(([a-z]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])*([a-z]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])))$/i.test(value); - }, - - // http://docs.jquery.com/Plugins/Validation/Methods/url - url: function( value, element ) { - // contributed by Scott Gonzalez: http://projects.scottsplayground.com/iri/ - return this.optional(element) || /^(https?|s?ftp):\/\/(((([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:)*@)?(((\d|[1-9]\d|1\d\d|2[0-4]\d|25[0-5])\.(\d|[1-9]\d|1\d\d|2[0-4]\d|25[0-5])\.(\d|[1-9]\d|1\d\d|2[0-4]\d|25[0-5])\.(\d|[1-9]\d|1\d\d|2[0-4]\d|25[0-5]))|((([a-z]|\d|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(([a-z]|\d|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])*([a-z]|\d|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])))\.)+(([a-z]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(([a-z]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])*([a-z]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])))\.?)(:\d*)?)(\/((([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:|@)+(\/(([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:|@)*)*)?)?(\?((([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:|@)|[\uE000-\uF8FF]|\/|\?)*)?(#((([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:|@)|\/|\?)*)?$/i.test(value); - }, - - // http://docs.jquery.com/Plugins/Validation/Methods/date - date: function( value, element ) { - return this.optional(element) || !/Invalid|NaN/.test(new Date(value).toString()); - }, - - // http://docs.jquery.com/Plugins/Validation/Methods/dateISO - dateISO: function( value, element ) { - return this.optional(element) || /^\d{4}[\/\-]\d{1,2}[\/\-]\d{1,2}$/.test(value); - }, - - // http://docs.jquery.com/Plugins/Validation/Methods/number - number: function( value, element ) { - return this.optional(element) || /^-?(?:\d+|\d{1,3}(?:,\d{3})+)?(?:\.\d+)?$/.test(value); - }, - - // http://docs.jquery.com/Plugins/Validation/Methods/digits - digits: function( value, element ) { - return this.optional(element) || /^\d+$/.test(value); - }, - - // http://docs.jquery.com/Plugins/Validation/Methods/creditcard - // based on http://en.wikipedia.org/wiki/Luhn - creditcard: function( value, element ) { - if ( this.optional(element) ) { - return "dependency-mismatch"; - } - // accept only spaces, digits and dashes - if ( /[^0-9 \-]+/.test(value) ) { - return false; - } - var nCheck = 0, - nDigit = 0, - bEven = false; - - value = value.replace(/\D/g, ""); - - for (var n = value.length - 1; n >= 0; n--) { - var cDigit = value.charAt(n); - nDigit = parseInt(cDigit, 10); - if ( bEven ) { - if ( (nDigit *= 2) > 9 ) { - nDigit -= 9; - } - } - nCheck += nDigit; - bEven = !bEven; - } - - return (nCheck % 10) === 0; - }, - - // http://docs.jquery.com/Plugins/Validation/Methods/equalTo - equalTo: function( value, element, param ) { - // bind to the blur event of the target in order to revalidate whenever the target field is updated - // TODO find a way to bind the event just once, avoiding the unbind-rebind overhead - var target = $(param); - if ( this.settings.onfocusout ) { - target.unbind(".validate-equalTo").bind("blur.validate-equalTo", function() { - $(element).valid(); - }); - } - return value === target.val(); - } - - } - -}); - -// deprecated, use $.validator.format instead -$.format = $.validator.format; - -}(jQuery)); - -// ajax mode: abort -// usage: $.ajax({ mode: "abort"[, port: "uniqueport"]}); -// if mode:"abort" is used, the previous request on that port (port can be undefined) is aborted via XMLHttpRequest.abort() -(function($) { - var pendingRequests = {}; - // Use a prefilter if available (1.5+) - if ( $.ajaxPrefilter ) { - $.ajaxPrefilter(function( settings, _, xhr ) { - var port = settings.port; - if ( settings.mode === "abort" ) { - if ( pendingRequests[port] ) { - pendingRequests[port].abort(); - } - pendingRequests[port] = xhr; - } - }); - } else { - // Proxy ajax - var ajax = $.ajax; - $.ajax = function( settings ) { - var mode = ( "mode" in settings ? settings : $.ajaxSettings ).mode, - port = ( "port" in settings ? settings : $.ajaxSettings ).port; - if ( mode === "abort" ) { - if ( pendingRequests[port] ) { - pendingRequests[port].abort(); - } - return (pendingRequests[port] = ajax.apply(this, arguments)); - } - return ajax.apply(this, arguments); - }; - } -}(jQuery)); - -// provides delegate(type: String, delegate: Selector, handler: Callback) plugin for easier event delegation -// handler is only called when $(event.target).is(delegate), in the scope of the jquery-object for event.target -(function($) { - $.extend($.fn, { - validateDelegate: function( delegate, type, handler ) { - return this.bind(type, function( event ) { - var target = $(event.target); - if ( target.is(delegate) ) { - return handler.apply(target, arguments); - } - }); - } - }); -}(jQuery)); diff --git a/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.type-view/type-view.hbs b/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.type-view/type-view.hbs deleted file mode 100644 index a52bdebc..00000000 --- a/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.type-view/type-view.hbs +++ /dev/null @@ -1,321 +0,0 @@ -
-

Door Manager

-
-
- -
- -
- -
- -
- - -
- - -
-

Prepare

-
-
    -
  • 01   Get the basic setup done - according to schematic below -
  • -
  • 02   Ensure your RaspberryPi Board - can connect to Internet. -
  • -
  • 03   Click on - [Download Agent] button above to get Automatic Door Locker agent. -
  • -
  • 04   Copy downloaded Agent into your - RaspberryPi. -
  • -
  • 05    Run "Agent.sh" script with root - privileges. -
  • -
-
-
- -
-

SCHEMATIC DIAGRAM

-
-

Click on the image to zoom

-
- - - -
-
-
- - -
-

Try Out

-
-
    -
  • 01   You can view - all your connected - devices at [Device - Management] - page. -
  • -
  • 02   Select one of - connected devices and check for available control operations as well as current state of door locker -
  • -
-
- -

Click on the image to zoom

-
- - - -
- -
- -{{#zone "topCss"}} - -{{/zone}} - -{{#zone "bottomJs"}} - {{js "/js/download.js"}} - {{js "/js/jquery.validate.js"}} -{{/zone}} \ No newline at end of file diff --git a/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.type-view/type-view.json b/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.type-view/type-view.json deleted file mode 100644 index 2def3808..00000000 --- a/modules/samples/doormanager/component/ui/src/main/resources/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.type-view/type-view.json +++ /dev/null @@ -1,20 +0,0 @@ -/**/ -{ - "version": "1.0.0" -} \ No newline at end of file diff --git a/modules/samples/doormanager/feature/feature/pom.xml b/modules/samples/doormanager/feature/feature/pom.xml deleted file mode 100644 index 0b0b5abe..00000000 --- a/modules/samples/doormanager/feature/feature/pom.xml +++ /dev/null @@ -1,209 +0,0 @@ - - - - - org.homeautomation - doormanager-feature - 1.0.0-SNAPSHOT - ../pom.xml - - 4.0.0 - 1.0.0-SNAPSHOT - org.homeautomation.doormanager.feature - pom - ${project.artifactId} - http://wso2.org - - - org.homeautomation - ${project-base-package}.plugin - 1.0.0-SNAPSHOT - - - org.homeautomation - ${project-base-package}.api - 1.0.0-SNAPSHOT - war - - - com.h2database.wso2 - h2-database-engine - 1.2.140.wso2v3 - - - - - - maven-resources-plugin - 2.7 - - - copy-resources - generate-resources - - copy-resources - - - src/main/resources - - - resources - - build.properties - p2.inf - - - - - - - - - org.apache.maven.plugins - maven-dependency-plugin - - - unpack - package - - unpack - - - - - org.homeautomation - ${project-base-package}.analytics - 1.0.0-SNAPSHOT - zip - true - - ${project.build.directory}/maven-shared-archive-resources/carbonapps - - **/* - - - org.homeautomation - ${project-base-package}.ui - - ${project.version} - zip - true - - ${project.build.directory}/maven-shared-archive-resources/jaggeryapps - - **/* - - - - - - copy-jaxrs-api-war - package - - copy - - - - - org.homeautomation - ${project-base-package}.api - war - true - - ${project.build.directory}/maven-shared-archive-resources/webapps/ - - doormanager.war - - - - - - - - org.apache.maven.plugins - maven-antrun-plugin - ${maven-antrun-plugin.version} - - - create-doormanager-plugin-mgt-schema - package - - run - - - - - - - - - - - - - - - - - - - - - org.wso2.maven - carbon-p2-plugin - ${carbon-p2-plugin.version} - - - p2-feature-generation - package - - p2-feature-gen - - - ${project-base-package} - ../../../features/etc/feature.properties - - - org.wso2.carbon.p2.category.type:server - org.eclipse.equinox.p2.type.group:true - - - - - org.homeautomation:${project-base-package}.plugin:1.0.0-SNAPSHOT - - - - org.wso2.carbon.core.server:${carbon.kernel.version} - - org.wso2.carbon.device.mgt.server:${carbon.device.mgt.version} - - - - - - - - - \ No newline at end of file diff --git a/modules/samples/doormanager/feature/feature/src/main/resources/agent/deviceConfig.properties b/modules/samples/doormanager/feature/feature/src/main/resources/agent/deviceConfig.properties deleted file mode 100644 index c0b9ccc7..00000000 --- a/modules/samples/doormanager/feature/feature/src/main/resources/agent/deviceConfig.properties +++ /dev/null @@ -1,30 +0,0 @@ -# Copyright (c) 2016, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. -# -# Licensed under the Apache License, Version 2.0 (the "License"); -# you may not use this file except in compliance with the License. -# You may obtain a copy of the License at -# -# http://www.apache.org/licenses/LICENSE-2.0 -# -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, -# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License. - -[Device-Configurations] -server-name=${SERVER_NAME} -owner=${DEVICE_OWNER} -username=${DEVICE_OWNER} -deviceId=${DEVICE_ID} -device-name=${DEVICE_NAME} -manager-context=/doormanager/controller/get_user_info -controller-context=/doormanager/controller -https-ep=${HTTPS_EP} -http-ep=${HTTP_EP} -apim-ep=${APIM_EP} -mqtt-ep=${MQTT_EP} -auth-method=token -auth-token=${DEVICE_TOKEN} -refresh-token=${DEVICE_REFRESH_TOKEN} -push-interval=15 diff --git a/modules/samples/doormanager/feature/feature/src/main/resources/agent/sketch.properties b/modules/samples/doormanager/feature/feature/src/main/resources/agent/sketch.properties deleted file mode 100644 index 9d8c6fd2..00000000 --- a/modules/samples/doormanager/feature/feature/src/main/resources/agent/sketch.properties +++ /dev/null @@ -1,3 +0,0 @@ -templates=deviceConfig.properties -zipfilename=doormanager.zip - diff --git a/modules/samples/doormanager/feature/feature/src/main/resources/agent/src/DoorManagerAgent.log b/modules/samples/doormanager/feature/feature/src/main/resources/agent/src/DoorManagerAgent.log deleted file mode 100644 index e69de29b..00000000 diff --git a/modules/samples/doormanager/feature/feature/src/main/resources/agent/src/DoorManagerAgent.py b/modules/samples/doormanager/feature/feature/src/main/resources/agent/src/DoorManagerAgent.py deleted file mode 100644 index ad24a818..00000000 --- a/modules/samples/doormanager/feature/feature/src/main/resources/agent/src/DoorManagerAgent.py +++ /dev/null @@ -1,194 +0,0 @@ -#!/usr/bin/env python -""" -/** -* Copyright (c) 2016, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. -* -* WSO2 Inc. licenses this file to you under the Apache License, -* Version 2.0 (the "License"); you may not use this file except -* in compliance with the License. -* You may obtain a copy of the License at -* -* http://www.apache.org/licenses/LICENSE-2.0 -* -* Unless required by applicable law or agreed to in writing, -* software distributed under the License is distributed on an -* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY -* KIND, either express or implied. See the License for the -* specific language governing permissions and limitations -* under the License. -**/ -""" - -import argparse -import httplib -import logging -import logging.handlers -import signal -import ssl -import sys -import threading -import time -from functools import wraps - -import RPi.GPIO as GPIO - -import MQTTHandler -import RFIDReader -import iotUtils - - -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -# Overriding the default SSL version used in some of the Python (2.7.x) versions -# This is a known issue in earlier Python releases -# But was fixed in later versions. Ex-2.7.11 -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -def sslwrap(func): - @wraps(func) - def bar(*args, **kw): - kw['ssl_version'] = ssl.PROTOCOL_TLSv1 - return func(*args, **kw) - - return bar -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ - -PUSH_INTERVAL = 5000 # time interval between successive data pushes in seconds - -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -# Logger defaults -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -LOG_FILENAME = "DoorManagerAgent.log" -logging_enabled = False -LOG_LEVEL = logging.INFO # Could be e.g. "DEBUG" or "WARNING" -#~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ - -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -# Python version -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -if sys.version_info < (2, 6, 0): - sys.stderr.write("You need python 2.6.0 or later to run this script\n") - exit(1) -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ - -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -# Define and parse command line arguments -# If the log file is specified on the command line then override the default -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -parser = argparse.ArgumentParser(description="Python service to push RPi info to the Device Cloud") -parser.add_argument("-l", "--log", help="file to write log to (default '" + LOG_FILENAME + "')") - -help_string_for_data_push_interval = "time interval between successive locker status push to server(default '" + str( - PUSH_INTERVAL) + "')" -parser.add_argument("-i", "--interval", type=int, help=help_string_for_data_push_interval) - -args = parser.parse_args() -if args.log: - LOG_FILENAME = args.log - -if args.interval: - PUSH_INTERVAL = args.interval -#~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ - -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -# A class we can use to capture stdout and sterr in the log -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -class IOTLogger(object): - def __init__(self, logger, level): - """Needs a logger and a logger level.""" - self.logger = logger - self.level = level - - def write(self, message): - if message.rstrip() != "": # Only log if there is a message (not just a new line) - self.logger.log(self.level, message.rstrip()) -#~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ - - -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -# Configure logging to log to a file, -# making a new file at midnight and keeping the last 3 day's data -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -def configureLogger(loggerName): - logger = logging.getLogger(loggerName) - logger.setLevel(LOG_LEVEL) # Set the log level to LOG_LEVEL - handler = logging.handlers.TimedRotatingFileHandler(LOG_FILENAME, when="midnight", - backupCount=3) # Handler that writes to a file, - # ~~~make new file at midnight and keep 3 backups - formatter = logging.Formatter('%(asctime)s %(levelname)-8s %(message)s') # Format each log message like this - handler.setFormatter(formatter) # Attach the formatter to the handler - logger.addHandler(handler) # Attach the handler to the logger - - if (logging_enabled): - sys.stdout = IOTLogger(logger, logging.INFO) # Replace stdout with logging to file at INFO level - sys.stderr = IOTLogger(logger, logging.ERROR) # Replace stderr with logging to file at ERROR level -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ - -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -# This is a Thread object for reading RFID card -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -class ListenRFIDhread(object): - def __init__(self): - thread = threading.Thread(target=self.run, args=()) - thread.daemon = True # Daemonize thread - thread.start() # Start the execution - - def run(self): - RFIDReader.main() -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ - -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -# This is a Thread object for listening for MQTT Messages -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -class ListenMQTTThread(object): - def __init__(self): - thread = threading.Thread(target=self.run, args=()) - thread.daemon = True # Daemonize thread - thread.start() # Start the execution - - def run(self): - MQTTHandler.main() -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ - -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -# When sysvinit sends the TERM signal, cleanup before exiting -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -def sigterm_handler(_signo, _stack_frame): - print("[] received signal {}, exiting...".format(_signo)) - sys.exit(0) -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ - -signal.signal(signal.SIGTERM, sigterm_handler) - - -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -# This method used to initialize GPIO ports -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -def initDoorLock(): - # GPIO.setmode(GPIO.BOARD) - GPIO.setup(iotUtils.DOOR_LOCKER_1_PORT, GPIO.OUT, initial=GPIO.HIGH) - GPIO.setup(iotUtils.DOOR_LOCKER_2_PORT, GPIO.OUT, initial=GPIO.HIGH) - GPIO.setup(iotUtils.LOCK_STATE_ON_NOTIFY_PORT, GPIO.OUT, initial=GPIO.LOW) - GPIO.setup(iotUtils.LOCK_STATE_OFF_NOTIFY_PORT, GPIO.OUT, initial=GPIO.LOW) -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ - -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -# The Main method of the Automatic Door Locker Agent -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -def main(): - configureLogger("AutomaticDoorLocker") - ListenMQTTThread() - ListenRFIDhread() - initDoorLock() - # registerUIDofRFIDCard() # Call the register endpoint and register Device I - # ListenMQTTThread() - while True: - try: - time.sleep(PUSH_INTERVAL) - except (KeyboardInterrupt, Exception) as e: - print "AutomaticDoorLockerStats: Exception in RaspberryAgentThread (either KeyboardInterrupt or Other)" - print ("AutomaticDoorLockerStats: " + str(e)) - print '~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~' - pass -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ - -if __name__ == "__main__": - main() diff --git a/modules/samples/doormanager/feature/feature/src/main/resources/agent/src/MFRC522.py b/modules/samples/doormanager/feature/feature/src/main/resources/agent/src/MFRC522.py deleted file mode 100644 index 9e15c843..00000000 --- a/modules/samples/doormanager/feature/feature/src/main/resources/agent/src/MFRC522.py +++ /dev/null @@ -1,396 +0,0 @@ -#!/usr/bin/env python -# -*- coding: utf8 -*- - -import RPi.GPIO as GPIO -import spi -import signal -import time - -class MFRC522: - NRSTPD = 22 - - MAX_LEN = 16 - - PCD_IDLE = 0x00 - PCD_AUTHENT = 0x0E - PCD_RECEIVE = 0x08 - PCD_TRANSMIT = 0x04 - PCD_TRANSCEIVE = 0x0C - PCD_RESETPHASE = 0x0F - PCD_CALCCRC = 0x03 - - PICC_REQIDL = 0x26 - PICC_REQALL = 0x52 - PICC_ANTICOLL = 0x93 - PICC_SElECTTAG = 0x93 - PICC_AUTHENT1A = 0x60 - PICC_AUTHENT1B = 0x61 - PICC_READ = 0x30 - PICC_WRITE = 0xA0 - PICC_DECREMENT = 0xC0 - PICC_INCREMENT = 0xC1 - PICC_RESTORE = 0xC2 - PICC_TRANSFER = 0xB0 - PICC_HALT = 0x50 - - MI_OK = 0 - MI_NOTAGERR = 1 - MI_ERR = 2 - - Reserved00 = 0x00 - CommandReg = 0x01 - CommIEnReg = 0x02 - DivlEnReg = 0x03 - CommIrqReg = 0x04 - DivIrqReg = 0x05 - ErrorReg = 0x06 - Status1Reg = 0x07 - Status2Reg = 0x08 - FIFODataReg = 0x09 - FIFOLevelReg = 0x0A - WaterLevelReg = 0x0B - ControlReg = 0x0C - BitFramingReg = 0x0D - CollReg = 0x0E - Reserved01 = 0x0F - - Reserved10 = 0x10 - ModeReg = 0x11 - TxModeReg = 0x12 - RxModeReg = 0x13 - TxControlReg = 0x14 - TxAutoReg = 0x15 - TxSelReg = 0x16 - RxSelReg = 0x17 - RxThresholdReg = 0x18 - DemodReg = 0x19 - Reserved11 = 0x1A - Reserved12 = 0x1B - MifareReg = 0x1C - Reserved13 = 0x1D - Reserved14 = 0x1E - SerialSpeedReg = 0x1F - - Reserved20 = 0x20 - CRCResultRegM = 0x21 - CRCResultRegL = 0x22 - Reserved21 = 0x23 - ModWidthReg = 0x24 - Reserved22 = 0x25 - RFCfgReg = 0x26 - GsNReg = 0x27 - CWGsPReg = 0x28 - ModGsPReg = 0x29 - TModeReg = 0x2A - TPrescalerReg = 0x2B - TReloadRegH = 0x2C - TReloadRegL = 0x2D - TCounterValueRegH = 0x2E - TCounterValueRegL = 0x2F - - Reserved30 = 0x30 - TestSel1Reg = 0x31 - TestSel2Reg = 0x32 - TestPinEnReg = 0x33 - TestPinValueReg = 0x34 - TestBusReg = 0x35 - AutoTestReg = 0x36 - VersionReg = 0x37 - AnalogTestReg = 0x38 - TestDAC1Reg = 0x39 - TestDAC2Reg = 0x3A - TestADCReg = 0x3B - Reserved31 = 0x3C - Reserved32 = 0x3D - Reserved33 = 0x3E - Reserved34 = 0x3F - - serNum = [] - - def __init__(self, dev='/dev/spidev0.0', spd=1000000): - spi.openSPI(device=dev,speed=spd) - GPIO.setmode(GPIO.BOARD) - GPIO.setup(22, GPIO.OUT) - GPIO.output(self.NRSTPD, 1) - self.MFRC522_Init() - - def MFRC522_Reset(self): - self.Write_MFRC522(self.CommandReg, self.PCD_RESETPHASE) - - def Write_MFRC522(self, addr, val): - spi.transfer(((addr<<1)&0x7E,val)) - - def Read_MFRC522(self, addr): - val = spi.transfer((((addr<<1)&0x7E) | 0x80,0)) - return val[1] - - def SetBitMask(self, reg, mask): - tmp = self.Read_MFRC522(reg) - self.Write_MFRC522(reg, tmp | mask) - - def ClearBitMask(self, reg, mask): - tmp = self.Read_MFRC522(reg); - self.Write_MFRC522(reg, tmp & (~mask)) - - def AntennaOn(self): - temp = self.Read_MFRC522(self.TxControlReg) - if(~(temp & 0x03)): - self.SetBitMask(self.TxControlReg, 0x03) - - def AntennaOff(self): - self.ClearBitMask(self.TxControlReg, 0x03) - - def MFRC522_ToCard(self,command,sendData): - backData = [] - backLen = 0 - status = self.MI_ERR - irqEn = 0x00 - waitIRq = 0x00 - lastBits = None - n = 0 - i = 0 - - if command == self.PCD_AUTHENT: - irqEn = 0x12 - waitIRq = 0x10 - if command == self.PCD_TRANSCEIVE: - irqEn = 0x77 - waitIRq = 0x30 - - self.Write_MFRC522(self.CommIEnReg, irqEn|0x80) - self.ClearBitMask(self.CommIrqReg, 0x80) - self.SetBitMask(self.FIFOLevelReg, 0x80) - - self.Write_MFRC522(self.CommandReg, self.PCD_IDLE); - - while(i self.MAX_LEN: - n = self.MAX_LEN - - i = 0 - while i -custom = true diff --git a/modules/samples/doormanager/feature/feature/src/main/resources/configs/doormanager.json b/modules/samples/doormanager/feature/feature/src/main/resources/configs/doormanager.json deleted file mode 100644 index 729872a6..00000000 --- a/modules/samples/doormanager/feature/feature/src/main/resources/configs/doormanager.json +++ /dev/null @@ -1,31 +0,0 @@ -{ - "deviceType": { - "label": "Door Manager", - "category": "iot" - }, - "analyticStreams": [ - { - "name": "smartLock", - "table": "DEVICE_smartLock_SUMMARY", - "ui_unit": { - "name": "cdmf.unit.analytics.line-chart", - "data": [ - { - "column": { - "name": "TIME", - "label": "time", - "ui-mapping": "x-axis" - } - }, - { - "column": { - "name": "smartLock", - "label": "smartLock", - "ui-mapping": "y-axis" - } - } - ] - } - } - ] -} \ No newline at end of file diff --git a/modules/samples/doormanager/feature/feature/src/main/resources/configs/doormanager.xml b/modules/samples/doormanager/feature/feature/src/main/resources/configs/doormanager.xml deleted file mode 100644 index e985bdf4..00000000 --- a/modules/samples/doormanager/feature/feature/src/main/resources/configs/doormanager.xml +++ /dev/null @@ -1,24 +0,0 @@ - - - - - - jdbc/doormanagerDM_DB - - diff --git a/modules/samples/doormanager/feature/feature/src/main/resources/database/doormanagerDM_DB.h2.db b/modules/samples/doormanager/feature/feature/src/main/resources/database/doormanagerDM_DB.h2.db deleted file mode 100644 index da2768b4f2ab9cf4c7f855250ed9fd87aa3ebe73..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 18432 zcmeI&J#W)M7zgl#v~}yMLJ^3r52a1w$|+|%uM@i1m&S@?m$Thagkt4{^FOEOes|{^oMI7LI*^_6{RR|^AdAnr z-&3jOR3?+c3k6UB1yBG5P~Zv+Y^=LHDL?&UbcKh3rK11}pa2S>018|}0MGwRU||#m zPyhu`00pjzz|!L8gKIJr90m%Y01BW03ZTFR1+ve+jgvpbb#p1Tke0r#NFQYB{i^i( zf<0gi1yBG5Pyhu`V0HrAu)WpxnoX6c>O-Pxs;(MpNiC}t1(e*;o%ZBT0SfukZ2(X> z-Il!_k4u)N*%gjGqW}t^01BW03e1^6c0D=&R~F{1E-VKHPyhu`00mHBb^_Tu$@#yG z=l|@Cv1b%O0Te(16qq-G?DsE8Ned}CEq%&J?-r#ulJsgtdbuh+U0XU7e+tMh!mZ5P zc`F?2L4p5KU>jiV@P^454H%fzY%vQ0+He@`g$>6xcR1U%{eW?1MV9Ar$1~fJPn)bD zi}!ypZt75%?lK-(Y~MCnWLvOLx!Iz;P%10ndI7khpOR)~Morqc%XTCozOifdyqQGl2_c*KnzEaMbqRZB_ zu&gM8`(yeXZeO^~lKSkF{6l3~DTwiXK5u+y7tG%+q{(7)X@?z8&L5W1OeQi98*9%e z^O!8quJ7q4A-k7{(RDC|3rg8pm2cHnbiY*7_CE54AeBn}ggVp9S!%hNuzR zjs;qYY(cI&ZtrqCU}8@?^Z?3)Y(kDFaVH$_X2|F79d$6?^pS5rW}sD!T4@7vPsYi~ fevFc*K@=S9F(7v#*E@MHc^U+Ehk0QDVsDV22yRGZ diff --git a/modules/samples/doormanager/feature/feature/src/main/resources/datasources/doormanager-datasources.xml b/modules/samples/doormanager/feature/feature/src/main/resources/datasources/doormanager-datasources.xml deleted file mode 100644 index ed8376e0..00000000 --- a/modules/samples/doormanager/feature/feature/src/main/resources/datasources/doormanager-datasources.xml +++ /dev/null @@ -1,47 +0,0 @@ - - - - - - org.wso2.carbon.ndatasource.rdbms.RDBMSDataSourceReader - - - - doormanagerDM_DB - The datasource used for the this device type - - jdbc/doormanagerDM_DB - - - - jdbc:h2:repository/database/doormanagerDM_DB;DB_CLOSE_ON_EXIT=FALSE - - wso2carbon - wso2carbon - org.h2.Driver - 50 - 60000 - true - SELECT 1 - 30000 - - - - - diff --git a/modules/samples/doormanager/feature/feature/src/main/resources/dbscripts/h2.sql b/modules/samples/doormanager/feature/feature/src/main/resources/dbscripts/h2.sql deleted file mode 100644 index 618a577e..00000000 --- a/modules/samples/doormanager/feature/feature/src/main/resources/dbscripts/h2.sql +++ /dev/null @@ -1,29 +0,0 @@ - --- ----------------------------------------------------- --- Agent Database --- ----------------------------------------------------- -CREATE TABLE IF NOT EXISTS `doormanager_DEVICE` ( - `doormanager_DEVICE_ID` VARCHAR(45) NOT NULL , - `DEVICE_NAME` VARCHAR(100) NULL DEFAULT NULL, - `ACCESS_TOKEN` VARCHAR(200) NULL DEFAULT NULL, - `REFRESH_TOKEN` VARCHAR(200) NULL DEFAULT NULL); - -CREATE TABLE IF NOT EXISTS `SHARED_DOORLOCK_SAFE` ( - `doormanager_DEVICE_ID` VARCHAR(45) NOT NULL , - `SERIAL_NUMBER` VARCHAR(45) NOT NULL , - `UID_of_USER` VARCHAR(100) NULL DEFAULT NULL, - `POLICY` VARCHAR(100) NULL DEFAULT NULL); - -CREATE TABLE IF NOT EXISTS `REGISTERED_DOORLOCK_SAFE` ( - `doormanager_DEVICE_ID` VARCHAR(45) NOT NULL , - `SERIAL_NUMBER` VARCHAR(100) NULL DEFAULT NULL, - `UID_of_USER` VARCHAR(100) NULL DEFAULT NULL, - `POLICY` VARCHAR(100) NULL DEFAULT NULL, - `EMAIL_ADDRESS` VARCHAR(100) NULL DEFAULT NULL, - `ACCESS_TOKEN` VARCHAR(200) NULL DEFAULT NULL, - `REFRESH_TOKEN` VARCHAR(200) NULL DEFAULT NULL); - - - - - diff --git a/modules/samples/doormanager/feature/feature/src/main/resources/dbscripts/mysql.sql b/modules/samples/doormanager/feature/feature/src/main/resources/dbscripts/mysql.sql deleted file mode 100644 index 7e22be61..00000000 --- a/modules/samples/doormanager/feature/feature/src/main/resources/dbscripts/mysql.sql +++ /dev/null @@ -1,12 +0,0 @@ --- ----------------------------------------------------- --- Agent Database --- ----------------------------------------------------- -CREATE TABLE IF NOT EXISTS `doormanager_DEVICE` ( - `doormanager_DEVICE_ID` VARCHAR(45) NOT NULL , - `DEVICE_NAME` VARCHAR(100) NULL DEFAULT NULL, - PRIMARY KEY (`doormanager_DEVICE_ID`) ) -ENGINE = InnoDB; - - - - diff --git a/modules/samples/doormanager/feature/feature/src/main/resources/p2.inf b/modules/samples/doormanager/feature/feature/src/main/resources/p2.inf deleted file mode 100644 index 0aa3bba7..00000000 --- a/modules/samples/doormanager/feature/feature/src/main/resources/p2.inf +++ /dev/null @@ -1,28 +0,0 @@ -instructions.configure = \ -org.eclipse.equinox.p2.touchpoint.natives.mkdir(path:${installFolder}/../../conf/device-types/);\ -org.eclipse.equinox.p2.touchpoint.natives.copy(source:${installFolder}/../features/org.homeautomation.doormanager_${feature.version}/configs/,target:${installFolder}/../../conf/device-types/,overwrite:true);\ -org.eclipse.equinox.p2.touchpoint.natives.mkdir(path:${installFolder}/../../deployment/server/webapps/);\ -org.eclipse.equinox.p2.touchpoint.natives.copy(source:${installFolder}/../features/org.homeautomation.doormanager_${feature.version}/webapps/,target:${installFolder}/../../deployment/server/webapps/,overwrite:true);\ -org.eclipse.equinox.p2.touchpoint.natives.mkdir(path:${installFolder}/../../resources/sketches/);\ -org.eclipse.equinox.p2.touchpoint.natives.mkdir(path:${installFolder}/../../resources/sketches/doormanager/);\ -org.eclipse.equinox.p2.touchpoint.natives.copy(source:${installFolder}/../features/org.homeautomation.doormanager_${feature.version}/agent/,target:${installFolder}/../../resources/sketches/doormanager/,overwrite:true);\ -org.eclipse.equinox.p2.touchpoint.natives.copy(source:${installFolder}/../features/org.homeautomation.doormanager_${feature.version}/dbscripts/,target:${installFolder}/../../../dbscripts/cdm/plugins/doormanager,overwrite:true);\ -org.eclipse.equinox.p2.touchpoint.natives.copy(source:${installFolder}/../features/org.homeautomation.doormanager_${feature.version}/datasources/,target:${installFolder}/../../conf/datasources/,overwrite:true);\ -org.eclipse.equinox.p2.touchpoint.natives.mkdir(path:${installFolder}/../../deployment/server/jaggeryapps/);\ -org.eclipse.equinox.p2.touchpoint.natives.copy(source:${installFolder}/../features/org.homeautomation.doormanager_${feature.version}/jaggeryapps/,target:${installFolder}/../../deployment/server/jaggeryapps/,overwrite:true);\ -org.eclipse.equinox.p2.touchpoint.natives.mkdir(path:${installFolder}/../../database/);\ -org.eclipse.equinox.p2.touchpoint.natives.copy(source:${installFolder}/../features/org.homeautomation.doormanager_${feature.version}/database/,target:${installFolder}/../../database/,overwrite:true);\ -org.eclipse.equinox.p2.touchpoint.natives.mkdir(path:${installFolder}/../../deployment/server/carbonapps/);\ -org.eclipse.equinox.p2.touchpoint.natives.copy(source:${installFolder}/../features/org.homeautomation.doormanager_${feature.version}/carbonapps/,target:${installFolder}/../../deployment/server/carbonapps/,overwrite:true);\ - -instructions.unconfigure = \ -org.eclipse.equinox.p2.touchpoint.natives.remove(path:${installFolder}/../../conf/device-types/doormanager.json);\ -org.eclipse.equinox.p2.touchpoint.natives.remove(path:${installFolder}/../../conf/device-types/doormanager.xml);\ -org.eclipse.equinox.p2.touchpoint.natives.remove(path:${installFolder}/../../deployment/server/webapps/doormanager.war);\ -org.eclipse.equinox.p2.touchpoint.natives.remove(path:${installFolder}/../../deployment/server/webapps/doormanager);\ -org.eclipse.equinox.p2.touchpoint.natives.remove(path:${installFolder}/../../../dbscripts/cdm/plugins/doormanager);\ -org.eclipse.equinox.p2.touchpoint.natives.remove(path:${installFolder}/../../resources/sketches/doormanager);\ -org.eclipse.equinox.p2.touchpoint.natives.remove(path:${installFolder}/../../conf/datasources/doormanager-datasources.xml);\ -org.eclipse.equinox.p2.touchpoint.natives.remove(path:${installFolder}/../../database/doormanagerDM_DB.h2.db);\ -org.eclipse.equinox.p2.touchpoint.natives.remove(path:${installFolder}/../../deployment/server/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.device-view);\ -org.eclipse.equinox.p2.touchpoint.natives.remove(path:${installFolder}/../../deployment/server/jaggeryapps/devicemgt/app/units/cdmf.unit.device.type.doormanager.type-view);\ diff --git a/modules/samples/doormanager/feature/pom.xml b/modules/samples/doormanager/feature/pom.xml deleted file mode 100644 index 28e141e1..00000000 --- a/modules/samples/doormanager/feature/pom.xml +++ /dev/null @@ -1,35 +0,0 @@ - - - - - - org.homeautomation - doormanager - 1.0.0-SNAPSHOT - ../pom.xml - - doormanager-feature - 4.0.0 - pom - 1.0.0-SNAPSHOT - - feature - - \ No newline at end of file diff --git a/modules/samples/doormanager/pom.xml b/modules/samples/doormanager/pom.xml deleted file mode 100644 index 5322686c..00000000 --- a/modules/samples/doormanager/pom.xml +++ /dev/null @@ -1,518 +0,0 @@ - - - - - org.wso2 - wso2 - 1 - - org.homeautomation - doormanager - 1.0.0-SNAPSHOT - pom - 4.0.0 - http://wso2.com - - component - feature - - - - - org.eclipse.osgi - org.eclipse.osgi - ${eclipse.osgi.version} - provided - - - org.eclipse.equinox - org.eclipse.equinox.common - ${eclipse.equinox.common.version} - provided - - - org.testng - testng - ${testng.version} - - - junit - junit - - - org.beanshell - bsh - - - org.yaml - snakeyaml - - - provided - - - org.eclipse.osgi - org.eclipse.osgi.services - 3.3.100.v20120522-1822 - provided - - - org.wso2.carbon - org.wso2.carbon.logging - ${carbon.kernel.version} - - - org.apache.log4j.wso2 - log4j - - - commons-logging - commons-logging - - - org.wso2.carbon - org.wso2.carbon.bootstrap - - - provided - - - - org.apache.cxf - cxf-rt-frontend-jaxws - ${cxf.version} - provided - - - org.apache.cxf - cxf-rt-frontend-jaxrs - ${cxf.version} - provided - - - org.apache.cxf - cxf-rt-transports-http - ${cxf.version} - provided - - - org.eclipse.paho - org.eclipse.paho.client.mqttv3 - ${paho.mqtt.version} - provided - - - org.codehaus.jackson - jackson-core-asl - ${jackson.version} - - - org.codehaus.jackson - jackson-jaxrs - ${jackson.version} - - - javax - javaee-web-api - 6.0 - provided - - - javax.ws.rs - jsr311-api - ${javax.ws.rs.version} - provided - - - org.apache.httpcomponents - httpasyncclient - 4.1 - provided - - - com.google.code.gson - gson - 2.2.4 - - - - org.homeautomation - ${project-base-package}.plugin - 1.0.0-SNAPSHOT - provided - - - org.wso2.carbon.devicemgt - org.wso2.carbon.apimgt.webapp.publisher - ${carbon.device.mgt.version} - system - - ${basedir}/../../../../repository/components/plugins/org.wso2.carbon.apimgt.webapp.publisher_${carbon.device.mgt.jar.version}.jar - - - - org.wso2.carbon - org.wso2.carbon.ndatasource.core - ${carbon.kernel.version} - system - - ${basedir}/../../../../repository/components/plugins/org.wso2.carbon.ndatasource.core_${carbon.kernel.version}.jar - - - - org.wso2.carbon.devicemgt-plugins - org.wso2.carbon.device.mgt.iot - ${carbon.iot.device.mgt.version} - system - - ${basedir}/../../../../repository/components/plugins/org.wso2.carbon.device.mgt.iot_${carbon.iot.device.mgt.jar.version}.jar - - - - org.wso2.carbon.devicemgt - org.wso2.carbon.device.mgt.core - ${carbon.device.mgt.version} - system - - ${basedir}/../../../../repository/components/plugins/org.wso2.carbon.device.mgt.core_${carbon.device.mgt.jar.version}.jar - - - - org.wso2.carbon.devicemgt - org.wso2.carbon.device.mgt.common - ${carbon.device.mgt.version} - system - - ${basedir}/../../../../repository/components/plugins/org.wso2.carbon.device.mgt.common_${carbon.device.mgt.jar.version}.jar - - - - org.wso2.carbon.devicemgt - org.wso2.carbon.certificate.mgt.core - ${carbon.device.mgt.version} - system - - ${basedir}/../../../../repository/components/plugins/org.wso2.carbon.certificate.mgt.core_${carbon.device.mgt.jar.version}.jar - - - - org.wso2.carbon.devicemgt - org.wso2.carbon.apimgt.annotations - ${carbon.device.mgt.version} - system - - ${basedir}/../../../../repository/components/plugins/org.wso2.carbon.apimgt.annotations_${carbon.device.mgt.jar.version}.jar - - - - org.wso2.carbon.devicemgt - org.wso2.carbon.device.mgt.analytics.data.publisher - ${carbon.device.mgt.version} - system - - ${basedir}/../../../../repository/components/plugins/org.wso2.carbon.device.mgt.analytics.data.publisher_${carbon.device.mgt.jar.version}.jar - - - - commons-httpclient.wso2 - commons-httpclient - ${commons-httpclient.orbit.version} - system - - ${basedir}/../../../../repository/components/plugins/commons-httpclient_3.1.0.wso2v2.jar - - - - commons-httpclient.wso2 - commons-httpclient - ${commons-httpclient.orbit.version} - system - - ${basedir}/../../../../repository/components/plugins/commons-httpclient_3.1.0.wso2v2.jar - - - - org.wso2.carbon - org.wso2.carbon.utils - ${carbon.kernel.version} - - - org.bouncycastle.wso2 - bcprov-jdk15on - - - org.wso2.carbon - org.wso2.carbon.user.api - - - org.wso2.carbon - org.wso2.carbon.queuing - - - org.wso2.carbon - org.wso2.carbon.base - - - org.apache.axis2.wso2 - axis2 - - - org.igniterealtime.smack.wso2 - smack - - - org.igniterealtime.smack.wso2 - smackx - - - jaxen - jaxen - - - commons-fileupload.wso2 - commons-fileupload - - - org.apache.ant.wso2 - ant - - - org.apache.ant.wso2 - ant - - - commons-httpclient.wso2 - commons-httpclient - - - org.eclipse.equinox - javax.servlet - - - org.wso2.carbon - org.wso2.carbon.registry.api - - - system - - ${basedir}/../../../../repository/components/plugins/org.wso2.carbon.utils_${carbon.kernel.version}.jar - - - - org.igniterealtime.smack.wso2 - smack - ${smack.wso2.version} - system - - ${basedir}/../../../../repository/components/plugins/smack_3.0.4.wso2v1.jar - - - - org.igniterealtime.smack.wso2 - smackx - ${smackx.wso2.version} - system - - ${basedir}/../../../../repository/components/plugins/smackx_3.0.4.wso2v1.jar - - - - org.json.wso2 - json - ${commons-json.version} - system - - ${basedir}/../../../../repository/components/plugins/json_3.0.0.wso2v1.jar - - - - commons-codec - commons-codec - 1.4.0.wso2v1 - system - - ${basedir}/../../../../repository/components/plugins/commons-codec_1.4.0.wso2v1.jar - - - - org.wso2.carbon - org.wso2.carbon.user.core - ${carbon.kernel.version} - system - - ${basedir}/../../../../repository/components/plugins/org.wso2.carbon.user.core_${carbon.kernel.version}.jar - - - - org.wso2.carbon - org.wso2.carbon.user.api - ${carbon.kernel.version} - system - - ${basedir}/../../../../repository/components/plugins/org.wso2.carbon.user.api_${carbon.kernel.version}.jar - - - - commons-io - commons-io - ${commons-io.version} - - - org.wso2.carbon.devicemgt - org.wso2.carbon.device.mgt.extensions - ${carbon.device.mgt.version} - system - - ${basedir}/../../../../repository/components/plugins/org.wso2.carbon.device.mgt.extensions_${carbon.device.mgt.jar.version}.jar - - - - org.wso2.carbon.devicemgt - org.wso2.carbon.apimgt.application.extension - ${carbon.device.mgt.version} - system - - ${basedir}/../../../../repository/components/plugins/org.wso2.carbon.apimgt.application.extension_${carbon.device.mgt.jar.version}.jar - - - - org.wso2.carbon.devicemgt - org.wso2.carbon.identity.jwt.client.extension - ${carbon.device.mgt.jar.version} - system - - ${basedir}/../../../../repository/components/plugins/org.wso2.carbon.identity.jwt.client.extension_${carbon.device.mgt.jar.version}.jar - - - - - - - wso2.releases - WSO2 internal Repository - http://maven.wso2.org/nexus/content/repositories/releases/ - - true - daily - ignore - - - - wso2.snapshots - Apache Snapshot Repository - http://maven.wso2.org/nexus/content/repositories/snapshots/ - - true - daily - - - false - - - - wso2-nexus - WSO2 internal Repository - http://maven.wso2.org/nexus/content/groups/wso2-public/ - - true - daily - ignore - - - - - - wso2-nexus - WSO2 internal Repository - http://maven.wso2.org/nexus/content/groups/wso2-public/ - - true - daily - ignore - - - - wso2.releases - WSO2 internal Repository - http://maven.wso2.org/nexus/content/repositories/releases/ - - true - daily - ignore - - - - wso2.snapshots - WSO2 Snapshot Repository - http://maven.wso2.org/nexus/content/repositories/snapshots/ - - true - daily - - - false - - - - gcm-server-repository - GCM Server repository - GitHub - https://github.com/slorber/gcm-server-repository/raw/master/releases/ - - - wso2-staging - WSO2 internal Repository - http://maven.wso2.org/nexus/content/repositories/orgwso2carbonapimgt-174/ - - true - daily - ignore - - - - - 4.4.3 - 1.1.0-SNAPSHOT - 1.1.0.SNAPSHOT - 1.5.3 - 1.0.2 - 3.0.0.wso2v1 - 3.8.1.v20120830-144521 - 2.1.0-SNAPSHOT - 2.1.0.SNAPSHOT - 1.1.1 - 2.4 - 3.0.4.wso2v1 - 3.0.4.wso2v1 - 2.6.1 - 1.9.0 - 3.1.0.wso2v2 - 3.6.100.v20120522-1841 - 1.7 - 1.7 - org.homeautomation.doormanager - 3.8.1 - 1.4.0 - 2.4.1 - 2.3.2 - 2.6 - 1.8 - 1.7.2 - -
- -

What it Does

-
-

Connect an Automatic Door Locker to WSO2 IoT Server and control and view current state - of door locker.

-
-

What You Need

-
-
    -
  • ITEM 01   Electronic solenoid door - lock - 2 -
  • -
  • ITEM 02   MFRC522 RFID Reader/Writer -
  • -
  • ITEM 03   2 Channel 5V Relay Module -
  • -
  • ITEM 04   12 Volt DC - 1 Amp (12V, 1A) - Power Supply -
  • -
  • ITEM 05   LED Bulbs (Red and Green) -
  • -
  • ITEM 06   Resistors (333ohms) -2 -
  • -
  •    Proceed to [Prepare] section. -
-
- - View API
  - Register New Lock Safe - -
- -
- -
- -
- - - -
- -
- -
- -
- -
- -
- -
- -
- -
- -
- -

-