Primo, un po 'di background: sono nuovo di ASP.NET MVC 2 e NHibernate. Sto iniziando la mia prima applicazione e voglio utilizzare NHibernate, perché provengo da applicazioni web JSP + Struts 1 + Hibernate.Quando eseguire il commit delle transazioni NHibernate nell'applicazione ASP.NET MVC 2?
Nessuno sembra parlare di questo, quindi immagino che debba essere abbastanza ovvio. Ancora mi gratto la testa perché non riesco a trovare una soluzione che compia le seguenti cose:
1) Voglio usare la strategia "sessione per richiesta". Quindi, ogni volta che un utente fa una richiesta, ottiene una sessione di Nhibernate, avvia una transazione e quando la richiesta è finita, la transazione si impegna e la sessione di NHibernate si chiude (e torna al pool se ce n'è una). Questo garantisce che le mie transazioni siano atomiche.
2) Quando si verifica un'eccezione del database (violazione PK, violazione univoca, qualsiasi cosa) Voglio catturare quell'eccezione, eseguire il rollback della transazione e fornire all'utente un messaggio esplicito: se si trattava di violazione PK, quel messaggio e il messaggio lo stesso con tutti gli errori di integrità.
Quindi, qual è il mio problema? Vengo da Java World, dove ho usato un filtro per aprire la sessione, avviare la transazione, elaborare la richiesta, quindi eseguire il commit della transazione e chiudere la sessione. Funziona, tranne quando si verifica un'eccezione DB e, quando si è nel filtro, non è possibile modificare la pagina di destinazione perché la risposta è già stata eseguita.
Così l'utente vede la pagina di successo quando in realtà la transazione è stata sottoposta a rollback. Per evitare ciò, devo scrivere molti controlli di integrità dei dati in Java per evitare tutte le eccezioni di integrità, perché non sono riuscito a gestirli correttamente. Questo è male perché sto facendo il lavoro invece di lasciarlo nel database (o forse ho sbagliato e devo sempre scrivere tutto questo codice di integrità dei dati nella mia app?).
Quindi ho trovato l'interfaccia IHttpModule che sto indovinando è praticamente lo stesso concetto di un javax.servlet.Filter (correggimi se sbaglio), quindi immagino di poter avere lo stesso problema di nuovo.
Dove devo inserire i miei commit per assicurarmi che le mie transazioni siano atomiche e quando generano eccezioni posso catturarle e cambiare la mia pagina di destinazione e dare all'utente un messaggio completo?
Finora l'unica soluzione possibile che ho trovato è quella di mantenere il mio IHttpModule per avviare e chiudere la transazione e inserire le chiamate di commit nell'ultima riga dei miei metodi di controller, in modo da poter acquisire eccezioni lì e quindi restituire una vista appropriata con il messaggio. Ora dovrei copiare quelle linee di gestione commit ed eccezione in tutti i miei metodi controller che richiedono commit. E c'è il problema della separazione delle preoccupazioni, che i miei controllori devono sapere su DB, che non mi piace affatto.
C'è un modo migliore?
Puoi mostrare un esempio nel codice? Sarebbe utile. –