673 lines
18 KiB
PHP
673 lines
18 KiB
PHP
<?php
|
|
/**
|
|
* Since 2013 Ovidiu Cimpean.
|
|
*
|
|
* Ovidiu Cimpean - Newsletter Pro © All rights reserved.
|
|
*
|
|
* DISCLAIMER
|
|
*
|
|
* Do not edit, modify or copy this file.
|
|
* If you wish to customize it, contact us at addons4prestashop@gmail.com.
|
|
*
|
|
* @author Ovidiu Cimpean <addons4prestashop@gmail.com>
|
|
* @copyright Since 2013 Ovidiu Cimpean
|
|
* @license Do not edit, modify or copy this file
|
|
*
|
|
* @version Release: 4
|
|
*/
|
|
|
|
use PQNP\Config;
|
|
|
|
class NewsletterProUpgrade
|
|
{
|
|
public $context;
|
|
|
|
public $module;
|
|
|
|
public $errors = [];
|
|
|
|
/**
|
|
* @var NewsletterProCookie
|
|
*/
|
|
public static $warningCookie = null;
|
|
|
|
public function __construct()
|
|
{
|
|
$this->context = Context::getContext();
|
|
$this->module = NewsletterPro::getInstance();
|
|
}
|
|
|
|
public static function getCookie()
|
|
{
|
|
if (!isset(self::$warningCookie)) {
|
|
self::$warningCookie = new NewsletterProCookie('pqnp_update_warning', time() + 108000);
|
|
}
|
|
|
|
return self::$warningCookie;
|
|
}
|
|
|
|
/**
|
|
* Update the database configuration
|
|
* If the configuration not exist the value will be created.
|
|
*
|
|
* @param string $name Condiguration name
|
|
* @param string $value Configuration value
|
|
*
|
|
* @return bool Return true if success
|
|
*/
|
|
public function updateConfiguration($name, $value)
|
|
{
|
|
try {
|
|
if (!Config::write($name, $value)) {
|
|
$this->addError(sprintf($this->module->l('Cannot update the configuration with the name "%s".'), $name));
|
|
|
|
return false;
|
|
}
|
|
} catch (Exception $e) {
|
|
$this->addError($e->getMessage());
|
|
|
|
return false;
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
public function deleteConfiguration($name)
|
|
{
|
|
try {
|
|
if (!Config::delete($name)) {
|
|
$this->addError(sprintf($this->module->l('Cannot delete the configuration with the name "%s".'), $name));
|
|
|
|
return false;
|
|
}
|
|
} catch (Exception $e) {
|
|
$this->addError($e->getMessage());
|
|
|
|
return false;
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
public function deletePSConfiguration($name)
|
|
{
|
|
try {
|
|
if (Configuration::hasKey($name)) {
|
|
if (!Configuration::deleteByName($name)) {
|
|
$this->addError(sprintf($this->module->l('Cannot delete the ps configuration with the name "%s".'), $name));
|
|
|
|
return false;
|
|
}
|
|
}
|
|
} catch (Exception $e) {
|
|
$this->addError($e->getMessage());
|
|
|
|
return false;
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
public function updatePSConfiguration($name, $value, $html = false, $id_shop_group = null, $id_shop = null)
|
|
{
|
|
try {
|
|
if (!Configuration::updateValue($name, $value, $html, $id_shop_group, $id_shop)) {
|
|
$this->addError(sprintf($this->module->l('Cannot update the ps configuration with the name "%s".'), $name));
|
|
|
|
return false;
|
|
}
|
|
} catch (Exception $e) {
|
|
$this->addError($e->getMessage());
|
|
|
|
return false;
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
public function createTable($name, $body)
|
|
{
|
|
try {
|
|
$this->refreshDb();
|
|
|
|
$sql = 'CREATE TABLE IF NOT EXISTS `'._DB_PREFIX_.$name.'` (';
|
|
$sql .= ' '.$body.' ';
|
|
$sql .= ') ENGINE='._MYSQL_ENGINE_.' DEFAULT CHARSET=utf8; ';
|
|
|
|
if (!Db::getInstance()->execute($sql)) {
|
|
$this->addError(sprintf($this->module->l('Cannot create the table "%s".'), _DB_PREFIX_.$name));
|
|
|
|
return false;
|
|
}
|
|
} catch (Exception $e) {
|
|
$this->addError($e->getMessage());
|
|
|
|
return false;
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
public function hasPrimaryKey($table)
|
|
{
|
|
$results = Db::getInstance()->executeS('SHOW INDEXES FROM `'._DB_PREFIX_.$table.'` WHERE `Key_name` = "PRIMARY"');
|
|
|
|
return count($results) > 0;
|
|
}
|
|
|
|
public function setPrimaryKey($table, $query)
|
|
{
|
|
try {
|
|
if ($this->tableExists($table) && !$this->hasPrimaryKey($table)) {
|
|
$this->refreshDb();
|
|
|
|
if (!Db::getInstance()->execute($query)) {
|
|
$this->addError(sprintf($this->module->l('Cannot set the primary key in the table "%s".'), $table));
|
|
|
|
return false;
|
|
}
|
|
}
|
|
} catch (Exception $e) {
|
|
$this->addError($e->getMessage());
|
|
|
|
return false;
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
public function alter($table, $query)
|
|
{
|
|
try {
|
|
if ($this->tableExists($table)) {
|
|
$this->refreshDb();
|
|
|
|
if (0 == Tools::strlen(trim($query))) {
|
|
return true;
|
|
}
|
|
|
|
$query = 'ALTER TABLE `'._DB_PREFIX_.$table.'` '."\n".$query;
|
|
|
|
if (!Db::getInstance()->execute($query)) {
|
|
$this->addError(sprintf($this->module->l('Cannot update the table "%s".'), $table));
|
|
|
|
return false;
|
|
}
|
|
}
|
|
} catch (Exception $e) {
|
|
$this->addError($e->getMessage());
|
|
|
|
return false;
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
public function addColumnIfNotExists($table, $column, $query, $comma = true)
|
|
{
|
|
if ($this->columnExists($table, $column)) {
|
|
return '';
|
|
}
|
|
|
|
return ' ADD COLUMN `'.$column.'` '.trim($query).($comma ? ',' : '');
|
|
}
|
|
|
|
public function addColumn($table, $name, $value, $after = null)
|
|
{
|
|
try {
|
|
if ($this->tableExists($table) && !$this->columnExists($table, $name)) {
|
|
$this->refreshDb();
|
|
|
|
$sql = '';
|
|
$sql .= 'ALTER TABLE `'._DB_PREFIX_.$table.'` ';
|
|
$sql .= 'ADD COLUMN ';
|
|
$sql .= $value.' ';
|
|
|
|
if (isset($after)) {
|
|
$sql .= 'AFTER `'.$after.'` ';
|
|
}
|
|
|
|
if (!Db::getInstance()->execute($sql)) {
|
|
$this->addError(sprintf($this->module->l('Cannot add the column "%s" in the table "%s".'), $name, $table));
|
|
|
|
return false;
|
|
}
|
|
}
|
|
} catch (Exception $e) {
|
|
$this->addError($e->getMessage());
|
|
|
|
return false;
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
public function renameTable($table, $new_name)
|
|
{
|
|
try {
|
|
if ($this->tableExists($table)) {
|
|
$this->refreshDb();
|
|
|
|
$sql = 'RENAME TABLE `'._DB_PREFIX_.$table.'` TO `'._DB_PREFIX_.$new_name.'`';
|
|
if (!Db::getInstance()->execute($sql)) {
|
|
$this->addError(sprintf($this->module->l('Cannot rename the table "%s" to "%s".'), $table, $new_name));
|
|
|
|
return false;
|
|
}
|
|
}
|
|
} catch (Exception $e) {
|
|
$this->addError($e->getMessage());
|
|
|
|
return false;
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
public function changeColumn($table, $name, $value)
|
|
{
|
|
try {
|
|
if ($this->tableExists($table) && $this->columnExists($table, $name)) {
|
|
$this->refreshDb();
|
|
|
|
$sql = '';
|
|
$sql .= 'ALTER TABLE `'._DB_PREFIX_.$table.'` ';
|
|
$sql .= 'CHANGE COLUMN `'.$name.'` ';
|
|
$sql .= $value;
|
|
|
|
if (!Db::getInstance()->execute($sql)) {
|
|
$this->addError(sprintf($this->module->l('Cannot change the column "%s" from the table "%s".'), $name, $table));
|
|
|
|
return false;
|
|
}
|
|
}
|
|
} catch (Exception $e) {
|
|
$this->addError($e->getMessage());
|
|
|
|
return false;
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
public function deleteColumn($table, $name)
|
|
{
|
|
try {
|
|
if ($this->tableExists($table) && $this->columnExists($table, $name)) {
|
|
$this->refreshDb();
|
|
|
|
$sql = 'ALTER TABLE `'._DB_PREFIX_.$table.'` DROP COLUMN `'.$name.'`';
|
|
if (!Db::getInstance()->execute($sql)) {
|
|
$this->addError(sprintf($this->module->l('Cannot delete the column "%s" from the table "%s".'), $name, $table));
|
|
|
|
return false;
|
|
}
|
|
}
|
|
} catch (Exception $e) {
|
|
$this->addError($e->getMessage());
|
|
|
|
return false;
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
public function deleteTable($table)
|
|
{
|
|
try {
|
|
if ($this->tableExists($table)) {
|
|
$this->refreshDb();
|
|
|
|
$sql = 'DROP TABLE IF EXISTS `'._DB_PREFIX_.$table.'`;';
|
|
|
|
if (!Db::getInstance()->execute($sql)) {
|
|
$this->addError(sprintf($this->module->l('Cannot delete the table "%s".'), $table));
|
|
|
|
return false;
|
|
}
|
|
}
|
|
} catch (Exception $e) {
|
|
$this->addError($e->getMessage());
|
|
|
|
return false;
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
public function addIndex($table, $name)
|
|
{
|
|
try {
|
|
if ($this->tableExists($table) && !$this->hasIndex($table, $name)) {
|
|
$this->refreshDb();
|
|
|
|
$sql = '';
|
|
$sql .= 'ALTER TABLE `'._DB_PREFIX_.$table.'` ';
|
|
$sql .= 'ADD INDEX `'.$name.'` (`'.$name.'`)';
|
|
|
|
if (!Db::getInstance()->execute($sql)) {
|
|
$this->addError(sprintf($this->module->l('Cannot add the index "%s" to the table "%s".'), $name, $table));
|
|
|
|
return false;
|
|
}
|
|
}
|
|
} catch (Exception $e) {
|
|
$this->addError($e->getMessage());
|
|
|
|
return false;
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
public function registerHook($name)
|
|
{
|
|
try {
|
|
if (!$this->module->registerHook($name)) {
|
|
$this->addError(sprintf($this->module->l('Cannot register the hook "%s".'), $name));
|
|
|
|
return false;
|
|
}
|
|
} catch (Exception $e) {
|
|
$this->addError($e->getMessage());
|
|
|
|
return false;
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
public function unregisterHook($name)
|
|
{
|
|
try {
|
|
if (!$this->module->unregisterHook($name)) {
|
|
$this->addError(sprintf($this->module->l('Cannot unregister the hook "%s".'), $name));
|
|
|
|
return false;
|
|
}
|
|
} catch (Exception $e) {
|
|
$this->addError($e->getMessage());
|
|
|
|
return false;
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
public function columnExists($table, $name)
|
|
{
|
|
$this->refreshDb();
|
|
|
|
return Db::getInstance()->getValue(
|
|
"
|
|
SELECT COUNT(*)
|
|
FROM INFORMATION_SCHEMA.COLUMNS
|
|
WHERE
|
|
TABLE_SCHEMA = '"._DB_NAME_."'
|
|
AND TABLE_NAME = '"._DB_PREFIX_.pSQL($table)."'
|
|
AND COLUMN_NAME = '".pSQL($name)."'"
|
|
);
|
|
}
|
|
|
|
public function addError($error)
|
|
{
|
|
$this->errors[] = $error;
|
|
}
|
|
|
|
public function mergeErrors($errors)
|
|
{
|
|
$this->errors = array_merge($this->errors, $errors);
|
|
}
|
|
|
|
public function getErrors()
|
|
{
|
|
return $this->errors;
|
|
}
|
|
|
|
public function hasErrors()
|
|
{
|
|
return !empty($this->errors);
|
|
}
|
|
|
|
public function success()
|
|
{
|
|
return empty($this->errors);
|
|
}
|
|
|
|
/**
|
|
* @param string|null $fromVersion
|
|
*
|
|
* @return bool
|
|
*
|
|
* @throws PrestaShopDatabaseException
|
|
*/
|
|
public function execute($fromVersion = null)
|
|
{
|
|
$files = $this->getUpgradeFiles($fromVersion);
|
|
|
|
foreach ($files as $file) {
|
|
if (file_exists($file['path'])) {
|
|
require_once $file['path'];
|
|
|
|
$function_name = 'upgrade_module_'.str_replace('.', '_', $file['version']);
|
|
|
|
if (function_exists($function_name)) {
|
|
if (!call_user_func($function_name, $this->module)) {
|
|
$this->addError(sprintf($this->module->l('Update failed at the version "%s".'), $file['version']));
|
|
}
|
|
} else {
|
|
$this->addError(sprintf($this->module->l('The update function "%s" not exists.'), $function_name));
|
|
}
|
|
} else {
|
|
$this->addError(sprintf($this->module->l('The file "%s" not exists.'), $file['name']));
|
|
}
|
|
}
|
|
|
|
if ($this->success()) {
|
|
if (!$this->updateDbVersion($this->module->version)) {
|
|
$this->addError($this->module->l('Cannot update the database version.'));
|
|
|
|
return false;
|
|
}
|
|
|
|
try {
|
|
if (pqnp_config('DEBUG_MODE')) {
|
|
$this->module->clearCache();
|
|
} else {
|
|
@$this->module->clearCache();
|
|
}
|
|
} catch (Exception $e) {
|
|
NewsletterProLog::writeStrip($e->getMessage(), NewsletterProLog::ERROR_FILE);
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
return false;
|
|
}
|
|
|
|
public function versionToFloat($version)
|
|
{
|
|
return (float) ('0.'.trim(str_replace('.', '', $version)));
|
|
}
|
|
|
|
/**
|
|
* @param string|null $fromVersion
|
|
*
|
|
* @return array
|
|
*/
|
|
public function getUpgradeFiles($fromVersion = null)
|
|
{
|
|
$files = [];
|
|
|
|
$version = $this->getDbVersion();
|
|
if (isset($fromVersion)) {
|
|
$version = $fromVersion;
|
|
}
|
|
|
|
$directory = new DirectoryIterator(dirname(__FILE__).'/../upgrade/');
|
|
$iterator = new RegexIterator($directory, '/^Upgrade-/', RecursiveRegexIterator::MATCH);
|
|
|
|
foreach ($iterator as $key => $file) {
|
|
if (preg_match('/^Upgrade-(?P<version>.*)\.php/', $file->getFilename(), $match)) {
|
|
// This will include the current targeted version
|
|
$equal = false;
|
|
if (isset($fromVersion)) {
|
|
$equal = 0 == version_compare($match['version'], $version);
|
|
}
|
|
|
|
$grather = 1 == version_compare($match['version'], $version);
|
|
if ($grather || $equal) {
|
|
$files[$key]['name'] = $file->getFilename();
|
|
$files[$key]['path'] = $file->getPathName();
|
|
$files[$key]['version'] = trim($match['version']);
|
|
}
|
|
}
|
|
}
|
|
|
|
usort($files, 'NewsletterProUpgrade::sortFilesByVersion');
|
|
|
|
return $files;
|
|
}
|
|
|
|
public static function sortFilesByVersion($a, $b)
|
|
{
|
|
return version_compare($a['version'], $b['version']);
|
|
}
|
|
|
|
public function getDbVersion()
|
|
{
|
|
return NewsletterProTools::getDbVersion();
|
|
}
|
|
|
|
public function updateDbVersion($version)
|
|
{
|
|
return Db::getInstance()->update('module', [
|
|
'version' => trim($version),
|
|
], '`name` = "'.pSQL($this->module->name).'"');
|
|
}
|
|
|
|
public function updateTabName($new_name = 'Newsletter Pro')
|
|
{
|
|
if ($id = (int) Tab::getIdFromClassName($this->module->class_name)) {
|
|
return Db::getInstance()->update('tab_lang', [
|
|
'name' => pSQL($new_name),
|
|
], '`id_tab` = '.(int) $id);
|
|
}
|
|
|
|
return false;
|
|
}
|
|
|
|
public function tableExists($name)
|
|
{
|
|
$this->refreshDb();
|
|
|
|
$sql = "SELECT COUNT(*) AS `count`
|
|
FROM INFORMATION_SCHEMA.TABLES
|
|
WHERE TABLE_SCHEMA = '"._DB_NAME_."'
|
|
AND TABLE_NAME = '"._DB_PREFIX_.$name."';";
|
|
|
|
return Db::getInstance()->getValue($sql);
|
|
}
|
|
|
|
public function hasIndex($table, $key_name)
|
|
{
|
|
$result = Db::getInstance()->executeS('SHOW INDEX FROM `'._DB_PREFIX_.$table.'` WHERE `Key_name` = "'.$key_name.'"');
|
|
|
|
return !empty($result);
|
|
}
|
|
|
|
public function valueExists($table, $field, $value)
|
|
{
|
|
$sql = 'SELECT COUNT(*) FROM `'._DB_PREFIX_.$table.'` WHERE `'.$field.'` = "'.$value.'"';
|
|
|
|
return Db::getInstance()->getValue($sql);
|
|
}
|
|
|
|
public function insertValue($table, $insert)
|
|
{
|
|
try {
|
|
$this->refreshDb();
|
|
|
|
if (!Db::getInstance()->insert($table, $insert)) {
|
|
$this->addError(sprintf($this->module->l('Cannot insert the value into the table table "%s".'), $table));
|
|
|
|
return false;
|
|
}
|
|
} catch (Exception $e) {
|
|
$this->addError($e->getMessage());
|
|
|
|
return false;
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
public function refreshDb()
|
|
{
|
|
$db = Db::getInstance();
|
|
$db->disconnect();
|
|
$db->connect();
|
|
}
|
|
|
|
public function showCacheWarning()
|
|
{
|
|
$this->updateConfiguration('SHOW_CLEAR_CACHE', 1);
|
|
}
|
|
|
|
public static function showWarningMessage($value)
|
|
{
|
|
if (!is_array($value)) {
|
|
$value = [$value];
|
|
}
|
|
|
|
$cookie = self::getCookie();
|
|
|
|
if (!$cookie->exists('content')) {
|
|
$cookie->set('content', []);
|
|
}
|
|
|
|
$content = $cookie->get('content');
|
|
|
|
if (!is_array($content)) {
|
|
$content = [];
|
|
}
|
|
|
|
foreach ($value as $key => $str) {
|
|
if (is_numeric($key)) {
|
|
if (!in_array($str, $content)) {
|
|
$content[] = $str;
|
|
} elseif (' ' === $str) {
|
|
$content[] = $str;
|
|
}
|
|
} else {
|
|
$content[$key] = $str;
|
|
}
|
|
}
|
|
|
|
$cookie->set('content', $content);
|
|
}
|
|
|
|
public static function clearWarningCookie()
|
|
{
|
|
$cookie = new NewsletterProCookie('pqnp_update_warning');
|
|
$cookie->destroy();
|
|
}
|
|
|
|
public static function getWarningContent()
|
|
{
|
|
$cookie = self::getCookie();
|
|
if (!$cookie->exists('content')) {
|
|
return [];
|
|
}
|
|
|
|
$content = $cookie->get('content');
|
|
|
|
if (!is_array($content)) {
|
|
return [];
|
|
}
|
|
|
|
return $content;
|
|
}
|
|
}
|