From 9127dd55b0bf70aa126584fa062e7d8aa10cb516 Mon Sep 17 00:00:00 2001 From: Matthieu Sieben Date: Thu, 23 Jan 2025 13:52:39 +0100 Subject: [PATCH] Use public api to resolve handle --- src/lib/api/resolve.ts | 2 +- .../components/ChangeHandleDialog.tsx | 8 ++--- src/state/queries/handle.ts | 33 +++++++++++-------- 3 files changed, 24 insertions(+), 19 deletions(-) diff --git a/src/lib/api/resolve.ts b/src/lib/api/resolve.ts index 3710623500..763a82db16 100644 --- a/src/lib/api/resolve.ts +++ b/src/lib/api/resolve.ts @@ -174,7 +174,7 @@ export async function resolveLink( throw new Error('getPost: post not found') } - // Forked from useFetchDid. TODO: move into RQ. + // TODO: move into RQ. async function fetchDid(handleOrDid: string) { let identifier = handleOrDid if (!identifier.startsWith('did:')) { diff --git a/src/screens/Settings/components/ChangeHandleDialog.tsx b/src/screens/Settings/components/ChangeHandleDialog.tsx index 37f6ed9eff..e8035a66e9 100644 --- a/src/screens/Settings/components/ChangeHandleDialog.tsx +++ b/src/screens/Settings/components/ChangeHandleDialog.tsx @@ -19,7 +19,7 @@ import {HITSLOP_10} from '#/lib/constants' import {cleanError} from '#/lib/strings/errors' import {sanitizeHandle} from '#/lib/strings/handles' import {createFullHandle, validateHandle} from '#/lib/strings/handles' -import {useFetchDid, useUpdateHandleMutation} from '#/state/queries/handle' +import {useResolveHandle, useUpdateHandleMutation} from '#/state/queries/handle' import {RQKEY as RQKEY_PROFILE} from '#/state/queries/profile' import {useServiceQuery} from '#/state/queries/service' import {useAgent, useSession} from '#/state/session' @@ -282,7 +282,7 @@ function OwnHandlePage({goToServiceHandle}: {goToServiceHandle: () => void}) { const [domain, setDomain] = useState('') const agent = useAgent() const control = Dialog.useDialogContext() - const fetchDid = useFetchDid() + const resolveHandle = useResolveHandle() const queryClient = useQueryClient() const { @@ -307,10 +307,10 @@ function OwnHandlePage({goToServiceHandle}: {goToServiceHandle: () => void}) { isSuccess: isVerified, error: verifyError, reset: resetVerification, - } = useMutation({ + } = useMutation({ mutationKey: ['verify-handle', domain], mutationFn: async () => { - const did = await fetchDid(domain) + const did = await resolveHandle(domain) if (did !== currentAccount?.did) { throw new DidMismatchError(did) } diff --git a/src/state/queries/handle.ts b/src/state/queries/handle.ts index 658b9e9c15..3c98fd8086 100644 --- a/src/state/queries/handle.ts +++ b/src/state/queries/handle.ts @@ -3,6 +3,7 @@ import {useMutation, useQueryClient} from '@tanstack/react-query' import {STALE} from '#/state/queries' import {useAgent} from '#/state/session' +import {createPublicAgent} from '#/state/session/agent' const handleQueryKeyRoot = 'handle' const fetchHandleQueryKey = (handleOrDid: string) => [ @@ -10,7 +11,7 @@ const fetchHandleQueryKey = (handleOrDid: string) => [ handleOrDid, ] const didQueryKeyRoot = 'did' -const fetchDidQueryKey = (handleOrDid: string) => [didQueryKeyRoot, handleOrDid] +const fetchDidQueryKey = (handle: string) => [didQueryKeyRoot, handle] export function useFetchHandle() { const queryClient = useQueryClient() @@ -51,25 +52,29 @@ export function useUpdateHandleMutation(opts?: { }) } -export function useFetchDid() { +export function useResolveHandle() { const queryClient = useQueryClient() - const agent = useAgent() + + // @NOTE: We are *not* using the logged in agent (from `useAgent()`) here. + // Using the public API rather than the user's PDS ensures that the handle + // properly resolves. + const publicAgent = React.useMemo(() => createPublicAgent(), []) return React.useCallback( - async (handleOrDid: string) => { + async (handle: string) => { return queryClient.fetchQuery({ - staleTime: STALE.INFINITY, - queryKey: fetchDidQueryKey(handleOrDid), - queryFn: async () => { - let identifier = handleOrDid - if (!identifier.startsWith('did:')) { - const res = await agent.resolveHandle({handle: identifier}) - identifier = res.data.did - } - return identifier + staleTime: STALE.MINUTES.ONE, + queryKey: fetchDidQueryKey(handle), + queryFn: async ({signal}) => { + const res = await publicAgent.resolveHandle( + {handle}, + // Retries should force a fresh resolution; avoid cache. + {signal, headers: {'cache-control': 'no-cache'}}, + ) + return res.data.did }, }) }, - [queryClient, agent], + [queryClient, publicAgent], ) }