Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Entities doing too much?

I having an old puzzle, so I thought I'll share it with you, may be will get right direction. Thing is, that some of our entities in database are quite big (read have many properties), and rarely business logic uses all of entity properties, so every time I need to think what properties must be loaded for business logic to work correctly. Very hypothetical sample:

public class Product 
{
    public string Title {get;set;}
    public string Description {get;set;}

    public string RetailPrice {get;set;}
    public string SupplierId {get;set;}

    public Supplier Supplier { get;set;}

    // many other properties
}

public class ProductDiscountService
{
    public decimal Get(Product product)
    {
        // use only RetailPrice and Supplier code
        return discount;
    }
}

public class ProductDescriptionService 
{
    public string GetSearchResultHtml(Product product) 
    {
        // use only Title and Description
        return html;
    }
}

It looks like I could extract interfaces IDiscountProduct and ISearchResultProduct, mark product as implementing those interfaces, then create smaller DTOs implementing each of those interfaces, but that looks at the moment as overkill (at least I haven't seen anyone grouping properties using interfaces).

To split entity in database to smaller entities also doesn't look reasonable, as all those properties belong to product and I'm afraid I'll be forced to use many joins to select something and if I'll decide that some property belongs to another entity, that move will be quite hard to implement.

To have every property used in particular method's business logic as method parameter also looks like bad solution.

like image 935
Giedrius Avatar asked May 31 '12 07:05

Giedrius


1 Answers

Unless the properties are big (read long strings and/or binaries) I'd just load them all.

The points below are for simple properties (e.g. Title)

  1. No extra code (get this product with title only, or get with price only, blah-blah)
  2. A product instance is always complete, so you can pass it around without checking if the property is null.
  3. If you'll have to lazy-load some other properties, it'll cost you more than loading them eagerly. If you have like 20 properties - this isn't even a big object (again, if your (hypothetical) Description property is not kilobytes in size).

Now, if you have related objects (ProductSupplier) - this should be lazy-loaded, imo, unless you know this property will be used.

like image 117
Evgeni Avatar answered Sep 23 '22 21:09

Evgeni