Yii Framework Forum: How to compare two Active Record Models - Yii Framework Forum

Jump to content

Page 1 of 1
  • You cannot start a new topic
  • You cannot reply to this topic

How to compare two Active Record Models and show the differences, if any

#1 User is offline   thyseus 

  • Advanced Member
  • PipPipPip
  • Yii
  • Group: Members
  • Posts: 301
  • Joined: 18-April 09
  • Location:Leipzig, Germany

Posted 06 July 2010 - 04:29 PM

*
POPULAR

Hey,

i have written a small behavior that hopefully can become useful for someone:

class CCompare extends CActiveRecordBehavior
{
  public function compare($other) {
    if(!is_object($other))
      return false;

    // does the objects have the same type?
    if(get_class($this->owner) !== get_class($other))
      return false;

    $differences = array();

    foreach($this->owner->attributes as $key => $value) {
      if($this->owner->$key != $other->$key)
        $differences[$key] = array(
            'old' => $this->owner->$key,
            'new' => $other->$key);
    }

    return $differences;
  }
}


Copy this Code as a file in your components/ directory and configure it like this in your AR Model:

  public function behaviors()  {
    return array( 'CCompare'); // <-- and other behaviors your model may have
  }


After that, you can use it this way:

$example_original = Demomodel1::model()->findByPk(5);
$example_comparison = Demomodel1::model()->findByPk(6);

$differences = $example_original->compare($example_fake);


After that, you will have all differences between your Original and Compared model.
If you provide another type of model to the compare function, false is returned.
If the models have the same attributes, only the Primary Key is returned, since it is the only attribute that differs.
Last but not least, if the Models are absolutely the same, an empty array is returned, since there are no differences.
5

#2 User is offline   betelgeuse 

  • Standard Member
  • PipPip
  • Yii
  • Group: Members
  • Posts: 101
  • Joined: 12-January 09

Posted 10 July 2010 - 02:12 PM

will be! thanks
a code snippet says more than a thousand words
0

#3 User is offline   Seal 

  • Standard Member
  • PipPip
  • Yii
  • Group: Members
  • Posts: 126
  • Joined: 02-February 10

Posted 03 August 2010 - 11:00 AM

thanks for sharing
Sylvester La-Tunje

Posted Image
0

#4 User is offline   DarkNSF 

  • Standard Member
  • PipPip
  • Yii
  • Group: Members
  • Posts: 287
  • Joined: 12-November 08
  • Location:Palm Bay, Florida

Posted 04 August 2010 - 02:14 PM

Excellent idea, this is very useful, only issue is that only classes that start with "C" are reserved for Yii classes.
1

#5 User is offline   Totto Roncone 

  • Junior Member
  • Pip
  • Yii
  • Group: Members
  • Posts: 55
  • Joined: 12-September 13
  • Location:Il piacere - Europe

Posted 29 April 2014 - 07:06 AM

View Postthyseus, on 06 July 2010 - 04:29 PM, said:

Hey,

i have written a small behavior that hopefully can become useful for someone:

class CCompare extends CActiveRecordBehavior
{
  public function compare($other) {
    if(!is_object($other))
      return false;

    // does the objects have the same type?
    if(get_class($this->owner) !== get_class($other))
      return false;

    $differences = array();

    foreach($this->owner->attributes as $key => $value) {
      if($this->owner->$key != $other->$key)
        $differences[$key] = array(
            'old' => $this->owner->$key,
            'new' => $other->$key);
    }

    return $differences;
  }
}


Copy this Code as a file in your components/ directory and configure it like this in your AR Model:

  public function behaviors()  {
    return array( 'CCompare'); // <-- and other behaviors your model may have
  }


After that, you can use it this way:

$example_original = Demomodel1::model()->findByPk(5);
$example_comparison = Demomodel1::model()->findByPk(6);

$differences = $example_original->compare($example_fake);


After that, you will have all differences between your Original and Compared model.
If you provide another type of model to the compare function, false is returned.
If the models have the same attributes, only the Primary Key is returned, since it is the only attribute that differs.
Last but not least, if the Models are absolutely the same, an empty array is returned, since there are no differences.



Late Congratulations @thyseus!


In my case, has to compare two model's item to manage whether is new or update register.

Using @thyseus behavior implementation I had a little problem with model validation producing by behavior.


Then, I resolve this thanks to Dana Luther and his post "How to use Behaviors in Yii".

She said, and I confirmed that this work, ...

Quote

"...what if I don't always want those events to fire off messages to the user when I update their data...? Not a problem -- just attach the behavior dynamically..."
.


And so I did...

                    	$modelLodging->attachBehavior( 
                        	'CCompare', 
                        	'application.components.behaviors.CCompare'
                    	);
                    	$modelLodging_Save->attachBehavior( 
                        	'CCompare', 
                        	'application.components.behaviors.CCompare'
                    	);
                    	//Update only when are equals:
                    	if($modelLodging->compare($modelLodging_Save))
                    	{



Thanks @thyseus and Dana Luther! :D
Thanks!
...Totto...
1

Share this topic:


Page 1 of 1
  • You cannot start a new topic
  • You cannot reply to this topic

1 User(s) are reading this topic
0 members, 1 guests, 0 anonymous users