Here is more Typescript eslint friendly way(no usage of any
)
Array chunk method in ArrayUtils.ts
export function chunk<M>(array: Array<M>, chunkSize: number) {
const ans: Array<Array<M>> = [];
for (let i = 0; i < array.length; i += chunkSize) {
ans[Math.floor(i / chunkSize)] = array.slice(i, i + chunkSize);
}
return ans;
}
now in FirebaseUtils.kt
, you can write
import { chunk } from "./ArrayUtils";
export async function inQuery<M>(
docRef: FirebaseFirestore.CollectionReference,
field: string | FirebaseFirestore.FieldPath,
values: Array<string>
) {
const querySnapshots = await Promise.all(
chunk(values, 10).map((chunkedArray) => {
return docRef.where(field, "in", chunkedArray).get();
})
);
return querySnapshots
.flatMap((querySnapshot) => querySnapshot.docs)
.map((documentData) => documentData.data() as M);
}
Few advantages over this answer
- Refactored as proper utility methods for reusability
- Used
Promise.all
which is parallel and more recommended than for await
as later is used when we don't have all the promises upfront. See this