/** * @NoAdminRequired */ public function removeFromGroup() { $response = new JSONResponse(); $params = $this->request->urlParams; $categoryId = $params['categoryId']; $categoryName = $this->request->post['name']; $ids = $this->request->post['contactIds']; //$response->debug('request: '.print_r($this->request->post, true)); if (is_null($categoryId) || $categoryId === '') { throw new \Exception(App::$l10n->t('Group ID missing from request.'), Http::STATUS_PRECONDITION_FAILED); } if (is_null($categoryName) || $categoryName === '') { throw new \Exception(App::$l10n->t('Group name missing from request.'), Http::STATUS_PRECONDITION_FAILED); } if (is_null($ids)) { throw new \Exception(App::$l10n->t('Contact ID missing from request.'), Http::STATUS_PRECONDITION_FAILED); } $backend = $this->app->getBackend('local'); foreach ($ids as $contactId) { $contact = $backend->getContact(null, $contactId, array('noCollection' => true)); if (!$contact) { $response->debug('Couldn\'t get contact: ' . $contactId); continue; } $obj = \Sabre\VObject\Reader::read($contact['carddata'], \Sabre\VObject\Reader::OPTION_IGNORE_INVALID_LINES); if ($obj) { if (!isset($obj->CATEGORIES)) { return $response; } if ($obj->removeFromGroup($categoryName)) { $backend->updateContact(null, $contactId, $obj, array('noCollection' => true)); } } else { $response->debug('Error parsing contact: ' . $contactId); } $response->debug('contactId: ' . $contactId . ', categoryId: ' . $categoryId); $this->tags->unTag($contactId, $categoryId); } return $response; }
/** * @NoAdminRequired */ public function start() { $request = $this->request; $response = new JSONResponse(); $params = $this->request->urlParams; $app = new App($this->api->getUserId()); $addressBook = $app->getAddressBook($params['backend'], $params['addressBookId']); if (!$addressBook->hasPermission(\OCP\PERMISSION_CREATE)) { $response->setStatus('403'); $response->bailOut(App::$l10n->t('You do not have permissions to import into this address book.')); return $response; } $filename = isset($request->post['filename']) ? $request->post['filename'] : null; $progresskey = isset($request->post['progresskey']) ? $request->post['progresskey'] : null; if (is_null($filename)) { $response->bailOut(App::$l10n->t('File name missing from request.')); return $response; } if (is_null($progresskey)) { $response->bailOut(App::$l10n->t('Progress key missing from request.')); return $response; } $filename = strtr($filename, array('/' => '', "\\" => '')); if (\OC\Files\Filesystem::isFileBlacklisted($filename)) { $response->bailOut(App::$l10n->t('Attempt to access blacklisted file:') . $filename); return $response; } $view = \OCP\Files::getStorage('contacts'); $proxyStatus = \OC_FileProxy::$enabled; \OC_FileProxy::$enabled = false; $file = $view->file_get_contents('/imports/' . $filename); \OC_FileProxy::$enabled = $proxyStatus; $writeProgress = function ($pct) use($progresskey) { \OC_Cache::set($progresskey, $pct, 300); }; $cleanup = function () use($view, $filename, $progresskey) { if (!$view->unlink('/imports/' . $filename)) { $response->debug('Unable to unlink /imports/' . $filename); } \OC_Cache::remove($progresskey); }; $writeProgress('20'); $nl = "\n"; $file = str_replace(array("\r", "\n\n"), array("\n", "\n"), $file); $lines = explode($nl, $file); $inelement = false; $parts = array(); $card = array(); foreach ($lines as $line) { if (strtoupper(trim($line)) == 'BEGIN:VCARD') { $inelement = true; } elseif (strtoupper(trim($line)) == 'END:VCARD') { $card[] = $line; $parts[] = implode($nl, $card); $card = array(); $inelement = false; } if ($inelement === true && trim($line) != '') { $card[] = $line; } } if (count($parts) === 0) { $response->bailOut(App::$l10n->t('No contacts found in: ') . $filename); $cleanup(); return $response; } //import the contacts $imported = 0; $failed = 0; $partially = 0; $processed = 0; // TODO: Add a new group: "Imported at {date}" foreach ($parts as $part) { try { $vcard = VObject\Reader::read($part); } catch (VObject\ParseException $e) { try { $vcard = VObject\Reader::read($part, VObject\Reader::OPTION_IGNORE_INVALID_LINES); $partially += 1; $response->debug('Import: Retrying reading card. Error parsing VCard: ' . $e->getMessage()); } catch (\Exception $e) { $failed += 1; $response->debug('Import: skipping card. Error parsing VCard: ' . $e->getMessage()); continue; // Ditch cards that can't be parsed by Sabre. } } try { $vcard->validate(MyVCard::REPAIR | MyVCard::UPGRADE); } catch (\Exception $e) { \OCP\Util::writeLog('contacts', __METHOD__ . ' ' . 'Error validating vcard: ' . $e->getMessage(), \OCP\Util::ERROR); $failed += 1; } /** * TODO * - Check if a contact with identical UID exists. * - If so, fetch that contact and call $contact->mergeFromVCard($vcard); * - Increment $updated var (not present yet.) * - continue */ try { if ($addressBook->addChild($vcard)) { $imported += 1; } else { $failed += 1; } } catch (\Exception $e) { $response->debug('Error importing vcard: ' . $e->getMessage() . $nl . $vcard->serialize()); $failed += 1; } $processed += 1; $writeProgress($processed); } //done the import sleep(3); // Give client side a chance to read the progress. $response->setParams(array('backend' => $params['backend'], 'addressBookId' => $params['addressBookId'], 'imported' => $imported, 'partially' => $partially, 'failed' => $failed)); return $response; }
/** * Saves the photo from ownCloud FS to oC cache * @return JSONResponse with data.tmp set to the key in the cache. * * @NoAdminRequired * @NoCSRFRequired */ public function cacheFileSystemPhoto() { $params = $this->request->urlParams; $response = new JSONResponse(); if (!isset($this->request->get['path'])) { $response->bailOut(App::$l10n->t('No photo path was submitted.')); } $localpath = \OC\Files\Filesystem::getLocalFile($this->request->get['path']); $tmpkey = 'contact-photo-' . $params['contactId']; if (!file_exists($localpath)) { return $response->bailOut(App::$l10n->t('File doesn\'t exist:') . $localpath); } $image = new \OCP\Image(); if (!$image) { return $response->bailOut(App::$l10n->t('Error loading image.')); } if (!$image->loadFromFile($localpath)) { return $response->bailOut(App::$l10n->t('Error loading image.')); } if ($image->width() > 400 || $image->height() > 400) { $image->resize(400); // Prettier resizing than with browser and saves bandwidth. } if (!$image->fixOrientation()) { // No fatal error so we don't bail out. $response->debug('Couldn\'t save correct image orientation: ' . $localpath); } if (!$this->server->getCache()->set($tmpkey, $image->data(), 600)) { return $response->bailOut('Couldn\'t save temporary image: ' . $tmpkey); } return $response->setData(array('tmp' => $tmpkey, 'metadata' => array('contactId' => $params['contactId'], 'addressBookId' => $params['addressBookId'], 'backend' => $params['backend']))); }
/** * @NoAdminRequired */ public function start() { $request = $this->request; $response = new JSONResponse(); $params = $this->request->urlParams; $app = new App(\OCP\User::getUser()); $addressBookId = $params['addressBookId']; $format = $params['importType']; $addressBook = $app->getAddressBook($params['backend'], $addressBookId); if (!$addressBook->hasPermission(\OCP\PERMISSION_CREATE)) { $response->setStatus('403'); $response->bailOut(App::$l10n->t('You do not have permissions to import into this address book.')); return $response; } $filename = isset($request->post['filename']) ? $request->post['filename'] : null; $progresskey = isset($request->post['progresskey']) ? $request->post['progresskey'] : null; if (is_null($filename)) { $response->bailOut(App::$l10n->t('File name missing from request.')); return $response; } if (is_null($progresskey)) { $response->bailOut(App::$l10n->t('Progress key missing from request.')); return $response; } $filename = strtr($filename, array('/' => '', "\\" => '')); if (\OC\Files\Filesystem::isFileBlacklisted($filename)) { $response->bailOut(App::$l10n->t('Attempt to access blacklisted file:') . $filename); return $response; } $view = \OCP\Files::getStorage('contacts'); $proxyStatus = \OC_FileProxy::$enabled; \OC_FileProxy::$enabled = false; $file = $view->file_get_contents('/imports/' . $filename); \OC_FileProxy::$enabled = $proxyStatus; $importManager = new ImportManager(); $formatList = $importManager->getTypes(); $found = false; $parts = array(); foreach ($formatList as $formatName => $formatDisplayName) { if ($formatName == $format) { $parts = $importManager->importFile($view->getLocalFile('/imports/' . $filename), $formatName); $found = true; } } if (!$found) { // detect file type $mostLikelyName = ""; $mostLikelyValue = 0; $probability = $importManager->detectFileType($view->getLocalFile('/imports/' . $filename)); foreach ($probability as $probName => $probValue) { if ($probValue > $mostLikelyValue) { $mostLikelyName = $probName; $mostLikelyValue = $probValue; } } if ($mostLikelyValue > 0) { // found one (most likely...) $parts = $importManager->importFile($view->getLocalFile('/imports/' . $filename), $mostLikelyName); } } if ($parts) { //import the contacts $imported = 0; $failed = 0; $processed = 0; $total = count($parts); foreach ($parts as $part) { /** * TODO * - Check if a contact with identical UID exists. * - If so, fetch that contact and call $contact->mergeFromVCard($part); * - Increment $updated var (not present yet.) * - continue */ try { $id = $addressBook->addChild($part); if ($id) { $imported++; $favourites = $part->select('X-FAVOURITES'); foreach ($favourites as $favourite) { if ($favourite->getValue() == 'yes') { $this->tagMgr->addToFavorites($id); } } } else { $failed++; } } catch (\Exception $e) { $response->debug('Error importing vcard: ' . $e->getMessage() . $nl . $part->serialize()); $failed++; } $processed++; $this->writeProcess($processed, $total, $progresskey); } } else { $imported = 0; $failed = 0; $processed = 0; $total = 0; } $this->cleanup($view, $filename, $progresskey, $response); //done the import sleep(3); // Give client side a chance to read the progress. $response->setParams(array('backend' => $params['backend'], 'addressBookId' => $params['addressBookId'], 'importType' => $params['importType'], 'imported' => $imported, 'count' => $processed, 'total' => $total, 'failed' => $failed)); return $response; }
/** * @NoAdminRequired */ public function moveChild() { $params = $this->request->urlParams; $targetInfo = $this->request->post['target']; $response = new JSONResponse(); // TODO: Check if the backend supports move (is 'local' or 'shared') and use that operation instead. // If so, set status 204 and don't return the serialized contact. $fromAddressBook = $this->app->getAddressBook($params['backend'], $params['addressBookId']); $targetAddressBook = $this->app->getAddressBook($targetInfo['backend'], $targetInfo['id']); $contact = $fromAddressBook->getChild($params['contactId']); if (!$contact) { throw new \Exception(App::$l10n->t('Error retrieving contact'), 500); } $contactId = $targetAddressBook->addChild($contact); // Retrieve the contact again to be sure it's in sync $contact = $targetAddressBook->getChild($contactId); if (!$contact) { throw new \Exception(App::$l10n->t('Error saving contact'), 500); } if (!$fromAddressBook->deleteChild($params['contactId'])) { // Don't bail out because we have to return the contact return $response->debug(App::$l10n->t('Error removing contact from other address book.')); } $serialized = JSONSerializer::serializeContact($contact); if (is_null($serialized)) { throw new \Exception(App::$l10n->t('Error getting moved contact')); } return $response->setParams($serialized); }
/** * @param $view * @param string $filename * @param $progresskey * @param JSONResponse $response */ protected function cleanup($view, $filename, $progresskey, $response) { if (!$view->unlink('/imports/' . $filename)) { $response->debug('Unable to unlink /imports/' . $filename); } $this->cache->remove($progresskey); $this->cache->remove($progresskey . '_total'); }
/** * @NoAdminRequired */ public function moveChild() { $params = $this->request->urlParams; $targetInfo = $this->request->post['target']; $response = new JSONResponse(); // TODO: Check if the backend supports move (is 'local' or 'shared') and use that operation instead. // If so, set status 204 and don't return the serialized contact. $fromAddressBook = $this->app->getAddressBook($params['backend'], $params['addressBookId']); $targetAddressBook = $this->app->getAddressBook($targetInfo['backend'], $targetInfo['id']); $contact = $fromAddressBook->getChild($params['contactId']); if (!$contact) { $response->bailOut(App::$l10n->t('Error retrieving contact.')); return $response; } try { $contactId = $targetAddressBook->addChild($contact); } catch (Exception $e) { return $response->bailOut($e->getMessage()); } $contact = $targetAddressBook->getChild($contactId); if (!$contact) { return $response->bailOut(App::$l10n->t('Error saving contact.')); } if (!$fromAddressBook->deleteChild($params['contactId'])) { // Don't bail out because we have to return the contact return $response->debug(App::$l10n->t('Error removing contact from other address book.')); } return $response->setParams(JSONSerializer::serializeContact($contact)); }
/** * @NoAdminRequired */ public function removeFromGroup() { $response = new JSONResponse(); $params = $this->request->urlParams; $categoryId = $params['categoryId']; $categoryname = $this->request->post['name']; $ids = $this->request->post['contactIds']; //$response->debug('request: '.print_r($this->request->post, true)); if (is_null($categoryId) || $categoryId === '') { $response->bailOut(App::$l10n->t('Group ID missing from request.')); return $response; } if (is_null($ids)) { $response->bailOut(App::$l10n->t('Contact ID missing from request.')); return $response; } $backend = $this->app->getBackend('local'); $tagMgr = $this->server->getTagManager()->load('contact'); foreach ($ids as $contactId) { $contact = $backend->getContact(null, $contactId, array('noCollection' => true)); if (!$contact) { $response->debug('Couldn\'t get contact: ' . $contactId); continue; } $obj = \Sabre\VObject\Reader::read($contact['carddata'], \Sabre\VObject\Reader::OPTION_IGNORE_INVALID_LINES); if ($obj) { if (!isset($obj->CATEGORIES)) { $obj->add('CATEGORIES'); } $obj->CATEGORIES->removeGroup($categoryname); $backend->updateContact(null, $contactId, $obj, array('noCollection' => true)); } else { $response->debug('Error parsing contact: ' . $contactId); } $response->debug('contactId: ' . $contactId . ', categoryId: ' . $categoryId); $tagMgr->unTag($contactId, $categoryId); } return $response; }