Skip to content

Commit

Permalink
🔧 refactor(providers.js): import lodash's isUndefined function for be…
Browse files Browse the repository at this point in the history
…tter null checking

🔧 refactor(providers.js): add subscription ref to keep track of subscription data
🔧 refactor(providers.js): add senderNo to defaultSystemProvider for better SMS handling
🔧 refactor(providers.js): add subscription value assignment after fetching subscription data
🔧 refactor(providers.js): change creditsCount calculation to include consumed credits
🔧 refactor(providers.js): add upsellSubscription function to handle subscription upgrades
🔧 refactor(providers.js): refactor topupProvider function to handle credit top-ups and limit checks
🔧 refactor(providers.js): add subscription to returned object for external access

📦 feat(CreditPurchaseDialog.vue): add new component for handling credit purchases

🔧 refactor(SettingsEmail.vue): import CreditPurchaseDialog component
🔧 refactor(SettingsEmail.vue): add creditsDialog ref for handling credit purchase dialog
🔧 refactor(SettingsEmail.vue): add openCreditsDialog function to handle opening of credit purchase dialog
🔧 refactor(SettingsEmail.vue): add processPurchase function to handle credit purchase processing
🔧 refactor(SettingsEmail.vue): add event listener for purchase event from CreditPurchaseDialog component
🔧 refactor(SettingsEmail.vue): add disabled attribute to Buy more credits button for system provider
🔧 refactor(SettingsEmail.vue): add default value for systemProvider's defaultFrom

🔧 refactor(SettingsSMS.vue): import CreditPurchaseDialog component
🔧 refactor(SettingsSMS.vue): add creditsDialog ref for handling credit purchase dialog
🔧 refactor(SettingsSMS.vue): add openCreditsDialog function to handle opening of credit purchase dialog
🔧 refactor(SettingsSMS.vue): add processPurchase function to handle credit purchase processing
🔧 refactor(SettingsSMS.vue): add event listener for purchase event from CreditPurchaseDialog component
🔧 refactor(SettingsSMS.vue): add disabled attribute to Buy more credits button for system provider
🔧 refactor(SettingsSMS.vue): add default value for provider's senderNo or defaultFrom

The changes were made to improve the handling of credit purchases and subscription upgrades. The addition of the CreditPurchaseDialog component allows users to purchase credits directly from the settings page. The refactoring of the topupProvider function in providers.js now handles credit top-ups and checks if the new credit amount exceeds the maximum limit. The addition of the upsellSubscription function handles subscription upgrades
  • Loading branch information
jmcruz14 committed Oct 27, 2023
1 parent 89087af commit 4d09074
Show file tree
Hide file tree
Showing 4 changed files with 145 additions and 12 deletions.
28 changes: 24 additions & 4 deletions src/boot/providers.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ import { ref } from 'vue';
import { useSdk } from 'boot/sdk.js';
import { useActiveMembership } from 'boot/membership.js';
import { deepFreeze } from 'boot/helpers';
import { isUndefined } from 'lodash'

