Posts

Showing posts from June, 2008

Memory leaks

As a follow up to yesterday's post here is a list of problems I found... 01: The following code for some reason causes the form holding the DirtyObjectCatcher to remain referenced. if (Owner.MdiParent != null) { Owner.MdiParent.Activated += new EventHandler(MdiParent_Activated); Owner.MdiParent.MdiChildActivate += new EventHandler(MdiParent_MdiChildActivate); } The odd thing about this is that it really is the events that matter! I subscribe Shown, Disposed, Activated on the Owner (which is a form) and that doesn't cause the same behaviour. The reason is that the Owner normally gets disposed and takes out the DirtyObjectCatcher with it, however, if I have Owner.MdiParent events referencing DirtyObjectCatcher then the form will never get disposed because DirtyObjectCatcher has a strong reference to Owner. Maybe I should change it, but for now the Shown and Activated events seem to be doing the trick. 02: This one was a real pain! DirtyObjectCatcher creates its own

DirtyObjectCatcher

Oh boy, what a nightmare! After days of messing around I finally found where the memory leak is in my app, it was in DirtyObjectCatcher! The DirtyObjectCatcher used to subscribe to the DirtyListService, so that it was notified whenever an object was made dirty. I experienced this problem... 01: User creates a "Call" to a customer site. 02: User edits a purchase order. 03: Save purchase order (merges the undo block to the Call undo block and closes the form) 04: Edit the purchase order again from the Call form The PurchaseOrder is already dirty so it wont get triggered again, this used to result in no constraints being checked etc and the possibility of entering dodgy data. The solution at the time was to have a static list in DirtyObjectCatcher private List Instances; whenever a new instance was created it would be added, whenever Dispose was called it would be removed. I then hooked into the cache chain and whenever a value changed I would call a static method on Dirty

TeamCoherence - disaster!

That's it, my short evaluation of TC is over! Problem 1: I emailed support with a question weeks ago, didn't get a response. Not impressed. Problem 2: I reinstalled my O/S recently so had to restore my version control folder. When I try to check files out I now get an "Object not found" error, whatever that means? Some searching reveals it is a bug that has been fixed in the version I have, I beg to differ. Problem 3: This one was the worst! I use TC client for a customer already which is why I decided to try out the server. I connected to the customer server, checked out loads of files, upgraded my VS2005 project to VS2008 and then checked everything back in. What a disaster! TC had replaced the source in the customer files with source from my private local server! I couldn't believe it! As I looked through Assembly.cs files I could see WinForm code from the last project I worked on locally! This is obviously bad because I had exposed source code from one con

TimeBasedSyncHandler

I recently had to tweak my remote persistence server settings. I noticed that I had leaft the SyncHandler.HistoryLength at the default value of 10,000 items. This was overkill because my clients sync every 3 seconds. I thought maybe I should drop this down to about 100, that should be okay? Each client only does about one update every few minutes so I it should, right? Problem is not all of my users are people. One user is a messenger service which looks for unsent messages, sends them one at a time, marking each in turn as sent and updating the database. This gets run every five minutes so probably sends about fifty messages at the most, but what if someone decides to change it to ten minutes, or thirty? So maybe I should increase the HistoryLength to about 200? Then there is the other client, this one syncs with an external database. This could perform hundreds of updates every minute. If the messenger is set to run every thirty minutes...I'm not sure what a good Histo

Making a generic type from a Type

List<Person> p = new List<Person>(); This works fine, but what about this? Type someType = typeof(Person); List<someType> p = new List<someType>(); Nope! But you can do this... Type genericType = typeof(List<>).MakeGenericType(someType); Why would I want to? Because I am creating a tool that generates plain old .NET objects from an EcoSpace's model, and I wanted to implement multi-role association ends as public List<Building> RoleName; rather than just public Building[] RoleName;

Returning a binary respose in ASP MVC RC3

In a previous post I showed how to return a binary file from a controller action, well, this no longer works in release candidate 3 of the framework. Instead you have to create a new ActionResult descendant to do the job for you. This is how I did it.... return new BinaryResult(data, Path.GetFileName(productFileName)); and the class is implemented like so: public class BinaryResult : ActionResult { private string ClientFileName; private byte[] Data; private string VirtualFileName; public BinaryResult(string virtualFileName, string clientFileName) { if (string.IsNullOrEmpty(virtualFileName)) throw new ArgumentNullException("VirtualFileName"); if (string.IsNullOrEmpty(clientFileName)) throw new ArgumentNullException("ClientFileName"); ClientFileName = clientFileName; VirtualFileName = virtualFileName; } public BinaryResult(byte[] data, string clientFileName) { if (data == null) throw new ArgumentNullExcep