Perche' usare una entity factory?

rated by 0 users
This post has 15 Replies | 3 Followers

Top 10 Partecipanti
Maschio
Post 268
Punteggio 4.907
petrux Posted: 03-01-2010 18.15
Ciao a tutti,

supponiamo che abbia una gerarchia di oggetti di dominio di una mia
applicazione:

interface IEntity {
object Key { get; }
}

public class Foo : IEntity
{
public Foo() { }
public object Key { get;set; }
}

perche' in diversi esempi vedo usare una EntityFactory di tipo (ad esempio):

interface IEntityFactory
{
T Create() where T : IEntity;
}

invece che usare

Foo f = new Foo();

ossina un banale, caro vecchio costruttore?

Ciao,
Giulio

--
  • | Punteggio Post: 35
Top 10 Partecipanti
Post 143
Punteggio 2.560
Ciao Giulio,

You wrote on 01/03/2010 :
> interface IEntityFactory
> {
> T Create() where T : IEntity;
> }
>
> invece che usare
>
> Foo f = new Foo();
>
> ossina un banale, caro vecchio costruttore?

ad esempio perch� hai questo:

IMyEntity e = factory.Create();

e non questo:

MyEntity e = new MyEntity();

ergo anche il dominio � accessibile solo via contratti.

..m

--
Mauro Servienti
{C67C0157-5D98-4733-A75E-93CAEE4BADC8}
Microsoft MVP - Visual C# / MCP
http://mvp.support.microsoft.com
http://blogs.ugidotnet.org/topics
whynot [ at ] topics [ dot ] it
  • | Punteggio Post: 20
Top 10 Partecipanti
Maschio
Post 268
Punteggio 4.907
Ciao Mauro,

mauroservienti wrote:
> ad esempio perch� hai questo:
>
> IMyEntity e = factory.Create();
>
> e non questo:
>
> MyEntity e = new MyEntity();
>
> ergo anche il dominio � accessibile solo via contratti.

Ok, ma questo significherebbe avere sia le interfacce che le
implementazioni... e c'è da scrivere un sacco di codice. ;-P

Ciao,
Giulio
--
  • | Punteggio Post: 20
Top 10 Partecipanti
Post 143
Punteggio 2.560
Ciao petrux,

You wrote on 04/03/2010 :
> Ok, ma questo significherebbe avere sia le interfacce che le
> implementazioni... e c'è da scrivere un sacco di codice. ;-P

esatto :-) ecco perch� non ha molto senso (se non in casi ben
particolari) usare una factory per generare le entit�.

..m

--
Mauro Servienti
{C67C0157-5D98-4733-A75E-93CAEE4BADC8}
Microsoft MVP - Visual C# / MCP
http://mvp.support.microsoft.com
http://blogs.ugidotnet.org/topics
whynot [ at ] topics [ dot ] it
  • | Punteggio Post: 5
Top 25 Partecipanti
Maschio
Post 67
Punteggio 1.440

Faccio una premessa: la mia sarà una risposta molto "DDD biased" :-) Meglio una factory (che io tipicamente implemento come metodo statico esposto dall'entità stessa), perché considero più leggibile ("Code is documentation"):

ProductionDowntime dt = ProductionDowntime.DefineDowntimeForMachine(theMachine, startingDateTime, endingDateTime, reason);

rispetto a:

ProductionDowntime dt = new ProductionDowntime(theMachine, startingDateTime, endingDateTime, reason);

in pratica, uso le factory (previa restrizione della visibilità del costruttore, che lascio sempre private o protected) e la loro firma per rendere più evidente il "senso" della costruzione che sto effettuando

.A 

Top 10 Partecipanti
Maschio
Post 243
Punteggio 3.383

Io uso factory quando le entity sono complesse, e qui quello che dice Andrea è sacrosanto. Se una entità ha più di un costruttore le factory aiutano. In un caso io ho

DownloadedPage page = new DownloadedPage (Uri, int, int)

e

DownloadedPage page = new DownloadedPage (Rui,String)

Il primo vieen usato in caso di errore e vuole l'errore http e un codice di errore interno, il secondo crea una pagina ok. Ora cosi il codice sarebbe molto più leggibile

DownloadedPage page = DownloadedPage,CreateForDownloadError (Uri, int, int)

e

DownloadedPage page = new DownloadedPage.CreateValid (Uri, int, int)

Il fatto di dovere scrivere più codice risulta banale con resharper, per cui puoi prendere una classe e fare Extract interface ed in qualsiasi momemnto puoi fare pull up e pull down nella gerarchia.

Alk.

  • | Punteggio Post: 5
Top 10 Partecipanti
Maschio
Post 268
Punteggio 4.907
Ciao andysal,

andysal wrote:
> Faccio una premessa: la mia sarà una risposta molto "DDD biased" :-)

E va be', tutti devono poter dire la loro, no? ;-)

> Meglio una factory (che io tipicamente implemento come metodo statico
> esposto dall'entità stessa), perché considero più leggibile ("Code is
> documentation"):

Ok, il fine "chiarificatorio" è assai nobile ma... non si parlava di
interfacce?
:-)

Ciao,
Giulio
--
  • | Punteggio Post: 20
Top 25 Partecipanti
Maschio
Post 67
Punteggio 1.440

No, non si parlava di interfacce :-) La tua domanda era: "perche' in diversi esempi vedo usare una EntityFactory ... invece che usare ...  un banale, caro vecchio costruttore?" ed io ti ho dato la risposta "DDD style". Tutto qui :-)

 
Top 10 Partecipanti
Maschio
Post 268
Punteggio 4.907
andysal wrote:
> No, non si parlava di interfacce :-) La tua domanda era: "perche' in
> diversi esempi vedo usare una EntityFactory ... invece che usare ... un
> banale, caro vecchio costruttore?" ed io ti ho dato la risposta "DDD
> style". Tutto qui :-)

