Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

10680 - Allow changing from GOVN -> PREMIUM #2636

Merged
merged 9 commits into from
Nov 15, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions auth-web/package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion auth-web/package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "auth-web",
"version": "2.4.43",
"version": "2.4.44",
"appName": "Auth Web",
"sbcName": "SBC Common Components",
"private": true,
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
<template>
<div>
<v-form ref="accountAccessTypeForm">
<v-form>
<v-card elevation="0">
<div class="account-label">
<div
Expand Down Expand Up @@ -60,7 +60,6 @@
v-model="selectedAccessType"
class="mt-0"
req
:rules="[selectedAccessTypeRules]"
>
<v-radio
:key="AccessType.REGULAR"
Expand All @@ -75,19 +74,6 @@
data-test="radio-govn"
/>
</v-radio-group>
<div
v-if="!isPad"
class="d-flex pb-3"
>
<v-icon
size="30"
color="error"
class="mt-1 mr-4"
>
mdi-alert-circle-outline
</v-icon>
<span class="error-text">{{ $t('accountAccessTypeUpdateWarning') }}</span>
</div>

<v-card-actions class="px-0 pt-0">
<v-row>
Expand All @@ -102,7 +88,7 @@
color="primary"
:loading="false"
aria-label="Save Account Access Type"
@click="updateDetails()"
@click="updateDetails(false)"
>
<span class="save-btn__label">Save</span>
</v-btn>
Expand All @@ -126,79 +112,139 @@
</div>
</v-card>
</v-form>
<!-- Confirm Access Type To Regular Dialog -->
<ModalDialog
ref="changeAccessTypeToRegularDialog"
title="Change Access Type To Regular?"
text="Regular access will not have the option to modify product fees."
dialog-class="notify-dialog"
max-width="720"
:isPersistent="true"
data-test="modal-change-access-type"
>
<template #icon>
<v-icon
large
color="error"
>
mdi-alert-circle-outline
</v-icon>
</template>
<template #actions>
<v-btn
large
depressed
class="font-weight-bold btn-dialog"
data-test="btn-confirm-change-access-type-dialog"
color="primary"
@click="updateDetails(true)"
>
Confirm
</v-btn>
<v-btn
outlined
large
depressed
class="btn-dialog"
color="primary"
data-test="btn-cancel-change-access-type-dialog"
@click="closeDialog"
>
Cancel
</v-btn>
</template>
</ModalDialog>
</div>
</template>

<script lang="ts">
import { AccessType, Account, PaymentTypes } from '@/util/constants'
import { Component, Emit, Prop, Vue, Watch } from 'vue-property-decorator'
import { Organization } from '@/models/Organization'

