Replies: 6 comments
-
Hi @iwikal, great observation, and cool solution! We actually have an experimental function for this, though it currently isn't documented: reactfire/reactfire/firestore/index.tsx Line 17 in e1daab4 The |
Beta Was this translation helpful? Give feedback.
-
I've started documenting this here. Maybe I should rename the section to "Preventing Waterfalls" |
Beta Was this translation helpful? Give feedback.
-
I didn't find a preload function for collection queries, is that in the works? Also, I don't really understand how this preloading works. Does it register a listener? If so, when does that get unsubscribed? If not, wouldn't that result in twice the reads? (Once to preload, once to register the actual listener) |
Beta Was this translation helpful? Give feedback.
-
I think the resource as return type pattern would work pretty well for the whole api too. If you do want to suspend immediately, you can always call const { docs } = useFirestoreCollection(query).read() You can also enforce preloading on the type level, if you say that a component wants a resource as a prop. That tells the parent component that they need to start fetching the resource before rendering the child. Maybe there's room for both. |
Beta Was this translation helpful? Give feedback.
-
Thanks for the thoughts and suggestions, @iwikal, and sorry for the winter holiday delay! I've had some time to think on this some more, and I think this is solvable without increasing ReactFire's API surface. Example: somewhere up the component tree when we're pretty sure we'll need some data later // loads the Firestore SDK (doesn't block render or suspend)
preloadFirestore().then(firestore => {
// preload two collections using the vanilla Firestore SDK
// non-blocking
// get() will close the connection to firestore automatically
// if we end up not using this farther down the tree
firestore()
.collection("animals")
.get();
firestore()
.collection("plants")
.get();
}); in the component that actually needs the data // hopefully, preloadFirestore has already loaded this in.
// if not, it will suspend
const firestore = useFirestore();
// both these requests are already in flight (managed by Firestore SDK)
// each will suspend if they're not ready, but that's ok, because this component
// needs both to be ready to render
const animals = useFirestoreCollectionData(firestore().collection("animals"));
const plants = useFirestoreCollectionData(firestore().collection("plants")); This is similar to Relay's It also means that if someone just wants to get an app working and doesn't yet care about waterfalls + preloading, they don't need to change any code down in their component later when they decide they want to increase perf by adding a preload. If you'd like to see it in action, I'm going to open a PR soon to try this in the |
Beta Was this translation helpful? Give feedback.
-
I can totally see that this "opt-in to preloading" approach would be desirable. Me and my team have been experimenting with a different design forgoing the preloads altogether, cutting away a whole bunch of features to get a proof of concept working. It's not really ready, yet, but that's probably what we'll end up using. We've discovered an issue with the We're also trading the double reads for a risk of having more long-running requests that don't end up being used. It's hard to say which is going to be cheaper in the general case. |
Beta Was this translation helpful? Give feedback.
Uh oh!
There was an error while loading. Please reload this page.
-
I have a use case where I want to subscribe to two queries simultaneously.
This will result in an unnecessary waterfall where we wait for the first query to unsuspend before sending off the next. I resolved this by writing this helper function:
But it would be nice if the API nudged us in this direction by default.
Beta Was this translation helpful? Give feedback.
All reactions