Пример #1
0
 public function perform()
 {
     $args = $this->args;
     if (empty($args['mainMember']) || empty($args['otherMemberIds'])) {
         ResqueUtil::log(['Merge member args error' => $args]);
         return;
     }
     $mainMember = unserialize($args['mainMember']);
     $otherMemberIds = unserialize($args['otherMemberIds']);
     //Get Name and phone
     $name = $phone = '';
     foreach ($mainMember->properties as $mainProperty) {
         if ($mainProperty['name'] === Member::DEFAULT_PROPERTIES_NAME) {
             $name = $mainProperty['value'];
         }
         if ($mainProperty['name'] === Member::DEFAULT_PROPERTIES_MOBILE) {
             $phone = $mainProperty['value'];
         }
     }
     ScoreHistory::updateAll(['$set' => ['memberId' => $mainMember->_id]], ['memberId' => ['$in' => $otherMemberIds]]);
     MemberLogs::deleteAll(['memberId' => ['$in' => $otherMemberIds]]);
     CampaignLog::updateAll(['$set' => ['member.id' => $mainMember->_id, 'member.cardNumber' => $mainMember->cardNumber, 'member.name' => $name, 'member.phone' => $phone]], ['member.id' => ['$in' => $otherMemberIds]]);
     PromotionCode::updateAll(['$set' => ['usedBy.memberId' => $mainMember->_id, 'usedBy.memberNumber' => $mainMember->cardNumber]], ['usedBy.memberId' => ['$in' => $otherMemberIds]]);
     GoodsExchangeLog::updateAll(['$set' => ['memberId' => $mainMember->_id, 'memberName' => $name, 'telephone' => $phone]], ['memberId' => ['$in' => $otherMemberIds]]);
     $otherMemberStrIds = [];
     foreach ($otherMemberIds as $otherMemberId) {
         $otherMemberStrIds[] = (string) $otherMemberId;
     }
     Order::updateAll(['$set' => ['consumer.id' => (string) $mainMember->_id, 'consumer.name' => $name, 'consumer.phone' => $phone]], ['consumer.id' => ['$in' => $otherMemberStrIds]]);
     Qrcode::deleteAll(['type' => Qrcode::TYPE_MEMBER, 'associatedId' => ['$in' => $otherMemberIds]]);
 }
 /**
  * export excel for the promotioncode to upload to qiniu,and return key to frontend
  */
 public function actionExport()
 {
     $params = $this->getQuery();
     if (empty($params['createdAt']) || empty($params['productId'])) {
         throw new BadRequestHttpException('missing param createdAt or productId');
     }
     $productId = new MongoId($params['productId']);
     $product = Product::findByPk($productId);
     if (empty($product)) {
         throw new BadRequestHttpException('invalid productId');
     }
     $startTime = new MongoDate($params['createdAt']);
     $endTime = new MongoDate($params['createdAt'] + 1);
     $condition = ['productId' => $productId, 'createdAt' => ['$gte' => $startTime, '$lt' => $endTime]];
     $data = PromotionCode::findOne($condition);
     if ($data) {
         $accountId = $this->getAccountId();
         list($sku, $code, $isUsed) = explode(',', Yii::t('product', 'export_promotioncode_title'));
         $header = ['code' => $code, 'isUsed' => $isUsed];
         $key = $product['name'] . '_' . date('Ymd') . '_' . $product['sku'];
         $status = ['vaild' => 'Y', 'unvaild' => 'N'];
         $fields = 'code,isUsed';
         $exportArgs = ['status' => $status, 'header' => $header, 'key' => $key, 'sku' => $product->sku, 'accountId' => (string) $accountId, 'condition' => serialize($condition), 'fields' => $fields, 'description' => 'Direct: export promotionCodes'];
         $jobId = Yii::$app->job->create('backend\\modules\\product\\job\\ExportPromotionCode', $exportArgs);
         $result = ['result' => 'success', 'message' => 'exporting file', 'data' => ['jobId' => $jobId, 'key' => $key]];
     } else {
         $result = ['result' => 'error', 'message' => 'no datas', 'data' => []];
     }
     return $result;
 }
Пример #3
0
 public function extraFields()
 {
     return array_merge(parent::extraFields(), ['isAssociated' => function () {
         $campaign = Campaign::getByProductId($this->_id);
         return !empty($campaign);
     }, 'promotionCodeCount' => function () {
         return PromotionCode::countByProductIds([$this->_id]);
     }]);
 }
