server = (PLUGIN_MDM_SERVER_SSL ? 'https://' : 'http://') . PLUGIN_MDM_SERVER; // Get the username and password from the Encryption store $encryptionStore = EncryptionStore::getInstance(); $this->username = $encryptionStore->get('username'); $this->password = $encryptionStore->get('password'); $this->url = $this->server .'/Microsoft-Server-ActiveSync?Cmd=WebserviceDevice&DeviceId=webservice&DeviceType=webservice&User=' . $this->username; } /** * Returns the version of the Z-Push server * @return String */ function getServerVersion() { // Make a call to the service, so we can read the version // from the response headers try { $url = $this->server .'/Microsoft-Server-ActiveSync?Cmd=WebserviceInfo&DeviceId=webservice&DeviceType=webservice&User=' . $this->username; $client = $this->getSoapClient($url); return $client->About(); } catch(Exception $e){} // If we can't find a version, we will simply return not available return dgettext('plugin_mdm', 'version not available'); } /** * Helper to setup a client. */ function getSoapClient($url='') { if ( empty($url) ){ $url = $this->url; } return new SoapClient(null, array( 'location' => $url, 'uri' => $this->server, 'trace' => 1, 'login' => $this->username, 'password' => $this->password )); } /** * Function which calls the soap call to do a full resync * @param int $deviceid of phone which has to be resynced * @return json $response object contains the response of the soap request from Z-Push */ function resyncDevice($deviceid) { $client = $this->getSoapClient(); return $client->ResyncDevice($deviceid); } /** * Function which calls the wipeDevice soap call * @param int $deviceid of phone which has to be wiped * @param string $password user password * @return json $response object contains the response of the soap request from Z-Push */ function wipeDevice($deviceid, $password) { if ($password == $this->password) { $client = $this->getSoapClient(); return $client->WipeDevice($deviceid); } else { return false; } } /** * function which calls the ListDeviceDetails soap call * @return array $response array contains a list of devices connected to the users account */ function getDevices() { $client = $this->getSoapClient(); return $client->ListDevicesDetails(); } /** * function which calls the wipeDevice soap call * @param int $deviceid of phone which has to be wiped * @return json $response object contains the response of the soap request from Z-Push */ function removeDevice($deviceid) { $client = $this->getSoapClient(); return $client->RemoveDevice($deviceid); } /** * Executes all the actions in the $data variable. * @return boolean true on success of false on fialure. */ function execute() { foreach($this->data as $actionType => $actionData) { if(isset($actionType)) { try { switch($actionType) { case 'wipe': $this->wipeDevice($actionData['deviceid'], $actionData['password']); $this->addActionData('wipe', array( 'type' => 3, 'wipe' => $this->wipeDevice($actionData['deviceid'], $actionData['password']) )); $GLOBALS['bus']->addData($this->getResponseData()); break; case 'resync': $this->addActionData('resync', array( 'type' => 3, 'resync' => $this->resyncDevice($actionData['deviceid']) )); $GLOBALS['bus']->addData($this->getResponseData()); break; case 'remove': $this->addActionData('remove', array( 'type' => 3, 'remove' => $this->removeDevice($actionData['deviceid']) )); $GLOBALS['bus']->addData($this->getResponseData()); break; case 'list': $items = array(); $date['page'] = array(); $rawData = $this->getDevices(); foreach($rawData as $device){ array_push($items, array('props' => $this->getDeviceProps($device->data))); } $data['page']['start'] = 0; $data['page']['rowcount'] = count($rawData); $data['page']['totalrowcount'] = $data['page']['rowcount']; $data = array_merge($data, array('item' => $items)); $this->addActionData('list', $data); $GLOBALS['bus']->addData($this->getResponseData()); break; case 'open': $data = array(); $rawData = $this->getDevices(); foreach($rawData as $device){ if($device->data['deviceid'] === $actionData['entryid']) { $data['props'] = $this->getDeviceProps($device->data); $data["sharedfolders"] = array("item" => $this->getAdditionalFolderList($actionData['entryid'])); } } $item = array("item" => $data); $this->addActionData('item', $item); $GLOBALS['bus']->addData($this->getResponseData()); break; default: $this->handleUnknownActionType($actionType); } } catch (SoapFault $fault) { $display_message = dgettext('plugin_mdm', 'Something went wrong.'); if ($fault->faultcode === 'HTTP') { if ($fault->getMessage() === "Unauthorized") { $display_message = dgettext('plugin_mdm', 'Unable to connect to Z-Push Server. Unauthorized.'); } if ($fault->getMessage() === "Could not connect to host") { $display_message = dgettext('plugin_mdm', 'Unable to connect to Z-Push Server. Could not connect to host.'); } if ($fault->getMessage() === "Not Found") { $display_message = dgettext('plugin_mdm', 'Unable to connect to Z-Push Server. Not found.'); } } else if ($fault->faultcode === "ERROR") { $display_message = dgettext('plugin_mdm', 'Device ID could not be found'); } $this->sendFeedback(false, array("type" => ERROR_GENERAL, "info" => array('display_message' => $display_message))); } catch (Exception $e) { $this->sendFeedback(true, array("type" => ERROR_GENERAL, "info" => array('display_message' => dgettext('plugin_mdm', 'Something went wrong')))); } } } } /** * Function which is use to get device properties. * * @param array $device array of device properties * @return array */ function getDeviceProps($device) { $item = array(); $propsList = ['devicetype', 'deviceos', 'devicefriendlyname', 'useragent', 'asversion', 'firstsynctime', 'lastsynctime', 'lastupdatetime', 'wipestatus', 'policyname', 'koeversion', 'koebuild', 'koebuilddate']; $item['entryid'] = $device['deviceid']; $item['message_class'] = "IPM.MDM"; foreach ($propsList as $prop) { if (isset($device[$prop])) { $item[$prop] = $device[$prop]; } } $item = array_merge($item, $this->getSyncFoldersProps($device)); return $item; } /** * Function which is use to gather some statistics about synchronized folders. * @param array $device array of device props * @return array $syncFoldersProps has list of properties related to synchronized folders */ function getSyncFoldersProps($device) { $contentData = $device['contentdata']; $folders = array_keys($contentData); $synchedFolderTypes = array(); $synchronizedFolders = 0; $hierarchyCache = isset($device['hierarchycache']) ? $device['hierarchycache'] : false; foreach ($folders as $folderid) { if (isset($contentData[$folderid][self::FOLDERUUID]) || isset($device['hierarchyuuid'])) { $type = $contentData[$folderid][self::FOLDERTYPE]; $name = "unknown"; if ($hierarchyCache) { if (array_key_exists($folderid, $hierarchyCache->cacheById)) { $folder = $hierarchyCache->cacheById[$folderid]; } else { $folder = $hierarchyCache->cacheByIdOld[$folderid]; } if ($folder) { $name = $folder->displayname; } } $folderType = $this->getSyncFolderType($type, $name); if (isset($contentData[$folderid][self::FOLDERUUID])) { $synchedFolderTypes[$folderType]++; } } } $syncFoldersProps = array(); foreach ($synchedFolderTypes as $key => $value) { $synchronizedFolders += $value; $syncFoldersProps[strtolower($key) . 'folder'] = $value; } $client = $this->getSoapClient(); $items = $client->AdditionalFolderList($device['deviceid']); $syncFoldersProps['sharedfolders'] = count($items); $syncFoldersProps["shortfolderids"] = $device['hasfolderidmapping'] ? dgettext('plugin_mdm', "Yes") : dgettext('plugin_mdm', "No"); $syncFoldersProps['synchronizedfolders'] = $synchronizedFolders + count($items); return $syncFoldersProps; } /** * Function which is use to get general type like Mail,Calendar,Contacts,etc. from folder type. * @param int $type foldertype for a folder already known to the mobile * @param string $name folder name * @return string general folder type */ function getSyncFolderType($type, $name) { $folderType = ''; switch ($type) { case SYNC_FOLDER_TYPE_APPOINTMENT: case SYNC_FOLDER_TYPE_USER_APPOINTMENT: if (KOE_GAB_NAME != "" && $name == KOE_GAB_NAME) { $folderType = "GAB"; } else { $folderType = "Calendars"; } break; case SYNC_FOLDER_TYPE_CONTACT: case SYNC_FOLDER_TYPE_USER_CONTACT: $folderType = "Contacts"; break; case SYNC_FOLDER_TYPE_TASK: case SYNC_FOLDER_TYPE_USER_TASK: $folderType = "Tasks"; break; case SYNC_FOLDER_TYPE_NOTE: case SYNC_FOLDER_TYPE_USER_NOTE: $folderType = "Notes"; break; default: $folderType = "Emails"; break; } return $folderType; } /** * Function which is use to get list of additional folders which was shared with given device * @param string $devid device id * @return array has list of properties related to shared folders */ function getAdditionalFolderList($devid) { $stores = $GLOBALS["mapisession"]->getAllMessageStores(); $client = $this->getSoapClient(); $items = $client->AdditionalFolderList($devid); $data = array(); foreach ($items as $item) { foreach ($stores as $store) { try { $entryid = mapi_msgstore_entryidfromsourcekey($store, hex2bin($item->folderid)); } catch (MAPIException $me) { continue; } } if (isset($entryid)) { $item->entryid = bin2hex($entryid); } array_push($data, array("props" => $item)); } return $data; } }; ?>