Chapeau. ;-)
Adesso complichiamo un po' la cosa e mettiamoci di mezzo un bel modello
delle entità generate con EntityFramework... che mi dici di bello?

Ciao,
petrux
--
  • | Punteggio Post: 20
Top 25 Partecipanti
Maschio
Post 67
Punteggio 1.440

"la mettiamo" che evito come la peste le "factory" che EF implementa nelle entità perché sono un insulto alla intelligenza umana e sto provando a verificare la "sostenibilità" di uno scenario "POCO/Code Only" con EF facendo fluent mapping. In entrambi i casi (EDMX "classico" e classi POCO) implemento le mie factory che devono "garantire" che gli aggregate nascano sotto una buona stella :-)

C'è un esempio "primordiale" nel DAL "EF" di NSK, ma è largamente incompleto (leggi: la quota di modello già mappata è ridotta) causa carenza di tempo.

 

buona serata,

.A

Top 10 Partecipanti
Maschio
Post 268
Punteggio 4.907
Ciao Andrea,

andysal wrote:
> "la mettiamo" che evito come la peste le "factory" che EF implementa
> nelle entità perché sono un insulto alla intelligenza umana e sto
> provando a verificare la "sostenibilità" di uno scenario "POCO/Code
> Only" con EF facendo fluent mapping. In entrambi i casi (EDMX "classico"
> e classi POCO) implemento le mie factory che devono "garantire" che gli
> aggregate nascano sotto una buona stella :-)
>
> C'è un esempio "primordiale" nel DAL "EF" di NSK, ma è largamente
> incompleto (leggi: la quota di modello già mappata è ridotta) causa
> carenza di tempo.

Sto guardando ora e, stranamente, sto capendo senza troppi sforzi.
Consideriamo come esempio la classe "Customer". Ha la sua brava factory
ed è una classe POCO. Poi con la classe CustomerConfiguration la mappi
sulla tabella. E fin qui non ci sono troppi problemi.

Però, al solito, ho un problema di concetto (che forse potrà sembrare
stupido). Non capisco quale sia la chiave primaria dell'entità/tabella
Customer. E' l'ID? Come viene mappata?

E poi: cosa sono gli aggregate? ;-)

Ciao e grazie,
petrux

--
  • | Punteggio Post: 20
Top 25 Partecipanti
Maschio
Post 67
Punteggio 1.440

L'Id di "Customer" è la proprietà "Id", e mi sembra che nel file di mapping emerga chiaramente... O forse non ho capito la domanda :-)

Argomento "Aggregate": visto che ho ricevuto anche alcune richieste via mail in merito a questo tema, credo che scriverò un post ad hoc sul blog. In breve (e semplificando), in DDD gli Aggregate sono i grafi di oggetti che il sistema si impegna a gestire: per esempio, un grafo che abbia come root l'entità "Order" molto probabilmente avrà una dignità propria e sarà un aggregate. Sempre per esempio, molto probabilmente in un dominio "real world" un grafo che abbia come root una istanza di OrderItem non sarà un aggregate, e quindi il sistema non ne prevederà una gestione diretta.

 

.A

Top 10 Partecipanti
Maschio
Post 268
Punteggio 4.907
Ciao Andrea,

andysal wrote:
> L'Id di "Customer" è la proprietà "Id", e mi sembra che nel file di
> mapping emerga chiaramente... O forse non ho capito la domanda :-)

Volevo dire che, come mi solito, non mi piace molto l'idea che una
chiave primaria o campo identificativo sia read-write. Comunque, AFAIK,
NHibernate lo setta via reflection, giusto? EF fa lo stesso?

> Argomento "Aggregate": visto che ho ricevuto anche alcune richieste via
> mail in merito a questo tema, credo che scriverò un post ad hoc sul
> blog. In breve (e semplificando), in DDD gli Aggregate sono i grafi di
> oggetti che il sistema si impegna a gestire: per esempio, un grafo che
> abbia come root l'entità "Order" molto probabilmente avrà una dignità
> propria e sarà un aggregate. Sempre per esempio, molto probabilmente in
> un dominio "real world" un grafo che abbia come root una istanza di
> OrderItem non sarà un aggregate, e quindi il sistema non ne prevederà
> una gestione diretta.

Ok, credo di aver capito.
Sto iniziando a buttare giù il Domain Model della mia applicazione, che
prevede mooooolti aggregate... speriamo di riuscire a sopravvivere. :-)
(leggi: sbritgati a scrivere!!! :-D)

Ciao,
Giulio
  • | Punteggio Post: 20
Top 10 Partecipanti
Maschio
Post 243
Punteggio 3.383

Ti consiglio comunque la lettura del libro di Evans, che secondo me è da leggere più di una volta :)

alk.

  • | Punteggio Post: 20
Top 10 Partecipanti
Maschio
Post 268
Punteggio 4.907
alkampfer wrote:
> Ti consiglio comunque la lettura del libro di Evans, che secondo me è da
> leggere più di una volta :)

Uhm... Cadel Evans, il ciclista? ;-)
Chi sarebbe sto evans? Di cosa parla il libro?

Ciao,
Giulio
--
  • | Punteggio Post: 20
Pagina 1 di 2 (16 elementi) 1 2 Avanti > | RSS
Powered by Community Server (Commercial Edition), by Telligent Systems