Jump to content

Writing modules - How about safe override on install/uninstall


fransjaeger

Recommended Posts

Hi

 

Im often facing the worries that my module will cause damage when overriding or deleting overrided files.

 

Is there any simple and yet powerfull way to solve this?

 

I imagine something like this could be a part of PS core: (that would really make it less worrisome to write a module)

 

on install

i would like it to check if file already exist, if it doesnt just copy file, else check if my function(s) is already in there, and if not, then add tmy functions, wrapped in a unique flag or something + add a flag that developer can remove if he/she is editing the function code.

 

on uninstall

only delete file/functions if nothing has been changed (check if flags is still there and only delete file if no other functions exist in file)

if other functioons inside file, then only delete module-related functions and leave rest of file alone

Edited by michaelhjulskov (see edit history)
  • Like 1
Link to comment
Share on other sites

Hi,

 

while you will add override/class or override/controllers folder inside your module, Prestashop will automatically check override functions. If we are talking about chnage .tpl files inside theme while installation (or something similar), than you can add need checks in your code.

And one of the `best-practicies` is add inside every overrided method check is module active now, because it isn't default behaviour.

 

Best Regards

Link to comment
Share on other sites

while you will add override/class or override/controllers folder inside your module, Prestashop will automatically check override functions. 

I dont think thats correct

are you saying that i dont need to copy any files inside the install() function?

are you saying that PS will not ever delete or override a file in override, that contains functions used by other modules. 

are you saying that PS can merge two overridden files into one

I dont think so

IF youre right though, its really cool - and I would like to see the class/controller that take care of this, so that I can see how its build.

Link to comment
Share on other sites

Wow, its true :)

Looks like its already there, but why isnt people using it then :) when they build a module. Hmmm. Ive seen many modules that do the override in stupid ways with fatal consequences for other modules. So I guess I gotta learn how to use this. Thanks for enlighting me.

Link to comment
Share on other sites

Wow, its true :)

Looks like its already there, but why isnt people using it then :) when they build a module. Hmmm. Ive seen many modules that do the override in stupid ways with fatal consequences for other modules. So I guess I gotta learn how to use this. Thanks for enlighting me.

Because there was life before PS v1.5 and v1.6 where these enhancements were made.  Modules used to have to install their own overrides

Link to comment
Share on other sites

  • 1 month later...

I have created a simple module for testing override. When Installing the files are placing correctly but while uninstalling they are not getting deleted. More strange thing is the class overrides removes some lines from the override class file. Any suggestion experts.

Link to comment
Share on other sites

from what I understand you saying, this is all expected behavior

I thought it removes the override files automatically. But why it erases code from the class override instead of deleting that file completely ?

Link to comment
Share on other sites

Can you help me or suggest me something.

 

I just want to change the URLs of cms pages and I am getting succeeded but I want to make it as module so it'll be easy to add/remove the feature.  

 

Currently I am overriding the default routes(Parameters in the routes) in Dispather.php. No function is there.

 

I am also overriding the controller/front/Cmscontroller.php.

 

Please give me some idea so that,

 

#1 I can delete the files while uninstalling the module

#2 Disable the override if the module is disabled.

 

I know we can check (Module::isEnabled('mymodule')). But how can I use it in a class or controller override file ?

 

 

I'll appreciate any help.

Link to comment
Share on other sites

I thought it removes the override files automatically. But why it erases code from the class override instead of deleting that file completely ?

It does not remove the file, it only removes the code that your module added to the file.  It is just the way they designed it to work.

 

#1 I can delete the files while uninstalling the module

 

It should not be necessary, Prestashop should remove the code from the override.  You should not attempt to remove the file, because there may be other modules overriding the same class/controller, and you will break that other module if you remove it

 

#2 Disable the override if the module is disabled

You should always protect the code in your override.  There are buggy PS versions that do not properly remove the override, so a simple check in your code is all you need

        $module = Module::getInstanceByName('modulename');
        if ($module->active)
        {
            //do you override code
        }
  • Like 2
Link to comment
Share on other sites

Hi Bellini,

