Komut işleyicileri ve DDD


11

Veri almak için bir sorgu hizmeti ve komut göndermek için bir komut hizmeti kullanan bir ASP.NET MVC uygulaması var. Benim sorum komut kısmı hakkında.

Bir istek gelirse, komut hizmeti, komutu belirtilen komut işleyicisine yönlendirecek bir komut dağıtıcı kullanır. Bu komut işleyici önce kodunu doğrular ve her şey kabul edilebilirse komutu yürütür.

Somut örnek: AddCommentToArticleCommandHandler, ArticleId, CommentText ve EmailAddress öğelerine sahip bir AddCommentToArticleCommand alır.

İlk; doğrulama yapılmalı, örneğin: - makalenin var olup olmadığını kontrol et - makalenin kapalı olup olmadığını kontrol et - yorum metninin doldurulup doldurulmadığını ve 20 ile 500 karakter arasında olup olmadığını kontrol et - e-posta adresinin doldurulup doldurulmadığını ve geçerli bir biçime sahip olup olmadığını kontrol edin.

Bu doğrulamayı nereye koyacağımı merak ediyorum?

1 / komut işleyicisinin kendisinde. Ancak, diğer komut işleyicilerinde yeniden kullanılamaz.

2 / etki alanı varlığında. Ancak bir etki alanı kuruluşu depolar veya hizmetler hakkında bilgi sahibi olmadığından, gerekli doğrulamayı yapamaz (bir makalenin var olup olmadığını kontrol edemez). Ancak öte yandan, varlık mantık içermiyorsa, DDD ilkelerine uymayan basit bir veri kabı haline gelir.

3 / komut işleyicisi doğrulayıcıları kullanır, böylece doğrulama diğer komut işleyicilerinde yeniden kullanılabilir.

4 / Diğer mekanizmalar?

Bu örnek için sorumluluk zincirini ve hangi nesnelerin (varlıklar, depolar, ...) içinde rol oynadığını arıyorum.

Komut işleyicisinden depolara kadar bunu nasıl uygulayacağınız konusunda fikirleriniz var mı?


"Ancak bir etki alanı kuruluşu depolar veya hizmetler hakkında bilgi sahibi olmadığından, gerekli doğrulama yapamaz"? Neden olmasın? Hangi DDD prensibi bunu gerektirir?
S.Lott

Bir işletmenin depolar veya başka bir şey hakkında bilmemesi gereken her yerde okudum.
L-Four

Ne okuduğunuza dair bir teklif, bağlantı veya örnek verebilir misiniz? Hangi DDD açıklamalarını okuduğunuzu bilmiyoruz.
S.Lott


Jimmy Bogard bu konu hakkında bazı görüşler paylaştı ... lostechies.com/jimmybogard/2009/02/15/validation-in-a-ddd-world
Mayo

Yanıtlar:


4

Bu durumda iki tür doğrulama ayırmanız gerektiğini düşünüyorum; etki alanı doğrulaması ve uygulama doğrulaması .

