[-] Classes : fix bug PSCFI-3367 - incorrect admin rights for created image folders

This commit is contained in:
tDidierjean
2011-09-20 16:58:58 +00:00
parent daff11df6b
commit 41e5a8d64e
+91 -88
View File
@@ -1,6 +1,6 @@
<?php <?php
/* /*
* 2007-2011 PrestaShop * 2007-2011 PrestaShop
* *
* NOTICE OF LICENSE * NOTICE OF LICENSE
* *
@@ -22,7 +22,7 @@
* @copyright 2007-2011 PrestaShop SA * @copyright 2007-2011 PrestaShop SA
* @version Release: $Revision: 7310 $ * @version Release: $Revision: 7310 $
* @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0) * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
* International Registered Trademark & Property of PrestaShop SA * International Registered Trademark & Property of PrestaShop SA
*/ */
class ImageCore extends ObjectModel class ImageCore extends ObjectModel
@@ -31,51 +31,54 @@ class ImageCore extends ObjectModel
/** @var integer Image ID */ /** @var integer Image ID */
public $id_image; public $id_image;
/** @var integer Product ID */ /** @var integer Product ID */
public $id_product; public $id_product;
/** @var string HTML title and alt attributes */ /** @var string HTML title and alt attributes */
public $legend; public $legend;
/** @var integer Position used to order images of the same product */ /** @var integer Position used to order images of the same product */
public $position; public $position;
/** @var boolean Image is cover */ /** @var boolean Image is cover */
public $cover; public $cover;
/** @var string image extension */ /** @var string image extension */
public $image_format = 'jpg'; public $image_format = 'jpg';
/** @var string path to index.php file to be copied to new image folders */ /** @var string path to index.php file to be copied to new image folders */
public $source_index; public $source_index;
/** @var string image folder */ /** @var string image folder */
protected $folder; protected $folder;
/** @var string image path without extension */ /** @var string image path without extension */
protected $existing_path; protected $existing_path;
/** @var int access rights of created folders (octal) */
protected $access_rights = 0775;
protected $tables = array ('image', 'image_lang'); protected $tables = array ('image', 'image_lang');
protected $fieldsRequired = array('id_product'); protected $fieldsRequired = array('id_product');
protected $fieldsValidate = array('id_product' => 'isUnsignedId', 'position' => 'isUnsignedInt', 'cover' => 'isBool'); protected $fieldsValidate = array('id_product' => 'isUnsignedId', 'position' => 'isUnsignedInt', 'cover' => 'isBool');
protected $fieldsRequiredLang = array('legend'); protected $fieldsRequiredLang = array('legend');
protected $fieldsSizeLang = array('legend' => 128); protected $fieldsSizeLang = array('legend' => 128);
protected $fieldsValidateLang = array('legend' => 'isGenericName'); protected $fieldsValidateLang = array('legend' => 'isGenericName');
protected $table = 'image'; protected $table = 'image';
protected $identifier = 'id_image'; protected $identifier = 'id_image';
protected static $_cacheGetSize = array(); protected static $_cacheGetSize = array();
public function __construct($id = NULL, $id_lang = NULL) public function __construct($id = NULL, $id_lang = NULL)
{ {
parent::__construct($id, $id_lang); parent::__construct($id, $id_lang);
$this->image_dir = _PS_PROD_IMG_DIR_; $this->image_dir = _PS_PROD_IMG_DIR_;
$this->source_index = _PS_PROD_IMG_DIR_.'index.php'; $this->source_index = _PS_PROD_IMG_DIR_.'index.php';
} }
public function getFields() public function getFields()
{ {
$this->validateFields(); $this->validateFields();
@@ -84,20 +87,20 @@ class ImageCore extends ObjectModel
$fields['cover'] = (int)($this->cover); $fields['cover'] = (int)($this->cover);
return $fields; return $fields;
} }
public function getTranslationsFieldsChild() public function getTranslationsFieldsChild()
{ {
$this->validateFieldsLang(); $this->validateFieldsLang();
return $this->getTranslationsFields(array('legend')); return $this->getTranslationsFields(array('legend'));
} }
public function delete() public function delete()
{ {
if (!parent::delete() || if (!parent::delete() ||
!$this->deleteProductAttributeImage() || !$this->deleteProductAttributeImage() ||
!$this->deleteImage()) !$this->deleteImage())
return false; return false;
// update positions // update positions
$result = Db::getInstance()->ExecuteS(' $result = Db::getInstance()->ExecuteS('
SELECT * SELECT *
@@ -105,16 +108,16 @@ class ImageCore extends ObjectModel
WHERE `id_product` = '.(int)$this->id_product.' WHERE `id_product` = '.(int)$this->id_product.'
ORDER BY `position`'); ORDER BY `position`');
$i = 1; $i = 1;
if ($result) if ($result)
foreach ($result AS $row) foreach ($result AS $row)
{ {
$row['position'] = $i++; $row['position'] = $i++;
Db::getInstance()->AutoExecute(_DB_PREFIX_.$this->table, $row, 'UPDATE', '`id_image` = '.(int)($row['id_image']), 1); Db::getInstance()->AutoExecute(_DB_PREFIX_.$this->table, $row, 'UPDATE', '`id_image` = '.(int)($row['id_image']), 1);
} }
return true; return true;
} }
/** /**
* Return available images for a product * Return available images for a product
* *
@@ -131,7 +134,7 @@ class ImageCore extends ObjectModel
WHERE i.`id_product` = '.(int)$id_product.' AND il.`id_lang` = '.(int)$id_lang.' WHERE i.`id_product` = '.(int)$id_product.' AND il.`id_lang` = '.(int)$id_lang.'
ORDER BY i.`position` ASC'); ORDER BY i.`position` ASC');
} }
/** /**
* Return Images * Return Images
* *
@@ -144,7 +147,7 @@ class ImageCore extends ObjectModel
FROM `'._DB_PREFIX_.'image` FROM `'._DB_PREFIX_.'image`
ORDER BY `id_image` ASC'); ORDER BY `id_image` ASC');
} }
/** /**
* Return number of images for a product * Return number of images for a product
* *
@@ -159,7 +162,7 @@ class ImageCore extends ObjectModel
WHERE `id_product` = '.(int)($id_product)); WHERE `id_product` = '.(int)($id_product));
return $result['total']; return $result['total'];
} }
/** /**
* Return highest position of images for a product * Return highest position of images for a product
* *
@@ -174,7 +177,7 @@ class ImageCore extends ObjectModel
WHERE `id_product` = '.(int)($id_product)); WHERE `id_product` = '.(int)($id_product));
return $result['max']; return $result['max'];
} }
/** /**
* Delete product cover * Delete product cover
* *
@@ -185,15 +188,15 @@ class ImageCore extends ObjectModel
{ {
if (!Validate::isUnsignedId($id_product)) if (!Validate::isUnsignedId($id_product))
die(Tools::displayError()); die(Tools::displayError());
if (file_exists(_PS_TMP_IMG_DIR_.'product_'.$id_product.'.jpg')) if (file_exists(_PS_TMP_IMG_DIR_.'product_'.$id_product.'.jpg'))
unlink(_PS_TMP_IMG_DIR_.'product_'.$id_product.'.jpg'); unlink(_PS_TMP_IMG_DIR_.'product_'.$id_product.'.jpg');
return Db::getInstance()->Execute(' return Db::getInstance()->Execute('
UPDATE `'._DB_PREFIX_.'image` UPDATE `'._DB_PREFIX_.'image`
SET `cover` = 0 SET `cover` = 0
WHERE `id_product` = '.(int)($id_product)); WHERE `id_product` = '.(int)($id_product));
} }
/** /**
*Get product cover *Get product cover
* *
@@ -203,11 +206,11 @@ class ImageCore extends ObjectModel
public static function getCover($id_product) public static function getCover($id_product)
{ {
return Db::getInstance()->getRow(' return Db::getInstance()->getRow('
SELECT * FROM `'._DB_PREFIX_.'image` SELECT * FROM `'._DB_PREFIX_.'image`
WHERE `id_product` = '.(int)($id_product).' WHERE `id_product` = '.(int)($id_product).'
AND `cover`= 1'); AND `cover`= 1');
} }
/** /**
* Copy images from a product to another * Copy images from a product to another
* *
@@ -288,34 +291,34 @@ class ImageCore extends ObjectModel
public function positionImage($position, $direction) public function positionImage($position, $direction)
{ {
Tools::displayAsDeprecated(); Tools::displayAsDeprecated();
$position = (int)($position); $position = (int)($position);
$direction = (int)($direction); $direction = (int)($direction);
// temporary position // temporary position
$high_position = Image::getHighestPosition($this->id_product) + 1; $high_position = Image::getHighestPosition($this->id_product) + 1;
Db::getInstance()->Execute(' Db::getInstance()->Execute('
UPDATE `'._DB_PREFIX_.'image` UPDATE `'._DB_PREFIX_.'image`
SET `position` = '.(int)($high_position).' SET `position` = '.(int)($high_position).'
WHERE `id_product` = '.(int)($this->id_product).' WHERE `id_product` = '.(int)($this->id_product).'
AND `position` = '.($direction ? $position - 1 : $position + 1)); AND `position` = '.($direction ? $position - 1 : $position + 1));
Db::getInstance()->Execute(' Db::getInstance()->Execute('
UPDATE `'._DB_PREFIX_.'image` UPDATE `'._DB_PREFIX_.'image`
SET `position` = `position`'.($direction ? '-1' : '+1').' SET `position` = `position`'.($direction ? '-1' : '+1').'
WHERE `id_image` = '.(int)($this->id)); WHERE `id_image` = '.(int)($this->id));
Db::getInstance()->Execute(' Db::getInstance()->Execute('
UPDATE `'._DB_PREFIX_.'image` UPDATE `'._DB_PREFIX_.'image`
SET `position` = '.$this->position.' SET `position` = '.$this->position.'
WHERE `id_product` = '.(int)($this->id_product).' WHERE `id_product` = '.(int)($this->id_product).'
AND `position` = '.(int)($high_position)); AND `position` = '.(int)($high_position));
} }
/** /**
* Change an image position and update relative positions * Change an image position and update relative positions
* *
* @param int $way position is moved up if 0, moved down if 1 * @param int $way position is moved up if 0, moved down if 1
* @param int $position new position of the moved image * @param int $position new position of the moved image
* @return int success * @return int success
@@ -324,7 +327,7 @@ class ImageCore extends ObjectModel
{ {
if (!isset($this->id) || !$position) if (!isset($this->id) || !$position)
return false; return false;
// < and > statements rather than BETWEEN operator // < and > statements rather than BETWEEN operator
// since BETWEEN is treated differently according to databases // since BETWEEN is treated differently according to databases
$result = (Db::getInstance()->Execute(' $result = (Db::getInstance()->Execute('
@@ -342,14 +345,14 @@ class ImageCore extends ObjectModel
return $result; return $result;
} }
public static function getSize($type) public static function getSize($type)
{ {
if (!isset(self::$_cacheGetSize[$type]) OR self::$_cacheGetSize[$type] === NULL) if (!isset(self::$_cacheGetSize[$type]) OR self::$_cacheGetSize[$type] === NULL)
self::$_cacheGetSize[$type] = Db::getInstance()->getRow('SELECT `width`, `height` FROM '._DB_PREFIX_.'image_type WHERE `name` = \''.pSQL($type).'\''); self::$_cacheGetSize[$type] = Db::getInstance()->getRow('SELECT `width`, `height` FROM '._DB_PREFIX_.'image_type WHERE `name` = \''.pSQL($type).'\'');
return self::$_cacheGetSize[$type]; return self::$_cacheGetSize[$type];
} }
/** /**
* Clear all images in tmp dir * Clear all images in tmp dir
*/ */
@@ -370,7 +373,7 @@ class ImageCore extends ObjectModel
WHERE `id_image` = '.(int)($this->id) WHERE `id_image` = '.(int)($this->id)
); );
} }
/** /**
* Delete the product image from disk and remove the containing folder if empty * Delete the product image from disk and remove the containing folder if empty
* Handles both legacy and new image filesystems * Handles both legacy and new image filesystems
@@ -379,20 +382,20 @@ class ImageCore extends ObjectModel
{ {
if (!$this->id) if (!$this->id)
return false; return false;
// Delete base image // Delete base image
if (file_exists($this->image_dir.$this->getExistingImgPath().'.'.$this->image_format)) if (file_exists($this->image_dir.$this->getExistingImgPath().'.'.$this->image_format))
unlink($this->image_dir.$this->getExistingImgPath().'.'.$this->image_format); unlink($this->image_dir.$this->getExistingImgPath().'.'.$this->image_format);
else else
return false; return false;
$files_to_delete = array(); $files_to_delete = array();
// Delete auto-generated images // Delete auto-generated images
$imageTypes = ImageType::getImagesTypes(); $imageTypes = ImageType::getImagesTypes();
foreach ($imageTypes AS $imageType) foreach ($imageTypes AS $imageType)
$files_to_delete[] = $this->image_dir.$this->getExistingImgPath().'-'.$imageType['name'].'.'.$this->image_format; $files_to_delete[] = $this->image_dir.$this->getExistingImgPath().'-'.$imageType['name'].'.'.$this->image_format;
// Delete watermark image // Delete watermark image
$files_to_delete[] = $this->image_dir.$this->getExistingImgPath().'-watermark.'.$this->image_format; $files_to_delete[] = $this->image_dir.$this->getExistingImgPath().'-watermark.'.$this->image_format;
// delete index.php // delete index.php
@@ -400,11 +403,11 @@ class ImageCore extends ObjectModel
// Delete tmp images // Delete tmp images
$files_to_delete[] = _PS_TMP_IMG_DIR_.'product_'.$this->id_product.'.'.$this->image_format; $files_to_delete[] = _PS_TMP_IMG_DIR_.'product_'.$this->id_product.'.'.$this->image_format;
$files_to_delete[] = _PS_TMP_IMG_DIR_.'product_mini_'.$this->id_product.'.'.$this->image_format; $files_to_delete[] = _PS_TMP_IMG_DIR_.'product_mini_'.$this->id_product.'.'.$this->image_format;
foreach ($files_to_delete as $file) foreach ($files_to_delete as $file)
if (file_exists($file) && !@unlink($file)) if (file_exists($file) && !@unlink($file))
return false; return false;
// Can we delete the image folder? // Can we delete the image folder?
if (is_dir($this->image_dir.$this->getImgFolder())) if (is_dir($this->image_dir.$this->getImgFolder()))
{ {
@@ -415,16 +418,16 @@ class ImageCore extends ObjectModel
$delete_folder = false; $delete_folder = false;
break; break;
} }
} }
if (isset($delete_folder) && $delete_folder) if (isset($delete_folder) && $delete_folder)
@rmdir($this->image_dir.$this->getImgFolder()); @rmdir($this->image_dir.$this->getImgFolder());
return true; return true;
} }
/** /**
* Recursively deletes all product images in the given folder tree and removes empty folders. * Recursively deletes all product images in the given folder tree and removes empty folders.
* *
* @param string $path folder containing the product images to delete * @param string $path folder containing the product images to delete
* @param string $format image format * @param string $format image format
* @return bool success * @return bool success
@@ -436,11 +439,11 @@ class ImageCore extends ObjectModel
foreach (scandir($path) as $file) foreach (scandir($path) as $file)
{ {
if (preg_match('/^[0-9]+(\-(.*))?\.'.$format.'$/', $file)) if (preg_match('/^[0-9]+(\-(.*))?\.'.$format.'$/', $file))
unlink($path.$file); unlink($path.$file);
else if (is_dir($path.$file) && (preg_match('/^[0-9]$/', $file))) else if (is_dir($path.$file) && (preg_match('/^[0-9]$/', $file)))
self::deleteAllImages($path.$file.'/', $format); self::deleteAllImages($path.$file.'/', $format);
} }
// Can we remove the image folder? // Can we remove the image folder?
$remove_folder = true; $remove_folder = true;
foreach (scandir($path) as $file) foreach (scandir($path) as $file)
@@ -455,22 +458,22 @@ class ImageCore extends ObjectModel
// we're only removing index.php if it's a folder we want to delete // we're only removing index.php if it's a folder we want to delete
if (file_exists($path.'index.php')) if (file_exists($path.'index.php'))
@unlink ($path.'index.php'); @unlink ($path.'index.php');
@rmdir($path); @rmdir($path);
} }
return true; return true;
} }
/** /**
* Returns image path in the old or in the new filesystem * Returns image path in the old or in the new filesystem
* *
* @ returns string image path * @ returns string image path
*/ */
public function getExistingImgPath() public function getExistingImgPath()
{ {
if (!$this->id) if (!$this->id)
return false; return false;
if (!$this->existing_path) if (!$this->existing_path)
{ {
if (Configuration::get('PS_LEGACY_IMAGES') && file_exists(_PS_PROD_IMG_DIR_.$this->id_product.'-'.$this->id.'.'.$this->image_format)) if (Configuration::get('PS_LEGACY_IMAGES') && file_exists(_PS_PROD_IMG_DIR_.$this->id_product.'-'.$this->id.'.'.$this->image_format))
@@ -481,62 +484,62 @@ class ImageCore extends ObjectModel
return $this->existing_path; return $this->existing_path;
} }
/** /**
* Returns the path to the folder containing the image in the new filesystem * Returns the path to the folder containing the image in the new filesystem
* *
* @return string path to folder * @return string path to folder
*/ */
public function getImgFolder() public function getImgFolder()
{ {
if (!$this->id) if (!$this->id)
return false; return false;
if (!$this->folder) if (!$this->folder)
$this->folder = self::getImgFolderStatic($this->id); $this->folder = self::getImgFolderStatic($this->id);
return $this->folder; return $this->folder;
} }
/** /**
* Create parent folders for the image in the new filesystem * Create parent folders for the image in the new filesystem
* *
* @return bool success * @return bool success
*/ */
public function createImgFolder() public function createImgFolder()
{ {
if (!$this->id) if (!$this->id)
return false; return false;
if (!file_exists(_PS_PROD_IMG_DIR_.$this->getImgFolder())) if (!file_exists(_PS_PROD_IMG_DIR_.$this->getImgFolder()))
{ {
// Apparently sometimes mkdir cannot set the rights, and sometimes chmod can't. Trying both. // Apparently sometimes mkdir cannot set the rights, and sometimes chmod can't. Trying both.
$success = @mkdir(_PS_PROD_IMG_DIR_.$this->getImgFolder(), 0755, true) $success = @mkdir(_PS_PROD_IMG_DIR_.$this->getImgFolder(), $access_rights, true)
|| @chmod(_PS_PROD_IMG_DIR_.$this->getImgFolder(), 0755); || @chmod(_PS_PROD_IMG_DIR_.$this->getImgFolder(), $access_rights);
// Create an index.php file in the new folder // Create an index.php file in the new folder
if ($success if ($success
&& !file_exists(_PS_PROD_IMG_DIR_.$this->getImgFolder().'index.php') && !file_exists(_PS_PROD_IMG_DIR_.$this->getImgFolder().'index.php')
&& file_exists($this->source_index)) && file_exists($this->source_index))
return @copy($this->source_index, _PS_PROD_IMG_DIR_.$this->getImgFolder().'index.php'); return @copy($this->source_index, _PS_PROD_IMG_DIR_.$this->getImgFolder().'index.php');
} }
return true; return true;
} }
/** /**
* Returns the path to the image without file extension * Returns the path to the image without file extension
* *
* @return string path * @return string path
*/ */
public function getImgPath() public function getImgPath()
{ {
if (!$this->id) if (!$this->id)
return false; return false;
$path = $this->getImgFolder().$this->id; $path = $this->getImgFolder().$this->id;
return $path; return $path;
} }
/** /**
* Returns the path to the folder containing the image in the new filesystem * Returns the path to the folder containing the image in the new filesystem
* *
@@ -548,7 +551,7 @@ class ImageCore extends ObjectModel
if (!is_numeric($id_image)) if (!is_numeric($id_image))
return false; return false;
$folders = str_split((string)$id_image); $folders = str_split((string)$id_image);
return implode('/', $folders).'/'; return implode('/', $folders).'/';
} }
/** /**
@@ -578,7 +581,7 @@ class ImageCore extends ObjectModel
// create the new folder if it does not exist // create the new folder if it does not exist
if (!$image->createImgFolder()) if (!$image->createImgFolder())
return false; return false;
// if there's already a file at the new image path, move it to a dump folder // if there's already a file at the new image path, move it to a dump folder
// most likely the preexisting image is a demo image not linked to a product and it's ok to replace it // most likely the preexisting image is a demo image not linked to a product and it's ok to replace it
$new_path = _PS_PROD_IMG_DIR_.$image->getImgPath().(isset($matches[3]) ? $matches[3] : '').'.jpg'; $new_path = _PS_PROD_IMG_DIR_.$image->getImgPath().(isset($matches[3]) ? $matches[3] : '').'.jpg';
@@ -586,8 +589,8 @@ class ImageCore extends ObjectModel
{ {
if(!file_exists(_PS_PROD_IMG_DIR_.$tmp_folder)) if(!file_exists(_PS_PROD_IMG_DIR_.$tmp_folder))
{ {
@mkdir(_PS_PROD_IMG_DIR_.$tmp_folder, 0755); @mkdir(_PS_PROD_IMG_DIR_.$tmp_folder, $access_rights);
@chmod(_PS_PROD_IMG_DIR_.$tmp_folder, 0755); @chmod(_PS_PROD_IMG_DIR_.$tmp_folder, $access_rights);
} }
$tmp_path = _PS_PROD_IMG_DIR_.$tmp_folder.basename($file); $tmp_path = _PS_PROD_IMG_DIR_.$tmp_folder.basename($file);
if (!@rename($new_path, $tmp_path) || !file_exists($tmp_path)) if (!@rename($new_path, $tmp_path) || !file_exists($tmp_path))
@@ -603,7 +606,7 @@ class ImageCore extends ObjectModel
} }
return true; return true;
} }
public static function testFileSystem() public static function testFileSystem()
{ {
$safe_mode = ini_get('safe_mode'); $safe_mode = ini_get('safe_mode');
@@ -618,8 +621,8 @@ class ImageCore extends ObjectModel
} }
if (file_exists($test_folder)) if (file_exists($test_folder))
return false; return false;
@mkdir($test_folder, 0755, true); @mkdir($test_folder, $access_rights, true);
@chmod($test_folder, 0755); @chmod($test_folder, $access_rights);
if (!is_writeable($test_folder)) if (!is_writeable($test_folder))
return false; return false;
@rmdir($test_folder); @rmdir($test_folder);
@@ -628,11 +631,11 @@ class ImageCore extends ObjectModel
return false; return false;
return true; return true;
} }
/** /**
* Returns the path where a product image should be created (without file format) * Returns the path where a product image should be created (without file format)
* *
* @return string path * @return string path
*/ */
public function getPathForCreation() public function getPathForCreation()
{ {