00001 <?php
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034 class Mage_Review_Model_Mysql4_Review extends Mage_Core_Model_Mysql4_Abstract
00035 {
00036 protected $_reviewTable;
00037 protected $_reviewDetailTable;
00038 protected $_reviewStatusTable;
00039 protected $_reviewEntityTable;
00040 protected $_reviewStoreTable;
00041 private $_deleteCache = array();
00042
00043 protected function _construct()
00044 {
00045 $this->_init('review/review', 'review_id');
00046 $this->_reviewTable = $this->getTable('review/review');
00047 $this->_reviewDetailTable = $this->getTable('review/review_detail');
00048 $this->_reviewStatusTable = $this->getTable('review/review_status');
00049 $this->_reviewEntityTable = $this->getTable('review/review_entity');
00050 $this->_reviewStoreTable = $this->getTable('review/review_store');
00051 $this->_aggregateTable = $this->getTable('review/review_aggregate');
00052 }
00053
00054
00055
00056
00057
00058
00059
00060
00061 protected function _getLoadSelect($field, $value, $object)
00062 {
00063 $select = parent::_getLoadSelect($field, $value, $object);
00064 $select->join($this->_reviewDetailTable, $this->getMainTable().".review_id = {$this->_reviewDetailTable}.review_id");
00065 return $select;
00066 }
00067
00068
00069
00070
00071
00072
00073 protected function _beforeSave(Mage_Core_Model_Abstract $object)
00074 {
00075 if (!$object->getId()) {
00076 $object->setCreatedAt(Mage::getSingleton('core/date')->gmtDate());
00077 }
00078 if ($object->hasData('stores') && is_array($object->getStores())) {
00079 $stores = $object->getStores();
00080 $stores[] = 0;
00081 $object->setStores($stores);
00082 } elseif ($object->hasData('stores')) {
00083 $object->setStores(array($object->getStores(), 0));
00084 }
00085 return $this;
00086 }
00087
00088
00089
00090
00091
00092
00093 protected function _afterSave(Mage_Core_Model_Abstract $object)
00094 {
00095
00096
00097
00098 $detail = array(
00099 'title' => $object->getTitle(),
00100 'detail' => $object->getDetail(),
00101 'nickname' => $object->getNickname(),
00102 );
00103 $select = $this->_getWriteAdapter()->select()
00104 ->from($this->_reviewDetailTable, 'detail_id')
00105 ->where('review_id=?', $object->getId());
00106 $detailId = $this->_getWriteAdapter()->fetchOne($select);
00107
00108 if ($detailId) {
00109 $this->_getWriteAdapter()->update($this->_reviewDetailTable,
00110 $detail,
00111 'detail_id='.$detailId
00112 );
00113 }
00114 else {
00115 $detail['store_id'] = $object->getStoreId();
00116 $detail['customer_id']= $object->getCustomerId();
00117 $detail['review_id'] = $object->getId();
00118 $this->_getWriteAdapter()->insert($this->_reviewDetailTable, $detail);
00119 }
00120
00121
00122
00123
00124
00125 $stores = $object->getStores();
00126 if(!empty($stores)) {
00127 $condition = $this->_getWriteAdapter()->quoteInto('review_id = ?', $object->getId());
00128 $this->_getWriteAdapter()->delete($this->_reviewStoreTable, $condition);
00129
00130 $insertedStoreIds = array();
00131 foreach ($stores as $storeId) {
00132 if (in_array($storeId, $insertedStoreIds)) {
00133 continue;
00134 }
00135
00136 $insertedStoreIds[] = $storeId;
00137 $storeInsert = array(
00138 'store_id' => $storeId,
00139 'review_id'=> $object->getId()
00140 );
00141 $this->_getWriteAdapter()->insert($this->_reviewStoreTable, $storeInsert);
00142 }
00143 }
00144
00145
00146 $this->_aggregateRatings(
00147 $this->_loadVotedRatingIds($object->getId()),
00148 $object->getEntityPkValue()
00149 );
00150
00151 return $this;
00152 }
00153
00154
00155
00156
00157
00158
00159 protected function _afterLoad(Mage_Core_Model_Abstract $object)
00160 {
00161 $select = $this->_getReadAdapter()->select()
00162 ->from($this->_reviewStoreTable, array('store_id'))
00163 ->where('review_id=?', $object->getId());
00164 $stores = $this->_getReadAdapter()->fetchCol($select);
00165 if (empty($stores) && Mage::app()->isSingleStoreMode()) {
00166 $object->setStores(array(Mage::app()->getStore(true)->getId()));
00167 } else {
00168 $object->setStores($stores);
00169 }
00170 return $this;
00171 }
00172
00173 protected function _beforeDelete(Mage_Core_Model_Abstract $object)
00174 {
00175
00176 $this->_deleteCache = array(
00177 'ratingIds' => $this->_loadVotedRatingIds($object->getId()),
00178 'entityPkValue' => $object->getEntityPkValue()
00179 );
00180 return $this;
00181 }
00182
00183
00184
00185
00186
00187
00188 protected function _afterDelete(Mage_Core_Model_Abstract $object)
00189 {
00190 $this->aggregate($object);
00191
00192
00193 $this->_aggregateRatings(
00194 $this->_deleteCache['ratingIds'],
00195 $this->_deleteCache['entityPkValue']
00196 );
00197 $this->_deleteCache = array();
00198
00199 return $this;
00200 }
00201
00202 public function getTotalReviews($entityPkValue, $approvedOnly=false, $storeId=0)
00203 {
00204 $select = $this->_getReadAdapter()->select()
00205 ->from($this->_reviewTable, "COUNT(*)")
00206 ->where("{$this->_reviewTable}.entity_pk_value = ?", $entityPkValue);
00207
00208 if($storeId > 0) {
00209 $select->join(array('store'=>$this->_reviewStoreTable),
00210 $this->_reviewTable.'.review_id=store.review_id AND store.store_id=' . (int)$storeId, array());
00211 }
00212 if( $approvedOnly ) {
00213 $select->where("{$this->_reviewTable}.status_id = ?", 1);
00214 }
00215 return $this->_getReadAdapter()->fetchOne($select);
00216 }
00217
00218 public function aggregate($object)
00219 {
00220 if( !$object->getEntityPkValue() && $object->getId() ) {
00221 $object->load($object->getReviewId());
00222 }
00223
00224 $ratingModel = Mage::getModel('rating/rating');
00225 $ratingSummaries= $ratingModel->getEntitySummary($object->getEntityPkValue(), false);
00226
00227 $nonDelete = array();
00228 foreach($ratingSummaries as $ratingSummaryObject) {
00229 if( $ratingSummaryObject->getCount() ) {
00230 $ratingSummary = round($ratingSummaryObject->getSum() / $ratingSummaryObject->getCount());
00231 } else {
00232 $ratingSummary = $ratingSummaryObject->getSum();
00233 }
00234
00235 $reviewsCount = $this->getTotalReviews($object->getEntityPkValue(), true, $ratingSummaryObject->getStoreId());
00236 $select = $this->_getReadAdapter()->select()
00237 ->from($this->_aggregateTable)
00238 ->where("{$this->_aggregateTable}.entity_pk_value = ?", $object->getEntityPkValue())
00239 ->where("{$this->_aggregateTable}.entity_type = ?", $object->getEntityId())
00240 ->where("{$this->_aggregateTable}.store_id = ?", $ratingSummaryObject->getStoreId());
00241
00242 $oldData = $this->_getReadAdapter()->fetchRow($select);
00243
00244 $data = new Varien_Object();
00245
00246 $data->setReviewsCount($reviewsCount)
00247 ->setEntityPkValue($object->getEntityPkValue())
00248 ->setEntityType($object->getEntityId())
00249 ->setRatingSummary( ($ratingSummary > 0) ? $ratingSummary : 0 )
00250 ->setStoreId($ratingSummaryObject->getStoreId());
00251
00252 $this->_getWriteAdapter()->beginTransaction();
00253 try {
00254 if( $oldData['primary_id'] > 0 ) {
00255 $condition = $this->_getWriteAdapter()->quoteInto("{$this->_aggregateTable}.primary_id = ?", $oldData['primary_id']);
00256 $this->_getWriteAdapter()->update($this->_aggregateTable, $data->getData(), $condition);
00257 } else {
00258 $this->_getWriteAdapter()->insert($this->_aggregateTable, $data->getData());
00259 }
00260 $this->_getWriteAdapter()->commit();
00261 } catch (Exception $e) {
00262 $this->_getWriteAdapter()->rollBack();
00263 }
00264 }
00265 }
00266
00267
00268
00269
00270
00271
00272
00273 protected function _loadVotedRatingIds($reviewId)
00274 {
00275 if (empty($reviewId)) {
00276 return array();
00277 }
00278 $select = $this->_getReadAdapter()->select()
00279 ->from(array('v' => $this->getTable('rating/rating_option_vote')), 'r.rating_id')
00280 ->joinInner(array('r' => $this->getTable('rating/rating')), 'v.rating_id=r.rating_id')
00281 ->where('v.review_id=?', $reviewId
00282 );
00283 return $this->_getReadAdapter()->fetchCol($select);
00284 }
00285
00286
00287
00288
00289
00290
00291
00292
00293
00294 protected function _aggregateRatings($ratingIds, $entityPkValue)
00295 {
00296 if ($ratingIds && !is_array($ratingIds)) {
00297 $ratingIds = array((int)$ratingIds);
00298 }
00299 if ($ratingIds && $entityPkValue
00300 && ($resource = Mage::getResourceSingleton('rating/rating_option'))
00301 ) {
00302 foreach ($ratingIds as $ratingId) {
00303 $resource->aggregateEntityByRatingId(
00304 $ratingId, $entityPkValue
00305 );
00306 }
00307 }
00308 return $this;
00309 }
00310
00311 public function reAggregateReview($reviewId, $entityPkValue)
00312 {
00313 $this->_aggregateRatings($this->_loadVotedRatingIds($reviewId), $entityPkValue);
00314 }
00315 }