| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472 |
- <?php
- /*
- * FecShop file.
- *
- * @link http://www.fecshop.com/
- * @copyright Copyright (c) 2016 FecShop Software LLC
- * @license http://www.fecshop.com/license/
- */
- namespace fecshop\services\cart;
- //use fecshop\models\mysqldb\cart\Coupon as MyCoupon;
- //use fecshop\models\mysqldb\cart\CouponUsage as MyCouponUsage;
- use fecshop\services\Service;
- use Yii;
- /**
- * Coupon services.
- * @author Terry Zhao <2358269014@qq.com>
- * @since 1.0
- */
- class Coupon extends Service
- {
- protected $_useCouponInit; // 是否初始化这个百年两
- protected $_customer_id; // 用户id
- protected $_coupon_code; // 优惠卷码
- protected $_coupon_model; // 优惠券model
- protected $_coupon_usage_model; // 优惠券使用次数记录model
-
- protected $_couponModelName = '\fecshop\models\mysqldb\cart\Coupon';
- protected $_couponModel;
- protected $_couponUsageModelName = '\fecshop\models\mysqldb\cart\CouponUsage';
- protected $_couponUsageModel;
-
- public $coupon_type_percent = 1;
- public $coupon_type_direct = 2;
-
- public function init()
- {
- parent::init();
- list($this->_couponModelName, $this->_couponModel) = Yii::mapGet($this->_couponModelName);
- list($this->_couponUsageModelName, $this->_couponUsageModel) = Yii::mapGet($this->_couponUsageModelName);
- }
-
- protected function actionGetPrimaryKey()
- {
- return 'coupon_id';
- }
- /**
- * @param $primaryKey | Int
- * @return Object($this->_couponModel)
- * 通过id找到cupon的对象
- */
- protected function actionGetByPrimaryKey($primaryKey)
- {
- $one = $this->_couponModel->findOne($primaryKey);
- $primaryKey = $this->getPrimaryKey();
- if ($one[$primaryKey]) {
- return $one;
- } else {
- return new $this->_couponModelName;
- }
- }
- /**
- * @param $customer_id | Int
- * @param $coupon_id | Int
- * 通过customer_id 和 coupon_id得到 Coupon Usage Model.
- */
- protected function actionGetCouponUsageModel($customer_id = '', $coupon_id = '')
- {
- if (!$this->_coupon_usage_model) {
- if (!$customer_id) {
- $customer_id = $this->_customer_id;
- }
- if (!$coupon_id) {
- $couponModel = $this->getCouponModel();
- $coupon_id = isset($couponModel['coupon_id']) ? $couponModel['coupon_id'] : '';
- }
- if ($customer_id && $coupon_id) {
- $one = $this->_couponUsageModel->findOne([
- 'customer_id' => $customer_id,
- 'coupon_id' => $coupon_id,
- ]);
- if ($one['customer_id']) {
- $this->_coupon_usage_model = $one;
- }
- }
- }
- if ($this->_coupon_usage_model) {
- return $this->_coupon_usage_model;
- }
- }
- /**
- * @param $coupon_code | String
- * 根据 coupon_code 得到 coupon model
- */
- protected function actionGetCouponModel($coupon_code = '')
- {
- if (!$this->_coupon_model) {
- if (!$coupon_code) {
- $coupon_code = $this->_coupon_code;
- }
- if ($coupon_code) {
- $one = $this->_couponModel->findOne(['coupon_code' => $coupon_code]);
- if ($one['coupon_code']) {
- $this->_coupon_model = $one;
- }
- }
- }
- if ($this->_coupon_model) {
- return $this->_coupon_model;
- }
- }
- /**
- * @param $filter|array
- * @return Array;
- * 通过过滤条件,得到coupon的集合。
- * example filter:
- * [
- * 'numPerPage' => 20,
- * 'pageNum' => 1,
- * 'orderBy' => ['_id' => SORT_DESC, 'sku' => SORT_ASC ],
- * 'where' => [
- * ['>','price',1],
- * ['<=','price',10]
- * ['sku' => 'uk10001'],
- * ],
- * 'asArray' => true,
- * ]
- */
- protected function actionColl($filter = '')
- {
- $query = $this->_couponModel->find();
- $query = Yii::$service->helper->ar->getCollByFilter($query, $filter);
- $coll = $query->all();
- return [
- 'coll' => $coll,
- 'count'=> $query->limit(null)->offset(null)->count(),
- ];
- }
- /**
- * @param $one|array , save one data .
- * @return int 保存coupon成功后,返回保存的id。
- */
- protected function actionSave($one)
- {
- $time = time();
- $primaryKey = $this->getPrimaryKey();
- $primaryVal = isset($one[$primaryKey]) ? $one[$primaryKey] : '';
- if ($primaryVal) {
- $model = $this->_couponModel->findOne($primaryVal);
- if (!$model) {
- Yii::$service->helper->errors->add('coupon {primaryKey} is not exist' , ['primaryKey' => $this->getPrimaryKey()] );
- return;
- }
- } else {
- $o_one = $this->_couponModel->find()
- ->where(['coupon_code' =>$one['coupon_code']])
- ->one();
- if ($o_one[$primaryKey]) {
- Yii::$service->helper->errors->add('coupon_code must be unique');
- return;
- }
- $model = new $this->_couponModelName;
- $model->created_at = time();
- if (isset(Yii::$app->user)) {
- $user = Yii::$app->user;
- if (isset($user->identity)) {
- $identity = $user->identity;
- $person_id = $identity['id'];
- $model->created_person = $person_id;
- }
- }
- }
- $model->attributes = $one;
- if ($model->validate()) {
- $model->updated_at = time();
- $model = Yii::$service->helper->ar->save($model, $one);
- $primaryVal = $model[$primaryKey];
- return $primaryVal;
- } else {
- $errors = $model->errors;
- Yii::$service->helper->errors->addByModelErrors($errors);
- return false;
- }
- }
- /**
- * @param $ids | Int or Array
- * @return bool
- * 如果传入的是id数组,则删除多个
- * 如果传入的是Int,则删除一个coupon
- */
- protected function actionRemove($ids)
- {
- if (!$ids) {
- Yii::$service->helper->errors->add('remove id is empty');
- return false;
- }
- if (is_array($ids) && !empty($ids)) {
- foreach ($ids as $id) {
- $model = $this->_couponModel->findOne($id);
- if (isset($model[$this->getPrimaryKey()]) && !empty($model[$this->getPrimaryKey()])) {
- $model->delete();
- } else {
- Yii::$service->helper->errors->add('Coupon remove errors:ID {id} is not exist.', ['id' => $id]);
- return false;
- }
- }
- } else {
- $id = $ids;
- $model = $this->_couponModel->findOne($id);
- if (isset($model[$this->getPrimaryKey()]) && !empty($model[$this->getPrimaryKey()])) {
- $model->delete();
- } else {
- Yii::$service->helper->errors->add('Coupon remove errors:ID {id} is not exist.', ['id' => $id]);
- return false;
- }
- }
- return true;
- }
- /**
- * @param $coupon_code | String 优惠卷码
- * 初始化对象变量,这个函数是在使用优惠券 和 取消优惠券的时候,
- * 调用相应方法前,通过这个函数初始化类变量
- * $_useCouponInit # 是否初始化过,如果初始化过了,则不会执行
- * $_customer_id # 用户id
- * $_coupon_code # 优惠卷码
- * $_coupon_model # 优惠券model
- * $_coupon_usage_model # 优惠券使用次数记录model
- * 这是一个内部函数,不对外开放。
- */
- protected function useCouponInit($coupon_code)
- {
- if (!$this->_useCouponInit) {
- // $this->_customer_id
- if (Yii::$app->user->isGuest) {
- $this->_customer_id = '';
- } else {
- if (Yii::$app->user->identity->id) {
- $this->_customer_id = Yii::$app->user->identity->id;
- }
- }
- // $this->getCouponUsageModel();
- // $this->getCouponModel();
- // $this->_coupon_code
- $this->_coupon_code = $coupon_code;
- $this->_useCouponInit = 1;
- }
- }
- /**
- * @param $isGetDiscount | boolean, 是否是获取折扣信息,
- * 1.如果值为true,说明该操作是获取cart 中的coupon的折扣操作步骤中的active判断,则只进行优惠券存在和是否过期判断,不对使用次数判断
- * 2.如果值为false,则是add coupon操作,除了优惠券是否存在, 是否过期判断,还需要对使用次数进行判断。
- * 查看coupon是否是可用的,如果可用,返回true,如果不可用,返回false
- */
- protected function couponIsActive($isGetDiscount = false)
- {
- if ($this->_customer_id) {
- if ($couponModel = $this->getCouponModel()) {
- $expiration_date = $couponModel['expiration_date'];
- // 未过期
- if ($expiration_date > time()) {
- if ($isGetDiscount) {
- return true;
- }
- $couponUsageModel = $this->getCouponUsageModel();
- $times_used = 0;
- if ($couponUsageModel['times_used']) {
- $times_used = $couponUsageModel['times_used'];
- }
- $users_per_customer = $couponModel['users_per_customer'];
- // 次数限制
- if ($times_used < $users_per_customer) {
- return true;
- } else {
- Yii::$service->helper->errors->add('The coupon has exceeded the maximum number of uses');
- }
- } else {
- Yii::$service->helper->errors->add('coupon is expired');
- }
- } else {
- //Yii::$service->helper->errors->add("coupon is not exist");
- }
- }
- return false;
- }
- /**
- * @param $coupon_code | String , coupon_code字符串
- * @param $dc_price | Float 总价格
- * 根据优惠券和总价格,计算出来打折后的价格。譬如原来10元,打八折后,是8元。
- */
- protected function actionGetDiscount($coupon_code, $dc_price)
- {
- $discount_cost = 0;
- $this->useCouponInit($coupon_code);
- if ($this->couponIsActive(true)) {
- $couponModel = $this->getCouponModel();
- $type = $couponModel['type'];
- $conditions = $couponModel['conditions'];
- $discount = $couponModel['discount'];
- //echo $conditions.'##'.$dc_price;;exit;
- if ($conditions <= $dc_price) {
- if ($type == $this->coupon_type_percent) { // 百分比
- // $base_discount_cost = $discount / 100 * $dc_price;
- $base_discount_cost = (1-$discount / 100) * $dc_price;
- } elseif ($type == $this->coupon_type_direct) { // 直接折扣
- // $base_discount_cost = $dc_price - $discount;
- $base_discount_cost = $discount;
- }
- $curr_discount_cost = Yii::$service->page->currency->getCurrentCurrencyPrice($base_discount_cost);
- }
- }
- return [
- 'baseCost' => $base_discount_cost,
- 'currCost' => $curr_discount_cost,
- ];
- }
- /**
- * @param $type | String add or cancel
- * @return bool
- * 增加或者减少优惠券使用的次数
- */
- protected function updateCouponUse($type)
- {
- if ($this->_customer_id) {
- $c_model = $this->getCouponModel();
- if ($c_model) {
- if ($type == 'add') {
- $cu_model = $this->getCouponUsageModel();
- if (!$cu_model) {
- $cu_model = new $this->_couponUsageModelName;
- $cu_model->times_used = 1;
- $cu_model->customer_id = $this->_customer_id;
- $cu_model->coupon_id = $c_model['coupon_id'];
- $cu_model->save();
- } else {
- // 通过update函数 将times_used +1
- $sql = 'update '.$this->_couponUsageModel->tableName().' set times_used = times_used + 1 where id = :id';
- $data = [
- 'id' => $cu_model['id'],
- ];
- $result = $this->_couponUsageModel->getDb()->createCommand($sql, $data)->execute();
- }
- // coupon的总使用次数+1
- $sql = 'update '.$this->_couponModel->tableName().' set times_used = times_used + 1 where coupon_id = :coupon_id ';
- $data = [
- 'coupon_id' => $c_model['coupon_id'],
- ];
- $result = $this->_couponModel->getDb()->createCommand($sql, $data)->execute();
- return true;
- } elseif ($type == 'cancel') {
- $couponModel = $this->getCouponModel();
- $cu_model = $this->getCouponUsageModel();
- if ($cu_model) {
- // $this->_couponUsageModel 使用次数-1
- $sql = 'update '.$this->_couponUsageModel->tableName().' set times_used = times_used - 1 where id = :id';
- $data = [
- 'id' => $cu_model['id'],
- ];
- $result = $this->_couponUsageModel->getDb()->createCommand($sql, $data)->execute();
- // $this->_couponModel 使用次数-1
- $sql = 'update '.$this->_couponModel->tableName().' set times_used = times_used - 1 where coupon_id = :coupon_id ';
- $data = [
- 'coupon_id' => $c_model['coupon_id'],
- ];
- $result = $this->_couponModel->getDb()->createCommand($sql, $data)->execute();
-
- return true;
- }
- }
- }
- }
- }
- /**
- * @param $coupon_code | String 优惠卷码
- * 检查当前购物车中是否存在优惠券,如果存在,则覆盖当前的优惠券
- * 如果当前购物车没有使用优惠券,则检查优惠券是否可以使用
- * 如果优惠券可以使用,则使用优惠券进行打折。更新购物车信息。
- */
- protected function actionAddCoupon($coupon_code)
- {
- $this->useCouponInit($coupon_code);
- if ($this->couponIsActive()) {
- $couponModel = $this->getCouponModel();
- $type = $couponModel['type'];
- $conditions = $couponModel['conditions'];
- $discount = $couponModel['discount'];
- // 判断购物车金额是否满足条件
- $cartProduct = Yii::$service->cart->quoteItem->getCartProductInfo();
- $product_total = isset($cartProduct['product_total']) ? $cartProduct['product_total'] : 0;
- if ($product_total) {
- //var_dump($product_total);
- $dc_price = Yii::$service->page->currency->getBaseCurrencyPrice($product_total);
- if ($dc_price > $conditions) {
- // 更新购物侧的coupon 和优惠券的使用情况。
- // 在service中不要出现事务等操作。在调用层使用。
- //$innerTransaction = Yii::$app->db->beginTransaction();
- //try {
- $set_status = Yii::$service->cart->quote->setCartCoupon($coupon_code);
- $up_status = $this->updateCouponUse('add');
- if ($set_status && $up_status) {
- //$innerTransaction->commit();
- return true;
- } else {
- Yii::$service->helper->errors->add('add coupon fail');
- }
- //Yii::$service->helper->errors->add('add coupon fail');
- //$innerTransaction->rollBack();
- //} catch (\Exception $e) {
- //Yii::$service->helper->errors->add('add coupon fail');
- //$innerTransaction->rollBack();
- //}
- } else {
- Yii::$service->helper->errors->add('The coupon can not be used if the product amount in the shopping cart is less than {conditions} dollars', ['conditions' => $conditions]);
- }
- }
- } else {
- Yii::$service->helper->errors->add('Coupon is not available or has expired');
- }
- }
- /**
- * @param $coupon_code | String
- * 取消优惠券
- */
- protected function actionCancelCoupon($coupon_code)
- {
- $this->useCouponInit($coupon_code);
- if ($this->_customer_id) {
- $couponModel = $this->getCouponModel($coupon_code);
- if ($couponModel) {
- $up_status = $this->updateCouponUse('cancel');
- $cancel_status = Yii::$service->cart->quote->cancelCartCoupon($coupon_code);
- if ($up_status && $cancel_status) {
- return true;
- }
- }
- }
- }
- }
|