استفاده از HttpContext خارج از یک MVC Controller در .Net Core 2.1

Loading...
HttpContext

در این مقاله به بررسی استفاده از HttpContext خارج از یک MVC Controller در .Net Core 2.1 میپردازیم. هنگام کار بر روی یک برنامه‏ ی وب مبتنی بر ASP.Net Core 2.1، با سناریویی روبرو شدم که باید تعدادی داده را داخل حافظه قرار می‏دادم. با این حال که این یک مشکل نیست، چیزی که در‏می‏یابیم این است که داده برای هر HTTP Session (نشست http) باید منحصر به فرد باشد.

این را به عنوان نگهداری یک کلید که برای استفاده در بین نما‏های مختلف برای نمایش اطلاعات مربوط به آن جلسه ‏ی خاص است در نظر بگیرید.

تنها راه حل ممکن که پاسخگوی نیاز‏های من بود، نگهداری “کلید” در جلسه بود. با این حال، آخرین نقطه در کد که به کلید دسترسی دارد یک کلاس کمکی ساده است و نه یک MVC Controller و که هیچ قصدی از نمایش “کلید” به کنترل‏ کننده ‏مان نداشتیم. بنا‏بر‏این، این پرسش باقی می‏ماند: چگونه کلید را در جلسه بدون نمایش آن به کنترل‏ کننده ذخیره کنیم؟

نمونه کد جهت کار با HttpContext

در کدی که در ادامه می ‏آید، یک برنامه ‏ی MVC بسیار ساده و پایه با HomeController خود داریم. ما همچنین یک RequestHandler داریم که مراقب تمام منطق پشت ‏زمینه است تا کنترل کننده ‏مان را تمیز و سبک کند.

using HttpContextProject.Helpers;  
using HttpContextProject.Models;  
using Microsoft.AspNetCore.Mvc;  
using System.Diagnostics;  
  
namespace HttpContextProject.Controllers  
{  
    public class HomeController : Controller  
    {  
        public IActionResult Index()  
        {  
            return View();  
        }  
  
        public IActionResult About()  
        {  
            // handle the request and do something  
            var requestHandler = new RequestHandler();  
            requestHandler.HandleAboutRequest();  
  
            ViewData["Message"] = "This is our default message for About Page!";  
            return View();  
        }  
    }  
}  
  
  
namespace HttpContextProject.Helpers  
{  
    public class RequestHandler  
    {  
        internal void HandleAboutRequest()  
        {  
            // do something here  
        }  
    }  
}  

همانطور که در کد بالا دیده می‏شود، داریم به سادگی یک پیام را در ViewData تنظیم و روی نما تفسیر می‏کنیم. تا به حال اتفاق خاصی در کار نیست. حال، بیایید ببینیم چگونه می‏توانیم پیام خود را در Http Session از RequestHandler تنظیم کنیم و بعد‏تر در داخل کنترل کننده به آن دسترسی پیدا کنیم.

استفاده از HttpContext در یک کلاس کمکی

با .Net Core 2.1 نمی‏توانیم به HttpContext خارج از یک کنترل کننده دسترسی پیدا کنیم، با این حال، می‏توانیم از IHttpContextAccessor برای دسترسی به نشست فعلی خارج از یک کنترل کننده استفاده کنیم.

برای انجام این کار، لازم است Session و میان-افزار HttpContextAccessor را به متد ConfigureServices از کلاس Startup خود همانطور که در کد زیر نشان داده شده اضافه کنیم.

using HttpContextProject.Helpers;  
using Microsoft.AspNetCore.Builder;  
using Microsoft.AspNetCore.Hosting;  
using Microsoft.AspNetCore.Http;  
using Microsoft.AspNetCore.Mvc;  
using Microsoft.Extensions.Configuration;  
using Microsoft.Extensions.DependencyInjection;  
  
namespace HttpContextProject  
{  
    public class Startup  
    {  
        public IConfiguration Configuration { get; }  
        public Startup(IConfiguration configuration)  
        {  
            Configuration = configuration;  
        }         
  
        public void ConfigureServices(IServiceCollection services)  
        {  
            services.Configure<CookiePolicyOptions>(options => {  
                options.CheckConsentNeeded = context => true;  
                options.MinimumSameSitePolicy = SameSiteMode.None;  
            });  
            services.AddSession();  
            services.AddSingleton<RequestHandler>();  
            services.AddHttpContextAccessor();  
            services.AddMvc().SetCompatibilityVersion(CompatibilityVersion.Version_2_1);  
        }  
  
        public void Configure(IApplicationBuilder app, IHostingEnvironment env)  
        {  
            if (env.IsDevelopment()) {  
                app.UseDeveloperExceptionPage();  
            }  
            else {  
                app.UseExceptionHandler("/Home/Error");  
            }  
            app.UseSession();  
            app.UseMvc(routes => {  
                routes.MapRoute(  
                    name: "default",  
                    template: "{controller=Home}/{action=Index}/{id?}");  
            });  
        }  
    }  
}  

