Reputation: 61
ive been watching people use useLoaderData() to extract the values that been passed to the react component
Here's my code in App.js,
const router = createBrowserRouter(
createRoutesFromElements(
<Route path='/' element={<RootLayout/>}>
<Route path='user' loader={userLoader} element={<User/>}></Route>
</Route>
)
)
In element,
import { useLoaderData, Link } from "react-router-dom";
const User = () => {
const users = useLoaderData();
return (
<div >
</div>
);
}
//loader function
export const userLoader = async () => {
const res = await fetch('http://localhost:8000/user');
return res.json();
}
export default User;
My question is, isit possible to fetch from multiple URL and return once to the browser and extract with useLoaderData()?
which something looks like this
export const userLoader = async () => {
const res1 = await fetch('http://localhost:8000/user');
const user= res1.json();
const res2 = await fetch('http://localhost:8000/car');
const car= res2.json();
return {user, car};
}
i had tried above code and it returns a weird promise
and i noticed whenever i surround the json result with {} in loader function it returns a promise, why is it so?
//loader function
export const userLoader = async () => {
const res = await fetch('http://localhost:8000/user');
return {res.json()}; ////why u cant put {}?
}
export default User;
Upvotes: 3
Views: 1973
Reputation: 203373
The curly brackets only define a scope or object literal, it's the function being declared async
that makes it implicitly return a Promise object. The useLoaderData
hook and RRD Data router do the awaiting. When you use the following
export const userLoader = async () => {
const res1 = await fetch('http://localhost:8000/user');
const user = res1.json();
const res2 = await fetch('http://localhost:8000/car');
const car = res2.json();
return { user, car };
}
The code is resolving the implicit return with an object with properties user
and car
that are themselves unresolved Promise objects, e.g. res.json()
returns a Promise.
The loader should await
the JSON Promises as well.
export const userLoader = async () => {
const res1 = await fetch('http://localhost:8000/user');
const user = await res1.json();
const res2 = await fetch('http://localhost:8000/car');
const car = await res2.json();
return { user, car };
}
If none of these fetch requests are dependent on any other previous request resolving then you can speed things up a little bit by fetching things concurrently using Promise.all
.
Example:
export const userLoader = async () => {
const [user, car] = await Promise.all([
fetch('http://localhost:8000/user').then(res => res.json()),
fetch('http://localhost:8000/car').then(res => res.json()),
]);
return { user, car };
}
Upvotes: 7