How to pass an array in query parameter url react - reactjs

I Am using multiselect dropdown, what i want is whatever i've selected in dropdown to send it to the server by calling an api which contains query param to accomodate these dropdown result. I have made an array of selected items.
Array(3) [ "contact", "fee", "inbox" ]
I want this array to get pass to below url like this:
http://localhost.com/api/influencers?status=contact&status=fee&status=inbox
With my approach i am ending up with this:
http://localhost:8080/details?status[]=contact&status[]=fee&status[]=inbox
Can anyone please help me with it
const InfluencersList = props => {
const [availability, setAvailability] = useState(null);
const handleAvailabilityChange = value => {
const availability1 = value;
setAvailability(value);
getFilterData(availability1, null);
};
const getFilterData = (search, pageNumber) => {
let params = {};
params.status = search; //search is array [contact,
if (pageNumber) {
params.page = pageNumber; // no is array is number
}
axios.get("/api/influencers", { params: params }).then(res => {
setState({
items: res.data.data
});
});
};
<ChoiceList
title="Availability"
titleHidden
choices={statuses}
selected={availability || []}
onChange={handleAvailabilityChange}
allowMultiple
/>
}

you would need to use URLSearchParams to build your params with multiple query with same name.
Iterate over search and for each value you append to your params a new status value:
const getFilterData = (search, pageNumber) => {
const params = new URLSearchParams();
search.forEach(value => params.append('status', value));
if (pageNumber) {
params.append('page', pageNumber) ;
}
axios.get("/api/influencers", { params }).then(res => {
setState({
items: res.data.data
});
});
};

Why not -with axios- you send a string as:
"contact;fee;inbox"
and in the backend convert this string to an array using a function like split(';')?

Related

Updating an object inside an array in Firebase Firestore react JS

