2013-02-20 8 views
11

Supponendo che ci sono due interfaccia repository:Le migliori pratiche di attuazione di unità di lavoro e il modello repository utilizzando ServiceStack.ORMLite

interface IFooRepository 
{ 
    void Delete(int id); 
} 

interface IBarRepository 
{ 
    void Delete(int id); 
} 

e un'interfaccia IUnitOfWork come:

interface IUnitOfWork : IDisposable 
{ 
    void Commit(); 
    void Rollback(); 
} 

ciò che è le migliori pratiche di implementare tali interfacce utilizzando ServiceStack.ORMLite in modo che l'utente possa utilizzarli come

MyFooRepository.Delete(4); 
// if an Exception throws here, Bar won't be deleted 
MyBarRepository.Delete(7); 

O

using (var uow = CreateUnitOfWork()) 
{ 
    MyFooRepository.Delete(4); 
    MyBarRepository.Delete(7); 
    uow.Commit(); //now they are in an transaction 
} 
+0

Si consiglia di evitare l'utilizzo dell'UOW tanto è possibile Passare a una transazione aperta come quella è generalmente un pessimo progetto. (Nelle precedenti revisioni ero colpevole di questa roba anch'io) modellista –

risposta

9

Non sono sicuro della vostra esigenza di repository + UnitOfWork modelli ma penso che ci sono alcune soluzioni alternative in ServiceStack + OrmLite che mantengono il codice 'a secco' prima che sia necessario introdurre eventuali modelli (soprattutto se si' principalmente cercando il supporto Transazione/Rollback). Qualcosa di simile in basso è dove vorrei iniziare.

public class Foo //POCO for data access 
{ 
    //Add Attributes for Ormlite 
    public int Id { get; set; } 
} 

public class Bar //POCO for data access 
{ 
    //Add Attributes for Ormlite 
    public int Id { get; set; } 
} 

//your request class which is passed to your service 
public class DeleteById 
{ 
    public int Id { get; set; } 
} 

public class FooBarService : MyServiceBase //MyServiceBase has resusable method for handling transactions. 
{ 
    public object Post(DeleteById request) 
    { 
     DbExec(dbConn => 
        { 
         dbConn.DeleteById<Foo>(request.Id); 
         dbConn.DeleteById<Bar>(request.Id); 
        }); 

     return null; 
    } 
} 

public class MyServiceBase : Service 
{ 
    public IDbConnectionFactory DbFactory { get; set; } 

    protected void DbExec(Action<IDbConnection> actions) 
    { 
     using (var dbConn = DbFactory.OpenDbConnection()) 
     { 
      using (var trans = dbConn.OpenTransaction()) 
      { 
       try 
       { 
        actions(dbConn); 
        trans.Commit(); 
       } 
       catch (Exception ex) 
       { 
        trans.Rollback(); 
        throw ex; 
       } 
      } 
     } 
    } 
} 

Alcuni riferimenti ...

https://github.com/ServiceStack/ServiceStack.RedisWebServices - Il codice di cui sopra viene modificato da questo esempio

https://groups.google.com/forum/#!msg/servicestack/1pA41E33QII/R-trWwzYgjEJ - discussione su strati in ServiceStack

http://ayende.com/blog/3955/repository-is-the-new-singleton - Ayende Rahien (NHibernate collaboratore core) su modello di deposito

+1

, sembra un buon modello – GorillaApe

+0

Nel caso in cui hai bisogno di logica speciale/complessa sql dove li inseriresti? – GorillaApe

+0

Immagino che si possa fare il numero sql speciale/complesso che si desidera all'interno dell'azione/funzione inviata al metodo DbExec. Potrebbe anche scrivere una funzione autonoma e passarla (l'azione/funzione) all'interno del blocco. Inoltre, questo esempio non è probabilmente l'approccio migliore per situazioni complesse. – paaschpa

Problemi correlati