@Component({
})
export default class AccountAccessType extends Vue {
@Prop({ default: undefined }) organization: Organization
@Prop({ default: true }) viewOnlyMode: boolean
@Prop({ default: false }) canChangeAccessType: boolean
@Prop({ default: undefined }) currentOrgPaymentType: string

$refs: {
accountAccessTypeForm: HTMLFormElement,
selectedAccessType: HTMLFormElement
}
private selectedAccessType: string = undefined
public AccessType = AccessType
public isLoading = false

public get isPad (): boolean {
return this.currentOrgPaymentType && this.currentOrgPaymentType === PaymentTypes.PAD
}

public get isChangeButtonEnabled (): boolean {
// Check access type and orgtype must be premium
const accessType: any = this.organization.accessType
const isAllowedAccessType = this.organization.orgType === Account.PREMIUM &&
[AccessType.REGULAR, AccessType.EXTRA_PROVINCIAL, AccessType.REGULAR_BCEID].includes(accessType)
return isAllowedAccessType && this.canChangeAccessType // canChangeAccessType is the role based access pasased as property
}
import { AccessType, Account } from '@/util/constants'
import { computed, defineComponent, reactive, toRefs, watch } from '@vue/composition-api'
import ModalDialog from '@/components/auth/common/ModalDialog.vue'

public get getAccessTypeText (): string {
let accessTypeText = 'Regular Access'
if (this.organization.accessType === AccessType.GOVN) {
accessTypeText = 'Government agency (other than BC provincial)'
} else if (this.organization.accessType === AccessType.GOVM) {
accessTypeText = 'BC Government Ministry'
export default defineComponent({
name: 'AccountAccessType',
components: {
ModalDialog
},
props: {
organization: {
type: Object,
default: undefined
},
viewOnlyMode: {
type: Boolean,
default: true
},
canChangeAccessType: {
type: Boolean,
default: false
},
currentOrgPaymentType: {
type: String,
default: undefined
}
return accessTypeText
}
},
emits: ['update:updateAndSaveAccessTypeDetails', 'update:viewOnlyMode'],
setup (props, { emit }) {
// const AccessType = AccessType
const state = reactive({
changeAccessTypeToRegularDialog: null,
selectedAccessType: undefined,
isLoading: false,
// Only allow PREMIUM -> GOVN and GOVN -> PREMIUM
isChangeButtonEnabled: computed<boolean>(() => {
// Check access type and orgtype must be premium
const accessType: any = props.organization.accessType
const isAllowedAccessType = props.organization.orgType === Account.PREMIUM &&
[AccessType.REGULAR, AccessType.EXTRA_PROVINCIAL, AccessType.REGULAR_BCEID, AccessType.GOVN].includes(accessType)
return isAllowedAccessType && props.canChangeAccessType // canChangeAccessType is the role based access passed as a property
}),
getAccessTypeText: computed<string>(() => {
let accessTypeText = 'Regular Access'
if (props.organization.accessType === AccessType.GOVN) {
accessTypeText = 'Government agency (other than BC provincial)'
} else if (props.organization.accessType === AccessType.GOVM) {
accessTypeText = 'BC Government Ministry'
}
return accessTypeText
})
})

// Watch property access type and update model
@Watch('organization', { deep: true, immediate: true })
onOrganizationChange () {
this.selectedAccessType = this.organization.accessType === AccessType.GOVN ? AccessType.GOVN : AccessType.REGULAR
}
const closeDialog = () => {
state.changeAccessTypeToRegularDialog.close()
}

// Custom rules for selectedAccessType v-model in form
public selectedAccessTypeRules (): any {
return this.selectedAccessType === AccessType.GOVN ? true : 'Please select Government agency'
}
const updateDetails = (confirmed: boolean) => {
if (state.selectedAccessType === AccessType.REGULAR && !confirmed) {
state.changeAccessTypeToRegularDialog.open()
} else {
emit('update:updateAndSaveAccessTypeDetails', state.selectedAccessType)
closeDialog()
}
}

// Currently, there is only one way change from Regular access type accounts to GovN. Not the other way around
public updateDetails () {
if (this.isPad && this.$refs.accountAccessTypeForm.validate()) {
this.$emit('update:updateAndSaveAccessTypeDetails', this.selectedAccessType)
const cancelEdit = () => {
state.selectedAccessType = props.organization.accessType === AccessType.GOVN ? AccessType.GOVN : AccessType.REGULAR
emit('update:viewOnlyMode', {
component: 'accessType',
mode: true
})
}
}

@Emit('update:viewOnlyMode')
cancelEdit () {
this.selectedAccessType = this.organization.accessType === AccessType.GOVN ? AccessType.GOVN : AccessType.REGULAR
watch(() => props.organization, (newVal) => {
state.selectedAccessType = newVal.accessType === AccessType.GOVN ? AccessType.GOVN : AccessType.REGULAR
}, { deep: true, immediate: true })

return {
component: 'accessType',
mode: true
AccessType,
...toRefs(state),
closeDialog,
updateDetails,
cancelEdit
}
}
}
})
</script>

<style lang="scss" scoped>
Expand All @@ -211,4 +257,8 @@ export default class AccountAccessType extends Vue {
color: var(--v-error-base) !important;
}

.btn-dialog {
height: 2.75em;
width: 6.25em;
}
</style>
Original file line number Diff line number Diff line change
Expand Up @@ -283,6 +283,7 @@

<script lang="ts">
import {
AccessType,
AccountStatus,
Pages,
Permission,
Expand Down Expand Up @@ -341,10 +342,12 @@ export default class AccountInfo extends Mixins(

@Action(useOrgStore) syncAddress!: () => Address
@Action(useOrgStore) getOrgPayments!: () => any
@Action(useOrgStore) updateOrganizationAccessType!: (accessType: string) => Promise<Organization>
@Action(useOrgStore) updateOrganizationAccessType!: (accessType: string, orgId: number, syncOrg: boolean) =>
Promise<boolean>

@Action(useOrgStore) syncOrganization!: (currentAccount: number) => Promise<Organization>
@Action(useOrgStore) suspendOrganization!: (selectedSuspensionReasonCode: string) => Promise<Organization>
@Action(useOrgStore) removeOrgAccountFees!: (orgId: number) => Promise<void>

private dialogTitle: string = ''
private dialogText: string = ''
Expand Down Expand Up @@ -417,7 +420,11 @@ export default class AccountInfo extends Mixins(

// update account access type from child component
public async updateAndSaveAccessTypeDetails (accessType: string) {
await this.updateOrganizationAccessType(accessType)
await this.updateOrganizationAccessType(accessType, this.currentOrganization.id, true)
// Only remove the account fees if going from GOVN -> PREMIUM (REGULAR)
if (accessType === AccessType.REGULAR) {
await this.removeOrgAccountFees(this.currentOrganization.id)
}
this.viewOnlyMode({ component: 'accessType', mode: true })
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -564,7 +564,6 @@ export default defineComponent({
}
})


// Methods
const closeAuthorizationRequestSentDialog = () => {
authorizationRequestSentDialog.value?.close()
Expand Down
1 change: 0 additions & 1 deletion auth-web/src/locales/en.json
Original file line number Diff line number Diff line change
Expand Up @@ -216,7 +216,6 @@
"acceptInviteLandingMessageBCEID": "To accept the invitation to this account, log in to Business Registry with a registered BCeID account, and verify your identity by a notarized affidavit.",
"pendingAffidavitAdminReviewTitle":"Your submission to join {team} has been requested ",
"pendingAffidvitAdminReviewMessage":"Once your information has been reviewed and approved, you will receive an email allowing you to join the account. Please allow {days} business days for this process",
"accountAccessTypeUpdateWarning": "This account currently can't change access type. Contact account admin to update the payment method to PAD in order to change the access type.",
"govnAccountDescription": "Service BC Staff will manually review your account information.",
"govnConfirmText": "BC Registry Staff will manually review the account to verify the account user. <b>Account will be rejected if account admin does not verify as a government other than BC provincial. </b>This is a option for townships, cities, districts, municipalities, and federal government.",
"searchAccountNoResult": "<h4>No Results</h4><p>None of the accounts matched this search. Try another search.</p>",
Expand Down
4 changes: 4 additions & 0 deletions auth-web/src/services/payment.services.ts
Original file line number Diff line number Diff line change
Expand Up @@ -188,4 +188,8 @@ export default class PaymentService {
const { product } = accountFeePayload
return axios.put(`${ConfigHelper.getPayAPIURL()}/accounts/${accountId}/fees/${product}`, accountFeePayload)
}

static removeAccountFees (accountId: string | number): AxiosPromise<any> {
return axios.delete(`${ConfigHelper.getPayAPIURL()}/accounts/${accountId}/fees`)
}
}
14 changes: 12 additions & 2 deletions auth-web/src/stores/org.ts
Original file line number Diff line number Diff line change
Expand Up @@ -997,7 +997,7 @@ export const useOrgStore = defineStore('org', () => {
return response?.data || {}
}

async function updateOrganizationAccessType ({ accessType, orgId = null, syncOrg = true }): Promise<boolean> {
async function updateOrganizationAccessType (accessType: string, orgId: number = null, syncOrg = true): Promise<boolean> {
if (!orgId) orgId = state.currentOrganization?.id as number
if (orgId && accessType) {
try {
Expand All @@ -1018,6 +1018,15 @@ export const useOrgStore = defineStore('org', () => {
}
}

async function removeOrgAccountFees (orgId: number) {
try {
await PaymentService.removeAccountFees(orgId)
} catch (error) {
// eslint-disable-next-line no-console
console.error('remove org account fees operation failed! - ', error)
}
}

return {
...toRefs(state),
isPremiumAccount,
Expand Down Expand Up @@ -1113,6 +1122,7 @@ export const useOrgStore = defineStore('org', () => {
revokeOrgApiKeys,
updateOrganizationAccessType,
$reset,
isStaffOrSbcStaff
isStaffOrSbcStaff,
removeOrgAccountFees
}
})
10 changes: 4 additions & 6 deletions auth-web/src/views/auth/staff/ReviewAccountView.vue
Original file line number Diff line number Diff line change
Expand Up @@ -186,7 +186,7 @@ export default defineComponent({
const taskRelationshipType: Ref<string> = ref('')
const productFeeFormValid: Ref<boolean> = ref(false)
const viewOnly = DisplayModeValues.VIEW_ONLY
const accountInfoAccessType = ref(null)
const accountInfoAccessType = ref<string>(null)
const accountInfoValid: Ref<boolean> = ref(true)
const showAccountInfoValidations: Ref<boolean> = ref(false)

Expand Down Expand Up @@ -598,11 +598,9 @@ export default defineComponent({

try {
if (accountInfoAccessType.value && accountInfoAccessType.value !== accountUnderReview.value.accessType) {
const success = await orgStore.updateOrganizationAccessType({
accessType: accountInfoAccessType.value as string,
orgId: accountUnderReview.value.id,
syncOrg: false
})
const success = await orgStore.updateOrganizationAccessType(
accountInfoAccessType.value, accountUnderReview.value.id, false
)
if (!success) throw new Error('Error updating account access type prevented review completion.')
}
if (isApprove) {
Expand Down
Loading
Loading