Merge branch '2015.11' into 2015.11-develop
authorPhilipp Schüle <p.schuele@metaways.de>
Mon, 27 Mar 2017 10:02:44 +0000 (12:02 +0200)
committerPhilipp Schüle <p.schuele@metaways.de>
Mon, 27 Mar 2017 10:02:44 +0000 (12:02 +0200)
Change-Id: I353deb0a3615e2acb3ae4cf1b3b43625b3ff60be

12 files changed:
1  2 
tests/tine20/Filemanager/Frontend/JsonTests.php
tests/tine20/Tinebase/Frontend/CliTest.php
tine20/Calendar/Backend/Sql.php
tine20/Calendar/Controller.php
tine20/Calendar/Controller/Event.php
tine20/Setup/Controller.php
tine20/Tinebase/Application.php
tine20/Tinebase/Backend/Sql/Abstract.php
tine20/Tinebase/Container.php
tine20/Tinebase/Controller/Record/Abstract.php
tine20/Tinebase/Core.php
tine20/Tinebase/User/Abstract.php

Simple merge
Simple merge
Simple merge
Simple merge
@@@ -487,14 -497,8 +488,14 @@@ class Tinebase_Applicatio
       * @param Tinebase_Model_Application $_applicationName
       * @return void
       */
-     public function removeApplicationData(Tinebase_Model_Application $_application)
+     public function removeApplicationAuxiliaryData(Tinebase_Model_Application $_application)
      {
 +        try {
 +            Tinebase_FileSystem::getInstance()->rmdir($_application->getId(), true);
 +        } catch (Tinebase_Exception_NotFound $tenf) {
 +            // nothing to do
 +        }
 +
          $dataToDelete = array(
              'container'     => array('tablename' => ''),
              'config'        => array('tablename' => ''),
Simple merge
@@@ -2165,106 -2107,35 +2165,140 @@@ abstract class Tinebase_Controller_Reco
      }
  
      /**
++<<<<<<< HEAD
 +     * returns path of record
 +     *
 +     * @param     $record
 +     * @param int $depth
 +     * @return Tinebase_Record_RecordSet
 +     * @throws Tinebase_Exception_Record_NotAllowed
 +     * @throws Tinebase_Exception
 +     */
 +    protected function _getPathsOfRecord($record, $depth = false)
 +    {
 +        if (false !== $depth && $depth > 8) {
 +            throw new Tinebase_Exception('too many recursions while calculating record path');
 +        }
 +
 +        $result = new Tinebase_Record_RecordSet('Tinebase_Model_Path');
 +
 +        $parentRelations = Tinebase_Relations::getInstance()->getRelationsOfRecordByDegree($record, Tinebase_Model_Relation::DEGREE_PARENT);
 +        foreach ($parentRelations as $parent) {
 +
 +            if (!is_object($parent->related_record)) {
 +                $parent->related_record = Tinebase_Core::getApplicationInstance($parent->related_model)->get($parent->related_id);
 +            }
 +
 +            if (false === $depth) {
 +                // we do not need to generate the parents paths, they should be in DB
 +                $parentPaths = Tinebase_Record_Path::getInstance()->getPathsForRecords($parent->related_record);
 +            } else {
 +                // we have to regenerate parents paths
 +                $parentPaths = $this->_getPathsOfRecord($parent->related_record, $depth === true ? 1 : $depth + 1);
 +            }
 +
 +            if (count($parentPaths) === 0) {
 +                $path = new Tinebase_Model_Path(array(
 +                    'path'          => $this->_getPathPart($parent->related_record) . $this->_getPathPart($record, $parent),
 +                    'shadow_path'   => '/' . $parent->related_id . $this->_getShadowPathPart($record, $parent),
 +                    'record_id'     => $record->getId(),
 +                    'creation_time' => Tinebase_DateTime::now(),
 +                ));
 +                $result->addRecord($path);
 +            } else {
 +                // merge paths
 +                foreach ($parentPaths as $path) {
 +                    $newPath = new Tinebase_Model_Path(array(
 +                        'path'          => $path->path . $this->_getPathPart($record, $parent),
 +                        'shadow_path'   => $path->shadow_path . $this->_getShadowPathPart($record, $parent),
 +                        'record_id'     => $record->getId(),
 +                        'creation_time' => Tinebase_DateTime::now(),
 +                    ));
 +
 +                    $result->addRecord($newPath);
 +                }
 +            }
 +        }
 +
 +        return $result;
 +    }
 +
 +    /**
 +     * @param $record
 +     * @param $relation
 +     * @return string
 +     *
 +     * TODO use decorators
 +     */
 +    protected function _getPathPart($record, $relation = null)
 +    {
 +        $type = $this->_getTypeForPathPart($relation);
 +
 +        return $type . '/' . mb_substr(str_replace('/', '', trim($record->getTitle())), 0, 32);
 +    }
 +
 +    protected function _getTypeForPathPart($relation)
 +    {
 +        return ($relation && ! empty($relation->type)) ? '{' . $relation->type . '}' : '';
 +    }
 +
 +    /**
 +     * @param $record
 +     * @param $relation
 +     * @return string
 +     *
 +     * TODO use decorators
 +     */
 +    protected function _getShadowPathPart($record, $relation = null)
 +    {
 +        $type = $this->_getTypeForPathPart($relation);
 +
 +        return $type . '/' . $record->getId();
 +    }
 +
 +    /**
 +     * shortcut to Tinebase_Record_Path::generatePathForRecord
 +     *
 +     * @param $record
 +     * @param $rebuildRecursively
 +     */
 +    public function buildPath($record, $rebuildRecursively = false)
 +    {
 +        if ($this->_useRecordPaths) {
 +            Tinebase_Record_Path::getInstance()->generatePathForRecord($record, $rebuildRecursively);
 +        }
 +    }
++
++    /**
+      * @param Tinebase_Model_Container $_container
+      * @param bool $_ignoreAcl
+      * @param null $_filter
+      */
+     public function deleteContainerContents(Tinebase_Model_Container $_container, $_ignoreAcl = FALSE, $_filter = null)
+     {
+         $model = $_container->model;
+         $filterName = $model . 'Filter';
+         // workaround to fix Filemanager as Tinebase_Filesystem does not implement search
+         if (method_exists($this->_backend, 'search') && ($_filter !== null || class_exists($filterName))) {
+             Tinebase_Core::getLogger()->info(__METHOD__ . '::' . __LINE__
+                 . ' Delete ' . $model . ' records in container ' . $_container->getId());
+             if (null === $_filter) {
+                 /** @var Tinebase_Model_Filter_FilterGroup $_filter */
+                 $_filter = new $filterName(array(), Tinebase_Model_Filter_FilterGroup::CONDITION_AND, array('ignoreAcl' => $_ignoreAcl));
+                 // we add the container_id filter like this because Calendar Filters have special behaviour that we want to avoid
+                 // alternatively the calender event controller would have to overwrite this method and deal with this application
+                 // specifics itself. But for the time being, this seems like a good generic solution
+                 $_filter->addFilter(new Tinebase_Model_Filter_Id('container_id', 'equals', $_container->id));
+             }
+             if ($_ignoreAcl) {
+                 $idsToDelete = $this->_backend->search($_filter, null, /* $_onlyIds */true);
+                 $this->delete($idsToDelete);
+             } else {
+                 $this->deleteByFilter($_filter);
+             }
+         }
+     }
  }
@@@ -384,12 -386,12 +386,15 @@@ class Tinebase_Cor
                  throw new Tinebase_Exception_NotFound('No Application Controller found (checked class ' . $controllerNameModel . ')!');
              } else {
                  $controllerName = $controllerNameModel;
+                 if (! class_exists($controllerName)) {
+                     throw new Tinebase_Exception_NotFound('No Application Controller found (checked class ' . $controllerName . ')!');
+                 }
              }
          } else if (! class_exists($controllerName)) {
 -            throw new Tinebase_Exception_NotFound('No Application Controller found (checked class ' . $controllerName . ')!');
 +            if (Tinebase_Core::isLogLevel(Zend_Log::TRACE)) Tinebase_Core::getLogger()->trace(__METHOD__ . '::' . __LINE__
 +                . ' Use generic application controller');
 +
 +            $controller = new Tinebase_Application_Controller($appName);
          }
          
          if (! $_ignoreACL && is_object(Tinebase_Core::getUser()) && ! Tinebase_Core::getUser()->hasRight($appName, Tinebase_Acl_Rights_Abstract::RUN)) {
Simple merge