Symfony Doctrine Sluggable – rebuilding empty slugs
If you add slugs with Sluggable behaviour in the middle of your project you’ll have empty slugs for all old records. To fix it you need to save your models via symfony, slugs will be built automatically.
You can automate it with help of this simple task:
class buildSlugTask extends sfBaseTask { protected function configure() { $this->addArguments(array( new sfCommandArgument('model', sfCommandArgument::REQUIRED, 'Model'), new sfCommandArgument('field', sfCommandArgument::REQUIRED, 'Slug source field'), )); $this->addOptions(array( new sfCommandOption('application', null, sfCommandOption::PARAMETER_REQUIRED, 'The application name'), new sfCommandOption('env', null, sfCommandOption::PARAMETER_REQUIRED, 'The environment', 'dev'), new sfCommandOption('connection', null, sfCommandOption::PARAMETER_REQUIRED, 'The connection name', 'doctrine'), )); $this->namespace = 'oxt'; $this->name = 'buildSlug'; $this->briefDescription = 'Rebuild empty slug'; $this->detailedDescription = <<<EOF The [buildSlug|INFO] task rebuilds empty slugs. Call it with: [php symfony buildSlug|INFO] EOF; } protected function execute($arguments = array(), $options = array()) { // initialize the database connection $databaseManager = new sfDatabaseManager($this->configuration); $connection = $databaseManager->getDatabase($options['connection'])->getConnection(); $items = Doctrine::getTable($arguments['model']) ->createQuery('m') ->where('m.slug IS NULL') ->execute(); foreach ($items as $item) { //cheat doctrine to re-save our model $field_value = $item->get($arguments['field']); $item->set($arguments['field'], ''); $item->set($arguments['field'], $field_value); $item->save(); } } }
Call it with model name and slug field name. If you have slug built from several fields you can pass any of them.
E.g.:
./symfony oxt:buildSlug Record title
Tags: doctrine, sluggable, symfony
January 4th, 2011 at 1:16 pm
wouldn’t it be easier to change state of a record
$item->state(Doctrine_Record::STATE_DIRTY);
$item->save();
than change value of sluggable field?
i’m using something like this in the model:
public function getSlug()
{
if($this->_data[‘slug’] == ”)
{
$this->state(Doctrine_Record::STATE_DIRTY);
$this->save();
}
return $this->_data[‘slug’];
}
and it’s works perfect
January 4th, 2011 at 1:20 pm
Yes, it’s easier, thanks
February 20th, 2012 at 9:01 am
Thanks for sharing, this is really useful.. especially since I need to update thousands of records from a legacy db!