Uygulama doğrulama, 'text' komut özelliğinin 20 ile 200 karakter arasında olduğunu doğruladığınızda sahip olduğunuzdur; böylece bunu GUI ve POST sonrasında sunucuda da çalışan bir view-model-validator ile doğrularsınız. Aynı şey e-posta için de geçerlidir (btw, umarım `` 32.d + "Hello World .42" @ mindomän.local "gibi bir e-postanın RFC'ye göre geçerli olduğunu fark edersiniz).

Sonra başka bir doğrulama daha var; makalenin var olup olmadığını kontrol edin - GUI'den gönderilen ve ona yorum eklemekle ilgili bir komut varsa, makalenin neden var olmaması gerektiğini kendinize sormalısınız. GUI nihayetinde tutarlı mıydı ve veri deposundan fiziksel olarak silinebilecek toplam bir köke, makaleye sahipsiniz? Bu durumda, komut işleyicisi toplam kökü yükleyemediğinden, komutu yalnızca hata kuyruğuna taşırsınız.

Yukarıdaki durumda, zehir mesajlarını işleyen bir altyapıya sahip olacaksınız - örneğin mesajı 1-5 kez tekrar dener ve daha sonra mesajların toplanmasını manuel olarak inceleyebileceğiniz ve ilgili olanları yeniden gönderebileceğiniz bir poision kuyruğuna taşırlar. İzlemek iyi bir şey.

Şimdi tartıştık:

  • Uygulama doğrulaması

    • GUI'de javascript ile
    • Web sunucusunda MVC doğrulaması ile
  • Toplam kök + zehir kuyrukları eksik

Alan adıyla senkronize olmayan komutlar ne olacak? Belki de alan mantığınızda, bir makaleye 5 yorum yapıldıktan sonra, sadece 400 karakterin altındaki yorumlara izin verildiğini, ancak bir adamın 5. yorumu ile çok geç olduğunu ve 6. olması gerektiğini söyleyen bir kuralınız var - GUI bunu yakalamadı çünkü komutunu gönderme noktasında alan adıyla tutarlı değildi; bu durumda alan adı mantığınızın bir parçası olarak bir 'doğrulama hatası' olur ve ilgili hata olayını döndürürsünüz.

Etkinlik, bir ileti aracısına veya özel dağıtım programınıza bir ileti biçiminde olabilir. Uygulama monolitikse, web sunucusu hem başarılı bir olayı hem de belirtilen başarısızlık olayını eşzamanlı olarak dinleyebilir ve uygun görünümü / kısmi görüntüleyebilir.

Çoğu zaman birçok komut türü için hata anlamına gelen özel bir etkinliğiniz vardır ve bu olay web sunucusunun bakış açısından abone olduğunuz olaydır.

Üzerinde çalıştığımız sistemde, bir MassTransit + RabbitMQ ileti yolu + aracısı üzerinden komutlar / olaylar ile istek yanıtı yapıyoruz ve bu belirli etki alanında (kısmen bir iş akışını modelleme) adlı bir etkinliğimiz var InvalidStateTransitionError. Durum grafiğindeki bir kenar boyunca hareket etmeye çalışan çoğu komut bu olayın gerçekleşmesine neden olabilir. Bizim durumumuzda, GUI'yi nihayetinde tutarlı bir paradigmadan sonra modelleyiyoruz ve bu nedenle kullanıcıyı 'komut kabul edildi' sayfasına gönderiyoruz ve daha sonra web sunucusunun görünümlerinin etkinlik abonelikleri yoluyla pasif olarak güncellenmesine izin veriyoruz. Ayrıca, toplam köklerde etkinlik kaynağı yaptığımız (ve ayrıca sagalar için de yapacağız) belirtilmelidir.

Gördüğünüz gibi, bahsettiğiniz doğrulamaların çoğu, gerçek alan mantığı değil, uygulama tipi doğrulamalardır. Etki alanınız basitse ancak DDD yapıyorsanız basit bir etki alanı modeline sahip olmanızda sorun yoktur. Ancak alan adınızı modellemeye devam ettikçe, alan adının ilk ortaya çıktığı kadar basit olmayabileceğini göreceksiniz. Çoğu durumda, toplu kök / varlık, bir komutun neden olduğu bir yöntem çağrısını kabul edebilir ve herhangi bir doğrulama bile gerçekleştirmeden durumunun bir kısmını değiştirebilir - özellikle de komutlarınıza web sunucusunda doğrularsanız yaptığınız gibi güveniyorsanız kontrol edersiniz.

DDD ile ilgili iki sunumu Norveç Geliştirici Konferansı 2011'den ve Greg'in Öredev 2010'daki sunumunu izlemeyi tavsiye edebilirim .

Şerefe, Henke


Teşekkürler! Doğrulama ile ilgili bir şey: şu anda bu doğrulama, Yorum varlığının kendisinin Validate () yöntemini kullanan kullanıcı arayüzü (hizmete bir Doğrulama (komut) isteği göndererek) tarafından tetiklenir. Daha sonra, komut geçerliyse, istemci bir Yürütme komutu verir, bu komut tekrar doğrulamak için Validate () komutunu yürütür ve geçerliyse gerçek komut yürütülür. Dolayısıyla, temel doğrulama Yorum kuruluşu tarafından yapılır, çünkü her bağlamda doğrulama aynı olacaktır (e-posta her zaman geçerli olmalıdır, yorum metni çok uzun değil, vb.) Bu iyi bir yaklaşım mı?
L-Four

Açıkladığınız doğrulama, bana 2 aşamalı bir doğrulama protokolü ile modelleme garantisi vermiyor gibi görünüyor - elbette, bir birim testinde test ettiğiniz gibi varlık üzerindeki yöntem çağırma parametrelerini doğrulayın, ancak bunun yanı sıra; uygulama katmanı / GUI, tanımladığınız kuralları etki alanına komutlar göndermeden kolayca doğrulayabilir. İmo. İstemci kötü niyetli olmadığı sürece komutun çalışması gerekir. İstemci kötü amaçlıysa, komut başarısız olur ve okuma modeliniz asla karşılık gelen bir olay almaz ve hata kuyruğundaki sorunlu komutu inceleyebilirsiniz.
Henrik

Kullanıcı arabiriminde (ASP.NET MVC) tüm doğrulamayı yapmak için doğrulama özniteliklerini kullanıyorum. Bu doğrulama başarılı olursa, o zaman etki alanı üzerinde tekrar doğrulamak zorunda değilim, ama sadece komutu yürütmek?
L-Four

1
Evet, komutu yürütürsünüz ancak komutun hem uygulama katmanında hem de etki alanında geçersiz olmadığından emin olun.
Henrik

0

EDIT: WaybackMachine bağlantısı: http://devlicio.us/blogs/billy_mccafferty/archive/2009/02/17/a-response-to-validation-in-a-ddd-world.aspx

Pat cevabı yok.

Validasyonun nerede yaşayacağını cevaplamaya çalıştığımda akla gelen iki açık proje senaryosu var. Birincisi, görünüm ve etki alanı katmanları arasında bilgi aktarmak için bir DTO katmanının kullanılmasıdır. Örneğin, alan adı katmanınızda bir Müşteri nesnesi ve Müşteri bilgilerini eşlediğiniz başka bir katmanda ilişkili bir Müşteri DTO'su olabilir ve daha sonra müşteri bilgilerini kullanıcıya sunma görünümüne verebilirsiniz.

İkinci senaryo, etki alanı katmanındaki varlıkların, verileri kullanıcıya sunmak için doğrudan görünümle paylaşıldığı bir projedir. Örneğin, görünüme verilecek ayrı bir DTO katmanını korumak ve etki alanı nesnesini DTO'larla eşlemek yerine, görünüm doğrudan Müşteri nesnesine verilebilir. Bu nedenle, Müşterinin adını göstermek için ayrı olarak tutulan bir DTO aracılığıyla konuşmak yerine, görünüm yalnızca Müşteri nesnesinin kendisinden bilgi ister.

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.