I want to be able to update a string inside an array that is stored in Firestore.
Now, I went througn their docs, and there is no such method. what they do provide is arrayUnion (to add another element to the array) and arrayRemove (to remove an element from an array).
So I thoguht I call on arrayUnion to add the new content and then arrayRemove to remove the old one thus, in practice, updating it.
However, if I only use arrayUnion it works fine, if I use both, only arrayRemove works and the new elemnt is not added. any Ideas?
const updateField = async (e, id, obj) => {
const taskDoc = doc(db, "Task", id);
if (e.target.id == "updateTodos") {
const updatedTask = {
Todos: arrayUnion(updatedTodo),
Todos: arrayRemove(obj),
};
await updateDoc(taskDoc, updatedTask);
setUpdateHadHappened(updateHasHappened + 1);
exitEditMode();
}
notice that writing:
Todos: arrayUnion(updatedTodo), arrayRemove(obj),
or
Todos: arrayUnion(updatedTodo); arrayRemove(obj);
does not work..
ok, solved it! it's all about syntax my friends:
const updateField = async (e, id, obj) => {
const taskDoc = doc(db, "Task", id);
if (e.target.id == "updateTodos") {
const updatedTask = {
Todos: arrayUnion(updatedTodo),
};
await updateDoc(taskDoc, updatedTask);
const updatedTask2 = {
Todos: arrayRemove(obj),
};
await updateDoc(taskDoc, updatedTask2);
setUpdateHadHappened(updateHasHappened + 1);
exitEditMode();
}

Update an array relation belongs to many with Strapi controller

I use Strapi V4. I have a link collection and I want to update likes.
How update the relation array ? When I put new data old value are replace by the new one.
Example :
likes : [1]
if I update another time
likes:[2].
BUT I want this likes : [1,2]
I try this but It d'oesn't work. Thans for your replay
'use strict';
/**
* link controller
*/
const { createCoreController } = require('#strapi/strapi').factories;
module.exports = createCoreController('api::link.link', ({ strapi }) => ({
// Method 2: Wrapping a core action (leaves core logic in place)
async find(ctx) {
const { data, meta } = await super.find(ctx);
const linkId = data.map((link) => link.id);
const allPosts = await strapi.entityService.findMany('api::link.link', {
fields: ["id"],
filters: { id: { $in: linkId } },
populate: {
likes: { count: true },
},
});
data.forEach(link => {
link.likes = allPosts.find(({ id }) => id === link.id)?.likes?.count || 0;
});
//update value with new array => need to be fix
await strapi.entityService.update("api::link.link", {
likes: [...allPosts.likes.map(({ id }) => id), ...likes],
});
return { data, meta };
},
}));
This part need to be fix. Can you help me ? Thanks
//update value with new array => need to be fix
await strapi.entityService.update("api::link.link", {
likes: [...allPosts.likes.map(({ id }) => id), ...likes],
});

How do I pass an array a component and have the components variables capture multiple values within each array whiten the Array sent from service

I have a service that puts an array in a variable (this.datapointarray) and I would like to send the values in the array (datapointarray) in the chart which is a seperate component. Can anyone shed light on how to do this? The data has to take 12 values each form the array. All values and names for each set (12 values) are in the array.
Service.ts
export class ResearchDataService {
getinstutioninformation(){
this.datapointupdate = new EventEmitter<InstitutionDataPoints[]>()
this.arrayUpdate = new EventEmitter<InstitutionData[]>()
this.arrayUpdate.subscribe(() => {
this.authService.getUserByToken().subscribe(user => {
const aArray = this.analysisarray
// const usertransformed:any = user
this.gtinstitutionService.getIChartData({
iChartClientID: user?.ClientID,
iChartClientID1: aArray[1]?.ClientID,
iChartStrtYear: 2019, // this has to be a drop down value
iChartDataName: 'Total Assets' //this has to be a dropdown value
}).subscribe(response => {
this.dataPointArray = response;
this.datapointupdate.emit(response)
// console.log("User Informatiion in array", user)
console.log("Response fom getIChartData: ", response)
})
})
});
}
Chart.ts
export class MixedWidget11Component implements OnInit {
getChartOptions(chartHeight: string, chartColor: string) {
const labelColor = getCSSVariableValue('--kt-gray-500');
const borderColor = getCSSVariableValue('--kt-gray-200');
const secondaryColor = getCSSVariableValue('--kt-gray-300');
const baseColor = getCSSVariableValue('--kt-' + chartColor);
return {
series: [
{
name: this.dataPointArray,
data: [1,2,56,43,32,45,33,23,232,334,333,34],
},
{
name: "selected institution analyzation list",
data: [1,2,56,43,32,45,33,23,232,334,333,34],
},
}

React Firestore - Retrieve all documents in an Array of document IDs

I am trying to retrieve an all documents of which document ID is within the given array. I have no issues retrieving the list of documentIDs and storing in the array. However, I am not sure on how to retrieve the documents of which ids are in the array. Please help Thanks!
portfolio doc:
docId{
docId: docId,
...
}
const getData = (bookmarkIds) => {
console.log("this is " )
console.log(bookmarkIds)
console.log("entering" )
const portfolioQuery = database.portfolioRef.where("docId", 'in', bookmarkIds);
portfolioQuery.onSnapshot((snapshot) => {
console.log(snapshot.docs)
if (snapshot.docs.length !== 0) {
var id = 1;
const tempItem = [];
snapshot.docs.forEach((doc) => {
tempItem.push({
id: id,
intervieweeName: doc.data().intervieweeName,
intervieweeEmail: doc.data().intervieweeEmail,
projectTitle: doc.data().projectTitle,
portfolioTitle: doc.data().portfolioTitle,
dateCreated: doc.data().dateCreated,
fbId: doc.id
})
id++;
})
setPortfolioData(tempItem)
}
})
}
useEffect(() => {
const getUserData = database.usersRef.where("email", "==", currentUser.email);
const bookmarkArray = [];
const unsub = getUserData.onSnapshot((snapshot) => {
snapshot.docs.forEach((doc) =>{
bookmarkArray.push(doc.data().bookmarkIds);
})
console.log(bookmarkArray);
getData(bookmarkArray)
})
return unsub;
}, [currentUser.email]);
Based on my current code above, I am receiving the following (Not getting any error just a blank return):
I realised I made a double array by doing
bookmarkArray.push(doc.data().bookmarkIds);
solved by doing
bookmarkArray = doc.data().bookmarkIds;

Is there a way to check nested resources in react-admin's matchSuggestion?

The goal is to make an AutocompleteInput check for the filter value not only in the suggestion list directly, but also in the suggestions' references to different resources.
Specifically, say a Quote has a reference to a Contact and to an Address, and the user enters 'abc' in the input. Now, a Quote whose address contains 'abc' should also be displayed in the suggestion list.
The most elegant way would be to use the useGetOne hook like in the following code snippet but you can't call that hook from outside a React component.
const matchAnyNested = (filter, value) => {
if (matchAnyField(filter, value)) return true;
const { data: contact } = useGetOne('contacts', value.contact_id);
if (matchAnyField(filter, contact)) return true;
const { data: account } = useGetOne('accounts', contact.account_id);
if (matchAnyField(filter, account)) return true;
for (let item of value.part_items) {
const part = useGetOne('parts', item.part_id);
if (matchAnyField(filter, part)) return true;
}
return false;
};
[...]
<AutocompleteInput ... matchSuggestion={matchAnyNested} />
Is there a way to fetch records from within the matchSuggestion function or some other way to validate suggestions based on nested records ? Thanks for any help
Because of the React rules of hooks, this doesn't seem to be possible. I ended up implementing this filtering functionality in the backend.
The useGetOne hook, just like other dataProvider hooks, accepts an enabled option. The example from the react-admin documentation shows its usage:
// fetch posts
const { ids, data: posts, loading: isLoading } = useGetList(
'posts',
{ page: 1, perPage: 20 },
{ field: 'name', order: 'ASC' },
{}
);
// then fetch categories for these posts
const { data: categories, loading: isLoadingCategories } = useGetMany(
'categories',
ids.map(id=> posts[id].category_id),
// run only if the first query returns non-empty result
{ enabled: ids.length > 0 }
);
It applies to your case:
const matchAnyNested = (filter, value) => {
const { data: contact } = useGetOne(
'contacts',
value.contact_id,
{ enabled: !matchAnyField(filter, value) }
);
const { data: account } = useGetOne(
'accounts',
contact.account_id,
{ enabled: !matchAnyField(filter, contact) }
);
// ...
};
This won't solve your problem in the loop, though, because of the rules of hooks.
If you do need that loop, your best bet is to use the useDataProvider hook to call the dataProvider directly:
const matchAnyNested = async (filter, value) => {
const dataProvider = useDataProvider();
if (matchAnyField(filter, value)) return true;
const { data: contact } = await dataProvider.getOne('contacts', { id: value.contact_id });
if (matchAnyField(filter, contact)) return true;
const { data: account } = await dataProvider.getOne('accounts', { id: contact.account_id });
if (matchAnyField(filter, account)) return true;
for (let item of value.part_items) {
const part = await dataProvider.getOne('parts', { id: item.part_id });
if (matchAnyField(filter, part)) return true;
}
return false;
};

Resources