Reputation: 849
I want to load options from backend. So i have to fetch data from API and then update options. But i don't know how to do it. Can someone help? Here's my code:
function myComponent() {
const loadOptions = () => {
console.log('on load options function')
axios.get(`/api/admin/roles`)
.then((response) => {
const options = []
response.data.permissions.forEach((permission) => {
options.push({
label: permission.name,
value: permission.id
})
})
return options
})
}
return (
<AsyncSelect
isMulti
cacheOptions
loadOptions={loadOptions}
/>
)
}
By the way nothing gets logged at all and that means the loadOptions function does not run. Here's my response from API:
response: {
data: {
permissions: [{
id: 13,
name: 'deposit'
}, {
id: 14,
name: 'withdraw'
}]
}
}
Upvotes: 4
Views: 4862
Reputation: 10454
The issue you're experiencing seems to be due to the fact that you're not returning anything at the top-level of the loadOptions
function.
The documentation highlights two ways to define your loadOptions
function.
Using callbacks:
const loadOptions = (inputValue, callback) => {
setTimeout(() => {
callback(options);
}, 1000);
};
Using promises:
const loadOptions = inputValue =>
new Promise(resolve => {
setTimeout(() => {
resolve(options);
}, 1000);
});
In your case, it might be simplest to try the callback option first since your existing syntax is conducive with it.
const loadOptions = (inputValue, callback) => {
console.log('on load options function')
axios.get(`/api/admin/roles`)
.then((response) => {
const options = []
response.data.permissions.forEach((permission) => {
options.push({
label: permission.name,
value: permission.id
})
})
callback(options);
})
}
In the future you can optionally leverage the inputValues
parameter to down-filter results.
Upvotes: 4
Reputation: 565
Try this
const loadOptions = async () => {
const response = await axios.get(`/api/admin/roles`)
const result = await response.data
return await result.permissions.map((permission) => ({
label: permission.name,
value: permission.id
}))
}
Upvotes: 0
Reputation: 281626
Your loadOptions
function must return a promise. Also you can pass defaultOptions
as true to make the request fire for initial set of options
const loadOptions = () => {
console.log('on load options function')
return axios.get(`/api/admin/roles`)
.then((response) => {
const options = []
response.data.permissions.forEach((permission) => {
options.push({
label: permission.name,
value: permission.id
})
})
return options
})
}
function myComponent() {
return (
<AsyncSelect
isMulti
cacheOptions
defaultOptions
loadOptions={loadOptions}
/>
)
}
P.S For performance reasons, you can declare your loadOptions function outside of the component so that it doesn't get recreated on every re-render
Upvotes: 2
Reputation: 2102
AsyncSelect expects a defaultOptions prop, which you have not provided. The docs are unclear about what behavior it should exhibit in this case, but I'd guess it defaults to loading on filter.
Upvotes: 0