I have tried to add that code after declaring the class name but the module is getting failed to installed.

class Dispatcher extends DispatcherCore
{
	$module = Module::getInstanceByName('cleancmsurl');

    if ($module->active)
    {
		public $default_routes = array(

The following module(s) could not be installed properly:

  • cleancmsurls : 
        Unable to install override: Class DispatcherOverride551e95c7647dc does not exist

So I have installed previous version and tried to add the condition to check but it also thros error

 

Parse error: syntax error, unexpected '$module' (T_VARIABLE), expecting function (T_FUNCTION) in /var/www/prestashop_new/override/classes/Dispatcher.php on line 30

 

Am I doing anything wrong ? Please rectify me.

Link to comment
Share on other sites

Yeah I understand and there is my issue. I am not overriding any function. I am just overriding the rules and parameters for the default routes.

 

Here is the overall code I am overriding.

<?php
/*
* 2015 Prestashop
*
* NOTICE OF LICENSE
*
* This source file is subject to the Academic Free License (AFL 3.0)
* It is available through the world-wide-web at this URL:
* http:*
* DISCLAIMER
* This code is provided as is without any warranty.
* No promise of being safe or secure
*
*  @author      [email protected]
*  @copyright   2015 Prestashop
*  @license     http:*  @code sorce: http:*/

class Dispatcher extends DispatcherCore
{
	public $default_routes = array(
		'category_rule' => array(
			'controller' =>	'category',
			'rule' =>		'{id}-{rewrite}',
			'keywords' => array(
				'id' =>				array('regexp' => '[0-9]+', 'param' => 'id_category'),
				'rewrite' =>		array('regexp' => '[_a-zA-Z0-9-\pL]*'),
				'meta_keywords' =>	array('regexp' => '[_a-zA-Z0-9-\pL]*'),
				'meta_title' =>		array('regexp' => '[_a-zA-Z0-9-\pL]*'),
			),
		),
		'supplier_rule' => array(
			'controller' =>	'supplier',
			'rule' =>		'{id}__{rewrite}',
			'keywords' => array(
				'id' =>				array('regexp' => '[0-9]+', 'param' => 'id_supplier'),
				'rewrite' =>		array('regexp' => '[_a-zA-Z0-9-\pL]*'),
				'meta_keywords' =>	array('regexp' => '[_a-zA-Z0-9-\pL]*'),
				'meta_title' =>		array('regexp' => '[_a-zA-Z0-9-\pL]*'),
			),
		),
		'manufacturer_rule' => array(
			'controller' =>	'manufacturer',
			'rule' =>		'{id}_{rewrite}',
			'keywords' => array(
				'id' =>				array('regexp' => '[0-9]+', 'param' => 'id_manufacturer'),
				'rewrite' =>		array('regexp' => '[_a-zA-Z0-9-\pL]*'),
				'meta_keywords' =>	array('regexp' => '[_a-zA-Z0-9-\pL]*'),
				'meta_title' =>		array('regexp' => '[_a-zA-Z0-9-\pL]*'),
			),
		),
		'cms_rule' => array(
			'controller' =>	'cms',
			'rule' =>		'{rewrite}.html',
			'keywords' => array(
				'id' =>				array('regexp' => '[0-9]+'),
				'rewrite' =>		array('regexp' => '[_a-zA-Z0-9-\pL]*', 'param' => 'cms_rewrite'),
				'meta_keywords' =>	array('regexp' => '[_a-zA-Z0-9-\pL]*'),
				'meta_title' =>		array('regexp' => '[_a-zA-Z0-9-\pL]*'),
			),
		),
		'cms_category_rule' => array(
			'controller' =>	'cms',
			'rule' =>		'info/{rewrite}/',
			'keywords' => array(
				'id' =>				array('regexp' => '[0-9]+'),
				'rewrite' =>		array('regexp' => '[_a-zA-Z0-9-\pL]*', 'param' => 'cms_category_rewrite'),
				'meta_keywords' =>	array('regexp' => '[_a-zA-Z0-9-\pL]*'),
				'meta_title' =>		array('regexp' => '[_a-zA-Z0-9-\pL]*'),
			),
		),
		'module' => array(
			'controller' =>	null,
			'rule' =>		'module/{module}{/:controller}',
			'keywords' => array(
				'module' =>			array('regexp' => '[_a-zA-Z0-9_-]+', 'param' => 'module'),
				'controller' =>		array('regexp' => '[_a-zA-Z0-9_-]+', 'param' => 'controller'),
			),
			'params' => array(
				'fc' => 'module',
			),
		),
		'product_rule' => array(
			'controller' =>	'product',
			'rule' =>		'{category:/}{id}-{rewrite}{-:ean13}.html',
			'keywords' => array(
				'id' =>				array('regexp' => '[0-9]+', 'param' => 'id_product'),
				'rewrite' =>		array('regexp' => '[_a-zA-Z0-9-\pL]*'),
				'ean13' =>			array('regexp' => '[0-9\pL]*'),
				'category' =>		array('regexp' => '[_a-zA-Z0-9-\pL]*'),
				'categories' =>		array('regexp' => '[/_a-zA-Z0-9-\pL]*'),
				'reference' =>		array('regexp' => '[_a-zA-Z0-9-\pL]*'),
				'meta_keywords' =>	array('regexp' => '[_a-zA-Z0-9-\pL]*'),
				'meta_title' =>		array('regexp' => '[_a-zA-Z0-9-\pL]*'),
				'manufacturer' =>	array('regexp' => '[_a-zA-Z0-9-\pL]*'),
				'supplier' =>		array('regexp' => '[_a-zA-Z0-9-\pL]*'),
				'price' =>			array('regexp' => '[0-9\.,]*'),
				'tags' =>			array('regexp' => '[a-zA-Z0-9-\pL]*'),
			),
		),
				'layered_rule' => array(
			'controller' =>	'category',
			'rule' =>		'{id}-{rewrite}{/:selected_filters}',
			'keywords' => array(
				'id' =>				array('regexp' => '[0-9]+', 'param' => 'id_category'),
				
				'selected_filters' =>		array('regexp' => '.*', 'param' => 'selected_filters'),
				'rewrite' =>		array('regexp' => '[_a-zA-Z0-9-\pL]*'),
				'meta_keywords' =>	array('regexp' => '[_a-zA-Z0-9-\pL]*'),
				'meta_title' =>		array('regexp' => '[_a-zA-Z0-9-\pL]*'),
			),
		),
	);
}

This is the whole code. I just want to override this. Any suggestion ? 

Link to comment
Share on other sites

  • 5 years later...

You rewrite definition for displatcher. For this you need append array. In your instance you can to do this:

class Dispatcher extends DispatcherCore
{
	public function __construct() {
		parent::__construct();

		$this->default_routes['category_rule'] = array(
			'controller' =>	'category',
			'rule' =>		'{id}-{rewrite}',
			'keywords' => array(
				'id' =>				array('regexp' => '[0-9]+', 'param' => 'id_category'),
				'rewrite' =>		array('regexp' => '[_a-zA-Z0-9-\pL]*'),
				'meta_keywords' =>	array('regexp' => '[_a-zA-Z0-9-\pL]*'),
				'meta_title' =>		array('regexp' => '[_a-zA-Z0-9-\pL]*'),
			),
		);
		$this->default_routes['supplier_rule'] = array(
			'controller' =>	'supplier',
			'rule' =>		'{id}__{rewrite}',
			'keywords' => array(
				'id' =>				array('regexp' => '[0-9]+', 'param' => 'id_supplier'),
				'rewrite' =>		array('regexp' => '[_a-zA-Z0-9-\pL]*'),
				'meta_keywords' =>	array('regexp' => '[_a-zA-Z0-9-\pL]*'),
				'meta_title' =>		array('regexp' => '[_a-zA-Z0-9-\pL]*'),
			),
		);
		// etc. etc.
	}
}

After require a file, it called constructor and first is last, in override, from override calling parent (core in root/classes)

Link to comment
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
×
×
  • Create New...