معرفی
ممکن است شرایطی وجود داشته باشد که لازم باشد چندین پیاده سازی از یک وابستگی را برای برنامه های خود ثبت کنید. به عنوان مثال، اگر میخواهید بدون تغییر کد موجود، ویژگیهایی را به برنامه خود اضافه کنید، یک راه خوب برای انجام آن اضافه کردن یک پیادهسازی جدید برای آن است. برنامه شما باید به روشی خاص نوشته شود تا این کار به درستی انجام شود. ما یک مثال واقعا ساده داریم که این را در این مقاله نشان می دهد. اما زمانی که در نهایت نیاز به انجام این کار دارید، ASP.Net Core داخلی قابلیتهای Dependency Injection ارائهدهندهها را برای دستیابی به این امر فراهم میکند. در این مقاله با یک مثال نحوه انجام این کار را بررسی خواهیم کرد.
ثبت اجرای چندگانه یک وابستگی
به عنوان مثال، بیایید یک وب سایت تجارت الکترونیک آنلاین را در نظر بگیریم. این سایت در مواقع خاص و در صورت رعایت شرایط خاص به مشتریان تخفیف می دهد. من یک رابط به نام IDiscount دارم که در آن تخفیف و منطق محاسبه آن را تعریف می کند. برای هر نوع تخفیفی که می خواهید در برنامه تجارت الکترونیکی خود ارائه دهید، می توانید یک پیاده سازی از رابط IDiscount داشته باشید. سپس من یک رابط به نام IDiscountProcessor دارم که در آن پیاده سازی این رابط، فراخوانی تمام پیاده سازی های IDiscount را برای محاسبه تخفیف نهایی برای یک سفارش داده شده انجام می دهد.
شما چند راه برای ثبت چندین پیاده سازی یک وابستگی در ASP.Net Core دارید. یک راه این است که فقط از روش های افزودنی ارائه شده در IServiceCollection استفاده کنید تا پیاده سازی های خود را با طول عمر مورد نظر ثبت کنید.
- services.AddScoped<IDiscountProcessor, OrderDiscountProcessor>();
- services.AddScoped<IDiscount, SeasonalDiscount>();
- services.AddScoped<IDiscount, LargeOrderDiscount>();
- services.AddScoped<IDiscount, ThreeOrModeDiscount>();
در اینجا، من پیاده سازی OrderDiscountProcessor IDiscountProcessor و 3 پیاده سازی رابط IDiscount را ثبت کرده ام.
هنگامی که ما در نهایت تمام پیاده سازی های رابط IDiscount را حل کنیم، این کار به خوبی انجام می شود و می توانیم تخفیف کل را محاسبه کنیم. اما مشکل زمانی پیش می آید که چندین ثبت از یک پیاده سازی داشته باشید. به عنوان مثال، فرض کنید یکی از توسعه دهندگان به طور تصادفی اجرای SeasonalDiscount را دو بار ثبت کرده است. اتفاقی که می افتد این است که تخفیف فصلی دو بار برای همه سفارش ها اعمال می شود و هزینه سازمان را در بر می گیرد.
یک راه بهتر برای ثبت چند پیاده سازی استفاده از روش پسوند TryAddEnumerable است که در فضای نام Microsoft.Extensions.DependencyInjection.Extensions ارائه شده است. این هیچ پیاده سازی تکراری را ثبت نمی کند و ثبت چند پیاده سازی را ایمن می کند. ثبت نام در جایی که باید از ServiceDescriptors برای ثبت وابستگی استفاده کنید کمی متفاوت است. پیاده سازی اصلاح شده به این صورت است.
- services.AddScoped<IDiscountProcessor, OrderDiscountProcessor>();
- services.TryAddEnumerable(new[]
- {
- ServiceDescriptor.Scoped<IDiscount, SeasonalDiscount>(),
- ServiceDescriptor.Scoped<IDiscount, LargeOrderDiscount>(),
- ServiceDescriptor.Scoped<IDiscount, ThreeOrModeDiscount>()
- });
تزریق و استفاده از چندین پیاده سازی یک وابستگی
هنگامی که پیاده سازی های شما در ظرف تزریق وابستگی ثبت شد، آماده استفاده هستند. برای تزریق همه پیاده سازی های ثبت شده، باید از IEnumerable<> از نوع پیاده سازی در سازنده خود استفاده کنید. بنابراین، سازنده شما چیزی شبیه به این خواهد بود. این پیاده سازی OrderDiscountProcessor ما است.
- public class OrderDiscountProcessor : IDiscountProcessor
- {
- private readonly IEnumerable<IDiscount> _discounts;
- public OrderDiscountProcessor(IEnumerable<IDiscount> discounts)
- {
- _discounts = discounts;
- }
- // ...
- }
در اینجا من IEnumerable<IDiscount> را تزریق می کنم که در آن تمام پیاده سازی های ثبت شده را به کلاس من تزریق می کند. سپس در روش ProcessDiscount () من می توانم از پیاده سازی هایی مانند این استفاده کنم.
- public (double, List<string>) ProcessDiscount(OrderViewModel order)
- {
- var discountDiscroptoons = new List<string>();
- var totalDiscount = 0.0;
- foreach (var discount in _discounts)
- {
- var addedDiscount = discount.CalculateDiscount(order);
- if (addedDiscount > 0)
- {
- discountDiscroptoons.Add(discount.Description);
- }
- totalDiscount += addedDiscount;
- }
- return (totalDiscount, discountDiscroptoons);
- }
اکنون می توانم تمام پیاده سازی های رابط IDiscount را تکرار کنم و متد CalculateDiscount() آن را برای محاسبه تخفیف برای سفارش داده شده فراخوانی کنم.
توجه داشته باشید که شما فقط می توانید از IEnumerable<> برای تزریق چندین پیاده سازی خود استفاده کنید. هر نوع دیگری مانند IList<>، ICollection<> در این مورد کار نخواهد کرد.
خلاصه
در این مقاله، به روند ثبت چند پیادهسازی یک وابستگی در ASP.NET Core و نحوه استفاده از این وابستگیها در کلاسهای خود با تزریق آنها پرداختیم. نمونه برنامه ساده ای که برای نشان دادن این کاربرد استفاده می شود با این مقاله برای دانلود در دسترس است یا می توانید کد منبع را در GitHub در مخزن زیر بیابید.