Files
exchange-2.0/app/Classes/Modules/Milestones/Processors/CheckMilestonesForRewardProcessor.php
2024-08-25 12:43:33 +08:00

171 lines
7.5 KiB
PHP

<?php
namespace App\Classes\Modules\Milestones\Processors;
use App\Classes\Modules\Vouchers\Services\Voucherify\CreatesVoucherifyVoucher;
use App\Classes\Modules\Vouchers\Services\CreatesVoucher;
use App\Classes\Modules\Vouchers\Services\FetchesVoucher;
use App\Classes\Modules\Vouchers\Services\Voucherify\FetchesVoucherifyVoucher;
use App\Classes\Modules\Vouchers\Services\Voucherify\ValidatesVoucherifyVoucher;
use App\Classes\Modules\Vouchers\DataTransferObjects\ValidateVoucherifyVoucherObject;
use App\Classes\Modules\Vouchers\DataTransferObjects\VoucherObject;
use App\Classes\Modules\Milestones\Services\FetchesMilestone;
use App\Classes\Modules\Milestones\Services\CreatesMilestoneProgress;
use App\Classes\Modules\Rewards\Services\CreatesUserReward;
use App\Classes\ValueObjects\Constants\RewardType;
use App\Models\Milestone;
use App\Models\MilestoneProgress;
use App\Models\Reward;
use App\Models\User;
use Illuminate\Support\Facades\Log;
class CheckMilestonesForRewardProcessor
{
/** @var CreatesVoucherifyVoucher */
private $createsVoucherifyVoucher;
/** @var CreatesVoucher */
private $createsVoucher;
/** @var CreatesMilestoneProgress */
private $createsMilestoneProgress;
/** @var FetchesMilestone */
private $fetchesMilestone;
/** @var CreatesUserReward */
private $createsUserReward;
/** @var FetchesVoucherifyVoucher */
private $fetchesVoucherifyVoucher;
/** @var FetchesVoucher */
private $fetchesVoucher;
/** @var ValidatesVoucherifyVoucher */
private $validatesVoucherifyVoucher;
/**
* CheckMilestonesForRewardProcessor constructor.
* @param CreatesVoucherifyVoucher $createsVoucherifyVoucher
* @param CreatesVoucher $createsVoucher
* @param FetchesMilestone $fetchesMilestone
* @param CreatesMilestoneProgress $createsMilestoneProgress
* @param CreatesUserReward $createsUserReward
* @param FetchesVoucherifyVoucher $fetchesVoucherifyVoucher
* @param FetchesVoucher $fetchesVoucher
* @param ValidatesVoucherifyVoucher $validatesVoucherifyVoucher
*/
public function __construct(CreatesVoucherifyVoucher $createsVoucherifyVoucher, CreatesVoucher $createsVoucher, FetchesMilestone $fetchesMilestone, CreatesMilestoneProgress $createsMilestoneProgress, CreatesUserReward $createsUserReward, FetchesVoucherifyVoucher $fetchesVoucherifyVoucher, FetchesVoucher $fetchesVoucher, ValidatesVoucherifyVoucher $validatesVoucherifyVoucher)
{
$this->createsVoucherifyVoucher = $createsVoucherifyVoucher;
$this->createsVoucher = $createsVoucher;
$this->fetchesMilestone = $fetchesMilestone;
$this->createsMilestoneProgress = $createsMilestoneProgress;
$this->createsUserReward = $createsUserReward;
$this->fetchesVoucherifyVoucher = $fetchesVoucherifyVoucher;
$this->fetchesVoucher = $fetchesVoucher;
$this->validatesVoucherifyVoucher = $validatesVoucherifyVoucher;
}
/**
* @param User $user
* @param array $milestone_constants
* @return void
* @throws \App\Classes\Exceptions\MalformedRequestException
* @throws \Voucherify\ClientException
*/
public function execute(User $user, array $milestone_constants)
{
try{
foreach($milestone_constants as $constant)
{
//update milestone progress
/** @var Milestone $milestone */
$milestone = $this->fetchesMilestone->execute(['name' => $constant]);
$result = null;
if($user->milestoneProgress->count() > 0){
$result = $user->milestoneProgress->where('milestone_id', $milestone->id)->first();
}
if(!$result){
$result = $this->createsMilestoneProgress->execute($milestone, $user->id);
}
if($result){
//fetch completed miletones
$completedMilestones = MilestoneProgress::where('user_id', $user->id)->pluck('milestone_id');
$rewards = $milestone->rewards;
//check for rewards that have a corresponding milestone count
if(count($rewards) > 0){
$this->checkMilestoneForReward($user, $completedMilestones, $rewards);
}
}
}
} catch (\Exception $e) {
Log::error($e);
}
}
/**
* @param User $user
* @param object $completedMilestones
* @param object $rewards
* @return void
*/
private function checkMilestoneForReward(User $user, object $completedMilestones, object $rewards)
{
$milestoneIds = $rewards[0]->milestones->pluck('id');
if ($milestoneIds->intersect($completedMilestones)->count() >= count($rewards[0]->milestones)) {
/** @var Reward $reward */
foreach ($rewards as $reward) {
$result = null;
if (!$user->rewards->contains('reward_id', $reward->id)) {
$voucherId = 0;
$voucherName = '';
$voucherType = "";
if($reward->type == RewardType::REWARD_AMOUNT){
//Voucherify - Create Voucher
$result = $this->createsVoucherifyVoucher->execute($user, intval($reward->value));
}
else{
//Voucherify - Validates Voucher
$ValidateVoucherifyVoucherObject = new ValidateVoucherifyVoucherObject(0, $reward->value, 0.00, $user);
$voucherifyVoucherValidated = $this->validatesVoucherifyVoucher->execute($ValidateVoucherifyVoucherObject);
if(!isset($voucherifyVoucherValidated->reason)){
//Voucherify - Get Voucher
$result = $this->fetchesVoucherifyVoucher->execute($user, $reward->value);
}
}
if($result && !isset($result->reason)){
$voucherName = isset($result->campaign) ? $result->campaign : $reward->name;
$voucherType = $result->discount->type;
$voucherValue = isset($result->discount->amount_off) ? $result->discount->amount_off : $result->discount->percent_off;
$voucherStartDate = $result->start_date;
$voucherEndDate = $result->expiration_date;
//create voucher
$voucherObject = new VoucherObject($result->code, isset($voucherName) ? $voucherName : "", null, $voucherType, $voucherValue, null, $voucherStartDate, $voucherEndDate);
$voucher = $this->createsVoucher->execute($voucherObject);
if(!$voucher) $voucher = $this->fetchesVoucher->execute(['code' => $voucherObject->getCode()]);
$voucherId = $voucher->id;
//create reward to user (user_reward)
$voucherCount = $user->rewards->where('voucher_id', $voucher->id)->count();
if($voucherCount == 0){
$this->createsUserReward->execute($reward, $user, $voucherId);
}
}
else{
Log::info('CheckMilestonesForRewardProcessor: no voucher fetched or created for reward '. json_encode($reward));
}
}
}
}
}
}