Пример #4
0
 public function perform()
 {
     # Run task
     $args = $this->args;
     //job update productId
     switch ($args['type']) {
         case self::JOB_UPDATE:
             if (!empty($args['oldProductId']) && !empty($args['newProductId'])) {
                 ModelPromotionCode::updateAll(['$set' => ['productId' => new \MongoId($args['newProductId'])]], ['productId' => new \MongoId($args['oldProductId']), 'isUsed' => false]);
                 return true;
             }
             break;
         case self::JOB_GENERATE:
             //job generateCodes
             if (empty($accountId = $args['accountId']) || empty($productId = $args['productId']) || !array_key_exists('count', $args)) {
                 ResqueUtil::log(['error' => 'generate codes params error', 'param' => $args]);
                 return false;
             }
             $createdAt = new \MongoDate(time(), 0);
             $count = $args['count'];
             $successCount = 0;
             $batchCount = $count / self::PER_BATCH;
             for ($i = 0; $i < $batchCount; $i++) {
                 $restCount = $count - self::PER_BATCH * $i;
                 $rowsCount = $restCount >= self::PER_BATCH ? self::PER_BATCH : $restCount;
                 $codes = ModelPromotionCode::generateCodes($rowsCount, new \MongoId($productId));
                 ResqueUtil::log(['info' => 'generate code ok', 'param' => $args]);
                 $promotionCodes = [];
                 foreach ($codes as $code) {
                     $promotionCode = ['productId' => new \MongoId($productId), 'code' => $code, 'isUsed' => false, 'accountId' => new \MongoId($accountId), 'createdAt' => $createdAt, 'random' => rand()];
                     $promotionCodes[] = $promotionCode;
                 }
                 ResqueUtil::log(['info' => 'generate codes', 'param' => $args]);
                 $result = ModelPromotionCode::batchInsert($promotionCodes);
                 if (!$result) {
                     ResqueUtil::log(['error' => 'save codes failed', 'param' => $args, 'success count' => $successCount]);
                 } else {
                     $successCount += $rowsCount;
                 }
             }
             //change the isBindCode
             $this->changeProductStatus(new \MongoId($productId));
             return true;
         case self::JOB_DELETE:
             if (!empty($args['productId'])) {
                 $productId = new \MongoId($args['productId']);
                 $condition = ['productId' => $productId];
             } else {
                 ResqueUtil::log(['error' => 'delete codes params error', 'param' => $args]);
                 return false;
             }
             if (!empty($args['createdAt'])) {
                 $createdAt = new \MongoDate($args['createdAt']);
                 $condition = array_merge($condition, ['createdAt' => $createdAt]);
             }
             //if delete all code successfully,judge to change isBindCode
             if (ModelPromotionCode::deleteAll($condition)) {
                 $count = ModelPromotionCode::count(["productId" => $productId]);
                 if ($count <= 0) {
                     Product::updateAll(['isBindCode' => false], ['_id' => $productId]);
                 }
             }
             return true;
         case self::JOB_INSERT:
             if (!isset($args['accountId']) || !isset($args['productId']) || !isset($args['filename'])) {
                 ResqueUtil::log(['error' => 'missing param accountId or productId or filename', 'param' => $args]);
                 return false;
             }
             if (!isset($args['import'])) {
                 $args['import'] = false;
             }
             $redis = \Yii::$app->cache->redis;
             $createdAt = new \MongoDate(time());
             $product = Product::findOne($args['productId']);
             if (empty($product)) {
                 ResqueUtil::log(['error' => 'product has been deleted', 'param' => $args]);
                 return false;
             }
             $productId = $product['sku'];
             $cacheKey = $args['accountId'] . "_" . $productId . "_" . $args['filename'];
             $cacheSet = PromotionCheckCode::SET_HEAD . md5($cacheKey);
             $total = $redis->scard($cacheSet);
             //redis hash key name
             $cacheHash = md5($cacheKey);
             $k = 0;
             $promotionCodes = [];
             for ($i = 1; $i <= $total; ++$i) {
                 // insert the code
                 if ($args['import']) {
                     $key = $redis->spop($cacheSet);
                     if (!empty($key)) {
                         $promotionCode = ['productId' => new \MongoId($args['productId']), 'code' => $key, 'isUsed' => false, 'accountId' => new \MongoId($args['accountId']), 'createdAt' => $createdAt];
                         $promotionCodes[$k++] = $promotionCode;
                     }
                     //set default value in redis to avoid to insert data in mongo failly
                     $redis->HSET($cacheHash, 'right', 0);
                     $redis->HSET($cacheHash, 'wrong', self::PROMO_CODE_REPEATED);
                     //have data to store
                     if (count($promotionCodes) > 0) {
                         if ($k % self::PER_BATCH == 0 || $i == $total) {
                             try {
                                 $result = ModelPromotionCode::batchInsert($promotionCodes);
                             } catch (MongoDuplicateKeyException $e) {
                                 return false;
                             }
                             $promotionCodes = [];
                             if (!$result) {
                                 ResqueUtil::log(['error' => 'save codes failed', 'param' => $args, 'success count' => $i - count($promotionCodes)]);
                             }
                         }
                     }
                 }
             }
             $redis->del($cacheSet);
             //change the isBindCode
             $this->changeProductStatus($product['_id']);
             //update duplicate key error
             $redis->HSET($cacheHash, 'wrong', 0);
             return true;
             break;
         case self::JOB_DELETE_REDIS_CODE:
             if (!isset($args['filename']) || !isset($args['productId']) || !isset($args['accountId'])) {
                 ResqueUtil::log(['error' => 'missing param', 'param' => $args]);
                 return false;
             }
             $redis = \Yii::$app->cache->redis;
             $cacheSet = PromotionCheckCode::SET_HEAD . md5($args['accountId'] . '_' . $args['productId'] . '_' . $args['filename']);
             $redis->del($cacheSet);
             unset($commonKey, $cacheTotalKey, $count);
             return true;
             break;
         default:
             break;
     }
 }
