![]() |
|
Code snippets for symfony 1.x |
|
The table i18n doesn't support default culture. This snippet add the support of the default culture.
This snippet is a port of the snippet "default culture content fallback for i18n tables" for Symfony 1.2
To enable the fallback, edit your table object class in lib/model/TableClassName.php and add the following code. Then search and replace TableClassName by your table object class name.
/** * Fetch the i18n object for this object culture. * * @param string $culture The culture to set * @return mixed A i18n object * @throws PropelException Any exceptions caught during processing will be rethrown wrapped into a PropelException. * @link http://snippets.symfony-project.org/snippet/237 -- modified for Symfony 1.2 */ public function getCurrentTableClassNameI18n($culture = null) { if (is_null($culture)) { $culture = is_null($this->culture) ? sfPropel::getDefaultCulture() : $this->culture; } if (!isset($this->current_i18n[$culture])) { $obj = TableClassNameI18nPeer::retrieveByPK($this->getId(), $culture); if ($obj !== null) { // Test if there is a translation for current culture $this->setTableClassNameI18nForCulture($obj, $culture); } else { // Create a translation for this culture $new_i18n = new TableClassNameI18n(); $default_culture = sfConfig::get('sf_default_culture'); // We try to fetch the default culture translation to initialise the new culture. if (!isset($this->current_i18n[$default_culture])) { $obj = TableClassNameI18nPeer::retrieveByPK($this->getId(), $default_culture); if ($obj !== null) { // Test if there is a translation for current culture $this->setTableClassNameI18nForCulture($obj, $default_culture); } } else { $obj = $this->current_i18n[$default_culture]; } if ($obj !== null) { $obj->copyInto($new_i18n); } $new_i18n->setId($this->getId()); $new_i18n->setCulture($culture); $this->setTableClassNameI18nForCulture($new_i18n, $culture); } } return $this->current_i18n[$culture]; }
You now need to add default translation when you create a new object. We do that with this doSave function.
To use this function, edit your table object class in lib/model/TableClassName.php and add the following code. Then search and replace TableClassName by your table object class name.
/** * Stores the object in the database while setting default culture if necessary. * * If the object is new, it inserts it; otherwise an update is performed. * All related objects are also updated in this method. * * @param Connection $con The database connection * @return int The number of rows affected by this insert/update and any referring fk objects' save() operations. * @throws PropelException Any exceptions caught during processing will be rethrown wrapped into a PropelException. * @see save() * @link http://snippets.symfony-project.org/snippet/237 -- modified for Symfony 1.2 */ protected function doSave(PropelPDO $con) { $default_culture = sfConfig::get('sf_default_culture'); $current_culture = is_null($this->culture) ? sfPropel::getDefaultCulture() : $this->culture; $obj = null; // We try to fetch the default culture translation to initialise the new culture. if (!isset($this->current_i18n[$default_culture])) { $obj = TableClassNameI18nPeer::retrieveByPK($this->getId(), $default_culture, $con); if ($obj !== null) { // Test if there is a translation for current culture $this->setTableClassNameI18nForCulture($obj, $default_culture); } } else { $obj = $this->current_i18n[$default_culture]; } if($obj === null && isset($this->current_i18n[$current_culture])) { $new_i18n = new TableClassNameI18n(); $this->current_i18n[$current_culture]->copyInto($new_i18n); $new_i18n->setId($this->getId()); $new_i18n->setCulture($default_culture); $this->setTableClassNameI18nForCulture($new_i18n, $default_culture); } return parent::doSave($con); }
To complete this snippet, here is a fallback version of doSelectWithI18n.
To enable the fallback, edit your table object peer class in lib/model/TableClassNamePeer.php and add the following code. Then search and replace TableClassName by your table object class name.
/** * Selects a collection of TableClassName objects pre-filled with their i18n objects. * * @param Criteria $criteria The criteria's object * @param string $culture The selected culture. * @param PropelPDO $con An optional database connection * @return array Array of TableClassName objects. * @throws PropelException Any exceptions caught during processing will be rethrown wrapped into a PropelException. * @link http://snippets.symfony-project.org/snippet/237 -- modified for Symfony 1.2 */ public static function doSelectWithI18n(Criteria $criteria, $culture = null, PropelPDO $con = null) { $criteria = clone $criteria; if ($culture === null) { $culture = sfContext::getInstance()->getUser()->getCulture(); } $default_culture = sfConfig::get('sf_default_culture'); // Set the correct dbName if it has not been overridden if ($criteria->getDbName() == Propel::getDefaultDB()) { $criteria->setDbName(self::DATABASE_NAME); } TableClassNamePeer::addSelectColumns($c); $startcol = (TableClassNamePeer::NUM_COLUMNS - TableClassNamePeer::NUM_LAZY_LOAD_COLUMNS) + 1; TableClassNameI18nPeer::addSelectColumns($c); $criteria->addJoin(TableClassNamePeer::ID, TableClassNameI18nPeer::ID); $criterion = $criteria->getNewCriterion(TableClassNameI18nPeer::CULTURE, $culture); $criterion->addOr($criteria->getNewCriterion(TableClassNameI18nPeer::CULTURE, $default_culture)); $criteria->add($criterion); $stmt = BasePeer::doSelect($c, $con); $results = array(); $uncultured_results = array(); while($row = $stmt->fetch(PDO::FETCH_NUM)) { $obj1 = new TableClassName(); $obj1->hydrate($row); $obj1->setCulture($culture); if(isset($results[$obj1->getId()])) { $obj1 = $results[$obj1->getId()]; } $omClass = TableClassNameI18nPeer::getOMClass($row, $startcol); $cls = Propel::importClass($omClass); $obj2 = new $cls(); $obj2->hydrate($row, $startcol); $obj1->setTableClassNameI18nForCulture($obj2, $obj2->getCulture()); $obj2->setTableClassName($obj1); if(!isset($uncultured_results[$obj1->getId()])) { $uncultured_results[$obj1->getId()] = $obj1; } if($obj2->getCulture() == $culture) { $uncultured_results[$obj1->getId()] = false; } if(!isset($results[$obj1->getId()])) { $results[$obj1->getId()] = $obj1; } elseif($obj2->getCulture() == $culture) { // Move result to the end of results array to fit eventual sort // criteria (ugly fix). unset($results[$obj1->getId()]); $results[$obj1->getId()] = $obj1; } } foreach ($uncultured_results as $obj1) { if ($obj1) { $obj1->setCulture($default_culture); $default_culture_object = $obj1->getCurrentTableClassNameI18n(); if ($default_culture_object) { $obj2 = new TableClassNameI18n(); $default_culture_object->copyInto($obj2); $obj2->setCulture($culture); $obj2->setTableClassName($obj1); $obj1->setTableClassNameI18nForCulture($obj2, $obj2->getCulture()); } $obj1->setCulture($culture); } } return array_values($results); }
Before enable the fallback, you must create a constant in your table object peer class in lib/model/TableClassNamePeer.php and replace table by your table name
const COUNT_DISTINCT = 'COUNT(DISTINCT table.ID)';
To enable the fallback, edit your table object peer class in lib/model/TableClassNamePeer.php and add the following code. Then search and replace TableClassName by your table object class name.
/** * Returns the number of rows matching criteria with I18N criteria. * * @param Criteria $criteria The criteria's object * @param boolean $distinct Whether to select only distinct columns (You can also set DISTINCT modifier in Criteria). * @param Connection $con An optional database connection * @param string $culture The selected culture. * @return int Number of matching rows. * @link http://snippets.symfony-project.org/snippet/237 -- modified for Symfony 1.2 */ public static function doCountWithI18n(Criteria $criteria = null, $distinct = false, PropelPDO $con = null, $culture = null) { // we're going to modify criteria, so copy it first if ($criteria === null){ $criteria = new Criteria(); } else { $criteria = clone $criteria; } $default_culture = sfConfig::get('sf_default_culture'); if ($culture === null) { // We use current user culture. $culture = sfContext::getInstance()->getUser()->getCulture(); } // clear out anything that might confuse the ORDER BY clause $criteria->clearSelectColumns()->clearOrderByColumns(); $criteria->addSelectColumn(TableClassNamePeer::COUNT_DISTINCT); // just in case we're grouping: add those columns to the select statement foreach($criteria->getGroupByColumns() as $column) { $criteria->addSelectColumn($column); } $criteria->addJoin(TableClassNamePeer::ID, TableClassNameI18nPeer::ID); $criterion = $criteria->getNewCriterion(TableClassNameI18nPeer::CULTURE, $culture); $criterion->addOr($criteria->getNewCriterion(TableClassNameI18nPeer::CULTURE, $default_culture)); $criteria->add($criterion); $rs = TableClassNamePeer::doSelectStmt($criteria, $con); if ($res = $rs->fetchColumn(0)) { return $res; } else { // no rows returned; we infer that means 0 matches. return 0; } }