کار بعدی که باید انجام دهیم افزودن یک وابستگی از IHttpContextAccessor در RequestHandler است. این کار به ما اجازه می‏دهد تا به HttpContext در داخل request handler (گرداننده ‏ی درخواست) دسترسی پیدا کنیم. پس از اینکه پردازش مورد نیاز برای درخواست را انجام دادیم، حال می‏توانیم پیام را، با استفاده از متد Session.SetString(key, value)، در نشست تنظیم کنیم. لطفا به کد زیر مراجعه کنید.

using Microsoft.AspNetCore.Http;  
  
namespace HttpContextProject.Helpers  
{  
    public class RequestHandler  
    {  
        IHttpContextAccessor _httpContextAccessor;  
        public RequestHandler(IHttpContextAccessor httpContextAccessor)  
        {  
            _httpContextAccessor = httpContextAccessor;  
        }  
  
        internal void HandleAboutRequest()  
        {  
            // handle the request  
            var message = "The HttpContextAccessor seems to be working!!";  
            _httpContextAccessor.HttpContext.Session.SetString("message", message);  
        }  
    }  
}  

حال که RequestHandler خود را بصورت کاملا تنظیم شده داریم، زمان این است که تغییراتی در HomeController ایجاد کنیم. هم اکنون، RequestHandler “جدید” در داخل متد عمل (action) قرار دارد، که این عمل خوبی نیست.

بنا‏بر‏این، گرداننده را از کنترل‏ کننده جدا کرده و ترجیحاً آن را به عنوان یک وابستگی در سازنده تزریق خواهم کرد. کار بعدی که انجام می‏دهیم این است که پیام را در ViewData از نشست تنظیم کنیم، همانطور که در کد زیر نشان داده شده است.

using HttpContextProject.Helpers;  
using HttpContextProject.Models;  
using Microsoft.AspNetCore.Mvc;  
using System.Diagnostics;  
  
namespace HttpContextProject.Controllers  
{  
    public class HomeController : Controller  
    {  
        private readonly RequestHandler _requestHandler;  
  
        public HomeController(RequestHandler requestHandler)  
        {  
            _requestHandler = requestHandler;  
        }  
  
        public IActionResult About()  
        {  
            _requestHandler.HandleAboutRequest();  
            ViewData["Message"] = HttpContext.Session.GetStringValue("message");  
            return View();  
        }  
    }  
}  

دقت داشته باشید که من از Session.GetStringValue(key) استفاده می‏کنم که یک متد افزودنی است که برای گرفتن داده ‏ها از نشست اضافه کرده ‏ام، با این حال، خیلی به آن نیازی نیست. می‏توانید به سادگی از Session.TryGetValue(key, value) نیز استفاده کنید.

در صورتی که هنوز متوجه آن نشده ‏اید، باید به شما بگویم که نیاز است RequestHandler خود را در متد ConfigureServices از کلاس Startup ثبت کنیم تا وابستگی برای کنترل کننده‏ مان بتواند حل شود.

خلاصه

با تغییرات بالا در جایگاه، حالا می‏توانیم به HttpContext.Session در گرداننده ‏ی درخواست خود دسترسی پیدا کنیم و مشابه آن می‏تواند برای هر کلاس دیگری نیز انجام شود. با این حال، یک مورد است که در رابطه با این رویکرد دوست ندارم.

برای هر کدام از اجزا که نیاز است در آنجا به نشست دسترسی پیدا کنیم، باید یک وابستگی از IHttpContextAccessor تزریق کنیم.در حالیکه برای یک یا دو جزء مشکلی نیست، می‏تواند بسیار وحشتناک باشد اگر قرار باشد همین کار را بارها و بارها انجام دهیم.روشی برای دستیابی به همان قابلیت دسترسی بدون نیاز به تزریق هرگونه وابستگی وجود دارد.که در مقالات بعدی به این موضوع اشاره خواهیم داشت.



مطالب مرتبط
ديدگاه خود را ارسال کنيد


۲ دیدگاه رو شما می توانید ببینید
  1. ای کاش بیشتر و بهتر میگفتین به نظر کار جالبی است

محبوب ترين ويدئو هاي انلاين
دوره برنامه نویسی فروشگاه اینترنتی
  • تعداد اعضا 80k
  • قيمت دوره۱۳۰,۰۰۰ تومان
  • امتيازدهي
    1 vote, average: 5٫00 out of 51 vote, average: 5٫00 out of 51 vote, average: 5٫00 out of 51 vote, average: 5٫00 out of 51 vote, average: 5٫00 out of 5( 5٫00 از 1 رای )
    Loading...
دوره آموزشی سیستم ثبت سفارش آنلاین
  • تعداد اعضا 80k
  • قيمت دوره--
  • امتيازدهي
    1 vote, average: 5٫00 out of 51 vote, average: 5٫00 out of 51 vote, average: 5٫00 out of 51 vote, average: 5٫00 out of 51 vote, average: 5٫00 out of 5( 5٫00 از 1 رای )
    Loading...
دوره طراحی سیستم مدیریت مشتریان
  • تعداد اعضا 80k
  • قيمت دوره۶۵,۵۰۰ تومان
  • امتيازدهي
    1 vote, average: 5٫00 out of 51 vote, average: 5٫00 out of 51 vote, average: 5٫00 out of 51 vote, average: 5٫00 out of 51 vote, average: 5٫00 out of 5( 5٫00 از 1 رای )
    Loading...