Пример #5
0
 /**
  * check the status for code in offline
  * @param $codes,array
  * @param $accountId,objectId
  * @param $member,object
  * @param $exchangeTime,mongoDate
  */
 public static function checkCodeStatus($codes, $accountId, $member, $exchangeTime, $params)
 {
     $invalid = $redeemed = $validCampaignCode = $redeemedMemberId = [];
     //check code redeem
     $condition = ['code' => ['$in' => $codes], 'isUsed' => true, 'accountId' => $accountId];
     //get member info when code is redeemed
     $redeemedCodes = PromotionCode::findAll($condition);
     $redeemInfo = self::getRedeemCodeAndRedeemMemberId($redeemedCodes);
     $redeemed = $redeemInfo['code'];
     $redeemedMemberId = $redeemInfo['memberIds'];
     if (count($codes) != count($redeemed)) {
         //if the code are not all redeem, we need select campaign
         //1.get promotioncode which is vaild
         $unRedeemedCodes = array_diff($codes, $redeemed);
         //1.code is valid,2.code is not exists in collection
         $promocodes = self::getNotRedeemCode($unRedeemedCodes, $accountId);
         if (empty($promocodes)) {
             //if the promocodes is empty,the code all are invalid
             $invalid = $unRedeemedCodes;
         } else {
             //validCodeInfo struct is a array,key is code value is productId
             $validCodeProductId = self::getValidCodeInfoFromPromotionCode($promocodes);
             $validCode = array_keys($validCodeProductId);
             $validProductId = array_values($validCodeProductId);
             $notExistsCode = self::getNotExitsCode($unRedeemedCodes, $validCode);
             //get all campaign
             $condition = ['promotion.data' => ['$in' => $validProductId], 'accountId' => $accountId];
             $campaigns = Campaign::findAll($condition);
             if (empty($campaigns)) {
                 $invalid = $validCode;
             } else {
                 //campaignCodeProductId is array.key is code value is productId
                 $campaignCodeProductId = self::getCodeInfoFitWithCampaign($campaigns, $validCodeProductId);
                 //merge not exists code and code whitch can not find any campaigns
                 $invalid = array_merge($notExistsCode, array_diff($validCode, array_keys($campaignCodeProductId)));
                 if (!empty($campaignCodeProductId)) {
                     //order the code with source code,first-in first-out
                     $campaignCodeProductId = self::orderCode($codes, $campaignCodeProductId);
                     $validCampaignCode = self::checkCode2CampainStatus($campaignCodeProductId, $member, $exchangeTime, $params);
                 }
             }
         }
     }
     $codes = [];
     if (!empty($invalid)) {
         foreach ($invalid as $invalidCode) {
             $codes[$invalidCode] = ['code' => $invalidCode, 'status' => self::CODE_STATUS_INVALID, 'score' => 0, 'description' => Yii::t('product', 'system_not_exists')];
         }
     }
     if (!empty($redeemed)) {
         $codes = array_merge($codes, self::setMemberName($redeemedMemberId, $redeemedCodes));
     }
     return array_merge($codes, $validCampaignCode);
 }