Bluesky app fork with some witchin' additions 馃挮
witchsky.app
bluesky
fork
client
1import {createContext, useContext, useMemo} from 'react'
2
3import {BSKY_SERVICE} from '#/lib/constants'
4import {getHostnameFromUrl} from '#/lib/strings/url-helpers'
5import {STALE} from '#/state/queries'
6import {useProfileQuery} from '#/state/queries/profile'
7import {useCheckEmailConfirmed} from '#/state/service-config'
8import {useSession} from '#/state/session'
9
10type EmailVerificationContext = {
11 needsEmailVerification: boolean
12}
13
14const EmailVerificationContext = createContext<EmailVerificationContext | null>(
15 null,
16)
17EmailVerificationContext.displayName = 'EmailVerificationContext'
18
19export function Provider({children}: {children: React.ReactNode}) {
20 const {currentAccount} = useSession()
21
22 const {data: profile} = useProfileQuery({
23 did: currentAccount?.did,
24 staleTime: STALE.INFINITY,
25 })
26
27 const checkEmailConfirmed = useCheckEmailConfirmed()
28
29 // Date set for 11 AM PST on the 18th of November
30 const isNewEnough =
31 !!profile?.createdAt &&
32 Date.parse(profile.createdAt) >= Date.parse('2024-11-18T19:00:00.000Z')
33
34 const isSelfHost =
35 currentAccount &&
36 getHostnameFromUrl(currentAccount.service) !==
37 getHostnameFromUrl(BSKY_SERVICE)
38
39 const needsEmailVerification =
40 !isSelfHost &&
41 checkEmailConfirmed &&
42 !currentAccount?.emailConfirmed &&
43 isNewEnough
44
45 const value = useMemo(
46 () => ({needsEmailVerification}),
47 [needsEmailVerification],
48 )
49
50 return (
51 <EmailVerificationContext.Provider value={value}>
52 {children}
53 </EmailVerificationContext.Provider>
54 )
55}
56Provider.displayName = 'EmailVerificationProvider'
57
58export function useEmail() {
59 const ctx = useContext(EmailVerificationContext)
60 if (!ctx) {
61 throw new Error('useEmail must be used within a EmailVerificationProvider')
62 }
63 return ctx
64}