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

24576 - Updates to NSF messaging #3207

Merged
merged 7 commits into from
Jan 21, 2025
Merged
Show file tree
Hide file tree
Changes from 6 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
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.7.5",
"version": "2.7.6",
"appName": "Auth Web",
"sbcName": "SBC Common Components",
"private": true,
Expand Down
2 changes: 1 addition & 1 deletion auth-web/src/assets/scss/layout.scss
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@
.view-header {
display: flex;
flex-direction: row;
margin-bottom: 2.75rem;
margin-bottom: 40px;

.back-btn {
margin-top: -0.25rem;
Expand Down
2 changes: 1 addition & 1 deletion auth-web/src/assets/scss/theme.scss
Original file line number Diff line number Diff line change
Expand Up @@ -69,7 +69,7 @@ $BCgovAGold4: #FFD4A2;
$BCgovGreen1: #2E7D32;

// Error Colors
$BCgovInputError: #ff5252;
$BCgovInputError: #d3272c;

// Form Inputs
$BCgovInputBG: #ffffff;
Expand Down
34 changes: 23 additions & 11 deletions auth-web/src/components/auth/account-freeze/AccountOverviewNSF.vue
Original file line number Diff line number Diff line change
@@ -1,7 +1,13 @@
<template>
<div>
<p class="mb-10">
This account has been suspended for a failed payment.
<p class="mb-10 subtitle">
<v-icon
color="#d3272c"
>
mdi-alert
</v-icon>
We were unable to process the payment from your bank account, and as a result, your account has been suspended.
Returned system error message: {{ reason }}.
</p>

<v-card
Expand All @@ -20,18 +26,18 @@
</v-row>
<v-divider class="my-2" />
<v-row>
<v-col cols="9">
<v-col cols="10">
<div>Dishonored Bank Instrument Fee</div>
<div class="font-italic">
As per PAD terms, you are charged $30 dishonored bank fee for every failed payment
As per PAD agreement, you are charged $30 dishonored bank fee for every failed payment
</div>
</v-col>
<v-col class="text-end">
${{ nsfAmount.toFixed(2) }}
</v-col>
</v-row>
<v-row>
<v-col cols="9">
<v-col cols="10">
Total Transactions
</v-col>
<v-col class="text-end">
Expand All @@ -40,7 +46,7 @@
</v-row>
<v-divider class="my-2" />
<v-row class="font-weight-bold">
<v-col cols="9">
<v-col cols="10">
Total Amount Due
</v-col>
<v-col class="text-end">
Expand Down Expand Up @@ -87,7 +93,6 @@
import { computed, defineComponent, onMounted, reactive, toRefs } from '@vue/composition-api'
import CommonUtils from '@/util/common-util'
import { FailedInvoice } from '@/models/invoice'
import moment from 'moment'
import { useOrgStore } from '@/stores/org'

export default defineComponent({
Expand All @@ -99,14 +104,15 @@ export default defineComponent({
const currentMembership = computed(() => orgStore.currentMembership)
const calculateFailedInvoices: any = orgStore.calculateFailedInvoices
const downloadNSFInvoicesPDF: any = orgStore.downloadNSFInvoicesPDF
const formatDate = CommonUtils.formatDisplayDate
const suspendedDate = (currentOrganization.value?.suspendedOn) ? formatDate(moment(currentOrganization.value.suspendedOn)) : ''

const state = reactive({
nsfAmount: 0,
totalAmount: 0,
totalAmountRemaining: 0,
totalPaidAmount: 0
totalPaidAmount: 0,
reason: '',
suspendedDate: currentOrganization.value?.suspendedOn
? CommonUtils.formatDateToHumanReadable(currentOrganization.value.suspendedOn) : ''
})

const goNext = () => {
Expand All @@ -118,13 +124,13 @@ export default defineComponent({
state.totalAmount = failedInvoices?.totalTransactionAmount || 0
state.nsfAmount = failedInvoices?.nsfFee || 0
state.totalAmountRemaining = failedInvoices?.totalAmountToPay || 0
state.reason = failedInvoices.reason || ''
})

return {
...toRefs(state),
currentOrganization,
currentMembership,
suspendedDate,
downloadNSFInvoicesPDF,
goNext
}
Expand All @@ -136,6 +142,12 @@ export default defineComponent({
<style lang="scss" scoped>
@import "$assets/scss/theme.scss";

.subtitle {
font-size: 1rem;
font-weight: 500;
color: $BCgovInputError;
}

.suspended-info-card {
border-color: $BCgovInputError !important;
border-width: 2px !important;
Expand Down
85 changes: 37 additions & 48 deletions auth-web/src/components/auth/common/AccountSuspendAlert.vue
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@
large
class="mt-2"
>
mdi-alert-circle-outline
mdi-alert
</v-icon>
<div
v-if="isSuspendedForNSF"
Expand All @@ -21,7 +21,7 @@
Account Suspended
</div>
<div>
Account has been suspended for {{ accountSuspendReason }}.
This acount has been suspended. Returned system error message: {{ reason }}.
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

acount

</div>
<div class="mt-6 title font-weight-bold">
BALANCE DUE: ${{ totalAmountToPay.toFixed(2) }}
Expand All @@ -38,7 +38,7 @@
class="d-flex flex-column ml-7"
>
<div class="title font-weight-bold">
Account Suspended ({{ suspendedReason() }})
Account Suspended ({{ suspendedReason }})
</div>
<div class="d-flex">
<span>Date Suspended: {{ suspendedDate }}<span class="vertical-line" /> Suspended by: {{ suspendedBy }}</span>
Expand All @@ -50,60 +50,49 @@
</template>

<script lang="ts">
import { AccountStatus, SuspensionReasonCode } from '@/util/constants'
import { Action, State } from 'pinia-class'
import { Component, Vue } from 'vue-property-decorator'
import { Code } from '@/models/Code'
import { computed, defineComponent, onMounted, reactive, toRefs } from '@vue/composition-api'
import { AccountStatus } from '@/util/constants'
import CommonUtils from '@/util/common-util'
import { FailedInvoice } from '@/models/invoice'
import { Organization } from '@/models/Organization'
import { useCodesStore } from '@/stores/codes'
import { useOrgStore } from '@/stores/org'

@Component
export default class AccountSuspendAlert extends Vue {
@Action(useOrgStore) private calculateFailedInvoices!: () => FailedInvoice
@State(useOrgStore) private currentOrganization!: Organization
@State(useCodesStore) private suspensionReasonCodes!: Code[]
private formatDate = CommonUtils.formatDisplayDate
export default defineComponent({
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thank you looks good

name: 'AccountSuspendAlert',
setup () {
const orgStore = useOrgStore()
const codesStore = useCodesStore()
const currentOrganization = computed(() => orgStore.currentOrganization)

totalTransactionAmount = 0
totalAmountToPay = 0
totalPaidAmount = 0
const state = reactive({
totalTransactionAmount: 0,
totalAmountToPay: 0,
totalPaidAmount: 0,
reason: '',
suspendedDate: currentOrganization.value?.suspendedOn
? CommonUtils.formatDateToHumanReadable(currentOrganization.value.suspendedOn) : '',
isSuspendedForNSF: computed(() => currentOrganization.value?.statusCode === AccountStatus.NSF_SUSPENDED),
suspendedBy: computed(() => currentOrganization.value?.decisionMadeBy),
suspendedReason: computed(() => {
return codesStore.suspensionReasonCodes?.find(
suspensionReasonCode => suspensionReasonCode?.code === currentOrganization.value?.suspensionReasonCode
)?.desc
})
})

get suspendedDate () {
return (this.currentOrganization?.suspendedOn)
? this.formatDate(new Date(this.currentOrganization.suspendedOn)) : ''
}

get isSuspendedForNSF (): boolean {
return this.currentOrganization?.statusCode === AccountStatus.NSF_SUSPENDED
}

get suspendedBy (): string {
return this.currentOrganization?.decisionMadeBy
}

get accountSuspendReason (): string {
if (this.currentOrganization?.suspensionReasonCode === SuspensionReasonCode.OVERDUE_EFT) {
return 'overdue EFT payments'
}
return 'outstanding balance (NSF)'
}

suspendedReason (): string {
return this.suspensionReasonCodes?.find(suspensionReasonCode =>
suspensionReasonCode?.code === this.currentOrganization?.suspensionReasonCode)?.desc
}

async mounted () {
if (this.isSuspendedForNSF) {
const failedInvoices: FailedInvoice = await this.calculateFailedInvoices()
this.totalTransactionAmount = failedInvoices.totalTransactionAmount || 0
this.totalAmountToPay = failedInvoices.totalAmountToPay || 0
onMounted(async () => {
if (state.isSuspendedForNSF) {
const failedInvoices: FailedInvoice = await orgStore.calculateFailedInvoices()
state.totalTransactionAmount = failedInvoices.totalTransactionAmount || 0
state.totalAmountToPay = failedInvoices.totalAmountToPay || 0
state.reason = failedInvoices.reason || ''
}
})
return {
...toRefs(state)
}
}
}
})
</script>

<style lang="scss" scoped>
Expand Down
2 changes: 2 additions & 0 deletions auth-web/src/models/invoice.ts
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,7 @@ export interface FailedInvoice {
totalAmountToPay?: number
invoices?: InvoiceList[]
statements?: Statement[]
reason?: string
}

export interface NonSufficientFundsInvoiceListResponse {
Expand All @@ -55,4 +56,5 @@ export interface NonSufficientFundsInvoiceListResponse {
totalAmount: number
totalAmountRemaining: number
nsfAmount: number
reason?: string
}
4 changes: 3 additions & 1 deletion auth-web/src/stores/org.ts
Original file line number Diff line number Diff line change
Expand Up @@ -793,13 +793,15 @@ export const useOrgStore = defineStore('org', () => {
const totalAmount = nsfInvoices?.totalAmount || 0
const totalAmountRemaining = nsfInvoices?.totalAmountRemaining || 0
const nsfAmount = nsfInvoices?.nsfAmount || 0
const reason = nsfInvoices?.reason || ''

return {
invoices: invoices,
statements: statements,
nsfFee: nsfAmount,
totalAmountToPay: totalAmountRemaining,
totalTransactionAmount: totalAmount
totalTransactionAmount: totalAmount,
reason: reason
}
}

Expand Down
11 changes: 9 additions & 2 deletions auth-web/src/util/common-util.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,14 +4,16 @@ import { NrRequestActionCodes, NrRequestTypeCodes } from '@bcrs-shared-component
import { NrRequestTypeStrings, Permission } from '@/util/constants'
import moment from 'moment'

type DateLike = string | Date | moment.Moment

/**
* A class to put all the common utility methods.
*/
export default class CommonUtils {
// formats two dates into a range string, takes in most date formats
// eg1. formatDateRange('2021-01-01', new Date()) => 'January 01, 2021 - May 27, 2024'
// eg2. formatDateRange('March 1 2024', moment()) => 'March 01 - May 27, 2024'
static formatDateRange (date1: string | Date | moment.Moment, date2: string | Date): string {
static formatDateRange (date1: DateLike, date2: DateLike): string {
const dateObj1 = moment(date1)
const dateObj2 = moment(date2)
const year = (dateObj1.year() === dateObj2.year()) ? dateObj1.year() : ''
Expand Down Expand Up @@ -138,7 +140,7 @@ export default class CommonUtils {
}

// Formatting date in the desired format for displaying in the template
static formatDisplayDate (date: Date | string | moment.Moment, format?: string) {
static formatDisplayDate (date: DateLike, format?: string) {
// not working in CI (getting UTC datetime)
return (date) ? moment(date.toLocaleString('en-US', { timeZone: 'America/Vancouver' }))
.format(format || 'YYYY-MM-DD') : ''
Expand All @@ -148,6 +150,11 @@ export default class CommonUtils {
static formatDatePickerDate (date?: Date) {
return moment(date || new Date()).format('YYYY-MM-DD')
}

static formatDateToHumanReadable (date: DateLike) {
return moment(date).format('MMMM DD, YYYY')
}

// Formatting date in the desired format for vue date pickers
static formatCurrentDate () {
return moment(new Date()).format('MMMM DD, YYYY')
Expand Down
9 changes: 1 addition & 8 deletions auth-web/src/views/auth/AccountSettings.vue
Original file line number Diff line number Diff line change
Expand Up @@ -85,16 +85,9 @@
{{ currentOrganization.name }}
</h1>
<p
v-if="isPremiumAccount"
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Aye good stuff

class="mt-3 mb-0"
>
Manage account information, and view account activity.
</p>
<p
v-else
class="mt-3 mb-0"
>
Manage account information, team members, and authentication settings.
Manage account settings, team members, and view transactions for this account
</p>
</div>

Expand Down
Loading
Loading