-
Notifications
You must be signed in to change notification settings - Fork 204
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Problems when working with a List<T> #255
Comments
Maybe I'm missing something, why would the fetcher return no entries? |
Because the Store's Key is based on a "post type" (effectively a "category"). There really could be any number of reasons that the fetcher may return an empty data set. For example, we may try to fetch posts with a postType of "Kotlin", but on the server, no posts have been created yet with the "Kotlin" category. Or maybe the underlying API call enforces some date restrictions, to only fetch data from the api that is new within the last 24 hours, and there is no new data. As I mentioned, there could be any number of reasons that a fetcher (an API call) returns an empty data set. |
@digitalbuddha hmm ... I guess I should distinguish between the |
What do you expect to be returned in this case from get? Alternatively you can not read directly from room but rather have a middle broker (state flow maybe?) which emits when null is written. Finally you can throw an exception from the fetcher, exceptions do not get saved to source of truth but do hit the collector. If you want to create an example project/test case if be happy to show the different variants of the above suggestions |
Good question. In this case, I would expect that if I call So, if I do the following:
That 2nd log message will never show up.
I may take you up on that. First I'll try some of your suggestions myself and see where it gets me. Throwing an exception fro the Fetcher may make sense in my case.. As I mentioned above, It's not imperative that my store can read/write nulls. But it seems like I HAVE to make the reader return nulls in order to trigger the fetcher. |
Thinking about this more, and triggering an error in the Fetcher when an empty data set is returned from the api seems like the right thing to do ... As I thought about it, this "problem" could also potentially arise from a single item (i.e. not a list). For example, ake a Store that returns a product by it's ID ... If the reader doesn't find the product on disk, it returns But, using the product example above, there's a key part that doesn't really make much sense:
that goes back to the original question from @digitalbuddha, "why would the fetcher return no entries?" ... Any sane network would not return an "empty" product. If the product wasn't found, it would return some sort of error code or message ("product not found"), and the Fetcher would handle that error or lack of data in some graceful way. My list scenario is the same ... if we ask the network for a list of X, and there are none, it should result in an error or lack of data that the fetcher handles. In my case (a list of posts) I think it's reasonable to throw a "No posts available for type X" Exception. |
I have the same problem: my network source returns a list of item owned by a user and that list could be of course empty, and in that case the server correctly returns an empty collection. My local db has a table containing items owned by the user as rows. Now the problem is that simply observing the table content Store is not able to understand whether it is empty because user has no items or because values weren't fetched yet. I think this could be a pretty common use case for Store. Is there a simple solution to this or is it something that Store doesn't support? |
Nothing built in. What is your expectation for an api? Do you want store response to tell you if any writes have occurred? What if you write to the dB table from outside store? Store only forwards what you tell it, do you want a isDiskEmpty callback that we can call? Let me know what a perspective api looks like. I'm not sure I understand what the expectation is |
I think we need Store to let the collector know that both the source of truth (the local data storage, in this case) and the fetcher have returned an empty data set. But, without understanding the full internals of Store, it seems that maybe this is simply a bug that ought to be fixed and not so much that there needs to be a new empty state returned from Store to the collector. |
So, I've found that this is actually causing serious issues for our app in some occasions and I can't wait for an official fix.
In my case, the stream does not cancel so any new updates to the source of truth will still notify the collector, assuming you're properly handling the exception at the collection side. |
Hi folks, out on paternity and catching up. I think store should have a configuration for the list handling @TylerMcCraw suggested... Treat empty set same as null or error. Would someone want to try to contribute, I would expect a configuration in store builder that then causes a wrapped fetcher/source of truth to be used. |
Hi friends, I'm back from paternity and am going to add a new fetcher type that throws on empty. Let me know if anyone has suggestions on how it should work |
Welcome back, Mike! Would it make more sense to create a different type of Fetcher? Or do you think this is something that should be passed in as some sort of configuration when instantiating the Fetcher that we have now? |
I think we should have a new |
I can try to find some time to contribute something, but if someone else has more free time than me, please don't hesitate :) One thing I want to clarify is that I don't know yet that throwing an exception is the right solution. |
Got it yeah not ideal, its almost like we want a custom Store.Data.EmptyableData wrapper type for store responses. Now you see why this hasn't been taken on yet ;-) |
This documentation conflating lists and single elements is a bit confusing. Are there plans to tackle this issue with Store5? |
Hey @Kernald - Thanks for checking in. Docs and sample apps are WIP. The larger issue is on our backlog. Will do our best to tackle it soon. PRs are very much welcomed! |
This issue has been linked to a Canny post: https://github.com/MobileNativeFoundation/Store/issues/255 🎉 |
Hey all - First stab at making it easier to work with lists: #548. Please consider taking a look and leaving feedback |
Hey all - #548 just merged. Please share any feedback 🙏 |
I'm trying to setup a pretty basic Store that works with a List that is backed by a (Room) SoT, but I am running into a few problems, outlined below. The crux of the problem is that a call to the store's
get()
method never returns in some cases when the list is empty.My setup is fairly straight forward:
This setup works OK, unless/until there are no posts to work with. I've specifically run into 2 problems:
get()
with this setup and there is no data in the SoT, the fetcher will not be called.From reading the source code, it appears that the Fetcher only gets called if the reader returns
null
. But when working with a list, the reader will return an empty list, and notnull
. Because of that, the fetcher never gets called.We can actually fix this problem fairly easily by converting an empty list to
null
in the reader:Now, an empty list is treated as
null
, and thus the fetcher gets called.get()
and there are no entries in the SoT, and the Fetcher also returns no entries, the suspendedget()
method will never finish/complete.That is because once the fetcher finishes up, there are no new entries to put into the database. The
get()
is ultimately (via astream
) observing the Flow from the reader, and that flow will not emit anything (since there were no writes). Because of that, there is never any value emitted on theFlow
(due to the filters setup in theget()
) method. And since there is no value ever emitted, the suspended get() method never finishes/completes.Is there a way to setup a Store that works with a List and ensure that the
get()
method will always return?The text was updated successfully, but these errors were encountered: