Databinding memory leaking - data-binding

Is there possibility below this method causes memory leak in anyway.
android:onClick="#{(v) -> viewModel.showList(v)}
My understanding is that, view reference is passed to view model, view model then uses reference and set its content to the view. On the fragment destroy, associated viewBinder is also destroy, the whole screen is releases from the memory. Are there anyway passed view reference going to be hold in the View Model once fragment is destroyed? I don't think so.
Do you recommend to use this notation? Can you share your experience if this is possibility of memory leak?

It can be memory leak in given scenario:
Let's say you click on view and this method viewModel.showList(v) get invoked along with view reference passed to it.
Now imagine that you've global variable globalViewRef in ViewModel that stores reference to this view, for example:
class MyViewModel: ViewModel(){
lateinit var globalViewRef: View
fun showList(v: View){
globalViewRef = v // Storing view reference globally for future methods/purpose etc.
}
}
And your ViewModel is shared across fragments with activity context, in such scenario if configuration change happens your viewModel leaks global view object due to change of context.
So, things to take in mind:
Never store view/context globally in ViewModel class (Use it locally inside method only if necessary).
If there's something you need hardly to store globally then override onCleared() & clean up reference there as it is the last call on ViewModel when it's going to destroy state (Consider this when ViewModel is not being shared across activity context).
If you've both things covered then there's no memory leak in your case that I can find of.

Related

Saving an entire one-to-many structure of transient objects in one query

In Short
I seem to have landed on a MAJOR anti-pattern of saving objects WAY too many times. I've read through the limited Objectify docs and can't seem to find the right pattern to use.
Details
I have multiple objects I want to store. They are all transient (they don't exist in the database yet) and they have a one-to-many relationship. I don't want to sit and call ofy().save() on every last object in my hierarchy.
In the following example, a Player has a List of Cards.
My Model:
#Entity
public class Player {
#Id private Long id = null;//will be generated
private List<Ref<Card>> cards = new ArrayList<Ref<Card>>();
//getters and setters here
}
public class Card{
#Id private Long id = null;//will be generated
//lots of other fields and getters and setters here
}
My Operation:
I need to create a new player and new card, with the player having a reference to the card in his List "cards."
IDEAL SOLUTION:
I would like to just create the player and card java objects, set their relationships, and pass them to Objectify to be saved. Like this:
Player player = new Player();
Card card = new Card();
player.setPlayer(Ref.create(card));
ofy.save().entity(player).now();
That will fail. The 3rd line attempts to create a new Ref for Card, which cannot be done because Card doesn't have an Id yet, which will be assigned to it once it's already persisted. It seems I must never associate an object with another until one has already been saved.
Current Crappy Solution
So, my solution must be to save the Card first, and then relate it to the Player, then save the player.
Player player = new Player();
Card card = new Card();
ofy().save().entity(card).now();
player.setPlayer(Ref.create(card));
ofy().save().entity(card).now();
This is insane. It seems reasonable at first, but my app is dealing with many more relationships than just this, and with this pattern my algorithm will be a spiderweb of checking for transient objects inside collections before saving the entity I'm actually concerned with.
There MUST be some way to tell Objectify to just SAVE all child/related entities along with the entity I've requested, and furthermore generate the Ids necessary instead of throwing an Exception at me.
Furthermore, I'll also need this sort of "recursive save" solution even when none of my objects are transient (ie they all have IDs already). I can't waste my time iterating through collections and then all the collections WITHIN those collections and saving them all. I'm going to need some way of telling Objectify to just SAVE THIS WHOLE HEIRARCHY OF OBJECTS I just passed you.
I've been reading around this #Load annotation and I feel like maybe there's something in there I'm missing... I don't know. Need help. Documentation is slim.
UPDATED SOLUTION
For posterity -
Using the allocateId() method decouples the entire ID generation constraint away from the database and you get a VERY clean pattern, particularly if you do as I did:
All database #Entity classes get a private constructor and a static public factory for creating transient objects. This static factory method ( createTransient() ) will always allocate a new ID. So then, all client code can use this method for acquiring new transient objects, or the obvious objectify load for acquiring existing persisted instances. Simple. Done. Lovely.
I recommend two things:
Allocate ids manually when you construct your objects using ObjectifyFactory.allocateId(). Do not use the "save with null autogenerates" feature. As you've noticed, it's a PITA to deal with entity objects that have null ids, so don't allow them to exist.
Use deferred saves. ofy().defer().save().entity(blah); You can save almost any number of things this way and they'll only get saved once on commit (or closing of the objectify session). Deferring save on the same entity multiple times produces only a single save.
This pattern of leaving ids null and filling it in on save is a holdover from the JPA days. It didn't work very well with JPA either; there were plenty of frustrating edge cases dealing with entities missing ids (especially when you wanted to put the in maps or sets). The best solution is to simply guarantee that no entity is ever missing an id in the first place.
Note that you'll want to allocate the id in a custom constructor, not the no-args constructor that Objectify uses to build your entity on load. Allocating an id is cheap but still a call to the GAE service layer and you don't want to do this on every load.

Asp.net: Can a delegate ("Action") be serialized into control state?

I am implementing a user control that has a method that takes an Action delegate as a parm.
Attempting to store the delegate in Control State yields a serialization error. Is it even possible to serialize a delegate into Control State?
BP
Not easily - and it could open the door for potential problems.
It is theoretically possible to use reflection to determine which method of an object the delegate is invoking, and write a custom serialization process for it. Upon deserialization you would once again need to write logic to convert the information into a delegate reference.
The problem is that in the general case, discovering the object at runtime that you need to re-generate the delegate for is not always possible. If the delegate refers to a lambda or anonymous method that complicates things even more because their may be closures involved.
You are probably better off either:
Not preserving the Action delegate between requests and having the ASP.NET code re-attach the delegate on postback. This is the least risky option IMHO.
Storing the delegate reference in session state and reattach it to the deserialized object on postback. This option is risky for two reasons:
a) holding on to object references indefinitely in memory if the end user never posts back, or you forget to clear the object from server state.
b) if the delegate references page elements (controls, etc) you may run
into subtle bugs because the delegate will operate against the objects from the previous request, and not the new request.
In this post the author serializes an Action object to be executed later in time.
You can extend at your own action serializing to a string instead to a file.
Very interesting:
http://mikehadlow.blogspot.com/2011/04/serializing-continuations.html

Does Prism/Unity have a "service preloader"?

I've got a number of modules in a Prism application which load data that takes 3-8 seconds to get from a service.
I would like to be able to say in my bootstrapper something like this:
PSEUDO-CODE:
Customers allCustomers = Preloader(Models.GetAllCustomers);
And this would run in a background thread and when the user actually needs the variable "allCustomers" it would be fully loaded.
Is there an automatic service in Prism/Unity which does this type of preloading?
No, there is not.
However...
What you can consider is adding your ViewModel with a ContainerControlledLifetime to the container in your ConfigureContainer method that the views can use. You'd kickoff your threaded request in the constructor of your ViewModel and allow Views to pull this ViewModel out of the Container.
Even if they grab the ViewModel out of the container before the GetAllCustomers method is done firing, they will be notified correctly if the property you store the customers in implements INotifyPropertyChanged correctly.
If it was more appropriate, you could also do this from the Modules (in the Initialize method), rather than in the bootstrapper (for instance, if your Module was what actually knew about your Customer's Model).

Handling client-side domain object state in a presentation model

I'm currently building the client side of a Flex/PHP project using the Presentation Model pattern.
What I'm trying to achieve:
I currently have a view displaying non-editable information about a domain object called Node. Depending on if the Node is editable and the user has the right privileges, an additional view becomes available where it's possible to make changes to this object. Any changes made are only committed to the server once the user decides to "Save Changes". If changes are made to a NodeA and the user navigates away to a different NodeB without saving them, NodeA is reverted to its original state.
Design:
I have a PM for the info view holding a reference to the current Node. The PM for the edit view is extended from this info PM, adding methods to make changes to the wrapped Node object. Both PMs has the same Node reference injected into them and all fields in the info/edit views are bound to the Node via their PMs.
The problem:
When the user makes changes to NodeA but doesn't commit them, I can't seem to think of an elegant solution to revert back to the original state. Basically, what I've thought of so far is to hold separate value copies on the edit PM, either clone-creating a new Node reference or through an identical set of Node properties. Of these two the former seems like the better idea because the Node already houses domain logic, but I wonder whether creating clones of unique domain objects is a bad practice, even if it's used in a limited scope.
I handle similar cases by storing the original data in an XML property of the Value Object ("VO"), and reset all of the other property values when the VO is needed.
So, when it is first needed to be viewed, I go get the XML:
<Node>
<prop1>value</prop1>
<prop2>value</prop2>
<prop3>value</prop3>
<prop4>value</prop4>
</Node>
When I retrieve the XML, in my result handler, the first thing I do is create an instance of my VO, and set the XML property, and then call a public function in a separate class to set the VO's properties:
private function getNodeResultHandler(event:ResultEvent):void
{
var myNode:Node = new Node();
myNode.xmlData = new XML(event.result);
nodeUtils.setNodeProperties(myNode);
}
public class nodeUtils
{
public function setNodeProperties(node:Node):void
{
var nodeXmlData:XML = node.xmlData;
myNode.prop1 = nodeXmlData.prop1;
myNode.prop2 = nodeXmlData.prop2;
myNode.prop3 = nodeXmlData.prop3;
myNode.prop4 = nodeXmlData.prop4;
}
}
Then, any time you switch your view to edit mode, you call that same function to reset the properties to the values stored in the XML.
The only other thing you need to do is reset that XML any time the user commits changes to the VO. I usually handle this by passing back the VO's data in the same format on a Save and Get, and then saving the XML just as above.
I usually do this in a Cairngorm MVC application, so I have event/command chains to handle all of this, but you can put this functionality in any number of classes, or in the VO class itself, whichever is easiest for you to maintain.
Each view should have it's own instance of your Presentation Model class. Just maintain it in memory if the user has not saved it when moving to another view. Cloning accomplishes basically the same thing through a more convoluted process.

Entity Framework: What negatives can I bump into by not disposing of my object context?

EDIT: Duplicate of Should Entity Framework Context be Put into Using Statement?
I've been tossing around this idea for some time wondering what bad could happen by not properly disposing my object context and allowing it to die with the GC. Normally, I would shun this, but there is a valid reason to do it.
We are using partial classes. In those partial classes we expose properties that access FK objects. For example, let's say I have a Customer class with a CustomerType FK object. In the class, I would expose a CustomerTypeName property that does this:
public string CustomerTypeName {
get {
if (CustomerType == null) {
CustomerTypeReference.Load()
}
return CustomerType.CustomerTypeName;
}
}
This works out very handy if the original query did not do a .Include("CustomerType").
However, if I dispose the context, the above property no longer works. So... I guess this leads to a couple of questions:
1) If I never explicitly dispose of the context, what negatives will I see, if any?
2) Is there any other way to accomplish lazy loading in the above scenario and still dispose of the context?
In my answer to 'LINQ to SQL - where does your DataContext live?' we have the page as owner of the DataContext for the life of the page, and it is the page that properly disposes of the DataContext when the page is itself disposed of.
As #Chu points out it's a little dirty, but if you're going to use what is arguably a data transfer object directly in your UI, then your UI should control the lifetime of the DataContext.
Well ObjectContext's that are left around indefinitely are fine, so long as you don't keep loading / adding lots of new objects.
Every object that is loaded or added will always be tracked by the ObjectContext until it is disposed, so if you never dispose, and you keep tracking more objects it will just get bigger and bigger.
One option you could look at doing is using some utility method to either access some well known context or create a temporary context.
The key to this is using the EntityReference.EntityKey and making sure both entities are detached.
i.e.
this.CustomerType = Utility.GetDetachedObjectByKey<Customer>(
this.CustomerTypeReference.EntityKey);
The basic implementation of GetDetachedObjectByKey is something like this:
public static T GetDetachedObjectByKey<T>(EntityKey key)
where T: EntityObject
{
using (MyContext ctx = new MyContext())
{
T t = ctx.GetObjectByKey(key) as T;
ctx.Detach(t);
return t;
}
}
This will only work if the original object target is detached too. You could experiment with where the Context used by this method comes from.
Hope this helps
Alex
Why not keep the context around for the length of your screen?

Resources