Skip to content

Commit

Permalink
✨ Add can't send email warning for users that can not receiv… (#176)
Browse files Browse the repository at this point in the history
* ✨ Show detailed error message when template saving fails

* ✨ Add language picker to comm templates

* 💄 Improved UI changes

* ✨ Better empty message

* ♻️ Refactor language name getter

* 🧹 Cleanup

* ✨ Add can't send email warning for users that can not receive emails

* ✨ Move allowed domain list to env var

* ✨ Change message in warning
  • Loading branch information
foysalit committed Sep 11, 2024
1 parent 56f85a8 commit b5db7ae
Show file tree
Hide file tree
Showing 4 changed files with 80 additions and 5 deletions.
33 changes: 29 additions & 4 deletions components/common/Alert.tsx
Original file line number Diff line number Diff line change
@@ -1,3 +1,9 @@
import {
ExclamationCircleIcon,
ExclamationTriangleIcon,
InformationCircleIcon,
} from '@heroicons/react/24/solid'

export const Alert = ({
type = 'info',
title = '',
Expand All @@ -19,16 +25,35 @@ export const Alert = ({
title: 'text-blue-800',
},
warning: {
container: 'border-yellow-800 bg-yellow-200 text-yellow-800',
container: 'border-yellow-800 bg-yellow-200 text-yellow-600',
title: 'text-yellow-800',
},
}
const iconSize = !title || !body ? 'h-4 w-4' : 'h-6 w-6'

return (
<div
className={`border text-sm rounded px-4 py-2 ${classNames[type].container}`}
className={`border text-sm rounded px-4 py-2 flex flex-row items-center ${classNames[type].container}`}
>
{title && <h4 className={`${classNames[type].title}`}>{title}</h4>}
{body && <p>{body}</p>}
{showIcon && (
<div className="mr-3">
{type === 'error' && (
<ExclamationCircleIcon className={`${iconSize} text-red-600`} />
)}
{type === 'warning' && (
<ExclamationTriangleIcon
className={`${iconSize} text-yellow-800`}
/>
)}
{type === 'info' && (
<InformationCircleIcon className={`${iconSize} text-blue-800`} />
)}
</div>
)}
<div>
{title && <h4 className={`${classNames[type].title}`}>{title}</h4>}
{body && <p>{body}</p>}
</div>
</div>
)
}
33 changes: 33 additions & 0 deletions components/email/useEmailRecipientStatus.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
import { DOMAINS_ALLOWING_EMAIL_COMMUNICATION } from '@/lib/constants'
import { resolveDidDocData } from '@/lib/identity'
import { useQuery } from '@tanstack/react-query'

export const useEmailRecipientStatus = (
did: string,
): { isLoading: boolean; error: any; cantReceive: boolean } => {
const { data, isLoading, error } = useQuery({
queryKey: ['email-capability-check', did],
queryFn: async () => {
const response = await resolveDidDocData(did)
if (!response?.services) {
return false
}

const pdsEndpoint = response.services['atproto_pds']?.endpoint
if (!pdsEndpoint) {
return false
}

return DOMAINS_ALLOWING_EMAIL_COMMUNICATION.some((domain) => {
return !!domain && pdsEndpoint.endsWith(domain)
})
},
})

return {
isLoading,
error,
// we only know for sure that the recipient can't receive emails if the result of the query is false is false
cantReceive: data === false,
}
}
15 changes: 14 additions & 1 deletion components/repositories/AccountView.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ import {
} from '@heroicons/react/20/solid'
import { AuthorFeed } from '../common/feeds/AuthorFeed'
import { Json } from '../common/Json'
import { buildBlueSkyAppUrl, classNames, truncate } from '@/lib/util'
import { buildBlueSkyAppUrl, truncate } from '@/lib/util'
import { ReportPanel } from '../reports/ReportPanel'
import React from 'react'
import {
Expand Down Expand Up @@ -52,6 +52,8 @@ import {
useWorkspaceRemoveItemsMutation,
} from '@/workspace/hooks'
import { Blocks } from './Blocks'
import { useEmailRecipientStatus } from 'components/email/useEmailRecipientStatus'
import { Alert } from '@/common/Alert'
import { Follows } from 'components/graph/Follows'
import { Followers } from 'components/graph/Followers'

Expand Down Expand Up @@ -745,6 +747,7 @@ export const EventsView = ({ did }: { did: string }) => {
}

const EmailView = (props: ComponentProps<typeof EmailComposer>) => {
const { cantReceive } = useEmailRecipientStatus(props.did)
return (
<div className="mx-auto mt-8 max-w-5xl px-4 pb-12 sm:px-6 lg:px-8">
<div className="flex flex-row justify-end items-center">
Expand All @@ -758,6 +761,16 @@ const EmailView = (props: ComponentProps<typeof EmailComposer>) => {
<ArrowTopRightOnSquareIcon className="inline-block h-4 w-4 ml-1" />
</LinkButton>
</div>
{cantReceive && (
<div className="my-2">
<Alert
showIcon
type="warning"
title="Can not send email to this user"
body="This user's account is hosted on PDS that does not allow sending emails. Please check the PDS of the user to verify."
/>
</div>
)}
<EmailComposer {...props} />
</div>
)
Expand Down
4 changes: 4 additions & 0 deletions lib/constants.ts
Original file line number Diff line number Diff line change
Expand Up @@ -40,3 +40,7 @@ export const YOUNG_ACCOUNT_MARKER_THRESHOLD_IN_DAYS = process.env
.NEXT_PUBLIC_YOUNG_ACCOUNT_MARKER_THRESHOLD_IN_DAYS
? parseInt(process.env.NEXT_PUBLIC_YOUNG_ACCOUNT_MARKER_THRESHOLD_IN_DAYS)
: 30

export const DOMAINS_ALLOWING_EMAIL_COMMUNICATION = (
process.env.NEXT_PUBLIC_DOMAINS_ALLOWING_EMAIL_COMMUNICATION || ''
).split(',')

0 comments on commit b5db7ae

Please sign in to comment.