All files / app/features/userQueries useLiteUsers.ts

100% Statements 27/27
90% Branches 9/10
100% Functions 9/9
100% Lines 23/23

Press n or j to go to the next uncovered block, b, p or k for the previous block.

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 6921x 21x 21x   21x 21x   21x         852x   504x 504x     129x 129x           504x   504x     250x           504x               76x 96x 76x         491x   97x         4x           491x     491x  
import { reactQueryRetries } from "appConstants";
import { liteUserKey, liteUsersKey } from "features/queryKeys";
import { RpcError, StatusCode } from "grpc-web";
import { GetLiteUsersRes, LiteUser } from "proto/api_pb";
import { useQuery } from "react-query";
import { service } from "service";
 
import { userStaleTime } from "./constants";
 
// React Query typically retains the last successful data until the next successful fetch
// if ids is `[]`, then `data` is `undefined`
function useLiteUsers(ids: (number | undefined)[] | undefined) {
  const nonFalseyIds = ids?.filter((id): id is number => !!id);
  // remove duplicate IDs from this list
  const uniqueIds = Array.from(new Set(nonFalseyIds));
  const query = useQuery<GetLiteUsersRes.AsObject, RpcError>({
    queryKey: liteUsersKey(uniqueIds),
    queryFn: () => {
      const result = service.user.getLiteUsers(uniqueIds);
      return result;
    },
    staleTime: userStaleTime,
    enabled: uniqueIds.length > 0, // run only if there are valid userIds
  });
 
  const isDataUndefined = !query.data || !query.data.responsesList;
  const usersById =
    query.isLoading || isDataUndefined
      ? undefined
      : new Map(
          query?.data?.responsesList.map((response) => [
            response?.user?.userId,
            response.user,
          ])
        );
 
  return {
    ...query,
    data: usersById,
  };
}
 
// Like above, but returns users in a list of the same size in same order
function useLiteUsersList(ids: (number | undefined)[] | undefined) {
  const liteUsersMap = useLiteUsers(ids);
  const usersList = ids?.map((id) => liteUsersMap.data?.get(id));
  return { ...liteUsersMap, usersById: liteUsersMap.data, data: usersList };
}
 
// React Query typically retains the last successful data until the next successful fetch
function useLiteUser(id: number | undefined) {
  const query = useQuery<LiteUser.AsObject, RpcError>({
    queryKey: liteUserKey(id),
    queryFn: () => service.user.getLiteUser(id?.toString() || ""),
    staleTime: userStaleTime,
    enabled: id !== undefined,
    retry: (failureCount, error) => {
      // don't retry if the user isn't found
      return (
        error.code !== StatusCode.NOT_FOUND && failureCount < reactQueryRetries
      );
    },
  });
 
  return query;
}
 
export { useLiteUser, useLiteUsers, useLiteUsersList };