Hi Experts,
I am working on a project Where I have multiple reposetories to fetch data from differnt tables. All my repositories are independent, they create new dataContext, Add row to table and apply submit changes command. Now if in my service, there is a situation where I have to insert data into multiple tables, but it should happen in one transaction. I can achieve that using TrnasctionScope stuff, but thats needs same dataContext. As I am using StrucutreMap to create my objects, I cant get same data context, so my transaction fails.
Here is how my objects are.
interface IConnection
{
MyDataContext GetContext();
}
public class Connection : IConnection
{
public MyDataContext GetContext()
{
return new MyDataContext();
}
}
interface IRepositryA
{
int SaveDataA(objectA a);
}
public class RepositoryA : IRepositryA
{
public int SaveDataA(objectA a)
{
var context = objectFactory.GetInstance<IConnection>().GetContext();
context.TableA.InsertOnSubmit(a);
context.SubmitChanges();
return a.ID;
}
}
interface IRepositryB
{
int SaveDataA(objectB b);
}
public class RepositoryA : IRepositryB
{
public int SaveDataB(objectB b)
{
var context = objectFactory.GetInstance<IConnection>().GetContext();
context.TableB.InsertOnSubmit(b);
context.SubmitChanges();
return b.ID;
}
}
Now in my Service layer I have call them as
public MyServiceClass ()
{
public SaveAll(ObjectA a, ObjectB b)
{
using (TransactionScope trn);
{
ObjectFactory.GetInstance<IRepositryA>().SaveDataA(a);
b.FkeyID = a.ID;
ObjectFactory.GetInstance<IRepositryB>().SaveDataB(b);
trn.complete();
}
}
}
How will I pass same data context to two differnt repositories. I option, I thought was creating one overloaded method in each repository which Accepts IDataContext parameter as given below.
interface IRepositryA
{
int SaveDataA(objectA a);
int SaveDataA(IConnection connection, objectA a);
}
public class RepositoryA : IRepositryA
{
public int SaveDataA(objectA a)
{
var connection = objectFactory.GetInstance<IConnection>();
return SaveData(connection, a);
}
public int SaveDataA(IConnection connection, objectA a)
{
var context = connection.GetContext();
context.TableA.InsertOnSubmit(a);
context.SubmitChanges();
return a.ID;
}
}
interface IRepositryB
{
int SaveDataA(objectB b);
int SaveDataA(IConnection connection, objectB b);
}
public class RepositoryA : IRepositryB
{
public int SaveDataB(objectB b)
{
var connection = objectFactory.GetInstance<IConnection>();
return SaveData(connection, b);
}
public int SaveDataA(IConnection connection, objectB b)
{
var context = connection.GetContext();
context.TableB.InsertOnSubmit(b);
context.SubmitChanges();
return b.ID;
}
}
and in my service layer, I would implement it as
public MyServiceClass ()
{
public SaveAll(ObjectA a, ObjectB b)
{
IConnection connection= ObjectFactory.GetInstance<IConnection>();
using (TransactionScope trn);
{
ObjectFactory.GetInstance<IRepositryA>().SaveDataA(connection,a);
b.FkeyID = a.ID;
ObjectFactory.GetInstance<IRepositryB>().SaveDataB(connection,b);
trn.complete();
}
}
}
Second thought I have is, if somehow I can configure DataContext to return same connection when I call GetContext method. so all repositories will use same connection. But I feel that will keep the connection alive all the time. I want this connection to available during the time of this SaveAll method only.
Your help will be appritiated. Thanks in advance.
Cheers Parminder