7
votes

Nibernate commit des modifications de DB sans expliquer l'appel à enregistrer ou à mettre à jour

J'utilise NHibernate 2.0 dans ASP.NET. Je commence la transaction à la mendicité de la page et commettre la transaction à la fin. Pendant la page: - Je reçois un objet - Je change la propriété objet - Je valide l'objet - Si la validation est OK, j'appelle Save-Update sur cet objet - Si la validation est tort, je ne fais pas d'appel à enregistrer-mettre à jour sur cet objet - Je commet toujours la transaction à la fin de la page.

Le problème est que c'est que lorsque la validation est fausse et que je n'ai pas appelé à enregistrer-mettre à jour sur l'objet, le COMMIT TRANSACTIN COMMIT l'évolution de la DB.

Je fixe le flushmode pour ne jamais changer de Nothig.

avoir une suggestion? Ce que je me trompe?


1 commentaires

Utilisez-vous le cadre de validation de NHibernate?


3 Réponses :


17
votes

Au cours de la page: - Je reçois un objet

Si vous obtenez un objet d'une session, vous êtes une mise à jour malentendante. La mise à jour consiste à joindre une entité existante à une session. Si vous obtenez une entité d'une session, elle est déjà jointe à cette session afin que la mise à jour n'a donc pas de sens.

SaveOnUpdate vs. La mise à jour dans ce cas n'a pas d'importance - même chose.

Nibernate Tracks passe à l'objet en session. Lorsque vous commettez une transaction ou rincer une session, il va vérifier les modifications (qu'il y a), puis de commettre ceux à la base de données. Tout cela est que ce n'est pas votre travail de suivre quels objets sont changés (sale), il est Nibert.

D'autres ormes peuvent exiger que vous suiviez vous-même les modifications et appelez une sorte de mise à jour explicitement sur n'importe quel objet changé que vous souhaitez persister, mais NH ne fonctionne pas de cette façon.

Pour répondre à votre question, si la validation échoue, vous ne souhaitez pas commettre la transaction.

NH est également l'opinion à l'unité de travail. Donc, si vous faites la validation dans une partie logique différente du programme de votre logique commerciale qui valide le travail, cela entraînera probablement un frottement.


0 commentaires

5
votes

Je viens de courir dans ce même problème. La réponse d'Eyston a été très utile, expliquant que peu importe si vous appelez ou non iSession.UPDate (objet) ou SaveOnUpdate (objet), NH suit les changements et l'engagement de la transaction commettre les modifications.

Il y a un Peu de façons que vous pouvez accomplir votre validation puis pour éviter les modifications de la base de données. Faites toutes votre validation et (possible) économiser dans une transaction séparée. P>

if (!myObj.ValidateForSave())
{
    session.Evict(myObj);
}


1 commentaires

Si vous avez une validation infructueuse, vous devez rouler votre transaction, ne pas l'engager. Si vous expulsez un seul objet, les modifications que vous apportez à d'autres objets de la session seront toujours engagées et cela va à l'encontre du grain d'une transaction étant une opération atomique - elle devrait être «tout ou rien».



1
votes

La solution qui fonctionne pour moi dans ce cas est la suivante:

  1. Définissez la session FlushMode sur "COMMIS".

  2. Supprimez toutes les références à "Flush" dans le code qui gère les mises à jour en mémoire sur l'objet.

  3. Online Seulement OUVERT OUVERT 1 transaction par session lors de la «sauvegarde», puis supprimez cette session.


0 commentaires