Question

Disons que j'ai un modèle de domaine avec une classe appelée Blog qui a une propriété appelée BlogEntries (qui contient des objets de type BlogEntry). Si j'ai un modèle de base de données avec deux tables " Blog " et "BlogEntry", il n’est pas impossible que je possède 1000 entrées de blog pour un blog. Si je devais afficher le blog sur un site Web, je ne voudrais afficher que 20 entrées de blog à la fois, de sorte que je devrais utiliser une sorte de pagination. Je ne veux évidemment pas que 1000 enregistrements soient extraits de la base de données tout le temps.

Comment pourrais-je m'y prendre? La propriété BlogEntries doit-elle même être dans l'objet de domaine Blog, ou peut-être dans le référentiel? J'aimerais toujours avoir la possibilité d'ajouter des entrées de blog et d'obtenir un résultat paginé des existantes. À quoi ressemblerait la cartographie NHibernate?

L’objet Blog / BlogEntry n’est qu’un exemple. Il pourrait tout aussi bien s’agir d’un exemple Client / Commande ou de tout autre scénario maître / détail.

Veuillez m'éclairer!

Était-ce utile?

La solution

Je ferais de BlogEntry sa propre racine d'agrégat, avec son propre référentiel. Vous obtiendrez des instances de BlogEntry pour un Blog particulier en interrogeant le référentiel BlogEntry pour tous les BlogEntry ayant un BlogID donné. Je ne peux pas fournir de détails supplémentaires sur le référentiel car il existe plusieurs stratégies différentes pour implémenter des référentiels (un référentiel générique ou plusieurs, des méthodes de recherche distinctes par rapport à une méthode prenant un objet de spécification complexe, etc.). La méthode de recherche du référentiel doit prendre en charge la pagination.

public class Blog
{
    public int ID {get;set;}
    // other stuff
}

public class BlogEntry
{
    public int ID {get;set;}
    public int BlogID {get;set;}
}

public class BlogEntryRepository
{
    public IEnumerable<BlogEntry> FindByBlogID(
        int blogID, int pageIndex, int pageSize) 
    {
        // implementation
    }
}

Vous pouvez également (avec BlogEntry modélisé comme une racine d'agrégat), ajouter une collection de BlogEntryID à votre classe Blog. Ce serait mieux que d'avoir les instances de BlogEntry elles-mêmes dans la classe Blog car vous auriez beaucoup moins de données à charger lorsque vous souhaitez obtenir une instance de Blog. Avec ces identifiants, vous pouvez en sélectionner un sous-ensemble et les transmettre à une méthode de référentiel BlogEntry qui accepte une collection d'identifiants. En d'autres termes, il y aurait un peu plus de logique dans votre domaine pour prendre en charge la pagination et un getter plus générique dans le référentiel.

public class Blog
{
    public int ID {get;set;}
    public IEnumerable<int> BlogEntryIDs {get;set;}
    // other stuff
}

public class BlogEntry
{
    public int ID {get;set;}
    public int BlogID {get;set;}
}

public class BlogEntryRepository
{
    public IEnumerable<BlogEntry> Get(IEnumerable<int> blogEntryIDs) 
    {
        // implementation
    }
}

L'utilisation de cette approche serait la suivante

// get the second page
var entries = 
  blogEntryRepo.Get(blog.BlogEntryIDs).Skip(1 * PAGE_SIZE).Take(PAGE_SIZE);

Dans la base de données, vous renverriez plusieurs lignes, une pour chaque entrée de blog. (Je préfère également renvoyer plusieurs ensembles de résultats pour obtenir toutes les lignes de toutes les tables associées dans un aller-retour de base de données. J'utilise également la fonction ROW_VERSION de SQL 2005 pour activer la pagination de la base de données.)

Je préfère généralement la deuxième méthode, à moins que l'utilisation typique ne montre des quantités prohibitives d'instances (par exemple plus de quelques milliers) BlogEntry associées à un blog. Un trop grand nombre d’intérêts me méfierait des performances et de la mémoire.

Autres conseils

Vous devez accéder au blog dans son propre référentiel pour obtenir une liste paginée.

Edit: Pourquoi un vote négatif? Est-ce faux?

Pour la collecte des entrées de blog, vous pouvez utiliser BatchSize. attribut. Cela vous permettra de ne pas sélectionner toute la collection de la base de données, mais uniquement les valeurs requises.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top