feat: add database backed membership tiers
This commit is contained in:
@@ -1,5 +1,5 @@
|
||||
<script setup>
|
||||
import { computed, reactive, ref } from 'vue';
|
||||
import { computed, onMounted, reactive, ref, watch } from 'vue';
|
||||
import { useI18n } from 'vue-i18n';
|
||||
import { useRouter } from 'vue-router';
|
||||
import { mdiAccountArrowRightOutline, mdiDomainPlus, mdiEmailOutline } from '@mdi/js';
|
||||
@@ -13,6 +13,7 @@
|
||||
|
||||
const createForm = reactive({
|
||||
name: '',
|
||||
membershipTierId: null,
|
||||
});
|
||||
const accessForm = reactive({
|
||||
targetType: 'organization',
|
||||
@@ -27,6 +28,29 @@
|
||||
{ title: t('organizationOnboarding.request.types.organization'), value: 'organization' },
|
||||
{ title: t('organizationOnboarding.request.types.workspace'), value: 'workspace' },
|
||||
]);
|
||||
const membershipTierOptions = computed(() =>
|
||||
organizationStore.membershipTiers.map(tier => ({
|
||||
title: tier.name,
|
||||
value: tier.id,
|
||||
props: {
|
||||
subtitle: formatTierPrice(tier),
|
||||
},
|
||||
}))
|
||||
);
|
||||
|
||||
function formatTierPrice(tier) {
|
||||
if (tier.isCustom || tier.monthlyPriceCents === null || tier.monthlyPriceCents === undefined) {
|
||||
return t('organizationOnboarding.create.tiers.customPrice');
|
||||
}
|
||||
|
||||
if (tier.monthlyPriceCents === 0) {
|
||||
return t('organizationOnboarding.create.tiers.freePrice');
|
||||
}
|
||||
|
||||
return t('organizationOnboarding.create.tiers.monthlyPrice', {
|
||||
price: `$${Math.round(tier.monthlyPriceCents / 100)}`,
|
||||
});
|
||||
}
|
||||
|
||||
async function createOrganization() {
|
||||
if (organizationStore.isCreating) {
|
||||
@@ -42,7 +66,10 @@
|
||||
}
|
||||
|
||||
try {
|
||||
await organizationStore.createOrganization({ name });
|
||||
await organizationStore.createOrganization({
|
||||
name,
|
||||
membershipTierId: createForm.membershipTierId,
|
||||
});
|
||||
await Promise.all([
|
||||
organizationStore.fetchOrganizations(),
|
||||
workspaceStore.fetchWorkspaces(),
|
||||
@@ -73,6 +100,20 @@
|
||||
window.location.href = `mailto:${encodeURIComponent(accessForm.adminEmail.trim())}?subject=${encodeURIComponent(subject)}&body=${encodeURIComponent(body)}`;
|
||||
requestStatus.value = t('organizationOnboarding.request.sent');
|
||||
}
|
||||
|
||||
onMounted(async () => {
|
||||
const tiers = await organizationStore.fetchMembershipTiers();
|
||||
createForm.membershipTierId = tiers[0]?.id ?? null;
|
||||
});
|
||||
|
||||
watch(
|
||||
() => organizationStore.membershipTiers,
|
||||
tiers => {
|
||||
if (!createForm.membershipTierId) {
|
||||
createForm.membershipTierId = tiers[0]?.id ?? null;
|
||||
}
|
||||
}
|
||||
);
|
||||
</script>
|
||||
|
||||
<template>
|
||||
@@ -114,6 +155,15 @@
|
||||
variant="outlined"
|
||||
hide-details
|
||||
/>
|
||||
<v-select
|
||||
v-model="createForm.membershipTierId"
|
||||
:items="membershipTierOptions"
|
||||
:label="t('organizationOnboarding.create.fields.membershipTier')"
|
||||
:loading="organizationStore.isLoadingMembershipTiers"
|
||||
:disabled="organizationStore.isCreating"
|
||||
variant="outlined"
|
||||
hide-details
|
||||
/>
|
||||
|
||||
<v-btn
|
||||
:loading="organizationStore.isCreating"
|
||||
|
||||
Reference in New Issue
Block a user