Al momento sto lavorando a un progetto e sto utilizzando questo progetto per provare a applicare DDD. Tuttavia, ci sono parti della mia implementazione che non riesco a capirmi o non mi sento giusto. Proverò a descrivere come attualmente ho la mia configurazione dell'applicazione;
Nel mio livello di dominio, ho i miei aggregati, oggetti valore e una classe di servizio per ogni contesto limitato. Ad esempio, ho un contesto limitato 'Account' con il seguente;
Account: account aggregate root
Profilo - oggetto valore
Indirizzo Email - oggetto valore
AccountValidator - convalida lo stato di un account
ProfileValidator - convalida uno stato dei profili
AccountRepository - interfaccia che descrive i metodi disponibili sul repository
AccountService - al momento questo ha un singolo metodo createNewAccount (), accetta un numero di valori primitivi e crea l'account e lo restituisce. Prima di creare l'account, prima controlla che il nome utente selezionato non esista già. Se il nome utente esiste, genera un'eccezione. (Questa regola dovrebbe essere nel servizio dominio?)
Nel mio livello di applicazione ho;
AccountRepositoryImp: un'implementazione dell'accountRepository nella classe domain, questa è un'interfaccia Spring Data standard che implementa accountRepository.
AccountFacade - fondamentalmente, un altro servizio account che fornisce metodi come findById (), findByUsername (), createNewAccount (), sendVerificationEmail (), verifyAccount.
AccountController - controller Spring standard che gestisce tutte le azioni relative all'account
Ho un numero di domande / problemi con il mio approccio;
- Ho due classi di servizio per ogni contenuto limitato, uno per il dominio e uno per l'applicazione e, mentre capisco, la classe del servizio di dominio dovrebbe essere utilizzata solo per applicare comportamenti o regole aziendali che non possono essere eseguite sull'aggregato di per sé (cioè bisogno di accesso db), sto faticando a determinare qual è una regola di applicazione e qual è una regola aziendale. Ad esempio, non è possibile creare un account se il nome utente è già in uso, l'ho messo nel mio servizio di dominio, ma sto iniziando a chiedermi se dovrebbe appartenere al metodo createNewAccount () nel servizio dell'applicazione. Un'altra regola: "Un account può essere cancellato solo da un amministratore o l'account si mantiene", è questa applicazione o azienda?
- Mentre aggiungo sempre più metodi al mio servizio applicativo, diventerà piuttosto grande. Questo mi porta a pensare all'implementazione di CQRS e ad avere una classe / metodo per ogni comando / query. Questo rompe le cose e rende più facile la gestione, ma non posso fare a meno di sentire che questo porterà un sacco di duplicazioni ad esso. Ad esempio, nel AccountRepository posso recuperare un account tramite il suo nome utente, e se l'account non esiste restituisce null. Invece di restituire null, ho scritto un metodo getByUsername () nel servizio dell'applicazione in modo che lanci un'eccezione se l'account non esiste, piuttosto che un null. Ciò significa che posso utilizzare questo metodo con altri metodi e non è necessario duplicare l'eccezione. Mi sento come se io uso CQRS, ho ancora intenzione di mantenere il servizio dell'applicazione in modo che possa contenere metodi che vengono utilizzati da più comandi / query per ridurre i duplicati. Finirò con un altro controller di livello - > comando / query - > applicationervice - > domainservice mi sembra che sto rendendo l'applicazione più complicata di quanto non debba essere
- Se utilizzo CQRS, il comando / query o controller è responsabile della creazione di ViewModels? Sono incline a cosa il comando / query può costruirle, dato che saranno basate sul caso d'uso e possono essere riutilizzate se dovessi aggiungere endpoint REST al sistema in futuro. Se ho permesso al controller di eseguire più comandi / query e di creare ViewModel, quindi se implemento REST in un secondo momento, dovrò duplicarlo.
-
Regole - come detto sopra, sto faticando ad assegnare regole all'applicazione o al dominio. Elencherò alcune regole qui sotto e se potessi avere qualche puntatore su dove potrebbero essere, sarebbe utile allenare il mio cervello;
- Non è possibile creare un account senza un'email, nome utente, nome e cognome (l'ho inserito nel dominio)
- Non è possibile creare un account se il nome utente è in uso (l'ho messo nel dominio)
- Un utente non può commentare un progetto se non è un membro del progetto.
- Un commento non può essere lasciato su un progetto chiuso
- Solo il proprietario del progetto può modificare / gestire / amministrare il progetto
Mi scuso se questa domanda è poco strutturata e i miei pensieri sembrano un po 'casuali. Sono stato così abituato a usare un modello anemico che ho tanti pensieri nella testa che non riesco a strutturare (da qui la domanda).