Merge branch 'master' of ssh://172.20.0.1/var/git/espo/backend

This commit is contained in:
Yuri Kuznetsov
2014-10-01 10:38:04 +03:00
9 changed files with 169 additions and 79 deletions
+9 -13
View File
@@ -79,19 +79,6 @@ class Extension extends \Espo\Core\Controllers\Record
return true;
}
public function actionDeletePackage($params, $data, $request)
{
if (!$request->isPost()) {
throw new Forbidden();
}
$manager = new \Espo\Core\ExtensionManager($this->getContainer());
$manager->delete($data['id']);
return true;
}
public function actionCreate()
{
throw new Forbidden();
@@ -112,6 +99,15 @@ class Extension extends \Espo\Core\Controllers\Record
throw new Forbidden();
}
public function actionDelete($params, $data, $request)
{
$manager = new \Espo\Core\ExtensionManager($this->getContainer());
$manager->delete($params['id']);
return true;
}
public function actionMassUpdate()
{
throw new Forbidden();
+43 -28
View File
@@ -58,16 +58,6 @@ abstract class Base
*/
const SCRIPTS = 'scripts';
/**
* Statuses of Extension Entity
*/
const DISABLED = 'Disabled';
/**
* Statuses of Extension Entity
*/
const ENABLED = 'Enabled';
/**
* Package types
*/
@@ -139,7 +129,7 @@ abstract class Base
return $this->entityManager;
}
protected function throwErrorWithDetelePackage($errorMessage = '')
protected function throwErrorAndRemovePackage($errorMessage = '')
{
$this->deletePackageFiles();
$this->deletePackageArchive();
@@ -220,7 +210,7 @@ abstract class Base
}
}
$this->throwErrorWithDetelePackage('Your EspoCRM version doesn\'t match for this installation package.');
$this->throwErrorAndRemovePackage('Your EspoCRM version doesn\'t match for this installation package.');
}
protected function checkPackageType()
@@ -232,11 +222,11 @@ abstract class Base
$manifestType = isset($manifest['type']) ? strtolower($manifest['type']) : $this->defaultPackageType;
if (!in_array($manifestType, $this->packageTypes)) {
$this->throwErrorWithDetelePackage('Unknown package type.');
$this->throwErrorAndRemovePackage('Unknown package type.');
}
if ($type != $manifestType) {
$this->throwErrorWithDetelePackage('Wrong package type. You cannot install '.$manifestType.' package via '.ucfirst($type).' Manager.');
$this->throwErrorAndRemovePackage('Wrong package type. You cannot install '.$manifestType.' package via '.ucfirst($type).' Manager.');
}
return true;
@@ -249,7 +239,7 @@ abstract class Base
*/
protected function runScript($type)
{
$packagePath = $this->getPath('packagePath');
$packagePath = $this->getPackagePath();
$scriptNames = $this->getParams('scriptNames');
$scriptName = $scriptNames[$type];
@@ -262,7 +252,12 @@ abstract class Base
if (file_exists($beforeInstallScript)) {
require_once($beforeInstallScript);
$script = new $scriptName();
$script->run($this->getContainer());
try {
$script->run($this->getContainer());
} catch (\Exception $e) {
$this->throwErrorAndRemovePackage($e->getMessage());
}
}
}
@@ -282,6 +277,11 @@ abstract class Base
return $path . $postfix;
}
protected function getPackagePath($isPackage = false)
{
return $this->getPath('packagePath', $isPackage);
}
/**
* Get a list of files defined in manifest.json
*
@@ -317,7 +317,7 @@ abstract class Base
protected function getCopyFileList()
{
if (!isset($this->data['fileList'])) {
$packagePath = $this->getPath('packagePath');
$packagePath = $this->getPackagePath();
$filesPath = Util::concatPath($packagePath, self::FILES);
$this->data['fileList'] = $this->getFileManager()->getFileList($filesPath, true, '', 'all', true);
@@ -326,6 +326,17 @@ abstract class Base
return $this->data['fileList'];
}
protected function copy($sourcePath, $destPath, $recursively = false, array $fileList = null, $copyOnlyFiles = false)
{
try {
$res = $this->getFileManager()->copy($sourcePath, $destPath, $recursively, $fileList, $copyOnlyFiles);
} catch (\Exception $e) {
$this->throwErrorAndRemovePackage($e->getMessage());
}
return $res;
}
/**
* Copy files from upgrade/extension package
*
@@ -334,31 +345,31 @@ abstract class Base
*/
protected function copyFiles()
{
$packagePath = $this->getPath('packagePath');
$packagePath = $this->getPackagePath();
$filesPath = Util::concatPath($packagePath, self::FILES);
return $this->getFileManager()->copy($filesPath, '', true);
return $this->copy($filesPath, '', true);
}
public function getManifest()
{
if (!isset($this->data['manifest'])) {
$packagePath = $this->getPath('packagePath');
$packagePath = $this->getPackagePath();
$manifestPath = Util::concatPath($packagePath, $this->manifestName);
if (!file_exists($manifestPath)) {
throw new Error('It\'s not an Installation package.');
$this->throwErrorAndRemovePackage('It\'s not an Installation package.');
}
$manifestJson = $this->getFileManager()->getContents($manifestPath);
$this->data['manifest'] = Json::decode($manifestJson, true);
if (!$this->data['manifest']) {
throw new Error('Syntax error in manifest.json.');
$this->throwErrorAndRemovePackage('Syntax error in manifest.json.');
}
if (!$this->checkManifest($this->data['manifest'])) {
throw new Error('Unsupported package.');
$this->throwErrorAndRemovePackage('Unsupported package.');
}
}
@@ -392,10 +403,14 @@ abstract class Base
*
* @return void
*/
protected function unzipArchive()
protected function unzipArchive($packagePath = null)
{
$packagePath = $this->getPath('packagePath');
$packageArchivePath = $this->getPath('packagePath', true);
$packagePath = isset($packagePath) ? $packagePath : $this->getPackagePath();
$packageArchivePath = $this->getPackagePath(true);
if (!file_exists($packageArchivePath)) {
throw new Error('Package Archive doesn\'t exist.');
}
$res = $this->getZipUtil()->unzip($packageArchivePath, $packagePath);
if ($res === false) {
@@ -410,7 +425,7 @@ abstract class Base
*/
protected function deletePackageFiles()
{
$packagePath = $this->getPath('packagePath');
$packagePath = $this->getPackagePath();
$res = $this->getFileManager()->removeInDir($packagePath, true);
return $res;
@@ -423,7 +438,7 @@ abstract class Base
*/
protected function deletePackageArchive()
{
$packageArchive = $this->getPath('packagePath', true);
$packageArchive = $this->getPackagePath(true);
$res = $this->getFileManager()->removeFile($packageArchive);
return $res;
@@ -46,7 +46,7 @@ class Delete extends \Espo\Core\Upgrades\Actions\Base
protected function deletePackage()
{
$packageArchivePath = $this->getPath('packagePath', true);
$packageArchivePath = $this->getPackagePath(true);
$res = $this->getFileManager()->removeFile($packageArchivePath);
return $res;
@@ -26,6 +26,13 @@ use Espo\Core\Exceptions\Error;
class Install extends \Espo\Core\Upgrades\Actions\Base
{
/**
* Is copied extension files to Espo
*
* @var [type]
*/
protected $isCopied = null;
/**
* Main installation process
*
@@ -42,8 +49,10 @@ class Install extends \Espo\Core\Upgrades\Actions\Base
$this->setProcessId($processId);
$this->isCopied = false;
/** check if an archive is unzipped, if no then unzip */
$packagePath = $this->getPath('packagePath');
$packagePath = $this->getPackagePath();
if (!file_exists($packagePath)) {
$this->unzipArchive();
$this->isAcceptable();
@@ -56,16 +65,17 @@ class Install extends \Espo\Core\Upgrades\Actions\Base
/* remove files defined in a manifest */
if (!$this->deleteFiles()) {
throw new Error('Permission denied to delete files.');
$this->throwErrorAndRemovePackage('Permission denied to delete files.');
}
/* copy files from directory "Files" to EspoCRM files */
if (!$this->copyFiles()) {
throw new Error('Cannot copy files.');
$this->throwErrorAndRemovePackage('Cannot copy files.');
}
$this->isCopied = true;
if (!$this->systemRebuild()) {
throw new Error('Error occurred while EspoCRM rebuild.');
$this->throwErrorAndRemovePackage('Error occurred while EspoCRM rebuild.');
}
/* run before install script */
@@ -78,4 +88,25 @@ class Install extends \Espo\Core\Upgrades\Actions\Base
$GLOBALS['log']->debug('Installation process ['.$processId.']: end run.');
}
protected function restoreFiles()
{
$backupPath = $this->getPath('backupPath');
$res = true;
if ($this->isCopied) {
$res &= $this->copy(array($backupPath, self::FILES), '', true);
$GLOBALS['log']->info('Restore: copy back');
}
$res &= $this->getFileManager()->removeInDir($backupPath, true);
return $res;
}
protected function throwErrorAndRemovePackage($errorMessage = '')
{
$this->restoreFiles();
parent::throwErrorAndRemovePackage($errorMessage);
}
}
@@ -22,7 +22,8 @@
namespace Espo\Core\Upgrades\Actions\Base;
use Espo\Core\Exceptions\Error;
use Espo\Core\Exceptions\Error,
Espo\Core\Utils\Util;
class Uninstall extends \Espo\Core\Upgrades\Actions\Base
{
@@ -41,14 +42,18 @@ class Uninstall extends \Espo\Core\Upgrades\Actions\Base
/* run before install script */
$this->runScript('beforeUninstall');
/* remove extension files, saved in fileList */
if (!$this->deleteFiles()) {
throw new Error('Permission denied to delete files.');
}
$backupPath = $this->getPath('backupPath');
if (file_exists($backupPath)) {
/* copy core files */
if (!$this->copyFiles()) {
throw new Error('Cannot copy files.');
/* remove extension files, saved in fileList */
if (!$this->deleteFiles()) {
throw new Error('Permission denied to delete files.');
}
/* copy core files */
if (!$this->copyFiles()) {
throw new Error('Cannot copy files.');
}
}
if (!$this->systemRebuild()) {
@@ -72,10 +77,25 @@ class Uninstall extends \Espo\Core\Upgrades\Actions\Base
return $extensionEntity->get('fileList');
}
protected function restoreFiles()
{
$packagePath = $this->getPath('packagePath');
$filesPath = Util::concatPath($packagePath, self::FILES);
if (!file_exists($filesPath)) {
$this->unzipArchive($packagePath);
}
$res = $this->copy($filesPath, '', true);
$res &= $this->getFileManager()->removeInDir($packagePath, true);
return $res;
}
protected function copyFiles()
{
$backupPath = $this->getPath('backupPath');
$res = $this->getFileManager()->copy(array($backupPath, self::FILES), '', true);
$res = $this->copy(array($backupPath, self::FILES), '', true);
return $res;
}
@@ -86,10 +106,13 @@ class Uninstall extends \Espo\Core\Upgrades\Actions\Base
* @param string $processId
* @return string
*/
protected function getPath($name = 'packagePath', $isPackage = false)
protected function getPackagePath($isPackage = false)
{
$name = ($name == 'packagePath') ? 'backupPath' : $name;
return parent::getPath($name, $isPackage);
if ($isPackage) {
return $this->getPath('packagePath', $isPackage);
}
return $this->getPath('backupPath');
}
protected function deletePackageFiles()
@@ -100,4 +123,10 @@ class Uninstall extends \Espo\Core\Upgrades\Actions\Base
return $res;
}
protected function throwErrorAndRemovePackage($errorMessage = '')
{
$this->restoreFiles();
throw new Error($errorMessage);
}
}
@@ -38,8 +38,8 @@ class Upload extends \Espo\Core\Upgrades\Actions\Base
$GLOBALS['log']->debug('Installation process ['.$processId.']: start upload the package.');
$packagePath = $this->getPath('packagePath');
$packageArchivePath = $this->getPath('packagePath', true);
$packagePath = $this->getPackagePath();
$packageArchivePath = $this->getPackagePath(true);
if (!empty($data)) {
list($prefix, $contents) = explode(',', $data);
@@ -58,12 +58,6 @@ class Delete extends \Espo\Core\Upgrades\Actions\Base\Delete
throw new Error('Extension Entity not found.');
}
$this->setExtensionEntity($extensionEntity);
/** check if extension archive exsists */
$packageArchivePath = $this->getPath('packagePath', true);
if (!file_exists($packageArchivePath)) {
throw new Error('Extension Archive doesn\'t exist.');
}
}
protected function afterRunAction()
@@ -51,11 +51,24 @@ class Install extends \Espo\Core\Upgrades\Actions\Base\Install
$fileList = $this->getCopyFileList();
$backupPath = $this->getPath('backupPath');
$res = $this->getFileManager()->copy('', array($backupPath, self::FILES), false, $fileList);
$res = $this->copy('', array($backupPath, self::FILES), false, $fileList);
/** copy scripts files */
$packagePath = $this->getPath('packagePath');
$res &= $this->getFileManager()->copy(array($packagePath, self::SCRIPTS), array($backupPath, self::SCRIPTS), true);
$packagePath = $this->getPackagePath();
$res &= $this->copy(array($packagePath, self::SCRIPTS), array($backupPath, self::SCRIPTS), true);
return $res;
}
protected function restoreFiles()
{
$res = true;
if ($this->isCopied) {
$extensionFileList = $this->getCopyFileList();
$res &= $this->getFileManager()->remove($extensionFileList);
}
$res &= parent::restoreFiles();
return $res;
}
@@ -125,7 +138,11 @@ class Install extends \Espo\Core\Upgrades\Actions\Base\Install
protected function storeExtension()
{
$entityManager = $this->getEntityManager();
$extensionEntity = $entityManager->getEntity('Extension');
$extensionEntity = $entityManager->getEntity('Extension', $this->getProcessId());
if (!isset($extensionEntity)) {
$extensionEntity = $entityManager->getEntity('Extension');
}
$manifest = $this->getManifest();
$fileList = $this->getCopyFileList();
@@ -133,7 +150,6 @@ class Install extends \Espo\Core\Upgrades\Actions\Base\Install
$data = array(
'id' => $this->getProcessId(),
'name' => $manifest['name'],
'status' => self::ENABLED,
'isInstalled' => true,
'version' => $manifest['version'],
'fileList' => $fileList,
@@ -157,10 +173,26 @@ class Install extends \Espo\Core\Upgrades\Actions\Base\Install
if (isset($extensionEntity)) {
$comparedVersion = version_compare($manifest['version'], $extensionEntity->get('version'));
if ($comparedVersion <= 0) {
$this->throwErrorWithDetelePackage('You cannot install an older version of this extension.');
$this->throwErrorAndRemovePackage('You cannot install an older version of this extension.');
}
}
}
/**
* Throw an exception and remove package files.
* Redeclared to prevent of deleting a package of installed extension.
*
* @param string $errorMessage [description]
* @return [type] [description]
*/
protected function throwErrorAndRemovePackage($errorMessage = '')
{
if (!$this->isNew()) {
throw new Error($errorMessage);
}
return parent::throwErrorAndRemovePackage($errorMessage);
}
}
@@ -58,12 +58,6 @@ class Uninstall extends \Espo\Core\Upgrades\Actions\Base\Uninstall
throw new Error('Extension Entity not found.');
}
$this->setExtensionEntity($extensionEntity);
/** check if backup of the extension exsists */
$backupPath = $this->getPath('backupPath');
if (!file_exists($backupPath)) {
throw new Error('Backup files don\'t exist.');
}
}
protected function afterRunAction()
@@ -71,7 +65,6 @@ class Uninstall extends \Espo\Core\Upgrades\Actions\Base\Uninstall
/** Set extension entity, isInstalled = false */
$extensionEntity = $this->getExtensionEntity();
$extensionEntity->set('status', self::DISABLED);
$extensionEntity->set('isInstalled', false);
$this->getEntityManager()->saveEntity($extensionEntity);
}