درخواست های ارتباط
جستجو
    لیست دوستان من
    صندوق پیام
    همه را دیدم
    • در حال دریافت لیست پیام ها
    صندوق پیام
    رویدادها
    همه را دیدم
    • در حال دریافت لیست رویدادها
    همه رویدادهای من
    اطلاعات مطلب
      مدرس/نویسنده
      حسین احمدی
      امتیاز: 464785
      رتبه:3
      340
      253
      402
      2670
      حسین احمدی ، بنیانگذار TOSINSO ، توسعه دهنده وب و برنامه نویس ، بیش از 12 سال سابقه فعالیت حرفه ای در سطح کلان ، مشاور ، مدیر پروژه و مدرس نهادهای مالی و اعتباری ، تخصص در پلتفرم دات نت و زبان سی شارپ ، طراحی و توسعه وب ، امنیت نرم افزار ، تحلیل سیستم های اطلاعاتی و داده کاوی ... پروفایل کاربر
      دوره های مرتبط
      دوره های توسینسو دوره آموزشی مقدماتی برنامه نویسی جاوا به زبان ساده
      دوره آموزشی مقدماتی برنامه نویسی جاوا به زبان ساده
      مدرس: مهدی عادلی فر
      این دوره را در 17 قسط خریداری کنید
      با خرید این دوره مبلغ 5,445 تومان هدیه بگیرید
      دوره آموزشی اسکریپت نویسی Batch یا Batch Scripting در ویندوز به زبان ساده
      دوره آموزشی اسکریپت نویسی Batch یا Batch Scripting در ویندوز به زبان ساده
      مدرس: حسین احمدی
      این دوره را در 11 قسط خریداری کنید
      دوره آموزشی مقدماتی برنامه نویسی به زبان سی شارپ
      دوره آموزشی مقدماتی برنامه نویسی به زبان سی شارپ
      مدرس: حسین احمدی
      این دوره را در 17 قسط خریداری کنید
      با خرید این دوره مبلغ 8,470 تومان هدیه بگیرید
      دوره آموزشی برنامه نویسی به زبان پرل بصورت پروژه محور
      دوره آموزشی برنامه نویسی به زبان پرل بصورت پروژه محور
      مدرس: ایمان جوادی
      این دوره را در 13 قسط خریداری کنید
      ساخت و مدیریت ربات تلگرام از صفر با زبان سی شارپ
      ساخت و مدیریت ربات تلگرام از صفر با زبان سی شارپ
      مدرس: مهدی عادلی فر
      این دوره را در 2 قسط خریداری کنید
      دوره آموزشی برنامه نویسی WPF در ویژوال استودیو
      دوره آموزشی برنامه نویسی WPF در ویژوال استودیو
      مدرس: امیر حسین فضلیخانی
      این دوره را در 12 قسط خریداری کنید
      دوره آموزشی برنامه نویسی اندروید با زبان جاوا به زبان ساده
      دوره آموزشی برنامه نویسی اندروید با زبان جاوا به زبان ساده
      مدرس: مهدی عادلی فر
      این دوره را در 27 قسط خریداری کنید
      با خرید این دوره مبلغ 8,110 تومان هدیه بگیرید
      دوره آموزشی برنامه نویسی حرفه ای پایتون به زبان ساده
      دوره آموزشی برنامه نویسی حرفه ای پایتون به زبان ساده
      مدرس: حسین احمدی
      این دوره را در 23 قسط خریداری کنید
      با خرید این دوره مبلغ 7,425 تومان هدیه بگیرید
      دوره آموزشی برنامه نویسی پیشرفته زبان سی شارپ
      دوره آموزشی برنامه نویسی پیشرفته زبان سی شارپ
      مدرس: حسین احمدی
      این دوره را در 78 قسط خریداری کنید
      با خرید این دوره مبلغ 82,245 تومان هدیه بگیرید
      دوره آموزشی پردازش متن با زبان برنامه نویسی پایتون
      دوره آموزشی پردازش متن با زبان برنامه نویسی پایتون
      مدرس: کاظم تقندیکی
      این دوره را در 20 قسط خریداری کنید
      با خرید این دوره مبلغ 7,040 تومان هدیه بگیرید
      دوره آموزشی ساخت ربات تلگرام
      دوره آموزشی ساخت ربات تلگرام
      مدرس: کاظم تقندیکی
      این دوره را در 8 قسط خریداری کنید
      دوره آموزشی طراحی رابط کاربری با JavaFX
      دوره آموزشی طراحی رابط کاربری با JavaFX
      مدرس: حسام رسولیان
      این دوره را در 13 قسط خریداری کنید
      دوره آموزشی Exploit نویسی به زبان Perl
      دوره آموزشی Exploit نویسی به زبان Perl
      مدرس: ایمان جوادی
      این دوره را در 7 قسط خریداری کنید
      دوره تخصصی آموزش متن کاوی با ابزار NLTK
      دوره تخصصی آموزش متن کاوی با ابزار NLTK
      مدرس: کاظم تقندیکی
      این دوره را در 11 قسط خریداری کنید

      امنیت در دات نت :: آشنایی با Identity و Principal (کنترل دسترسی کاربران)

      تاریخ 13 ماه قبل
      نظرات 0
      بازدیدها 170
      یکی از مباحث بسیار مهم در دات نت مبحث امنیت (Security) است. زمانی که شما قصد توسعه یک نرم افزار را دارید علاوه بر پیاده سازی کلیات منطق برنامه، می بایست به نحوی برنامه را پیاده سازی کنید که امنیت اطلاعات برنامه نیز تضمین شود. این تضمین شامل کنترل دسترسی کاربران به بخش های مختلف برنامه و همچنین ذخیره سازی اطلاعات مهم به صورت رمزنگاری شده در بخش های ذخیره سازی اطلاعات مانند بانک اطلاعاتی است. در این مطلب به مورد اول یعنی کنترل دسترسی کاربرها به برنامه خواهیم پرداخت. در ابتدا با دو مفهوم اصلی در امنیت یعنی Authentication و Authorization آشنا می شویم:

      1. Authentication: پروسه ای که کاربر در آن شناسایی می شود تا مجوز های دسترسی به اون تخصیص داده شود Authentication نام دارد. برای مثال، زمانی که شما قصد استفاده از وب سایت ITPRO را دارید، برای استفاده از برخی امکانات سایت باید با نام کاربری و کلمه عبور خود به سایت وارد شوید. بعد از وارد کردن نام کاربری و کلمه عبور هویت شما در وب سایت تائید شده و اجازه دسترسی به برخی بخش های سایت را خواهید داشت. پروسه تائید هویت به صورت های گوناگونی امکان پذیر است، مانند وارد کردن نام کاربری و کلمه عبور، اسکن عنبیه چشم، اسکن صورت و ... که همگی بر اساس یکسری پارامتر هویت کاربر را بررسی و تصدیق می کنند.
      2. Authorization: پس از تصدیق هویت کاربر یکسری مجوز ها برای او صادر می شود. مجدد وب سایت ITPRO را مثال می زنیم، زمانی که شما پروسه Authentication یا تائید هویت را پشت سر گذاشتید، مجوزهای مربوطه برای شما صادر می شود، برای مثال، امکان ارسال پست، ارسال مقاله و ... برای شما فعال می شود، اما برای مثال، شما در وب سایت امکان ویرایش مشخصات پروفایل سایر کاربران را نخواهید داشت و تنها می توانید اطلاعات پروفایل خود را ویرایش کنید، پروسه Authentication مشخص می کند که کاربر تائید هویت شده چه دسترسی هایی خواهد داشت.

      در برنامه های دات نت نیز می توان پروسه های Authentication و Authorization را جهت کنترل دسترسی کاربران پیاده سازی کرد. برای این کار نیاز به آشنایی با مفاهیم Identity و Principal در دات نت داریم. زمانی که در برنامه های دات نت یک کاربر به سیستم وارد می شود بوسیله Identity اطلاعات آن کاربر را نگهداری می کنیم و در کنار آن، دسترسی های کاربر را بوسیله Principal مشخص می کنیم. دو اینترفیس IIdentity و IPrincipal در دات نت برای اینکار وجود دارند و البته کلاس هایی هم هستند که این اینترفیس را پیاده سازی کرده اند. این کلاس ها و اینترفیس ها در فضای نام System.Security.Principal قرار دارند:

      1. کلاس های WindowsIdentity و WindowsPrincipal: این کلاس ها حاوی اطلاعات کاربر ویندوز هستند، زمانی که یک کاربر به ونیدوز لاگین می کند، اطلاعات کاربری او در ویندوز بواسطه این دو کلاس قابل دسترس است.
      2. کلاس های GenericIdentity و GenericPrincipal: در صورتی که بخواهید پروسه Authentication و Authorization را جدا از حساب کاربری ویندوز پیاده سازی کنید می توانید از این دو کلاس استفاده کنید.

      علاوه بر کلاس های بالا، از نسخه 4.5 دات قابلیت جدیدی اضافه شده به نام Claims که می توان به صورت جدیدی Identity ها و Principal ها را استفاده کرد که در دات نت اصطلاحاً به آن WIF یا Windows Identity Foundation گفته می شود.


      کلاس های WindowsIdentity و WindowsPrincipal


      برای شروع ابتدا با کلاس های WindowsIdentity و WindowsPrincipal آشنا شده و اینکه چگونه برنامه خود را با حساب های کاربری ویندوز یکپارچه کنیم. برای بدست آوردن کاربر جاری ویندوز کافیست به صورت زیر عمل کنیم:

      var identity = WindowsIdentity.GetCurrent();
      Console.WriteLine(identity.Name);
      

      خروجی دستورات بالا نام حساب کاربری ویندوز خواهد که بر روی سیستم من عبارت زیر نمایش داده می شود:

      DESKTOP-CRF890N\Hossein Ahmadi
      

      بعد از بدست آوردن حساب کاربری ویندوز از روش بالا، کلاس Principal را به صورت ایجاد کرده و استفاده می کنیم:

      var identity = WindowsIdentity.GetCurrent();
      Console.WriteLine(identity.Name);
      
      var principal = new WindowsPrincipal(identity);
      Console.WriteLine(principal.IsInRole("BuiltIn\\Users"));
      

      همانطور که در کد بالا مشاهده می کنید برای ایجاد کلاس Principal به عنوان پارامتر سازنده کلاس WindowsPrincipal، شئ identity استفاده شده است. با اینکار و بوسیله کلاس WindowsIdentity می توانیم بررسی کنیم که یک کاربر دسترسی های مورد نظر را دارد یا خیر، برای نمونه در کد بالا بوسیله متد IsInRole بررسی کردیم که کاربر جاری عضو گروه Users در سیستم Local هست یا خیر. به عنوان مثال بعدی، در کد زیر لیست کلیه گروه هایی که کاربر در آن ها عضو می باشد را در خروجی نمایش می دهیم:

      foreach(var group in identity.Groups)
      {
          Console.WriteLine(group.Value);
      }
      

      با اجرای کد بالا خروجی نمایش داده شده حاوی یکسری کدها و اعداد نامفهوم است:

      S-1-5-21-2167674382-1402212879-1573101476-513
      S-1-1-0
      S-1-5-114
      S-1-5-21-2167674382-1402212879-1573101476-1002
      S-1-5-32-544
      S-1-5-32-562
      S-1-5-32-578
      S-1-5-32-559
      S-1-5-32-545
      S-1-5-4
      S-1-2-1
      S-1-5-11
      S-1-5-15
      S-1-5-113
      S-1-2-0
      S-1-5-64-10
      S-1-5-32-4028125388-2803578072-1053907958-341417128-2434011155-477421480-740873757-3973419746
      S-1-5-32-2745667521-2937320506-1424439867-4164262144-2333007343-2599685697-2993844191-2003921822
      S-1-5-32-1034403361-4122601751-838272506-684212390-1217345422-475792769-1698384238-1075311541
      

      در حقیقت خروجی که ما دریافت کردیم شامل شناسه گروه های موجود در سیستم می باشد. برای دریافت اسامی گروه ها کافیست کد بالا را به صورت زیر تغییر دهیم:

      foreach(var group in identity.Groups)
      {
          Console.WriteLine(group.Translate(typeof(NTAccount)));
      }
      

      بوسیله کد بالا و بوسیله متد Translate گروه مورد نظر را به کلاس NTAccount ترجمه کردیم و با اینکار به جای دریافت شناسه گروه ها نام گروه ها به صورت زیر در خروجی نمایش داده می شود:

      Everyone
      NT AUTHORITY\Local account and member of Administrators group
      DESKTOP-CRF890N\HelpLibraryUpdaters
      BUILTIN\Administrators
      BUILTIN\Distributed COM Users
      BUILTIN\Hyper-V Administrators
      BUILTIN\Performance Log Users
      BUILTIN\Users
      NT AUTHORITY\INTERACTIVE
      CONSOLE LOGON
      NT AUTHORITY\Authenticated Users
      NT AUTHORITY\This Organization
      NT AUTHORITY\Local account
      LOCAL
      NT AUTHORITY\NTLM Authentication
      

      متد Translate در موارد دیگری نیز کاربر دارد، برای مثال، در ابتدای مقاله کد زیر را برای بدست آوردن اطلاعات حساب کاربر جاری ویندوز استفاده کردیم:

      var identity = WindowsIdentity.GetCurrent();
      Console.WriteLine(identity.Name);
      

      بوسیله کد زیر می توان شناسه حساب کاربری جاری را در سیستم بدست آورد:

      var identity = WindowsIdentity.GetCurrent();
      Console.WriteLine(identity.Name);
      var account = new NTAccount(identity.Name);
      Console.WriteLine(account.Translate(typeof(SecurityIdentifier)));
      

      خروجی دستورات بالا به صورت زیر خواهد بود:

      DESKTOP-CRF890N\Hossein Ahmadi
      S-1-5-21-2167674382-1402212879-1573101476-1001
      

      برای پارامتر ورودی متد Translate می توان از دو کلاس SecurityIdentifier و NTAccount استفاده کرد که کلاس اولی برای بدست آوردن Identitfer گروه یا کاربر استفاده شده و کلاس دوم برعکس مورد اولی است که کاربرد هر دوی آن ها را در کد های بالا مشاهده کردید.

      همانطور که گفتیم از متد IsInRole برای بررسی دسترسی یک کاربر استفاده می شود. علاوه بر اینکه می توان نام دسترسی را به صورت مستقیم به متد IsInRole در کلاس WindowsIdentity ارسال کرد، امکان ارسال دسترسی مورد نظر به صورت کلاس SecurityIdentifier نیز وجود دارد. برای مثال، در کد زیر ما از کلاس SecurityIdentifier و همچنین enum ای با نام WellKnownSidType برای بررسی دسترسی مورد نظر استفاده کردیم:

      var identity = WindowsIdentity.GetCurrent();
      Console.WriteLine(identity.Name);
      var principal = new WindowsPrincipal(identity);
      var sid = new SecurityIdentifier(WellKnownSidType.BuiltinUsersSid, null);
      Console.WriteLine(principal.IsInRole(sid));
      

      بوسیله کد بالا همان دسترسی BuiltinUsers را بوسیله کلاس SecurityIdentifier بررسی کردیم. در WellKnownSidType آیتم های دیگری نیز وجود دارد که می توان از آن ها برای بررسی دسترسی استفاده کرد. همانطور که در کد بالا مشاهده کردید، برای پارامتر دوم کلاس SecurityIdentifier مقدار null را استفاده کردیم. برای بررسی دسترسی در سطح domain می توان از از پارامتر دوم استفاده کرد. برای مثال، در کد زیر بررسی می کنیم که کاربر در سطح domain دسترسی مدیریتی دارد یا خیر:


      var identity = WindowsIdentity.GetCurrent();
      Console.WriteLine(identity.Name);
      var principal = new WindowsPrincipal(identity);
      var account = identity.User.AccountDomainSid.Translate(typeof(NTAccount));
      var sid = new SecurityIdentifier(WellKnownSidType.AccountDomainAdminsSid, identity.User.AccountDomainSid);
      Console.WriteLine(principal.IsInRole(sid));
      


      کلاس های GenericIdentity و GenericPrincipal



      تا این لحظه با نحوه استفاده از کلاس های WindowsIdentity و WindowsPrincipal آشنا شدیم. اما اگر بخواهیم روند Authentication و Authorization را بر اساس حساب های کاربری که در خود برنامه تعریف شده پیاده سازی کنیم می بایست از کلاس های GenericIdentity و GenericPrincipal استفاده کنیم. استفاده از این کلاس ها خیلی ساده است، در نمونه کد زیر با فرض اینکه کاربری با نام Hossein از برنامه استفاده می کند و دسترسی های UsersAdmin و ProductsAdmin را دارد از کلاس های ذکر شده استفاده می کنیم:

      var username = "Hossein";
      var identity = new GenericIdentity(username);
      
      var roles = new[] { "UsersAdmin", "ProductsAdmin" };
      
      var principal = new GenericPrincipal(identity, roles);
      

      همانطور که مشاهده می کنید نام کاربری به عنوان پارامتر به کلاس GenericIdentity ارسال شده و شئ identity و متغیر roles نیز به کلاس GenericPrincipal ارسال شده اند. فراموش نکنید که مقادیر username و roles می بایست از بانک اطلاعاتی خوانده شوند و بعد از تائید هویت کاربر کلاس های بالا را ایجاد کنید. بعد از انجام کارهای بالا، در قدم بعدی می بایست Principal ایجاد شده را برای Thread جاری به صورت زیر ست کنید:

      Thread.CurrentPrincipal = principal;
      

      بعد از ست کردن Principal می توانیم روند بررسی دسترسی ها را به صورت زیر انجام دهیم:

      public static void CheckPrincipal()
      {
          if (Thread.CurrentPrincipal.IsInRole("UsersAdmin"))
          {
              Console.WriteLine("welcome to Users Admin section.");
          }
          else
          {
              Console.WriteLine("You don't have permission to access this section!");
          }
      }
      

      با کد بالا مشکلی در اجرای کد وجود نخواهد داشت، به این خاطر که در زمان ساخت principal دسترسی UsersAdmin برای کاربر تعریف شده و کاربر می تواند به متد CheckPrincipal دسترسی داشته باشد.

      علاوه بر متد IsInRole می توان از Attribute ای به نام PrincipalPermission نیز برای کنترل دسترسی استفاده کرد. متد CheckPrincipal را در کد بالا بوسیله PrincipalPermission مجدد پیاده سازی می کنیم:

      [PrincipalPermission(SecurityAction.Demand, Role = "Other")]
      public static void CheckPrincipal()
      {
          Console.WriteLine("Welcome");
      }
      

      با فراخوانی متد بالا پیغام خطایی به صورت زیر دریافت می کنیم:

      Unhandled Exception: System.Security.SecurityException: Request for principal permission failed.
      

      به این خاطر که دسترسی Other برای principal تعریف نشده است، اما اگر به جای Other از UsersAdmin استفاده می کردیم، متد بالا بدون مشکل فراخوانی می شود. علاوه بر اینکه می توان از PrincipalPermission به صورت Attribute استفاده کرد، امکان استفاده از آن به صورت مستقیم در کد نیز وجود دارد:

      new PrincipalPermission(null, "Other").Demand();
      

      نویسنده: حسین احمدی
      منبع: ITpro
      برچسب ها
      مطالب مرتبط

      در حال دریافت اطلاعات

      نظرات
      هیچ نظری ارسال نشده است

        برای ارسال نظر ابتدا به سایت وارد شوید

        arrow