Skip to content

Commit

Permalink
admin/donations: Fix not being able to link user to donation if billi…
Browse files Browse the repository at this point in the history
…ngEmail is null (#1504)

* donations/grid: Fix donations association to user

* admin/donations: Extend donor's autocomplete to look for email

* admin/donations: Move autocomplete filter to its own function

* personFilter: Expand filter rules to look for last name
  • Loading branch information
sashko9807 authored Jul 20, 2023
1 parent ad26e28 commit 6f8e06e
Show file tree
Hide file tree
Showing 3 changed files with 32 additions and 21 deletions.
17 changes: 4 additions & 13 deletions src/components/admin/donations/grid/RenderEditBillingEmailCell.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ import { DonationResponse, UserDonationInput } from 'gql/donations'
import { useEditDonation } from 'service/donation'
import { ApiErrors } from 'service/apiErrors'
import { AlertStore } from 'stores/AlertStore'
import { personFilter } from 'components/common/person/PersonAutoCompleteFilter'

interface RenderEditCellProps {
params: GridRenderEditCellParams
Expand All @@ -35,7 +36,7 @@ export default function RenderEditBillingEmailCell({
const initialPerson = {
firstName: params.row.billingEmail,
lastName: '',
email: params.row.email || params.row.billingEmail || null,
email: params.row.email || params.row.billingEmail || '',
}
const [person, setPerson] = React.useState<PersonResponse | null>({
...initialPerson,
Expand All @@ -59,6 +60,7 @@ export default function RenderEditBillingEmailCell({
const onClick = () => {
if (person) {
const donationData: UserDonationInput = params.row
donationData.targetPersonId = undefined
donationData.billingEmail = person.email
mutation.mutate(donationData)
} else {
Expand Down Expand Up @@ -86,18 +88,7 @@ export default function RenderEditBillingEmailCell({
</Box>
)}
isOptionEqualToValue={(option, value) => option.email === value.email}
filterOptions={(options, state) => {
const displayOptions = options.filter(
(option) =>
option.firstName
.toLowerCase()
.trim()
.includes(state.inputValue.toLowerCase().trim()) ||
option.email.toLowerCase().trim().includes(state.inputValue.toLowerCase().trim()),
)

return displayOptions
}}
filterOptions={personFilter}
clearText={t('donations:cta.clear')}
noOptionsText={t('donations:noOptions')}
openText={t('donations:cta.open')}
Expand Down
13 changes: 5 additions & 8 deletions src/components/admin/donations/grid/RenderEditPersonCell.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -4,13 +4,14 @@ import { useMutation } from '@tanstack/react-query'
import { useTranslation } from 'next-i18next'
import { GridRenderEditCellParams } from '@mui/x-data-grid'
import { TextField, Tooltip, Box } from '@mui/material'
import Autocomplete, { createFilterOptions } from '@mui/material/Autocomplete'
import Autocomplete from '@mui/material/Autocomplete'
import { Save } from '@mui/icons-material'
import { PersonResponse } from 'gql/person'
import { DonationResponse, UserDonationInput } from 'gql/donations'
import { useEditDonation } from 'service/donation'
import { ApiErrors } from 'service/apiErrors'
import { AlertStore } from 'stores/AlertStore'
import { personFilter } from 'components/common/person/PersonAutoCompleteFilter'

interface RenderEditCellProps {
params: GridRenderEditCellParams
Expand All @@ -37,7 +38,7 @@ export default function RenderEditPersonCell({
params.row.person && params.row.person.firstName ? params.row.person.firstName : 'Anonymous',
lastName:
params.row.person && params.row.person.lastName ? params.row.person.lastName : 'Donor',
email: params.row.email || params.row.billingEmail || null,
email: params.row.email || params.row.billingEmail || '',
}
const [person, setPerson] = React.useState<PersonResponse | null>({
...initialPerson,
Expand All @@ -62,6 +63,7 @@ export default function RenderEditPersonCell({
if (person) {
const donationData: UserDonationInput = params.row
donationData.targetPersonId = person.id
donationData.billingEmail = undefined
mutation.mutate(donationData)
} else {
AlertStore.show(t('donations:alerts.requiredError'), 'error')
Expand All @@ -86,12 +88,7 @@ export default function RenderEditPersonCell({
</Box>
)}
isOptionEqualToValue={(option, value) => option.firstName === value.firstName}
filterOptions={createFilterOptions<PersonResponse>({
matchFrom: 'any',
limit: 5,
ignoreCase: true,
trim: true,
})}
filterOptions={personFilter}
clearText={t('donations:cta.clear')}
noOptionsText={t('donations:noOptions')}
openText={t('donations:cta.open')}
Expand Down
23 changes: 23 additions & 0 deletions src/components/common/person/PersonAutoCompleteFilter.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
import { PersonResponse } from 'gql/person'
import { FilterOptionsState } from '@mui/material'

/**
* Custom function to filter person related autocomplete inputs, based on either firstname, lastname or email
* @param options AutoComplete prop
* @param state AutoComplete prop
* @returns
*/
export const personFilter = (
options: PersonResponse[],
state: FilterOptionsState<PersonResponse>,
) => {
const displayOptions = options.filter((option) => {
const name = `${option.firstName.toLowerCase()} ${option.lastName.toLowerCase()}`
return (
name.includes(state.inputValue.toLowerCase()) ||
option.email.toLowerCase().includes(state.inputValue.toLowerCase())
)
})

return displayOptions
}

0 comments on commit 6f8e06e

Please sign in to comment.