57 votes

Quand dois-je disposer d'un contexte de données

Je suis actuellement à la rédaction d'une couche d'accès aux données pour une application. La couche d'accès fait un large usage des classes linq pour renvoyer les données. Actuellement, afin de refléter les données dans la base de données, j'ai ajouté des données privées contexte membre et une méthode de sauvegarde. Le code ressemble à ceci:

private DataContext myDb;
public static MyClass GetMyClassById(int id)
{
    DataContext db = new DataContext();
    MyClass result = (from item in db.MyClasss
                      where item.id == id
                      select item).Single();
    result.myDb = db;
    return result;
}

public void Save()
{
    db.SubmitChanges();
}

C'est une brute de simplification, mais il donne l'idée générale. Est-il une meilleure façon de gérer ce genre de modèle? Je devrais être de l'instanciation d'un contexte de données chaque fois que je veux visiter la db?

69voto

Jon Skeet Points 692016

Il ne fait pas trop d'importance. J'ai demandé à Matt Warren de l'LINQ to SQL de l'équipe à propos de ça il y a longtemps, et voici la réponse:

Il ya quelques raisons nous avons mis en place IDisposable:

Si la logique de l'application doit tenir sur une entité au-delà de quand la DataContext est prévu pour être utilisé ou valide, vous pouvez faire valoir ce que de contrat par l'appel de la Jeter. Différés chargeurs de cette entité sera toujours référencement le DataContext et essayez de l'utiliser si aucun code tente de naviguer dans le différés propriétés. Ces tentatives va échouer. Disposer les forces de l' DataContext de vider son cache de matérialisé entités de sorte qu'un seul entité du cache ne sera pas accidentellement garder vivante de toutes les entités matérialisé à travers cette DataContext, qui serait autre cause de ce qui semble être un fuite de mémoire.

La logique qui se ferme automatiquement le DataContext de connexion peut être trompé en laissant la connexion ouvert. Le DataContext s'appuie sur l' le code de l'application l'énumération de tous les les résultats d'une requête depuis l'obtention de la fin d'un resultset déclenche l' connexion à fermer. Si l' l'application utilise IEnumerable de l' Méthode MoveNext au lieu d'un foreach déclaration en C# ou en VB, vous pouvez quitter l'énumération prématurément. Si votre l'application rencontre des problèmes avec les connexions ne ferme pas, et vous suspect le comportement de fermeture automatique ne fonctionne pas, vous pouvez utiliser le Jeter modèle comme un travail autour de.

Mais, fondamentalement, vous n'avez pas vraiment besoin de les éliminer dans la plupart des cas - et c'est par la conception. Personnellement, je préfère le faire de toute façon, comme il est plus facile de suivre la règle de "disposer de tout ce qui implémente IDisposable" que de rappeler une charge d'exceptions - mais vous avez peu de chances de fuite d'une ressource si vous n' oubliez pas d'en disposer.

17voto

Perpetualcoder Points 7381

Traiter votre datacontext comme une ressource. Et la règle de l'utilisation des ressources dit

"l'acquisition d'une ressource comme la fin de possible, dès que son coffre-fort"

5voto

tvanfosson Points 268301

DataContext est très léger et est destiné à une unité de travail de l'application que vous utilisez. Je ne pense pas que je voudrais garder le DataContext dans mon objet, cependant. Vous regardez le référentiel de modèles si vous n'allez pas utiliser le code généré par le concepteur pour gérer votre business objects. Le modèle de référentiel va vous permettre de travailler avec vos objets détachés du contexte de données, puis de les reconnecter avant de faire les mises à jour, etc.

Personnellement, je suis capable de vivre avec les DBML code généré par le concepteur pour la plupart, avec vue partielle implémentations de la classe pour mon entreprise et la logique de validation. Je fais aussi le concepteur des données générées par le contexte abstrait et hériter d'elle pour me permettre d'intercepter des choses comme la procédure stockée et de la fonction table des méthodes qui sont directement ajoutées au contexte de données et d'appliquer une logique d'entreprise.

Un modèle que j'ai utilisé dans ASP.NET MVC est d'injecter une usine de classe qui crée de données approprié des contextes aussi nécessaire pour les unités de travail. En utilisant le réglage d'usine permet de me moquer le contexte de données raisonnablement facile par (1) à l'aide d'un wrapper autour de l'existant classe de contexte de données de sorte qu'il est mockable (simulation de l'emballage depuis DataContext est pas facilement mockable) et (2) la création de Faux/se Moquer des contextes et des usines à créer. Être capable de créer à volonté à partir d'une usine qu'il fait en sorte que je n'ai pas à garder une autour de pour de longues périodes de temps.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X