views:

283

answers:

2

For our senior design project my group is making a Silverlight application that utilizes graph theory concepts and stores the data in a database on the back end. We have a situation where we add a link between two nodes in the graph and upon doing so we run analysis to re-categorize our clusters of nodes. The problem is that this re-categorization is quite complex and involves multiple queries and updates to the database so if multiple instances of it run at once it quickly garbles data and breaks (by trying to re-insert already used primary keys). Essentially it's not thread safe, and we're trying to make it safe, and that's where we're failing and need help :).

The create link function looks like this:

private Semaphore dblock = new Semaphore(1, 1);

// This function is on our service reference and gets called
// by the client code.
public int addNeed(int nodeOne, int nodeTwo)
{
    dblock.WaitOne();
    submitNewNeed(createNewNeed(nodeOne, nodeTwo));
    verifyClusters(nodeOne, nodeTwo);
    dblock.Release();
    return 0;
}

private void verifyClusters(int nodeOne, int nodeTwo)
{
    // Run analysis of nodeOne and nodeTwo in graph
}

All copies of addNeed should wait for the first one that comes in to finish before another can execute. But instead they all seem to be running and conflicting with each other in the verifyClusters method. One solution would be to force our front end calls to be made synchronously. And in fact, when we do that everything works fine, so the code logic isn't broken. But when it's launched our application will be deployed within a business setting and used by internal IT staff (or at least that's the plan) so we'll have the same problem. We can't force all clients to submit data at different times, so we really need to get it synchronized on the back end. Thanks for any help you can give, I'd be glad to supply any additional information that you could need!

A: 

I wrote a series to specifically address this situation - let me know if this works for you (sequential asynchronous workflows):

Part 2 (has a link back to the part1): http://csharperimage.jeremylikness.com/2010/03/sequential-asynchronous-workflows-part.html

Jeremy

Jeremy Likness
Hey, thanks for the link, but I think you're articles are attacking the problem from the front end where we really need to solve this on the back end. We can set up our add_data method to make the async calls sequentially, but that only solves that part of the problem. We really need the back end to handle all the asyc calls intelligently so that multiple users acting at the same time won't cause data integrity loss. Which is something we can't achieve through client side code. That's why we tried to use semaphores and we're really hoping there's a simple solution there. Thanks for your reply!
Eric Lifka
A: 

Wrap your database updates in a transaction. Escalate to a table lock if necessary

Kyle Reed