views:

353

answers:

1

I'm trying to achieve a cascading UPDATE and DELETE effect in a MyISAM database (similar effect as you can create in InnoDB tables with foreign keys). Two example tables:

  • albums
  • photos (has an album_id column that is a "foreign key" to the albums table)

Now when I delete a row in the albums table I would like Zend_Db_Table to automatically delete all related rows in the photos table. This is what I have in the albums table:

protected $_name = 'albums';

protected $_dependentTables = array(
    'Photos'
);

And I have this in the photos table:

protected $_name = 'photos';

protected $_referenceMap = array(
    'Album' => array(
        'columns' => array('album_id'),
        'refTableClass' => 'Albums',
        'refColumns' => array('id')
    )
);

Yes when I delete a row in the albums table, the photos from that album do not get removed.

This is how I'm removing the album:

public function remove($id)
{
    $where = $this->getAdapter()->quoteInto('id = ?', $id, 'INTEGER');
    return $this->delete($where);
}
+2  A: 

You need to setup the cascade delete. So your reference map should be:

protected $_referenceMap = array(
'Album' => array(
    'columns' => array('album_id'),
    'refTableClass' => 'Albums',
    'refColumns' => array('id'),
    'onDelete' => self::CASCADE
));

See full description of cascading operations here: http://framework.zend.com/manual/en/zend.db.table.relationships.html#zend.db.table.relationships.cascading

NB Cascading operations are only triggered when functions called on the actual row of the results set (i.e. Zend_Db_Table_Row class). To trigger the delete function in this example:

$album = $albums->find($id);
$album->delete();//This triggers the cascading delete
Akeem
Yep, I added that there and still it doesn't work.
Richard Knop
the cascading operation is only triggered when you call the delete function on a row i.e. $album->delete();
Akeem
Yes I know, I'm using the $this->delete. Check my OP.
Richard Knop
Calling delete on the model doesn't trigger the cascading delete. Only deleting on the actual row eg. $album = $albums->find($id); $album->delete();
Akeem
Well, that's not very good because I'm calling the delete on all of my models in my application so it would take long time to rewrite all controllers and models. But, fortunately, I have convinced my web hosting provider to enable InnoDB storage engine on the server where my application is so I will just convert all tables to InnoDB and add foreign keys. That will be much easier solution.
Richard Knop