Example #1
0
 /**
  * Start a editing session or return an existing one
  * @param string $uid of the user starting a session
  * @param \OCA\Documents\File $file - file object
  * @return array
  * @throws \Exception
  */
 public static function start($uid, File $file)
 {
     list($ownerView, $path) = $file->getOwnerViewAndPath();
     // Create a directory to store genesis
     $genesis = new Genesis($ownerView, $path, $file->getOwner());
     $oldSession = new Db_Session();
     $oldSession->loadBy('file_id', $file->getFileId());
     //If there is no existing session we need to start a new one
     if (!$oldSession->hasData()) {
         $newSession = new Db_Session(array($genesis->getPath(), $genesis->getHash(), $file->getOwner(), $file->getFileId()));
         if (!$newSession->insert()) {
             throw new \Exception('Failed to add session into database');
         }
     }
     $session = $oldSession->loadBy('file_id', $file->getFileId())->getData();
     $memberColor = Helper::getRandomColor();
     $member = new Db_Member(array($session['es_id'], $uid, $memberColor, time()));
     if ($member->insert()) {
         // Do we have OC_Avatar in out disposal?
         if (!class_exists('\\OC_Avatar') || \OC_Config::getValue('enable_avatars', true) !== true) {
             //$x['avatar_url'] = \OCP\Util::linkToRoute('documents_user_avatar');
             $imageUrl = 'data:image/gif;base64,R0lGODlhAQABAIAAAAAAAAAAACH5BAAAAAAALAAAAAABAAEAAAICTAEAOw==';
         } else {
             // https://github.com/owncloud/documents/issues/51
             // Temporary stub
             $imageUrl = $uid;
             /*
             				$avatar = new \OC_Avatar($uid);
             				$image = $avatar->get(64);
             					// User has an avatar 
             				if ($image instanceof \OC_Image) {
             					$imageUrl = \OC_Helper::linkToRoute(
             							'core_avatar_get',
             							array( 'user' => $uid, 'size' => 64)
             					) . '?requesttoken=' . \OC::$session->get('requesttoken');
             				} else {
             					//shortcircuit if it's not an image
             					$imageUrl = 'data:image/gif;base64,R0lGODlhAQABAIAAAAAAAAAAACH5BAAAAAAALAAAAAABAAEAAAICTAEAOw==';
             				}
             */
         }
         $session['member_id'] = (string) $member->getLastInsertId();
         $op = new Db_Op();
         $op->addMember($session['es_id'], $session['member_id'], \OCP\User::getDisplayName($uid), $memberColor, $imageUrl);
     } else {
         throw new \Exception('Failed to add member into database');
     }
     $session['permissions'] = $ownerView->getFilePermissions($path);
     return $session;
 }
 /**
  * Store the document content to its origin
  */
 public static function save()
 {
     try {
         $esId = @$_SERVER['HTTP_WEBODF_SESSION_ID'];
         if (!$esId) {
             throw new \Exception('Session id can not be empty');
         }
         $memberId = @$_SERVER['HTTP_WEBODF_MEMBER_ID'];
         $currentMember = new Db\Member();
         $currentMember->load($memberId);
         if (is_null($currentMember->getIsGuest()) || $currentMember->getIsGuest()) {
             self::preDispatchGuest();
         } else {
             $uid = self::preDispatch();
         }
         //check if member belongs to the session
         if ($esId != $currentMember->getEsId()) {
             throw new \Exception($memberId . ' does not belong to session ' . $esId);
         }
         // Extra info for future usage
         // $sessionRevision = Helper::getArrayValueByKey($_SERVER, 'HTTP_WEBODF_SESSION_REVISION');
         $stream = fopen('php://input', 'r');
         if (!$stream) {
             throw new \Exception('New content missing');
         }
         $content = stream_get_contents($stream);
         $session = new Db\Session();
         $session->load($esId);
         if (!$session->getEsId()) {
             throw new \Exception('Session does not exist');
         }
         try {
             if ($currentMember->getIsGuest()) {
                 $file = File::getByShareToken($currentMember->getToken());
             } else {
                 $file = new File($session->getFileId());
             }
             list($view, $path) = $file->getOwnerViewAndPath(true);
         } catch (\Exception $e) {
             //File was deleted or unshared. We need to save content as new file anyway
             //Sorry, but for guests it would be lost :(
             if (isset($uid)) {
                 $view = new \OC\Files\View('/' . $uid . '/files');
                 $dir = \OCP\Config::getUserValue(\OCP\User::getUser(), 'documents', 'save_path', '');
                 $path = Helper::getNewFileName($view, $dir . 'New Document.odt');
             }
         }
         $member = new Db\Member();
         $members = $member->getActiveCollection($esId);
         $memberIds = array_map(function ($x) {
             return $x['member_id'];
         }, $members);
         // Active users except current user
         $memberCount = count($memberIds) - 1;
         if ($view->file_exists($path)) {
             $proxyStatus = \OC_FileProxy::$enabled;
             \OC_FileProxy::$enabled = false;
             $currentHash = sha1($view->file_get_contents($path));
             \OC_FileProxy::$enabled = $proxyStatus;
             if (!Helper::isVersionsEnabled() && $currentHash !== $session->getGenesisHash()) {
                 // Original file was modified externally. Save to a new one
                 $path = Helper::getNewFileName($view, $path, '-conflict');
             }
             $mimetype = $view->getMimeType($path);
         } else {
             $mimetype = Storage::MIMETYPE_LIBREOFFICE_WORDPROCESSOR;
         }
         $data = Filter::write($content, $mimetype);
         if ($view->file_put_contents($path, $data['content'])) {
             // Not a last user
             if ($memberCount > 0) {
                 // Update genesis hash to prevent conflicts
                 Helper::debugLog('Update hash');
                 $session->updateGenesisHash($esId, sha1($data['content']));
             } else {
                 // Last user. Kill session data
                 Db\Session::cleanUp($esId);
             }
             $view->touch($path);
         }
         \OCP\JSON::success();
     } catch (\Exception $e) {
         Helper::warnLog('Saving failed. Reason:' . $e->getMessage());
         //\OCP\JSON::error(array('message'=>$e->getMessage()));
         \OC_Response::setStatus(500);
     }
     exit;
 }
 /**
  * Store the document content to its origin
  */
 public static function save()
 {
     try {
         $esId = @$_SERVER['HTTP_WEBODF_SESSION_ID'];
         if (!$esId) {
             throw new \Exception('Session id can not be empty');
         }
         $memberId = @$_SERVER['HTTP_WEBODF_MEMBER_ID'];
         $sessionRevision = @$_SERVER['HTTP_WEBODF_SESSION_REVISION'];
         $stream = fopen('php://input', 'r');
         if (!$stream) {
             throw new \Exception('New content missing');
         }
         $content = stream_get_contents($stream);
         $session = new Db_Session();
         $session->load($esId);
         if (!$session->hasData()) {
             throw new \Exception('Session does not exist');
         }
         $sessionData = $session->getData();
         $file = new File($sessionData['file_id']);
         if (!$file->isPublicShare()) {
             self::preDispatch();
         } else {
             self::preDispatchGuest();
         }
         list($view, $path) = $file->getOwnerViewAndPath();
         $isWritable = $view->file_exists($path) && $view->isUpdatable($path) || $view->isCreatable($path);
         if (!$isWritable) {
             throw new \Exception($path . ' does not exist or is not writable for user ' . $uid);
         }
         $member = new Db_Member();
         $members = $member->getActiveCollection($esId);
         $memberIds = array_map(function ($x) {
             return $x['member_id'];
         }, $members);
         //check if member belongs to the session
         if (!in_array($memberId, $memberIds)) {
             throw new \Exception($memberId . ' does not belong to session ' . $esId);
         }
         // Active users except current user
         $memberCount = count($memberIds) - 1;
         if ($view->file_exists($path)) {
             $proxyStatus = \OC_FileProxy::$enabled;
             \OC_FileProxy::$enabled = false;
             $currentHash = sha1($view->file_get_contents($path));
             \OC_FileProxy::$enabled = $proxyStatus;
             if (!Helper::isVersionsEnabled() && $currentHash !== $sessionData['genesis_hash']) {
                 // Original file was modified externally. Save to a new one
                 $path = Helper::getNewFileName($view, $path, '-conflict');
             }
         }
         if ($view->file_put_contents($path, $content)) {
             // Not a last user
             if ($memberCount > 0) {
                 // Update genesis hash to prevent conflicts
                 Helper::debugLog('Update hash');
                 $session->updateGenesisHash($esId, sha1($content));
             } else {
                 // Last user. Kill session data
                 Db_Session::cleanUp($esId);
             }
             $view->touch($path);
         }
         \OCP\JSON::success();
         exit;
     } catch (\Exception $e) {
         Helper::warnLog('Saving failed. Reason:' . $e->getMessage());
         \OCP\JSON::error(array('message' => $e->getMessage()));
         exit;
     }
 }