元々はこちらで紹介されている方法です。
How to handle loading and error state in a generic way?
ローディング中にコンテンツを覆うモーダルウィンドウ。
const LoadingModal: React.FC = () => (
<Dialog open>
<ProgressImage />
</Dialog>
);
エラーメッセージを表示するダイアログ。
import { ApolloError } from 'apollo-client';
interface ErrorModalProps {
error: ApolloError;
onClose(): void;
}
const ErrorModal: React.FC<ErrorModalProps> = ({ error, onClose }) => {
const [open, setOpen] = useState<boolean>(!!error);
const handleClose = () => {
setOpen(false);
onClose();
};
return (
<Dialog open onClose={handleClose}>
{error.message}
<Button onClick={handleClose}>
close
</Button>
</Dialog>
);
};
PropsでuseQuery
ORuseMutate
のステータス値を受け取り、必要に応じてダイアログを表示するコンポーネント。
interface HandleQueryProps {
loading: boolean;
error?: ApolloError;
}
const HandleQuery: React.FC<HandleQueryProps> = ({
loading,
error,
children,
}) => {
const onError = ()=> {
setOpen(false);
// 必要に応じてリダイレクトなど
};
return (
<>
{children}
{loading && <LoadingModal />}
{error && <ErrorModal error={error} onClose={onError} />}
</>
);
};
HandleQuery
コンポーネント利用例。
const SameComponent: React.FC = () => {
const { data, loading, error } = useQuery(QUERY);
return (
<HandleQuery loading={loading} error={error}>
<ChildComponent data={data} />
</HandleQuery>
);
}
参考情報
APOLLO DOCS > Client(React) > Error handling
React > Error Boundary