export function fetchProvider (type, opts) {
opts = Object.assign({
Expand All @@ -10,13 +11,15 @@ export function fetchProvider (type, opts) {

const sdk = useSdk();
const activeMembership = useActiveMembership();
const subscription = ref(null);

// default 0-credit system provider
const defaultSystemProvider = deepFreeze({
id: `system-${type}`,
type: 'sms',
label: `MYCURE ${type} provider`,
defaultFrom: '[email protected]',
senderNo: '+12017482119',
isSystemProvider: true,
creditsCount: 0,
});
Expand All @@ -39,10 +42,11 @@ export function fetchProvider (type, opts) {
const sub = await sdk.get('subscriptions', {
organization: activeMembership.value.organization.id,
});
subscription.value = sub;
const creditsMax = sub?.[`${type}CreditsMax`] || 0;
const creditsConsumed = sub?.[`${type}CreditsConsumed`] || 0;
return Object.assign({}, defaultSystemProvider, {
creditsCount: Math.max(0, creditsMax - creditsConsumed),
creditsCount: Math.max(0, creditsMax + creditsConsumed),
});
};
const fetchProvider = async () => {
Expand Down Expand Up @@ -96,15 +100,31 @@ export function fetchProvider (type, opts) {
provider.value = await fetchSystemProvider();
};

// upgrade subscription
const upsellSubscription = (subscription) => {
// redirect trialing user to upgrade their subscription plan
console.warn('SUBSCRIPTION-CHECK', subscription);
}

// for system provider
const topupProvider = async (item, credits) => {
// TODO: implement
await new Promise(resolve => setTimeout(resolve, 1000));
const topupProvider = async (type, credits) => {
const newAmt = credits + subscription.value?.[`${type}CreditsMax`]
const maxAmt = subscription.value?.package?.products?.[`${type}CreditsMax`]?.max
if (!subscription.value && !type) return;
if (!isUndefined(maxAmt) && newAmt > maxAmt) return new Error('New credit exceeds acceptable limit!')
// if (subscription.value?.status !== 'paid') await upsellSubscription(subscription);
const query = {};
query[`${type}CreditsMax`] = newAmt;
// const res = await sdk.get('subscriptions', { id: subscription.value?.id } )
// // console.warn('SUBSCRIPTION-DATA', res);
const res = await sdk.update('subscriptions', subscription.value?.id, query)
subscription.value = res
};

return {
loading,
provider,
subscription,
fetchProvider,
fetchSystemProvider,
createProvider,
Expand Down
57 changes: 57 additions & 0 deletions src/components/CreditPurchaseDialog.vue
Original file line number Diff line number Diff line change
@@ -0,0 +1,57 @@
<template lang="pug">
q-card(style="width: 400px")
q-card-section.row.justify-between.q-pb-sm
div.column
span.text-h6 Add credits
span.text-caption.text-grey-6 Input the number of credits for purchase.
q-space
q-btn(dense flat round icon="mdi-close" @click.stop="onClose" style="height: 25px")
q-card-section.q-pa-none.q-pb-md
q-input(
v-model.number="creditsForPurchase"
type="number"
label="Credits"
).q-px-md.q-pt-none
//- span.q-px-md.text-weight-normal.text-caption Max amount
q-card-actions.row.justify-end.q-gutter-xs.bg-grey-2.q-pr-md
q-btn(
unelevated
no-caps
color="primary"
@click.stop="onPurchase"
) Purchase
</template>

<script>
import { ref } from 'vue';
export default {
props: {
dialog: {
type: Boolean,
default: false,
}
},
setup (props, { emit }) {
const dialog = ref(props.creditsDialog);
const creditsForPurchase = ref(0);
const onPurchase = () => {
emit('purchase', creditsForPurchase)
dialog.value = false
}
const onClose = () => {
emit('close')
}
return {
dialog,
creditsForPurchase,
onPurchase,
onClose,
}
}
}
</script>
28 changes: 25 additions & 3 deletions src/pages/SettingsEmail.vue
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,13 @@ div.row.q-mb-md
span.text-h6 Select Email Provider
span.text-caption.text-grey-6 Manage your Email providers here

// set credit amount
q-dialog(v-model="creditsDialog" persistent)
credit-purchase-dialog(
@close="creditsDialog = false"
@purchase="processPurchase"
)

// providers
q-card(bordered flat)
// loading
Expand Down Expand Up @@ -42,7 +49,7 @@ q-card(bordered flat)
q-card-section.row.items-center.q-pr-md
span.subtitle2.text-grey {{ systemProvider?.creditsCount || '0' }} Credits
q-space
q-btn(flat unelevated dense no-caps type="a") Buy more credits
q-btn(flat unelevated dense no-caps type="a" disabled) Buy more credits

div.col-xs-12.col-sm-6
q-card(bordered flat style="height:180px;").bg-blue-1.text-primary
Expand All @@ -65,6 +72,7 @@ q-card(bordered flat)
q-item-section Edit
q-item(clickable v-close-popup @click="onDelete(provider)")
q-item-section Delete
//- q-icon(name="mdi-delete" color="negative")
q-card-section.row.items-center.q-pr-md
span.subtitle2.text-grey {{ provider?.creditsCount || '0' }} Credits
q-space
Expand All @@ -81,7 +89,7 @@ q-card(bordered flat)
q-avatar(rounded size="lg" :style="{ width: '50px' }").bg-white
q-img(src="../assets/logo.png" :style="{ width: '50%' }")
span.text-h6 MYCURE Email provider
span.text-body2.text-weight-medium {{ systemProvider?.defaultFrom }}
span.text-body2.text-weight-medium {{ systemProvider?.defaultFrom || '[email protected]' }}
//- span.text-subtitle1.text-grey-6 This is a backend provided by the system if you have enough credits
q-space
q-btn(flat unelevated dense icon="mdi-dots-vertical" disabled size="md")
Expand All @@ -93,7 +101,7 @@ q-card(bordered flat)
q-card-section.row.items-center.q-pr-md
span.subtitle2.text-grey {{ provider.creditsCount }} Credits
q-space
q-btn(flat unelevated dense no-caps type="a") Buy more credits
q-btn(flat unelevated dense no-caps type="a" @click.stop="openCreditsDialog") Buy more credits
// div
q-btn(
no-caps
Expand All @@ -120,13 +128,15 @@ q-card(bordered flat)

<script>
import EmailProviderForm from 'components/EmailProviderForm.vue';
import CreditPurchaseDialog from 'components/CreditPurchaseDialog.vue';
import { ref, onMounted, watch, toRef } from 'vue';
import { fetchProvider } from 'boot/providers';
import { handleAction } from 'boot/helpers';
export default {
name: 'SettingsEmail',
components: {
CreditPurchaseDialog,
EmailProviderForm,
},
setup () {
Expand All @@ -137,6 +147,7 @@ export default {
// actions
const createDialog = ref(false);
const creditsDialog = ref(false);
const onCreateBtnClick = () => {
createDialog.value = true;
};
Expand All @@ -161,13 +172,21 @@ export default {
});
onMounted(() => {
console.warn('DATASET-PROVIDER', dataset.provider)
if (dataset.provider.backend !== 'system') {
selected.value = 'custom_provider';
} else {
selected.value = 'system';
}
})
const openCreditsDialog = () => {
creditsDialog.value = true;
}
const processPurchase = (creditsForPurchase) => {
const topupProvider = dataset.topupProvider;
topupProvider('email', creditsForPurchase.value);
}
return {
loading: dataset.loading,
Expand All @@ -176,11 +195,14 @@ export default {
selected,
createDialog,
creditsDialog,
onCreateBtnClick,
onEditBtnClick,
onCreateCancel,
onCreate,
onDelete,
openCreditsDialog,
processPurchase,
};
},
};
Expand Down
44 changes: 39 additions & 5 deletions src/pages/SettingsSMS.vue
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,14 @@ div.row.q-mb-md
span.text-h6 Configure SMS Provider
span.text-caption.text-grey-6 Manage your SMS providers here

// set credit amount
q-dialog(v-model="creditsDialog" persistent)
credit-purchase-dialog(
@close="creditsDialog = false"
@purchase="processPurchase"
)


// providers
q-card(bordered flat)
// loading
Expand All @@ -20,7 +28,9 @@ q-card(bordered flat)
div.col-xs-12.col-sm-6
q-skeleton(height="200px" square)

// custom provider


// custom provider / open provider
template(v-else-if="!provider.isSystemProvider")
q-card-section.row.q-col-gutter-md
div.col-xs-12.col-sm-6
Expand All @@ -41,7 +51,7 @@ q-card(bordered flat)
q-card-section.row.items-center.q-pr-md
span.subtitle2.text-grey {{ systemProvider?.creditsCount || '0' }} Credits
q-space
q-btn(flat unelevated dense no-caps type="a") Buy more credits
q-btn(flat unelevated dense no-caps type="a" disabled @click.stop="openCreditsDialog") Buy more credits

div.col-xs-12.col-sm-6
q-card(bordered flat style="height:180px;").bg-blue-1.text-primary
Expand All @@ -64,7 +74,16 @@ q-card(bordered flat)
q-item-section Edit
q-item(clickable v-close-popup @click="onDelete(provider)")
q-item-section Delete
q-card-section.row.items-center.q-pr-md
//- q-btn(
//- dense
//- round
//- flat
//- icon="mdi-delete"
//- color="negative"
//- @click="onDelete(provider)"
//- )
//- q-tooltip Delete this custom provider
//- q-card-section.row.items-center.q-pr-md
span.subtitle2.text-grey {{ provider?.creditsCount || '0' }} Credits
q-space
q-btn(flat unelevated dense no-caps type="a") Buy more credits
Expand All @@ -80,7 +99,7 @@ q-card(bordered flat)
q-avatar(rounded size="lg" :style="{ width: '50px' }").bg-white
q-img(src="../assets/logo.png" :style="{ width: '50%' }")
span.text-h6.text-weight-bolder MYCURE SMS provider
span.text-body2.text-weight-medium {{ provider?.defaultFrom }}
span.text-body2.text-weight-medium {{ provider?.senderNo || provider?.defaultFrom }}
//- span.text-subtitle1.text-grey-6 This is a backend provided by the system if you have enough credits
q-space
//- q-btn(icon="mdi-dots-vertical" size="sm" disabled @click="onCreateBtnClick(true)")
Expand All @@ -92,7 +111,7 @@ q-card(bordered flat)
q-card-section.row.items-center.q-pr-md
span.subtitle2.text-grey {{ provider?.creditsCount }} Credits
q-space
q-btn(flat unelevated dense no-caps type="a") Buy more credits
q-btn(flat unelevated dense no-caps type="a" @click.stop="openCreditsDialog") Buy more credits
// div
q-btn(
no-caps
Expand All @@ -119,19 +138,22 @@ q-card(bordered flat)

<script>
import SmsProviderForm from 'components/SMSProviderForm.vue';
import CreditPurchaseDialog from 'components/CreditPurchaseDialog.vue';
import { ref, onMounted, watch } from 'vue';
import { fetchProvider } from 'boot/providers';
import { handleAction } from 'boot/helpers';
export default {
name: 'SettingsSMS',
components: {
CreditPurchaseDialog,
SmsProviderForm,
},
setup () {
// data
const dataset = fetchProvider('sms');
const systemDataset = dataset.fetchSystemProvider();
const subscription = dataset.subscription;
const selected = ref(null)
onMounted(() => {
Expand All @@ -140,10 +162,12 @@ export default {
} else {
selected.value = 'system';
}
console.warn('SUBSCRIPTION-LOADED', subscription);
})
// actions
const createDialog = ref(false);
const creditsDialog = ref(false);
const onCreateBtnClick = (isEditing) => {
createDialog.value = true;
};
Expand All @@ -163,6 +187,13 @@ export default {
loaderMessage: item => `Deleting ${item.label} provider...`,
confirmMessage: item => `Would you like to delete ${item.label} provider? This action cannot be reversed`,
});
const openCreditsDialog = () => {
creditsDialog.value = true;
}
const processPurchase = (creditsForPurchase) => {
const topupProvider = dataset.topupProvider;
topupProvider('sms', creditsForPurchase.value);
}
return {
loading: dataset.loading,
Expand All @@ -171,10 +202,13 @@ export default {
selected,
createDialog,
creditsDialog,
onCreateBtnClick,
onCreateCancel,
onCreate,
onDelete,
openCreditsDialog,
processPurchase,
};
},
};
Expand Down

0 comments on commit 4d09074

Please sign in to comment.