2017-09-11 2 views
1

Est-ce que je veux retourner des Dtos Full-Fat; c'est-à-dire avec les informations d'entité parente de base, c'est Id et name, et les collections d'entités enfants converties en collections de dtos enfants; ou dépouiller tout et ne retourner que des identifiants pour les entités parentes? Le choix maigre apparaîtra dans beaucoup d'appels à l'adresse web pour remplir les détails manquants, mais le dto complet sera un objet assez lourd si une entité a de nombreux enfants, petits-enfants, relations etc.Objets DTO complètement gras ou maigres?

Existe-t-il une option semi-écrêtée pour arrêter la sérialisation dto à un certain niveau?

Pour ajouter un peu de contexte supplémentaire: nous emballons une API tierce destinée à un usage interne. La 3ème partie utilise l'approche "skinny" pour renvoyer ~ 18 000 entités, soit environ 18 Mo. Pour que ce soit quelque chose de plus qu'une collection d'identifiants, nous devons ajouter au moins un certain contexte. Les entités Id et Name sont assez simples à inclure mais où les champs associés peuvent avoir des relations enfants qui, en raison de la conception de base de données sous-jacente, mènent à des relations circulaires intéressantes ...

+0

Ceci n'est pas vraiment responsable dans son actuel forme. Il n'y a pas de solution miracle. La réponse est "ça dépend". Vous seul savez exactement de quoi vous avez besoin et quelles options sont viables. – CodeCaster

Répondre

3

"Approche DTO, comme vous l'avez surnommé. La performance est une fonctionnalité, et il n'y a pas de meilleure façon de réduire les performances que d'ajouter un tas de latence réseau inutile. Je dirais que, sauf si vous avez affaire à une machine à ressources limitées sévèrement, que de devenir gras, au bénéfice de la réduction du nombre d'allers-retours vers et depuis le serveur.

Vous n'avez pas donné beaucoup d'informations, mais je suppose que vous êtes soutenu par des tables DB ici? Si c'est le cas, je préfère exposer les "entités" comme de simples représentations d'enregistrements DB individuels (en omettant évidemment les champs sensibles). Et en créant une API RESTful pour exposer et naviguer.

EDIT: Pour élaborer avec un code sur ce que je veux dire par « riche en matière grasse » (note: certains détails superflus sont omis pour réduire la verbosité).

Exemple de configuration SQL:

create table dbo.User (
    Id int identity primary key, 
    Name nvarchar(50) 
); 

create table dbo.Post (
    Id int identity primary key, 
    UserId int not null foreign key references dbo.User(Id), 
    Title nvarchar(50), 
    Body nvarchar(max) 
); 

Exemple CLR Objets:

public sealed class User 
{ 
    public int Id { get; set; } 
    public string Name { get; set; } 

    public IEnumerable<Post> Posts { get; set; } 
} 

public sealed class Post 
{ 
    public int Id { get; set; } 
    public int UserId { get; set; } 
    public string Title { get; set; } 
    public string Body { get; set; } 

    public User User { get; set; } 
} 

Compte tenu de la configuration ci-dessus, un exemple sur la façon d'exposer l'objet (s) serait restfully être comme suit:

/api/users   /*users collection*/ 
/api/users/1   /*user resource*/ 
/api/users/1/posts /*user resource with posts sub-collection*/ 

/api/posts   /*posts collection*/ 
/api/posts/1?user=1|0 /*post resource with/without User*/ 
0

Le choix dépend entièrement du contexte dans lequel vous devez appliquer votre solution.

Je mélange généralement les deux. Si j'ai un type de vue «maître-détail», par exemple une boutique en ligne, et que je dois afficher des produits dans une liste où l'utilisateur ne voit que le nom et le prix du produit, je choisis une version «maigre». Ensuite, l'utilisateur peut cliquer sur le produit pour voir la page de détails, j'envoie la version «complète».

Mais s'il y a une catégorie associée à chaque produit, je n'enverrais probablement que le categoryid et peut-être le nom de la catégorie dans le produit 'detail'. Ensuite, lorsque l'utilisateur clique sur une catégorie pour voir les détails de la catégorie et peut-être d'autres produits, j'envoie le reste.

2

La réponse est "Avez-vous besoin de" Dto?

Renvoyez uniquement les données dont vous avez besoin. Par exemple, la structure client Commandes

  • Pour la méthode qui va utiliser uniquement customer.Id et customer.Name vous pouvez retourner seulement { Id: 1, Name: "One" }
  • Pour la méthode qui ont besoin de info plus client vous retournerez plus d'informations
    { Id: 1, Name: "One", Street: "Street 12", City: "City" }
  • Pour méthode qui nécessite des données plus complexes, vous allez créer des API qui retourner des données plus complexes

N'essayez pas d'être générique dès le début, développez des méthodes API concrètes dont vos applications ont besoin, alors vous pouvez voir des méthodes globales d'image et de refactorisation pour être plus génériques, jouer avec différents compromis