mirror of
https://gitlab.com/CIEFWorldwideSdnBhd/exchange-2.0.git
synced 2026-08-22 05:53:58 +00:00
Second voucher (first milestone) for user upon reaching 2 completed bookings
This commit is contained in:
@@ -2,7 +2,6 @@
|
||||
|
||||
namespace App\Classes\General\Eloquent\Filters;
|
||||
|
||||
use App\Classes\ValueObjects\Constants\RoleTypes;
|
||||
use Illuminate\Database\Eloquent\Builder;
|
||||
use Illuminate\Support\Facades\Auth;
|
||||
|
||||
@@ -12,33 +11,17 @@ class HasActiveReward implements Filter
|
||||
/**
|
||||
* @param Builder $builder
|
||||
* @param $value
|
||||
* @return mixed
|
||||
* @return Builder|mixed
|
||||
*/
|
||||
public static function apply(Builder $builder, $value)
|
||||
{
|
||||
if(in_array(Auth::user()->type, RoleTypes::ADMIN_ROLES)){
|
||||
// $userId = $value !== 1 ? $value : Auth::user()->id;
|
||||
$userId = $value;
|
||||
return $builder->where('user_id', $userId)
|
||||
->where(function ($query) {
|
||||
$query->whereHas('reward', function ($subquery) {
|
||||
$subquery->where('is_active', true);
|
||||
})
|
||||
->orWhereDoesntHave('reward');
|
||||
})
|
||||
->whereDoesntHave('voucher.redemptions.transaction.booking.company.employees', function ($query) use ($userId) {
|
||||
$query->where('user_id', $userId);
|
||||
return $builder->where('user_id', Auth::user()->id) //cief todo: should not use Auth::user()->id
|
||||
->where(function ($query) {
|
||||
$query->whereHas('reward', function ($subquery) {
|
||||
$subquery->where('is_active', true);
|
||||
});
|
||||
}
|
||||
else{
|
||||
return $builder->where('user_id', Auth::user()->id)
|
||||
->where(function ($query) {
|
||||
$query->whereHas('reward', function ($subquery) {
|
||||
$subquery->where('is_active', true);
|
||||
})
|
||||
->orWhereDoesntHave('reward');
|
||||
})
|
||||
->whereDoesntHave('voucher.redemptions.transaction.owner');
|
||||
}
|
||||
// ->orWhereDoesntHave('reward');
|
||||
});
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -0,0 +1,26 @@
|
||||
<?php
|
||||
|
||||
namespace App\Classes\General\Eloquent\Filters;
|
||||
|
||||
use Illuminate\Database\Eloquent\Builder;
|
||||
|
||||
class HasActiveRewardForAdmin implements Filter
|
||||
{
|
||||
|
||||
/**
|
||||
* @param Builder $builder
|
||||
* @param $value
|
||||
* @return Builder|mixed
|
||||
*/
|
||||
public static function apply(Builder $builder, $value)
|
||||
{
|
||||
return $builder->where('user_id', $value)
|
||||
->where(function ($query) {
|
||||
$query->whereHas('reward', function ($subquery) {
|
||||
$subquery->where('is_active', true);
|
||||
});
|
||||
// ->orWhereDoesntHave('reward');
|
||||
});
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,44 @@
|
||||
<?php
|
||||
|
||||
namespace App\Classes\General\Eloquent\Filters;
|
||||
|
||||
use App\Classes\ValueObjects\Constants\RoleTypes;
|
||||
use Illuminate\Database\Eloquent\Builder;
|
||||
use Illuminate\Support\Facades\Auth;
|
||||
|
||||
class HasVouchersAll implements Filter
|
||||
{
|
||||
|
||||
/**
|
||||
* @param Builder $builder
|
||||
* @param $value
|
||||
* @return mixed
|
||||
*/
|
||||
public static function apply(Builder $builder, $value)
|
||||
{
|
||||
if(in_array(Auth::user()->type, RoleTypes::ADMIN_ROLES)){
|
||||
// $userId = $value !== 1 ? $value : Auth::user()->id;
|
||||
$userId = $value;
|
||||
return $builder->where('user_id', $userId)
|
||||
->where(function ($query) {
|
||||
$query->whereHas('reward', function ($subquery) {
|
||||
$subquery->where('is_active', true);
|
||||
})
|
||||
->orWhereDoesntHave('reward');
|
||||
})
|
||||
->whereDoesntHave('voucher.redemptions.transaction.booking.company.employees', function ($query) use ($userId) {
|
||||
$query->where('user_id', $userId);
|
||||
});
|
||||
}
|
||||
else{
|
||||
return $builder->where('user_id', Auth::user()->id)
|
||||
->where(function ($query) {
|
||||
$query->whereHas('reward', function ($subquery) {
|
||||
$subquery->where('is_active', true);
|
||||
})
|
||||
->orWhereDoesntHave('reward');
|
||||
})
|
||||
->whereDoesntHave('voucher.redemptions.transaction.owner');
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,20 +0,0 @@
|
||||
<?php
|
||||
|
||||
namespace App\Classes\General\Eloquent\Filters;
|
||||
|
||||
use Illuminate\Database\Eloquent\Builder;
|
||||
|
||||
class RandomName implements Filter
|
||||
{
|
||||
|
||||
/**
|
||||
* @param Builder $builder
|
||||
* @param $value
|
||||
* @return Builder|mixed
|
||||
*/
|
||||
public static function apply(Builder $builder, $value)
|
||||
{
|
||||
return $builder->where('is_active', $value);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,38 @@
|
||||
<?php
|
||||
|
||||
namespace App\Classes\Jobs;
|
||||
|
||||
use App\Classes\Modules\Milestones\Processors\MilestoneRewardByTransactionProcessor;
|
||||
use App\Models\Transaction;
|
||||
use Illuminate\Bus\Queueable;
|
||||
use Illuminate\Contracts\Queue\ShouldQueue;
|
||||
use Illuminate\Foundation\Bus\Dispatchable;
|
||||
use Illuminate\Queue\InteractsWithQueue;
|
||||
use Illuminate\Queue\SerializesModels;
|
||||
|
||||
class CreateMilestoneRewardByTransactionJob implements ShouldQueue
|
||||
{
|
||||
use Dispatchable, InteractsWithQueue, Queueable, SerializesModels;
|
||||
|
||||
/** @var Transaction */
|
||||
private $transaction;
|
||||
|
||||
/** @var array */
|
||||
private $milestones;
|
||||
|
||||
/**
|
||||
* CreateMilestoneRewardByTransactionJob constructor.
|
||||
* @param Transaction $transaction
|
||||
* @param array $milestones
|
||||
*/
|
||||
public function __construct(Transaction $transaction, array $milestones)
|
||||
{
|
||||
$this->transaction = $transaction;
|
||||
$this->milestones = $milestones;
|
||||
}
|
||||
|
||||
public function handle()
|
||||
{
|
||||
(App()->make(MilestoneRewardByTransactionProcessor::class))->execute($this->transaction, $this->milestones);
|
||||
}
|
||||
}
|
||||
@@ -44,17 +44,6 @@ class ListDocumentsJob implements ShouldQueue
|
||||
}
|
||||
|
||||
$result = (App()->make(ListDocumentsJobProcessor::class))->execute($this->listGenericJobObject);
|
||||
|
||||
//cief todo: Insert into DB: job id, query result, timestamp
|
||||
// Store the result in the job_results table
|
||||
|
||||
//cief todo: why cannot save data in table like this
|
||||
// $model = new JobResult();
|
||||
// $model->job_id = $this->job->getJobId();
|
||||
// $model->result = json_encode($result);
|
||||
// $model->save();
|
||||
|
||||
// Log::error(json_encode($model->id));
|
||||
}
|
||||
|
||||
public function getJobId(){
|
||||
|
||||
@@ -11,7 +11,6 @@ use App\Classes\Modules\Companies\Processors\AssignEmployeeProcessor;
|
||||
use App\Classes\Modules\Companies\Processors\AssignSegmentProcessor;
|
||||
use App\Classes\Modules\Companies\Processors\CreateCompanyProcessor;
|
||||
use App\Classes\Modules\Contacts\Processors\CreateContactProcessor;
|
||||
use App\Classes\Modules\Milestones\Processors\CheckMilestonesForRewardProcessor;
|
||||
use App\Classes\Modules\Vouchers\Processors\Voucherify\NewCustomerToVoucherifyProcessor;
|
||||
use App\Classes\Modules\Vouchers\Processors\CreateVoucherProcessor;
|
||||
use App\Classes\Modules\Companies\DataTransferObjects\EmploymentObject;
|
||||
@@ -69,9 +68,6 @@ class CreateCustomerLogic extends AbstractControllerLogic
|
||||
/** @var CreatesSeasonalSegment */
|
||||
private $createsSeasonalSegment;
|
||||
|
||||
/** @var CheckMilestonesForRewardProcessor */
|
||||
private $checkMilestonesForRewardProcessor;
|
||||
|
||||
/** @var NewCustomerToVoucherifyProcessor */
|
||||
private $newCustomerToVoucherifyProcessor;
|
||||
|
||||
@@ -88,12 +84,11 @@ class CreateCustomerLogic extends AbstractControllerLogic
|
||||
* @param AuthenticationProcessor $authenticationProcessor
|
||||
* @param GenerateEmailVerificationAttemptProcessor $generateEmailVerificationAttemptProcessor
|
||||
* @param CreatesSeasonalSegment $createsSeasonalSegment
|
||||
* @param CheckMilestonesForRewardProcessor $checkMilestonesForRewardProcessor
|
||||
* @param NewCustomerToVoucherifyProcessor $newCustomerToVoucherifyProcessor
|
||||
* @param CreateVoucherProcessor $createVoucherProcessor
|
||||
*/
|
||||
public function __construct(CreateUserProcessor $createUserProcessor, CreateCompanyProcessor $createCompanyProcessor, CreateContactProcessor $createContactProcessor, AssignEmployeeProcessor $assignEmployeeProcessor, AssignSegmentProcessor $assignSegmentProcessor, AuthenticationProcessor $authenticationProcessor, GenerateEmailVerificationAttemptProcessor $generateEmailVerificationAttemptProcessor,
|
||||
CreatesSeasonalSegment $createsSeasonalSegment, CheckMilestonesForRewardProcessor $checkMilestonesForRewardProcessor, NewCustomerToVoucherifyProcessor $newCustomerToVoucherifyProcessor, CreateVoucherProcessor $createVoucherProcessor)
|
||||
CreatesSeasonalSegment $createsSeasonalSegment, NewCustomerToVoucherifyProcessor $newCustomerToVoucherifyProcessor, CreateVoucherProcessor $createVoucherProcessor)
|
||||
{
|
||||
$this->createUserProcessor = $createUserProcessor;
|
||||
$this->createCompanyProcessor = $createCompanyProcessor;
|
||||
@@ -103,7 +98,6 @@ class CreateCustomerLogic extends AbstractControllerLogic
|
||||
$this->authenticationProcessor = $authenticationProcessor;
|
||||
$this->generateEmailVerificationAttemptProcessor = $generateEmailVerificationAttemptProcessor;
|
||||
$this->createsSeasonalSegment = $createsSeasonalSegment;
|
||||
$this->checkMilestonesForRewardProcessor = $checkMilestonesForRewardProcessor;
|
||||
$this->newCustomerToVoucherifyProcessor = $newCustomerToVoucherifyProcessor;
|
||||
$this->createVoucherProcessor = $createVoucherProcessor;
|
||||
}
|
||||
|
||||
@@ -82,7 +82,7 @@ class AuthenticationProcessor
|
||||
}
|
||||
|
||||
//cief todo: case study 1
|
||||
//$this->checkMilestonesForRewardProcessor->execute($user, [Milestones::MILESTONE_1]);
|
||||
//$this->checkMilestonesForRewardProcessor->execute($user, [Milestones::MILESTONE_DEMO_1]);
|
||||
|
||||
return ['access_token' => $this->generatesAuthenticationToken->execute($user), 'redirect_url' => $this->authenticationRedirect->url($user)];
|
||||
}
|
||||
|
||||
@@ -26,6 +26,8 @@ use App\Classes\Modules\Transactions\Services\UpdatesTransactionStatus;
|
||||
use Illuminate\Support\Facades\Auth;
|
||||
use Illuminate\Support\Facades\Log;
|
||||
use App\Classes\Modules\Wallets\Services\RecalculatesWalletBalance;
|
||||
use App\Classes\Jobs\CreateMilestoneRewardByTransactionJob;
|
||||
use App\Classes\ValueObjects\Constants\Milestones;
|
||||
|
||||
class CallbackBillplzLogic
|
||||
{
|
||||
@@ -55,7 +57,9 @@ class CallbackBillplzLogic
|
||||
* @param FetchesTransaction $fetchesTransaction
|
||||
* @param UpdatesTransactionStatus $updatesTransactionStatus
|
||||
* @param UpdatesWalletBalance $updatesWalletBalance
|
||||
* @param CreateCashBackTransactionProcessor $createCashBackTransactionProcessor
|
||||
* @param RecalculatesWalletBalance $recalculatesWalletBalance
|
||||
* @param CreateMilestoneRewardJob $createMilestoneRewardJob
|
||||
*/
|
||||
public function __construct(GetBillplzBill $getBillplzBill, FetchesTransaction $fetchesTransaction, UpdatesTransactionStatus $updatesTransactionStatus, UpdatesWalletBalance $updatesWalletBalance, CreateCashBackTransactionProcessor $createCashBackTransactionProcessor, RecalculatesWalletBalance $recalculatesWalletBalance)
|
||||
{
|
||||
@@ -87,7 +91,8 @@ class CallbackBillplzLogic
|
||||
if(!$billPlz) throw new ResourceNotFoundException('Billplz bill not found.');
|
||||
|
||||
$transaction = $this->fetchesTransaction->execute(['payment_reference' => $billplzXSignatureObject->getBillPlzId()]);
|
||||
|
||||
CreateMilestoneRewardByTransactionJob::dispatch($transaction, [Milestones::MILESTONE_1]);
|
||||
|
||||
if($billPlz->state === 'paid') {
|
||||
$status = ApprovalStatus::APPROVED;
|
||||
}
|
||||
@@ -117,4 +122,4 @@ class CallbackBillplzLogic
|
||||
return $request->method() === 'POST' ? true : view('pages.payments_redirect', ['marking' => $marking ?? null, 'transaction' => $transaction, 'status' => $status]);
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -81,9 +81,12 @@ class CheckMilestonesForRewardProcessor
|
||||
try{
|
||||
foreach($milestone_constants as $constant)
|
||||
{
|
||||
//update milestone progress
|
||||
/** @var Milestone $milestone */
|
||||
$milestone = $this->fetchesMilestone->execute(['name' => $constant]);
|
||||
//update milestone progres
|
||||
$milestone = Milestone::where('name', $constant)->first();
|
||||
if(!$milestone) {
|
||||
Log::error("{$constant} NOT FOUND!");
|
||||
continue;
|
||||
}
|
||||
$result = null;
|
||||
if($user->milestoneProgress->count() > 0){
|
||||
$result = $user->milestoneProgress->where('milestone_id', $milestone->id)->first();
|
||||
@@ -130,6 +133,10 @@ class CheckMilestonesForRewardProcessor
|
||||
//Voucherify - Create Voucher
|
||||
$result = $this->createsVoucherifyVoucher->execute($user, intval($reward->value));
|
||||
}
|
||||
else if($reward->type == RewardType::REWARD_CODE){
|
||||
//Voucherify - Get Voucher
|
||||
$result = $this->fetchesVoucherifyVoucher->execute($user, $reward->value);
|
||||
}
|
||||
else{
|
||||
//Voucherify - Validates Voucher
|
||||
$ValidateVoucherifyVoucherObject = new ValidateVoucherifyVoucherObject(0, $reward->value, 0.00, $user);
|
||||
|
||||
@@ -0,0 +1,48 @@
|
||||
<?php
|
||||
|
||||
namespace App\Classes\Modules\Milestones\Processors;
|
||||
|
||||
|
||||
use App\Classes\Modules\Milestones\Processors\CheckMilestonesForRewardProcessor;
|
||||
use App\Classes\ValueObjects\Constants\ApprovalStatus;
|
||||
use App\Classes\ValueObjects\Constants\Milestones;
|
||||
use App\Models\Booking;
|
||||
use App\Models\Transaction;
|
||||
use Illuminate\Support\Facades\Log;
|
||||
|
||||
class MilestoneRewardByTransactionProcessor
|
||||
{
|
||||
/** @var CheckMilestonesForRewardProcessor */
|
||||
private $checkMilestonesForRewardProcessor;
|
||||
|
||||
/**
|
||||
* MilestoneRewardByTransactionProcessor constructor.
|
||||
* @param CheckMilestonesForRewardProcessor $checkMilestonesForRewardProcessor
|
||||
*/
|
||||
public function __construct(CheckMilestonesForRewardProcessor $checkMilestonesForRewardProcessor)
|
||||
{
|
||||
$this->checkMilestonesForRewardProcessor = $checkMilestonesForRewardProcessor;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @param Transaction $transaction
|
||||
* @param array $milestones
|
||||
* @throws \App\Classes\Exceptions\AccessForbiddenException
|
||||
* @throws \App\Classes\Exceptions\MalformedRequestException
|
||||
*/
|
||||
public function execute(Transaction $transaction, array $milestones)
|
||||
{
|
||||
$company = $transaction->owner instanceof Booking ? $transaction->owner()->first()->company : null;
|
||||
if($company){
|
||||
$completedBookingCount = count($company->bookings()->where('status', ApprovalStatus::COMPLETED)->get());
|
||||
Log::info("Number of completed bookings completed for company ".$company->reference. ": " .$completedBookingCount);
|
||||
if (in_array(Milestones::MILESTONE_1, $milestones)) {
|
||||
if($completedBookingCount === 2){
|
||||
$user = $company->employees()->first();
|
||||
$this->checkMilestonesForRewardProcessor->execute($user, [Milestones::MILESTONE_1]);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -6,8 +6,9 @@ class MilestoneCreationOptions
|
||||
{
|
||||
const OPTIONS_MILESTONE_NAME= [
|
||||
['text' => 'MILESTONE 1', 'id' => Milestones::MILESTONE_1],
|
||||
['text' => 'MILESTONE 2', 'id' => Milestones::MILESTONE_2],
|
||||
['text' => 'MILESTONE 3', 'id' => Milestones::MILESTONE_3],
|
||||
// ['text' => 'MILESTONE DEMO 1', 'id' => Milestones::MILESTONE_DEMO_1],
|
||||
// ['text' => 'MILESTONE 2', 'id' => Milestones::MILESTONE_2],
|
||||
// ['text' => 'MILESTONE 3', 'id' => Milestones::MILESTONE_3],
|
||||
// ['text' => 'MILESTONE 4', 'id' => Milestones::MILESTONE_4],
|
||||
// ['text' => 'MILESTONE 5', 'id' => Milestones::MILESTONE_5],
|
||||
// ['text' => 'MILESTONE 6', 'id' => Milestones::MILESTONE_6],
|
||||
|
||||
@@ -4,9 +4,10 @@ namespace App\Classes\ValueObjects\Constants;
|
||||
|
||||
class Milestones
|
||||
{
|
||||
public const MILESTONE_1 = 'MILESTONE 1'; //Authentication (Sign in) or CreateCustomerLogic (Sign up)
|
||||
public const MILESTONE_2 = 'MILESTONE 2'; //Create Identification Document
|
||||
public const MILESTONE_3 = 'MILESTONE 3'; //Assign Company to Segment Logic -segment.assign when accept 1688
|
||||
public const MILESTONE_1 = 'MILESTONE 1'; //Has 2 successful bookings
|
||||
// public const MILESTONE_DEMO_1 = 'MILESTONE_DEMO_1 1'; //Authentication (Sign in) or CreateCustomerLogic (Sign up)
|
||||
// public const MILESTONE_2 = 'MILESTONE 2'; //Create Identification Document
|
||||
// public const MILESTONE_3 = 'MILESTONE 3'; //Assign Company to Segment Logic -segment.assign when accept 1688
|
||||
// public const MILESTONE_4 = 'MILESTONE 4'; //Create Bank Logic (Transfer Now from dashboard)
|
||||
// public const MILESTONE_5 = 'MILESTONE 5'; //Create Booking Logic
|
||||
// public const MILESTONE_6 = 'MILESTONE 6'; //Create Address Logic (At transfer page before create booking)
|
||||
|
||||
@@ -16,7 +16,7 @@ class VoucherResource extends JsonResource
|
||||
public function toArray($request)
|
||||
{
|
||||
$filteredRedemptions = new ArrayObject([]);
|
||||
if ($request->has('filters') && str_contains($request->input('filters'), "has_active_reward")) {
|
||||
if ($request->has('filters') && str_contains($request->input('filters'), "has_vouchers_all")) {
|
||||
$filteredRedemptions = new ArrayObject([]);
|
||||
}
|
||||
else{
|
||||
|
||||
@@ -0,0 +1,42 @@
|
||||
<template>
|
||||
<div class="row h-100 parentContainer">
|
||||
<div class="col">
|
||||
<a :href="route('rewards')" >
|
||||
<div class="text-white all-caps fs-12">Vouchers</div>
|
||||
<div v-if="showVoucherUpdateIndicator" class="update-indicator"></div>
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
<script>
|
||||
export default {
|
||||
computed: {
|
||||
showVoucherUpdateIndicator() {
|
||||
return this.$store.getters.showVoucherUpdateIndicator;
|
||||
}
|
||||
},
|
||||
created(){
|
||||
this.submit(this.route('api.voucher.user.list') + '?filters=' + JSON.stringify( { 'has_vouchers_all': true, order_by:{ column:'id', DESC:true }} ), 'get', 'voucherNavigationSection', false, false);
|
||||
},
|
||||
methods: {
|
||||
successHandler(response){
|
||||
this.$store.dispatch('updateLatestVoucherTimestamp', response.payload.data.length > 0 ? response.payload.data[0].created_at : null)
|
||||
.then(() => {
|
||||
this.$store.dispatch('updateVoucherCount', response.payload.data.length);
|
||||
});
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
</script>
|
||||
<style>
|
||||
.update-indicator {
|
||||
width: 10px;
|
||||
height: 10px;
|
||||
background-color: red;
|
||||
border-radius: 50%;
|
||||
position: absolute;
|
||||
top: 0px;
|
||||
right: 5px;
|
||||
}
|
||||
</style>
|
||||
@@ -68,11 +68,13 @@
|
||||
},
|
||||
successHandler(){
|
||||
this.$store.dispatch('userAuthentication', {access_token: '', redirect_url: this.route('login')});
|
||||
this.$store.dispatch('clearVoucher');
|
||||
},
|
||||
errorHandler(){
|
||||
this.$store.dispatch('userAuthentication', {access_token: '', redirect_url: this.route('login')});
|
||||
this.$store.dispatch('clearVoucher');
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
</script>
|
||||
</script>
|
||||
|
||||
@@ -12,11 +12,14 @@
|
||||
<span>{{ item.voucher.code }}</span>
|
||||
</div>
|
||||
<div class="row">
|
||||
<span v-if="item.voucher.end_date">
|
||||
<span v-if="item.voucher.end_date && new Date() > new Date(item.voucher.end_date)">
|
||||
This voucher has expired.
|
||||
</span>
|
||||
<span v-else-if="item.voucher.end_date">
|
||||
Valid till {{ item.voucher.end_date }}
|
||||
</span>
|
||||
<span v-else>
|
||||
No expiry date
|
||||
Non-expired
|
||||
</span>
|
||||
</div>
|
||||
</div>
|
||||
@@ -62,7 +65,7 @@
|
||||
fetchVouchers(){
|
||||
this.isLoading = true;
|
||||
if(this.employee){
|
||||
this.submit(route('api.voucher.user.list') + '?filters=' + JSON.stringify( { 'has_active_reward': this.employee.id} ), 'get', this.section, false, false);
|
||||
this.submit(route('api.voucher.user.list') + '?filters=' + JSON.stringify( { 'has_vouchers_all': this.employee.id} ), 'get', this.section, false, false);
|
||||
}
|
||||
},
|
||||
successHandler(response){
|
||||
|
||||
@@ -26,11 +26,14 @@
|
||||
<p v-if="item.voucher.type == 'AMOUNT'">RM{{ item.voucher.value/100 }} Discount</p>
|
||||
<p v-if="item.voucher.type == 'PERCENT'">{{ item.voucher.value }}% Discount</p>
|
||||
</div>
|
||||
<div class="col" v-if="item.voucher.end_date">
|
||||
<div class="col" v-if="item.voucher.end_date && new Date() > new Date(item.voucher.end_date)">
|
||||
This voucher has expired.
|
||||
</div>
|
||||
<div class="col" v-else-if="item.voucher.end_date">
|
||||
Valid till {{ item.voucher.end_date }}
|
||||
</div>
|
||||
<div class="col" v-else>
|
||||
No expiry date
|
||||
Non-expired
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
@@ -76,7 +79,7 @@
|
||||
fetchVouchers(){
|
||||
this.isLoading = true;
|
||||
if(this.employee){
|
||||
this.submit(route('api.voucher.user.list') + '?filters=' + JSON.stringify( { 'has_active_reward': this.employee.id} ), 'get', this.section, false, false);
|
||||
this.submit(route('api.voucher.user.list') + '?filters=' + JSON.stringify( { 'has_vouchers_all': this.employee.id} ), 'get', this.section, false, false);
|
||||
}
|
||||
},
|
||||
successHandler(response){
|
||||
|
||||
+4
-1
@@ -17,11 +17,14 @@
|
||||
<p v-if="item.voucher && item.voucher.is_redeemed">
|
||||
Voucher claimed
|
||||
</p>
|
||||
<p v-else-if="item.voucher.end_date && new Date() > new Date(item.voucher.end_date)">
|
||||
This voucher has expired.
|
||||
</p>
|
||||
<p v-else-if="item.voucher && item.voucher.end_date">
|
||||
Valid till {{ item.voucher.end_date }}
|
||||
</p>
|
||||
<p v-else>
|
||||
-
|
||||
Non-expired
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
+1
@@ -201,6 +201,7 @@
|
||||
</div>
|
||||
</div>
|
||||
<div class="col-12 col-lg-3">
|
||||
<vouchers-summary-component></vouchers-summary-component>
|
||||
<wallet-component :data="company"></wallet-component>
|
||||
<verification-warning-component v-if="!isLoading" :data="company"></verification-warning-component>
|
||||
<new-service-announcement-component :data="company"></new-service-announcement-component>
|
||||
|
||||
+2
-1
@@ -141,6 +141,7 @@
|
||||
<div class="col">
|
||||
<div class="row">
|
||||
<div class="col m-b-15">
|
||||
<vouchers-summary-admin-component v-if="company" :company="company"></vouchers-summary-admin-component>
|
||||
<wallet-component :data="company" :creditable=true></wallet-component>
|
||||
</div>
|
||||
</div>
|
||||
@@ -213,4 +214,4 @@
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
</script>
|
||||
|
||||
+7
-2
@@ -52,7 +52,7 @@
|
||||
<div class="col">
|
||||
<div class="row">
|
||||
<div class="col" v-if="this.$store.getters.getUserId">
|
||||
<list-component section="customerVouchersListSection" :endpoint="route('api.voucher.user.list')" :options="{ 'has_active_reward': id }">
|
||||
<list-component section="customerVouchersListSection" :endpoint="route('api.voucher.user.list')" :options="{ 'has_vouchers_all': id }">
|
||||
<template slot="list" slot-scope="{data}">
|
||||
<single-user-reward-item-component :data="data"></single-user-reward-item-component>
|
||||
</template>
|
||||
@@ -69,10 +69,15 @@
|
||||
<div class="col">
|
||||
<div class="row">
|
||||
<div class="col" v-if="this.$store.getters.getUserId">
|
||||
<list-component section="customerRewardsListSection" :endpoint="route('api.reward.list.details.admin', id)" :options="{'is_active': true, order_by:{ column:'order', DESC:false}}">
|
||||
<!-- <list-component section="customerRewardsListSection" :endpoint="route('api.reward.list.details.admin', id)" :options="{'is_active': true, order_by:{ column:'order', DESC:false}}">
|
||||
<template slot="list" slot-scope="{data}">
|
||||
<single-reward-details-item-component :data="data"></single-reward-details-item-component>
|
||||
</template>
|
||||
</list-component> -->
|
||||
<list-component section="customerRewardsListSection" :endpoint="route('api.voucher.user.list')" :options="{'has_active_reward_for_admin': id}">
|
||||
<template slot="list" slot-scope="{data}">
|
||||
<single-user-reward-item-component :data="data"></single-user-reward-item-component>
|
||||
</template>
|
||||
</list-component>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
+15
-6
@@ -19,7 +19,7 @@
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="col m-r-5 d-none d-md-inline">
|
||||
<!-- <div class="col m-r-5 d-none d-md-inline">
|
||||
<div class="row fs-12 text-center">
|
||||
<div class="col p-t-20 p-b-20 bg-master-lighter tabButton" tab-name="rewards">
|
||||
<div class="row">
|
||||
@@ -29,7 +29,7 @@
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div> -->
|
||||
<div class="col m-r-5 d-none d-md-inline">
|
||||
<div class="row fs-12 text-center">
|
||||
<div class="col p-t-20 p-b-20 bg-master-lighter tabButton" tab-name="used">
|
||||
@@ -52,7 +52,7 @@
|
||||
<div class="col">
|
||||
<div class="row">
|
||||
<div class="col" v-if="this.$store.getters.getUserId">
|
||||
<list-component section="customerVouchersListSection" :endpoint="route('api.voucher.user.list')" :options="{ 'has_active_reward': true }">
|
||||
<list-component section="customerVouchersListSection" :endpoint="route('api.voucher.user.list')" :options="{ 'has_vouchers_all': true }">
|
||||
<template slot="list" slot-scope="{data}">
|
||||
<single-user-reward-item-component :data="data"></single-user-reward-item-component>
|
||||
</template>
|
||||
@@ -69,11 +69,16 @@
|
||||
<div class="col">
|
||||
<div class="row">
|
||||
<div class="col" v-if="this.$store.getters.getUserId">
|
||||
<list-component section="customerRewardsListSection" :endpoint="route('api.reward.list.details')" :options="{'random_name': true, order_by:{ column:'order', DESC:false}}">
|
||||
<!-- <list-component section="customerRewardsListSection" :endpoint="route('api.reward.list.details')" :options="{'has_active_reward': true, order_by:{ column:'order', DESC:false}}">
|
||||
<template slot="list" slot-scope="{data}">
|
||||
<single-reward-details-item-component :data="data"></single-reward-details-item-component>
|
||||
</template>
|
||||
</list-component>
|
||||
</list-component> -->
|
||||
<!-- <list-component section="customerRewardsListSection" :endpoint="route('api.voucher.user.list')" :options="{'has_active_reward': true}">
|
||||
<template slot="list" slot-scope="{data}">
|
||||
<single-user-reward-item-component :data="data"></single-user-reward-item-component>
|
||||
</template>
|
||||
</list-component> -->
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
@@ -108,5 +113,9 @@
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {}
|
||||
export default {
|
||||
created(){
|
||||
this.$store.dispatch('markVouchersAsSeen');
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
@@ -0,0 +1,42 @@
|
||||
<template>
|
||||
<div class="row parentContainer" style="margin-bottom: 8px;">
|
||||
<div class="col">
|
||||
<div class="bg-complete">
|
||||
<div class="row align-items-end" style="padding: 8px 25px;">
|
||||
<div class="col-auto">
|
||||
<a :href="route('customer.reward', company.reference)" target="_blank">
|
||||
<i class="fa fa-spinner fa-spin m-b-5 text-white" v-show="$store.getters.isLoading(section)"></i>
|
||||
<div v-show="!$store.getters.isLoading(section)" class="text-primary-lighter fs-10 text-uppercase">Vouchers: <span class="text-white no-margin bold">{{ vouchersCount }}</span><i class="fa fa-external-link text-white m-l-10"></i></div>
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
props: {
|
||||
company: {
|
||||
type: Object,
|
||||
required: true
|
||||
}
|
||||
},
|
||||
data(){
|
||||
return {
|
||||
section: 'customerVouchersSummaryAdminSection',
|
||||
vouchersCount: 0,
|
||||
}
|
||||
},
|
||||
created(){
|
||||
this.submit(this.route('api.voucher.user.list') + '?filters=' + JSON.stringify( { 'has_vouchers_all': this.company.employee.id, order_by:{ column:'id', DESC:true }} ), 'get', this.section, false, false);
|
||||
},
|
||||
methods: {
|
||||
successHandler(response){
|
||||
this.vouchersCount = response.payload.data.length;
|
||||
},
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
@@ -0,0 +1,26 @@
|
||||
<template>
|
||||
<div class="row parentContainer" style="margin-bottom: 8px;">
|
||||
<div class="col">
|
||||
<div class="bg-complete">
|
||||
<div class="row align-items-end" style="padding: 8px 25px;">
|
||||
<div class="col-auto">
|
||||
<a :href="route('rewards')" >
|
||||
<div class="text-primary-lighter fs-10 text-uppercase">Vouchers: <span class="text-white no-margin bold">{{ vouchersCount }}</span></div>
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
computed: {
|
||||
vouchersCount() {
|
||||
return this.$store.getters.getVouchersCount;
|
||||
}
|
||||
},
|
||||
}
|
||||
</script>
|
||||
|
||||
@@ -0,0 +1,60 @@
|
||||
const initialState = {
|
||||
vouchersCount: localStorage.getItem('voucher-count') || 0,
|
||||
latestVoucherTimestamp: localStorage.getItem('latest-voucher-timestamp') || null,
|
||||
lastSeenVoucherTimestamp: localStorage.getItem('last-seen-voucher-timestamp') || null,
|
||||
};
|
||||
|
||||
export default {
|
||||
state: { ...initialState },
|
||||
getters: {
|
||||
getVouchersCount: state => {
|
||||
return state.vouchersCount;
|
||||
},
|
||||
showVoucherUpdateIndicator: state => {
|
||||
if (!state.lastSeenVoucherTimestamp && state.voucherCount > 0) {
|
||||
return true;
|
||||
}
|
||||
if (!state.latestVoucherTimestamp) {
|
||||
return false;
|
||||
}
|
||||
const latestTime = new Date(state.latestVoucherTimestamp).getTime();
|
||||
const lastSeenTime = new Date(state.lastSeenVoucherTimestamp).getTime();
|
||||
return latestTime > lastSeenTime;
|
||||
}
|
||||
},
|
||||
mutations: {
|
||||
SET_VOUCHER_LATEST_TIMESTAMP(state, timestamp) {
|
||||
state.latestVoucherTimestamp = timestamp;
|
||||
},
|
||||
SET_VOUCHER_LAST_SEEN_TIMESTAMP(state, timestamp) {
|
||||
state.lastSeenVoucherTimestamp = timestamp;
|
||||
},
|
||||
SET_VOUCHER_COUNT(state, count) {
|
||||
state.vouchersCount = count;
|
||||
},
|
||||
RESET_VOUCHER_STATE(state) {
|
||||
Object.assign(state, initialState);
|
||||
}
|
||||
},
|
||||
actions: {
|
||||
updateLatestVoucherTimestamp(store, timestamp){
|
||||
localStorage.setItem('latest-voucher-timestamp', timestamp);
|
||||
store.commit('SET_VOUCHER_LATEST_TIMESTAMP', timestamp);
|
||||
},
|
||||
markVouchersAsSeen(store) {
|
||||
const latestVoucherTimestamp = store.state.latestVoucherTimestamp;
|
||||
localStorage.setItem('last-seen-voucher-timestamp', latestVoucherTimestamp);
|
||||
store.commit('SET_VOUCHER_LAST_SEEN_TIMESTAMP', latestVoucherTimestamp);
|
||||
},
|
||||
updateVoucherCount(store, count){
|
||||
localStorage.setItem('voucher-count', count);
|
||||
store.commit('SET_VOUCHER_COUNT', count);
|
||||
},
|
||||
clearVoucher(store, count){
|
||||
localStorage.removeItem('voucher-count');
|
||||
localStorage.removeItem('latest-voucher-timestamp');
|
||||
localStorage.removeItem('last-seen-voucher-timestamp');
|
||||
store.commit('RESET_VOUCHER_STATE');
|
||||
},
|
||||
}
|
||||
}
|
||||
Vendored
+3
-1
@@ -7,6 +7,7 @@ import crudRequest from './modules/crudRequest'
|
||||
import crudRequestV2 from './modules/crudRequestV2'
|
||||
import authentication from './modules/authentication'
|
||||
import loadRequestQueue from './modules/loadRequestQueue'
|
||||
import voucherUpdates from './modules/voucherUpdates'
|
||||
|
||||
Vue.use(Vuex);
|
||||
|
||||
@@ -18,6 +19,7 @@ export default new Vuex.Store({
|
||||
createNotification,
|
||||
crudRequest,
|
||||
crudRequestV2,
|
||||
authentication
|
||||
authentication,
|
||||
voucherUpdates
|
||||
}
|
||||
})
|
||||
|
||||
@@ -61,9 +61,10 @@
|
||||
<div v-if="$store.getters.isCustomer" class="col-auto p-r-20">
|
||||
<a href="{{route('banks')}}"><div class="text-white all-caps fs-12">Bank Accounts</div></a>
|
||||
</div>
|
||||
<!-- <div v-if="$store.getters.isCustomer" class="col-auto p-r-20">
|
||||
<a href="{{route('rewards')}}"><div class="text-white all-caps fs-12">Vouchers</div></a>
|
||||
</div> -->
|
||||
<div v-if="$store.getters.isCustomer" class="col-auto p-r-20">
|
||||
<vouchers-navigation-bar-component></vouchers-navigation-bar-component>
|
||||
<!-- <a href="{{route('rewards')}}"><div class="text-white all-caps fs-12">Vouchers</div></a> -->
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
+1
-3
@@ -60,15 +60,13 @@ Route::group(['middleware' => 'api', 'prefix' => 'v1', 'as' => 'api.'], function
|
||||
require __DIR__ . '/wallet.php';
|
||||
|
||||
require __DIR__ . '/voucher.php';
|
||||
|
||||
|
||||
require __DIR__ . '/accounting.php';
|
||||
|
||||
require __DIR__ . '/reward.php';
|
||||
|
||||
require __DIR__ . '/milestone.php';
|
||||
|
||||
// require __DIR__ . '/accounting.php'; //cief todo: To check if this is needed
|
||||
|
||||
require __DIR__ . '/job.php';
|
||||
|
||||
// require __DIR__ . '/rate.php';
|
||||
|
||||
Reference in New Issue
Block a user