Asp.Net Core Validation Kurallarını FluentValidation ve Filter ile Yönetmek
Validasyon işlemleri development aşamasında elzem konulardan biridir. Asp.Net projelerinde validasyon için bir kaç farklı senaryo ile karşılaşmak mümkün. Bunlardan biri Attribute model nesnesi üzerine konularak gerekli yerde validasyon durumu kontrol edilebilir. Ancak bu senaryoda geliştirilen proje dinamik bir yapıda ise bu çözüm yeterli olmayabilir. Örneğin; model içindeki bir nesnenin bir kaç farklı kurala göre validasyon kuralından geçirilmesi gibi durumlarda attribute tek bir kurala göre doğrulama yapacağından ihtiyacı karşılayamaz.
Gelelim karmaşık senaryolarda validasyon işlemlerine. FluentValidation özelleştirilebilir senaryolar sunan bir yapı olarak karşımıza çıkmaktadır. Üstelik iyi dökümantasyonu, kullanım sıklığı ve açık kaynaklı olması gibi durumlarda göz önünde bulundurulduğunda benim için artı bir değer taşımaktadır.
Nuget ortamından projemize kurulumu yaptıktan sonra kurulum ayarlarına başlayabiliriz.
Startup.cs içerisinde ConfigureServices içerisinde bulunan services.Mvc’yi aşağıdaki gibi güncelleme yapmak yeterlidir.
Katmanlı mimari ile geliştirme yapıyorsanız Validasyon kurallarını Business katmanında yapmanızı öneririm. Tek bir proje içerisinde bütün işlerinizi yürütüyorsanız da klasörleme yapmak iş yönetimini daha da kolaylaştıracaktır. Tercih sizin. Ben katmalı mimari ile geliştirme yapmaktayım, bunun için Business katmanına ValidationRules isimli bir klasör açıyorum ve çalıştığım teknoloji ile ilgili bir isimlendirme yaparak FluentValidation isimli bir klasör daha açıyorum. Validasyon için kullanacağım sınıfları bu klasör içinde tutacağım.
Bir class’ın FluentValidation’a dönüşümü için AbstractValidator<> generic class’ından türemesi gerekmektedir. Constructor’da RuleFor yazarak istediğiniz field için validasyon kuralınızı yazabilirsiniz. Bunun dışında class içinde farklı methodlar oluşturarak özelleştirilebilir kurallar yazma olanağınız da vardır.
Şimdi gelelim tüm bunları kapsayan bir Validasyon örneğine;
Kuralımızı oluşturduğumuza göre bunu nasıl kullanacağız kısmına geçebiliriz. Burada da sizin iş ya da geliştirme senaryonuza göre değişiklik gösterbilir bir durum söz konusu. Örneğin Aspect Oriented Programming kapsamında bir custom ActionFilterAttribute oluşturup Create ya da Update metodlarınızın önünde çalıştırmanız mümkün ya da daha genel bir filter yazarak aynı işi yapmak da mümkün. AOP ile ActionFilterAttribut yazmak başka bir makalenin konusu olacak. Biz burada IAsyncActionFilter’dan türeyen bir filter yazacağız.
Filter yazımından önce hata durumunu daha iyi yönetebilmek için ErrorModel isimli bir class oluşturuyorum. İçeriğinde FieldName ve Message adında iki field eklemesi yapıyorum. FieldName validasyon kuralına uymayayan key için, Message ise gösterilecek hata mesajı için kullanılacaktır.
Birden fazla hata durumunu aynı anda göstermek için geriye dönecek responsu yönetebilmek için ErrorResponse isimli bir class daha oluşturuyorum.
Şimdi filter yazmaya başlayabiliriz. ValidationFilter isminde bir class oluşturuyorum ve IAsyncActionFilter interface implementasyonunu yapıyorum.
OnActionExecutionAsync isimli method içinde ModelState.Isvalid olmama durumunda hata döndürecek bir kodlama yapıyorum. Öncelikle ModelState üzerinden gelen hataları yakalıyorum. Yakaladığım hataları foreach ile dönüp Error yönetimi için oluşturduğum instance üzerinde ekliyorum.
Son olarak oluşturduğumuz bu filter’ı Dotnet’e tanıtmaktan başka bir işimiz kalmadı. Bunun için de Startup içinde şöyle bir yapılanma yapmak yeterlidir;
Geriye kalan dotnet run :)