مطالب
معرفی Bit Platform
پلتفرم Bit یک پروژه تماما Open Source در GitHub میباشد که هدف آن تسهیل توسعه نرم افزار با کیفیت و پرفرمنس بالا بر بستر ASP.NET Core و زبان #C است که با آن بتوان فقط با یکبار کدنویسی و با کمک استانداردهای وب همچون HTML / CSS و Web Assembly ، خروجی‌هایی چون Android / iOS / Windows را با دسترسی کامل به امکانات سیستم‌عامل به همراه برنامه‌های تحت وب SPA و PWA (با یا بدون Pre-Rendering) گرفت.
پلتفرم Bit تا به اینجا از دو قسمت Bit Blazor Components (شامل بیش از ۳۰ کمپوننت کاربردی، کم حجم و High Performance مانند Tree / Multi Select / Data Grid / Date Picker / Color Picker و...) به همراه Bit Project Templates (قالب پروژه‌های حاوی امکانات پر استفاده) تشکیل شده است.
برخی مواردی که در رابطه با آنها صحبت شد، ممکن است برای شما آشنا نباشند، بنابراین قبل از بررسی مفصل‌‌تر Bit Platform، نگاهی به آن می‌اندازیم:


وب اسمبلی چیست؟

برای درک بهتر وب اسمبلی ابتدا باید بدانیم این تکنولوژی اصلا از کجا آمده و هدف آن چیست؟
میدانیم که مرورگر‌ها پروایدر صفحات وب هستند و ما برای اینکه بتوانیم اپلیکیشنی که ساختیم را در محیط وب برای کاربران به اشتراک بگذاریم باید از این مرورگر‌ها و زبان ارتباطی آن‌ها پیروی کنیم. این زبان‌های ارتباطی مشخصا سه چیز است: HTML CSS JavaScript
اما آیا راهی هست که بتوان بجای JavaScript از زبان‌های دیگر هم در سمت مرورگر استفاده کرد؟
وب اسمبلی یا همان WASM، آمده تا به ما اجازه دهد از هر زبانی که خروجی به Web Assembly دارد، برای تعاملات UI استفاده کنیم. یعنی با زبان هایی مثل #C / C++ / C و... میتوان کدی نوشت که مرورگر آن را اجرا کند. این یک تحول بزرگ است که امروزه تمامی مرورگرها (به جز مرورگرهایی که از دور خارج شده اند) از آن پشتیانی می‌کنند چرا که Web Assembly به یکی از اجزای استاندارد وب تبدیل شده است.
اطلاعات بیشتر در رابطه با وب اسمبلی را میتوانید از این مقاله بخوانید. 


تعریف SPA و PWA:
SPA: Single Page Application
PWA: Progressive Web Application
در گذشته برای رندر کردن صفحات وب با عوض شدن URL یا درخواست کاربر برای دریافت اطلاعات جدید از سرور و نمایش آن ، صفحه مرورگر ملزم به رفرش شدن مجدد و از سر گیری کل فرایند تولید HTML میشد. طبیعتا این تکرار برای کاربر هنگام استفاده از اپلیکیشن خیلی خوشایند نبود چرا که هربار میبایست زمانی بیشتر صرف تولید مجدد صفحات را منتظر میماند. اما در مقابل آن Single Page Application (SPA)‌‌ها این پروسه را تغیر داد.
در رویکرد SPA، کل CSS , HTML و JS ای که برای اجرای هر صفحه ای از اپلیکیشن نیاز هست در همان لود اولیه برنامه توسط مرورگر دانلود خواهد شد. با این روش هنگام تغییر URL صفحات مرورگر دیگر نیازی به لود دوباره اسکریپت‌ها ندارد. همچنین وقتی قرار است اطلاعات جدیدی از سرور آپدیت و نمایش داده شود این درخواست بصورت یک دستور Ajax به سرور ارسال شده و سرور با فرمت JSON اطلاعات درخواست شده را پاسخ میدهد. در نهایت مرورگر نیز اطلاعات برگشتی از سرور را مجدد جای گذاری میکند و کل این روند بدون هیچگونه رفرش دوباره صفحه انجام میشود.
در نتیجه‌ی این امر، کاربر تجربه خوشایند‌تری هنگام کار کردن با SPA‌ها خواهد داشت. اما همانقدر که این تجربه در طول زمان استفاده از برنامه بهبود یافت، لود اولیه اپلیکیشن را کند‌تر کرد، چرا که اپلیکیشن میبایست همه کدهای مورد نیاز خود برای صفحاتش را در همان ابتدا دانلود کند.(در ادامه با قابلیت Pre-Rendering این اشکال را تا حدود زیادی رفع میکنیم)
با استفاده از PWA میتوانید وبسایت‌های SPA را بصورت یک برنامه نصبی و تمام صفحه، با آیکن مجزایی همانند اپلیکیشن‌های دیگر در موبایل و دسکتاپ داشته باشید. همچنین وقتی از PWA استفاده میکنیم برنامه وب میتواند به صورت آفلاین نیز کار کند.
البته حتی در برنامه‌هایی که لازم نیست آفلاین کار کنند، در صورت قطعی ارتباط کاربر با شبکه، به جای دیدن دایناسور معروف، اینکه برنامه در هر حالتی باز شود و به صورتی کاربر پسند و قطعی نت به وی اعلام شود ایده خیلی بهتری است (": 


قابلیت Pre-Rendering:
هدف Pre-Rendering بهبود گشت گذار کاربر در سایت است. شیوه کارکرد آن به این صورت است که وقتی کاربر وارد وبسایت میشود، سرور در همان ابتدای کار و جلوتر از اتمام دانلود اسمبلی‌ها، فایلی حاوی HTML ، CSS‌های صفحه ای که کاربر درخواست کرده را در سمت سرور می‌سازد و به مرورگر ارسال میکند. در همین حین، اسمبلی‌ها نیز توسط مرورگر دانلود می‌شوند و برنامه از محتوای صرف خارج شده و حالت تعاملی می‌گیرد. اصطلاحا به این قابلیت Server-Side Rendering(SSR) نیز میگویند. در این حالت کاربر زودتر محتوایی از برنامه را میبیند و تجربه بهتری خواهد داشت. این امر در بررسی Search Engine‌‌ها و سئو وبسایت نیز تاثیر بسزایی دارد. 


نگاهی به Blazor:
تا اینجا هر آنچه که نیاز بود برای درک بهتر از Blazor بدانیم را فهمیدیم، اما خود Blazor چیست؟ در یک توضیح کوتاه، فریمورکی ارائه شده توسط مایکروسافت میباشد برای پیاده‌سازی UI و منطق برنامه‌ها شامل امکانات Routing ، Binding و...
بلیزر در انواع مختلفی ارائه شده که هرکدام کاربرد مشخصی دارد:

Blazor Server
در بلیزر سرور پردازش‌ها جهت تعامل UI درون سرور اجرا خواهد شد. برای مثال وقتی کاربر روی دکمه ای کلیک میکند و آن دکمه مقداری عددی را افزایش می‌دهد که از قضا متن یک Label به آن عدد وابسته است، رویداد کلیک شدن این دکمه توسط SignalR WebSocket به سرور ارسال شده و سرور تغیر متن Label را روی همان وب سوکت به کلاینت ارسال می‌کند.
با توجه به این که تعامل کاربر با صفحات برنامه، بسته به میزان کندی اینترنت کاربر، ممکن است کند شود و همچنین Blazor Server قابلیت PWA شدن ندارد و علاوه بر این بار پردازش زیادی روی سرور می‌اندازد (بسته به پیچیدگی پروژه) و در نهایت ممکن است در آن از Component هایی استفاده کنیم که چون در حالت Blazor Server پردازش سمت سرور بوده، متوجه حجم دانلود بالای آنها نشویم و کمی بعدتر که با Blazor Hybrid می‌خواهیم خروجی Android / iOS بگیریم متوجه حجم بالای آنها شویم، استفاده از Blazor Server را در Production توصیه نمی‌کنیم، ولی این حالت برای Debugging بهترین تجربه را ارائه می‌دهد، بالاخص با امکان Hot Reload و دیدن آنی تغییرات C# / HTML / CSS در ظاهر و رفتار برنامه موقع کدنویسی.

Blazor WebAssembly
در بلیزر وب اسمبلی منطق مثال قبلی که با C# .NET نوشته شده است، روی مرورگر و با کمک Web Assembly اجرا می‌شود و نیازی به ارتباط جاری با سرور توسط SignalR نیست. این باعث میشود که با بلیزر وب اسمبلی بتوان اپلیکیشن‌های PWA نیز نوشت.
یک برنامه Blazor Web Assembly می‌تواند چیزی در حدود دو الی سه مگ حجم داشته باشد که در دنیای امروزه حجم بالایی به حساب نمیاید، با این حال با کمک Pre Rendering و CDN می‌توان تجربه کاربر را تا حدود زیادی بهبود داد.
برای مثال سایت Component‌های Bit Platform جزو معدود دموهای Component‌های Blazor است که در حالت Blazor Web Assembly ارائه می‌شود و شما می‌توانید با باز کردن آن، تجربه حدودی کاربرانتان را در حین استفاده از Blazor Web Assembly ببینید. به علاوه، در dotnet 7 سرعت عملکرد Blazor Web Assembly بهبود قابل توجهی پیدا کرده است.

Blazor Hybrid
از Blazor Hybrid زمانی استفاده می‌کنیم که بخواهیم برنامه‌های موبایل را برای Android , iOS و برنامه‌های Desktop را برای ویندوز، با کمک HTML , CSS توسعه دهیم. نکته اصلی در Blazor Hybrid این است که اگر چه از Web View برای نمایش HTML / CSS استفاده شده، اما منطق سمت کلاینت برنامه که با C# .NET توسعه داده شده است، بیرون Web View و به صورت Native اجرا می‌شود که ضمن داشتن Performance بالا، به تمامی امکانات سیستم عامل دسترسی دارد. علاوه بر دسترسی به کل امکانات Android / iOS Sdk در همان C# .NET ، عمده کتابخانه‌های مطرح مانند Firebase، با ابزار Binding Library ارائه شده توسط مایکروسافت، دارای Wrapper قابل استفاده در C# .NET هستند و ساختن Wrapper برای هر کتابخانه Objective-C ، Kotlin، Java، Swift با این ابزار فراهم است.

اگر شما در حال حاضر فقط #HTML , CSS , C بدانید، اکنون با بلیزر میتوانید هر اپلیکیشنی که بخواهید توسعه دهید. از وبسایت‌های SPA گرفته تا اپ‌های موبایل Android ، IOS و برنامه‌های دسکتاپی برای Windows , Mac و بزودی نیز برای Linux
سری آموزش بلیزر را میتوانید از این لینک‌ها (1 ، 2) دنبال کنید. 


معرفی پکیج Bit Blazor UI:
پکیج Bit Blazor UI مجموعه ای از کامپوننت‌های مرسومی است که بر پایه بلیزر نوشته شده و به ما این امکان را میدهد تا المان‌های پیچیده ای مثل Date Picker , Grid , Color Picker , File Upload , DropDown و بسیاری از المان‌های دیگر را با شکلی بهینه، بدون نیاز به اینکه خودمان بخواهیم برای هر یک از اینها از نو کدنویسی کنیم، آن را در اختیار داشته باشیم.
عمده مشکل کامپوننت‌های ارائه شده برای بلیزر حجم نسبتا بالای آن است که باعث میشد بیشتر در مصارفی از قبیل ایجاد Admin Panel کارایی داشته باشد. اما این موضوع به خوبی در Bit Blazor UI مدیریت شده و در حال حاضر با بیش از 30 کامپوننت با حجم بسیار پایینی، چیزی حدود 200 کیلوبایت قابل نصب است. از لحاظ حجمی نسبت به رقبای خود برتری منحصر به فردی دارد که باعث میشود به راحتی حتی در اپلیکیشن‌های موبایل هم قابل استفاده باشد و کماکان پرفرمنس خوبی ارائه دهد.
این کامپوننت‌ها با ظاهر Fluent پیاده سازی شده و میتوانید لیست کامپوننت‌های بلیزر Bit را از این لینک ببینید. 


معرفی Bit TodoTemplate:
قبل از اینکه به معرفی Bit TodoTemplate بپردازیم باید بدانیم که اصلا پروژه‌های Template چه هستند. در واقع وقتی شما Visual Studio را باز میکنید و روی گزینه Create New Project کلیک میکنید با لیستی از پروژه‌های تمپلیت روبرو میشوید که هرکدام چهارچوب خاصی را با اهدافی متفاوت در اختیارتان قرار میدهند.
Bit Platform هم Project Template ای با نام TodoTemplate توسعه داده که میتوانید پروژه‌های خودتان را از روی آن بسازید، اما چه امکاناتی به ما میدهد؟
در یک جمله، هر آنچه تا به اینجا توضیح داده شد بصورت یکجا در TodoTemplate وجود دارد.
در واقع TodoTemplate چهارچوبی را فراهم کرده تا شما تنها با دانستن همین مفاهیمی که در این مقاله خواندید، از همان ابتدا امکاناتی چون صفحات SignUp، SignIn یا Email Confirmation و... را داشته باشید و در نهایت بتوانید تمامی خروجی‌های قابل تصور را بگیرید.
اما چگونه؟
در TodoTemplate همه این قابلیت‌ها تنها درون یک فایل و با کمترین تغیر ممکن نوع خروجی کدی که نوشته اید را مشخص میکند. این تنظیمات به شکل زیر است :
<BlazorMode> ... </BlazorMode>
<WebAppDeploymentType> ... </WebAppDeploymentType>
شما میتوانید با تنظیم <BlazorMode> بین انواع hosting model‌های بلیزر سوییچ کنید. مثلا برای زمانی که در محیط development هستید نوع بلیزر را Blazor Server قرار دهید تا از قابلیت‌های debugging بهتری برخوردار باشید ، وقتی میخواهید وبسایت تکمیل شده تان را بصورت SPA / PWA پابلیش کنید نوع بلیزر را به Blazor WebAssembly و برای پابلیش‌های Android ، IOS ، Windows ، Mac نوع بلیزر را به Blazor Hybrid تغیر دهید.
به علاوه، شما تنها با تغیر <WebAppDeploymentType> قادر خواهید بود بین SPA (پیش فرض)، SSR و PWA سوئیچ کنید.
قابلیت‌های TodoTemplate در اینجا به پایان نمیرسد و بخشی دیگر از این قابلیت‌ها به شرح زیر است :
  • وجود سیستم Exception handling در سرور و کلاینت (این موضوع به گونه ای بر اساس Best Practice‌‌ها پیاده سازی شده که اپلیکیشن را از بروز هر خطایی که بخواهد موجب Crash کردن برنامه شود ایزوله کرده)
  • وجود سیستم User Authentication بر اساس JWT که شما در همان ابتدا که از این تمپلیت پروژه جدیدی میسازید صفحات SignIn ، SignUp را خواهید داشت.
  • پکیج Bit Blazor UI که بالاتر درمورد آن صحبت کرده ایم از همان ابتدا در TodoTemplate نصب و تنظیم شده تا بتوانید به راحتی صفحات جدید با استفاده از آن بسازید.
  • کانفیگ استاندارد Swagger در سمت سرور.
  • ارسال ایمیل در روند SignUp.
  • وجود خاصیت AutoInject برای ساده‌سازی تزریق وابستگی ها.
  • و بسیاری موراد دیگر که در داکیومنت‌های پروژه میتوانید آنهارا ببینید.
با استفاده از TodoTemplate پروژه ای با نام Todo ساخته شده که میتوانید چندین مدل از خروجی‌های این پروژه را در لینکهای پایین ببینید و پرفرمنس آن را بررسی کنید.
توجه داشته باشید هدف TodoTemplate ارائه ساختار Clean Architecture نبوده ، بلکه هدف ارائه بیشترین امکانات با ساده‌ترین حالت کدنویسی ممکن بوده که قابل استفاده برای همگان باشد و شما میتوانید از هر پترنی که میخواهید براحتی در آن استفاده کنید.
پلتفرم Bit یک تیم توسعه کاملا فعال تشکیل داده که بطور مداوم در حال بررسی و آنالیز خطاهای احتمالی ، ایشو‌های ثبت شده و افزودن قابلیت‌های جدید میباشد که شما به محض استفاده از این محصولات میتوانید در صورت بروز هر اشکال فنی برای آن ایشو ثبت کنید تا تیم مربوطه آن را بررسی و در دستور کار قرار دهد. در ادامه پلتفرم Bit قصد دارد بزودی تمپلیت جدیدی با نام Admin Panel Template با امکاناتی مناسب برای Admin Panel مثل Dashboard و Chart و... با تمرکز بر Clean Architecture نیز ارائه کند. چیزی که مشخص است اوپن سورس بودن تقریبا %100 کارها میباشد از جلسات و گزارشات کاری گرفته تا جزئیات کارهایی که انجام میشود و مسیری که در آینده این پروژه طی خواهد کرد.
میتوانید اطلاعات بیشتر و مرحله به مرحله برای شروع استفاده از این ابزار‌ها را در منابعی که معرفی میشود دنبال کنید.

منابع:

مشارکت در پروژه:
  • شما میتوانید این پروژه را در گیتهاب مشاهده کنید.
  • برای اشکالات یا قابلیت هایی که میخواهید برطرف شود Issue ثبت کنید.
  • پروژه را Fork کنید و Star دهید.
  • ایشوهایی که وجود دارد را برطرف کنید و Pull Request ارسال کنید.
  • برای در جریان بودن از روند توسعه در جلسات برنامه ریزی (Planning Meeting) و گزارشات هفتگی (Standup Meeting ) که همه اینها در Microsoft Teams برگزار میشود شرکت کنید. 
پروژه‌ها
ادغام، اضافه کردن و جدا کردن صفحات PDF
این پروژه ساده را به صورت Windows Form Application و با زبان Python ساختم. می‌تواند مثالی باشد برای کسانی که میخواهند پایتون را در ویندوز یاد بگیرند و اجرا کنند. اگر کسی پروژه را امتحان کرد، خوشحال خواهم شد خطا‌ها و اشکالات را اینجا اعلام کند.
  1. ادغام چند فایل PDF به صورت فایل واحد (Merging)
  2. اضافه کردن یک فایل PDF به یک فایل موجود (Appending)
  3. جدا کردن صفحات دلخواه از یک فایل و ذخیره آنها در یک فایل جدا (Splitting)
نحوه اجرا: 
  1. در صورت نصب امکانات پایتون برای ویژوال استودیو مثل سایر پروژه‌های دات نت قابل اجرا و دیباگ است.
  2. از طریق خط فرمان  و دستور ipy که در ادامه مثالی میزنم.
  3. من خودم از طریق یک برنامه کنسول ساده پروژه را خارج از محیط توسعه اجرا میکنم که در ادامه مثالی میزنم.
 اجرا از خط فرمان:
  ipy C:\\PdfTools\\PdfTools.py

اجرا از برنامه کنسول:
var process = new Process();
var startInfo = new ProcessStartInfo
      {
            WindowStyle = ProcessWindowStyle.Hidden,
            FileName = "CMD.exe",
            Arguments = "/C ipy C:\\PdfTools\\PdfTools.py"
      };
process.StartInfo = startInfo;
process.Start();
نکته: در صورتی که بخواهید از برنامه کنسول برای اجرا استفاده کنید آیکن‌های برنامه باید در پوشه Debug وجود داشته باشند! 

نظرات اشتراک‌ها
مقایسه کارآیی ORMهای مطرح دات نت
ADO.NET شبیه به زبان اسمبلی دسترسی به اطلاعات در دات نت هست. این پایین‌ترین سطحی است که برای کار با بانک‌های اطلاعاتی در دنیای دات نت وجود دارد. تمام ORMهای موجود لایه‌ای هستند بر روی این سطح.
مطالب
Span در C# 7.2
C# 7.2 به همراه تعداد کوچکی از بهبودهای کامپایلر است و با Visual Studio 2017 نگارش 15.5 ارائه شده و روش فعالسازی آن با نگارش 7.1 آن یکی است (انتخاب گزینه‌ی «C# latest minor version (latest)» در تنظیمات پیشرفته‌ی Build خواص پروژه). همچنین اگر از VSCode استفاده می‌کنید، نگارش 1.14 افزونه‌ی #C آن، پشتیبانی کاملی را از C# 7.2 به همراه دارد؛ در اینجا، افزودن خاصیت <LangVersion>latest</LangVersion> به فایل csproj برنامه برای استفاده‌ی از آخرین نگارش کامپایلر نصب شده، کفایت می‌کند. البته باید دقت داشت کامپایلر C# 7.2 به همراه NET Core SDK 2.1.2. ارائه شده‌است. بنابراین تنها نصب آخرین نگارش افزونه‌ی #C مخصوص VSCode برای کامپایل آن کافی نیست و باید حداقل SDK یاد شده (یا نگارش جدیدتر آن) را هم نصب کنید.
 

نوع‌های جدید <Span<T و  <ReadOnlySpan<T در C# 7.2

نوع‌های جدید <Span<T و <ReadOnlySpan<T جهت ارائه‌ی ناحیه‌های اختیاری پیوسته‌ای از حافظه، شبیه به آرایه‌ها تدارک دیده شده‌اند و هدف استفاده‌ی از آن‌ها، تولید برنامه‌های سمت سرور با کارآیی بالا است.
برای کار با این نوع‌ها، هم نیاز به کامپایلر C# 7.2 است و هم نصب بسته‌ی نیوگت System.Memory:
<Project Sdk="Microsoft.NET.Sdk">
  <PropertyGroup>
    <OutputType>Exe</OutputType>
    <TargetFramework>netcoreapp2.0</TargetFramework>
    <LangVersion>latest</LangVersion>
  </PropertyGroup>
  <ItemGroup>
    <PackageReference Include="System.Memory" Version="4.4.0-preview1-25305-02" />
  </ItemGroup>
</Project>
این بسته از .NETStandard 1.0. به بعد را پشتیبانی می‌کند؛ یعنی با +NET 4.5+ ،Mono 4.6.  و +NET Core 1.0. سازگار است.


Spanها و امکان دسترسی به انواع حافظه

Spanها می‌توانند به حافظه‌ی مدیریت شده، حافظه‌ی بومی (native) و حافظه‌ی اختصاص داده شده‌ی در Stack اشاره کنند. به عبارتی Spanها یک لایه انتزاعی، برفراز تمام انواع و اقسام حافظه‌هایی هستند که می‌توانند در اختیار توسعه دهندگان NET. باشند.
- البته اکثر توسعه دهندگان دات نت از حافظه‌ی مدیریت شده استفاده می‌کنند. برای مثال Stack memory تنها از طریق کدهای unsafe و واژه‌ی کلیدی stackalloc قابل تخصیص است. این نوع حافظه بسیار سریع است و همچنین بسیار کوچک؛ کمتر از یک مگابایت که به خوبی در CPU cache جا می‌شود. اما اگر در این بین حجم حافظه‌ی تخصیصی بیشتر از یک مگابایت شود، بلافاصله استثنای StackOverflowException غیرقابل مدیریتی را به همراه خاتمه‌ی فوری برنامه به همراه خواهد داشت. برای نمونه از این نوع حافظه در جهت مدیریت رخ‌دادهای داخلی corefx زیاد استفاده می‌شود.
- حافظه‌ی مدیریت شده، همان حافظه‌ای است که توسط واژه‌ی کلیدی new در برنامه، جهت ایجاد اشیاء، تخصیص داده می‌شود و طول عمر آن تحت مدیریت GC است.
- حافظه‌ی مدیریت نشده یا بومی از دید GC مخفی است و توسط متدهایی مانند Marshal.AllocHGlobal و Marshal.AllocCoTaskMem در اختیار برنامه قرار می‌گیرند. این حافظه باید به صورت صریحی توسط توسعه دهنده به کمک متدهایی مانند Marshal.FreeHGlobal و Marshal.FreeCoTaskMem آزاد شود. وب سرور Kestrel مخصوص ASP.NET Core، از این روش جهت کار با آرایه‌های حجیم، جهت کاهش بار GC استفاده می‌کند.

مزیت کار با Spanها این است که دسترسی امن و type safeایی را به انواع حافظه‌های مهیا، جهت توسعه دهندگانی که عموما کدهای unsafe ایی را نمی‌نویسند و با اشاره‌گرها به صورت مستقیم کار نمی‌کنند، میسر می‌کند. برای مثال تا پیش از معرفی Spanها، برای دسترسی به 1000 عنصر یک آرایه‌ی 10 هزار عنصری و ارسال آن به یک متد، نیاز بود تا ابتدا یک کپی از این 1000 عنصر را تهیه کرد. این عملیات از لحاظ میزان مصرف حافظه و همچنین زمان انجام آن، بسیار هزینه‌بر است. با استفاده از <Span<T می‌توان یک دید مجازی از آن آرایه را بدون اختصاص آرایه‌ای و یا آرایه‌هایی جدید، ارائه کرد.


مثالی از کاربرد Spanها جهت کاهش تعداد بار تخصیص‌های حافظه

برای نمونه، متد IsValidName زیر، بررسی می‌کند که طول رشته‌ی دریافتی حداقل 2 باشد و حتما با یک حرف شروع شده باشد:
    static class NameValidatorUsingString
    {
        public static bool IsValidName(string name)
        {
            if (name.Length < 2)
                return false;

            if (char.IsLetter(name[0]))
                return true;

            return false;
        }
    }
در این حالت یک نمونه مثال از استفاده‌ی آن می‌تواند به صورت زیر باشد:
string fullName = "User 1";
string firstName = fullName.Substring(0, 4);
NameValidatorUsingString.IsValidName(firstName);
در اینجا زمانیکه از متد Substring استفاده می‌شود، در حقیقت تخصیص حافظه‌ی دومی جهت تولید firstName رخ می‌دهد.

همچنین اگر این اطلاعات را از طریق شبکه دریافت کرده باشیم، ممکن است به صورت آرایه‌ای از حروف دریافت شوند:
char[] anotherFullName = { 'A', 'B' };
که به صورت مستقیم در متد IsValidName قابل استفاده نیست و خطای عدم امکان تبدیل []char به string، از طرف کامپایلر صادر می‌شود:
NameValidatorUsingString.IsValidName(anotherFullName);
در این حالت برای استفاده‌ی از این آرایه، نیاز است یک تخصیص حافظه‌ی دیگر نیز صورت گیرد:
NameValidatorUsingString.IsValidName(new string(anotherFullName));

اکنون در C# 7.2، بازنویسی این متد توسط ReadOnlySpan، به صورت ذیل است:
    static class NameValidatorUsingSpan
    {
        public static bool IsValidName(ReadOnlySpan<char> name)
        {
            if (name.Length < 2)
                return false;

            if (char.IsLetter(name[0]))
                return true;

            return false;

        }
    }
که این مزایا را به همراه دارد:
ReadOnlySpan<char> fullName = "User 1".AsSpan();
ReadOnlySpan<char> firstName = fullName.Slice(0, 4);
NameValidatorUsingSpan.IsValidName(firstName);
کار با API مربوط به Spanها به همراه تخصیص حافظه‌ی جدیدی نیست. برای نمونه در اینجا متد Slice این API، سبب تخصیص حافظه‌ی جدیدی نمی‌شود (برخلاف متد Substring) و فقط به قسمتی از حافظه‌ی موجود اشاره می‌کند (بدون نیاز به کار مستقیم با اشاره‌گرها و کدهای unsafe).

و یا اینبار امکان استفاده‌ی از آرایه‌ای از کاراکترها، بدون نیاز به تخصیص حافظه‌ای جدید، برای بررسی اعتبار مقادیر دریافتی میسر است:
char[] anotherFullName = { 'A', 'B' };
NameValidatorUsingSpan.IsValidName(anotherFullName);

برای نمونه از یک چنین APIایی در پشت صحنه‌ی کتابخانه‌هایی مانند SignalR و یا Roslyn، برای بالا بردن کارآیی برنامه، با کاهش تعداد بار تخصیص‌های حافظه‌ی مورد نیاز، بسیار استفاده شده‌است. برای نمونه در NET Core 2.1.، حجم رشته‌های تخصیص داده شده‌ی در فریم ورک‌های وابسته، به این ترتیب به شدت کاهش یافته‌است.


مثال‌هایی از کار با API نوع Span

امکان ایجاد یک Span از یک array
var arr = new byte[10];
Span<byte> bytes = arr; // Implicit cast from T[] to Span<T>
پس از آن کار با این span همانند کار با آرایه‌های معمولی است؛ با این تفاوت که این span تنها یک دید مجازی از قسمتی از این آرایه را ارائه می‌دهد؛ بدون سربار تخصیص حافظه‌ی اضافی و کپی اطلاعات:
Span<byte> slicedBytes = bytes.Slice(start: 5, length: 2);
slicedBytes[0] = 42;
slicedBytes[1] = 43;
slicedBytes[2] = 44; // Throws IndexOutOfRangeException
bytes[2] = 45; // OK
در اینجا slicedBytes یک دید مجازی از ایندکس 5 تا 7 آرایه‌ی arr را ارائه می‌دهد. کار کردن با آن نیز همانند آرایه‌ها، توسط ایندکس‌ها میسر است.
همچنین تغییرات بر روی Span (غیر read only) بر روی آرایه‌ی اصلی نیز تاثیر گذار است. برای مثال در اینجا با تغییر bytes[2]، مقدار arr[2] نیز تغییر می‌کند.

و یا روش دیگر ایجاد Span استفاده از متد AsSpan است:
var array = new byte[100];
Span<byte> interiorRef1 = array.AsSpan().Slice(start: 20);
همین عملیات را توسط new Span نیز می‌توان به صورت ساده‌تری ارائه داد:
Span<byte> interiorRef2 = new Span<byte>(array: array, start: 20, length: array.Length - 20);


محدودیت‌های کار با Spanها

- Span تنها یک نوع stack-only است.
- Spanها در بین تردها به اشتراک گذاشته نمی‌شوند. هر استک در یک زمان تنها توسط یک ترد قابل دسترسی است. بنابراین Spanها thread-safe هستند.
- طول عمر Spanها کوتاه است و قابلیت قرارگیری بر روی heap با طول عمر بیشتر را ندارند؛ یعنی:
  • به صورت فیلد در یک نوع non-stackonly قابل تعریف نیستند:
class Impossible
{
   Span<byte> field;
}
فیلدهای یک کلاس در heap ذخیره می‌شوند. بنابراین محل ذخیره سازی spanها نیستند.
  • به عنوان پارامترهای متدهای async قابل استفاده نیستند. چون در این بین در پشت صحنه یک AsyncMethodBuilder تشکیل می‌شود که در قسمتی از آن، پارامترها بر روی heap قرار می‌گیرند.
  • هرجائیکه عملیات boxing صورت گیرد، نتیجه‌ی عملیات بر روی heap قرار می‌گیرد. بنابراین در یک چنین مواردی نمی‌توان از Spanها استفاده کرد. برای مثال تعریف Func<T> valueProvider و سپس فراخوانی ()valueProvider.Invoke به همراه یک boxing است. بنابراین نمی‌توان از spanها به عنوان نوع آرگومان جنریک استفاده کرد. این مورد هرچند کامپایل می‌شود، اما در زمان اجرا سبب خاتمه‌ی برنامه خواهد شد و یا نمونه‌ی دیگر، عدم امکان دسترسی به آن‌ها توسط reflection invoke APIs است که سبب boxing می‌شود.


معرفی نوع <Memory<T

با توجه به محدودیت‌های Span و خصوصا اینکه به عنوان پارامتر متدهای async قابل استفاده نیست (چون بر روی stack ذخیره می‌شوند)، نوع دیگری به نام <Memory<T نیز به همراه C# 7.2 ارائه شده‌است. البته این نوع هنوز به بسته‌ی نیوگت فوق اضافه نشده‌است و به همراه ارائه نهایی NET Core 2.1. ارائه خواهد شد.
این نوع، محدودیت <Span<T را نداشته و قابلیت ذخیره سازی بر روی heap را دارا است.
static async Task<int> ChecksumReadAsync(Memory<byte> buffer, Stream stream)
{
   int bytesRead = await stream.ReadAsync(buffer);
   return Checksum(buffer.Span.Slice(0, bytesRead));
   // Or buffer.Slice(0, bytesRead).Span
}
در اینجا نیز می‌توان از یک آرایه، یک <Memory<T را ایجاد و سپس یک <Span<T را از آن دریافت و با Sliceهای آن کار کرد.
نظرات مطالب
ASP.NET MVC #18
سلام ،سال نو مبارک ممنون از پاسخ شما.
من از vs 2013 update1 و win 8.1  استفاده میکنم  و برنامه رو با .NetFrameWork 4.5.1  تست کردم.یعنی شما می‌فرمایید که اگه این بسته‌ی ارتقاع رو نصب کنم مشکل حل میشه؟ (مشکل صدا زدن RoleProvider)
اگر هم تو سیستم لوکال خودم حل شه! به سیستم عامل Host که دسترسی ندارم .بخوام اونم به روز کنم.
من در دات نت 4 که با وب فرم کار می‌کردم همیشه از RoleProvider  سفارشی استفاده می‌کردم و مشکلی نداشت.با مطالعه مقاله شما علاقه مند شدم تا از این به بعد برنامه هامو با MVC توسعه بدم. ولی چون آموزش شما با MVC4 هست و الان که MVC5 عرضه شده سوالات زیادی ذهنم رو مشغول کرده یکی اینکه آیا احتمال داره طی این زمان که از انتشار این مقاله می‌گذره روش‌ها عوض شده و یا روش بهتری برای MVC ارائه شده باشه؟
بازم ممنون از زحمتتتون.
نظرات مطالب
lambda expression در Vb.net
اصولا این گونه نظرات نسبت به زبانی مثل وی بی دات نت به دلیل عدم سابقه تجربی و دانش کافی در مورد آن است. از نظر کارایی و سرعت و قدرت که تفاوت خاصی بین زبان‌های قابل استفاده در دات نت نیست. از نظر زیبایی سینتکس وی بی دات نت برتری داره و به همین دلیل برای آموزش و شروع کار بسیار بهتر است و برای ادامه هم هیچ مشکلی ندارد. سی شارپ هم جذابیت‌های خود را دارد. گاهی همان خلاصه نویسی آن لذت بخش است. اما اصولا یه برنامه نویس حرفه ای که یکی از این زبان‌ها را انتخاب کرده به راحتی می‌تواند در چند ساعت در دیگری نیز مهارت لازم را کسب نماید. بحث عمر تلف شدن در وی بی بسیار جالب است!
مطالب
اتصال به سرویس WCF در NETCF 3.5

با توجه به پیشرفتی که در حوزه اپلیکشن‌های وابسته به فریمورک دات نت بوجود آمده، ولی شاید حرکت عملی بزرگی از سمت تولیدکندگان در حوزه کامپکت صورت نگرفته و همچنان شاهد فرمانروایی سیستم عاملهایی چون Windows Compact 6.0 با استفاده از دات نت فریمورک‌هایی نهایت با نسخه 3.5 هستیم. البته میتوان ارزان‌تر بودن در خارج و مسئله تحریم در داخل را هم در نظر داشت و نمونه عینی این مورد را میتوان در دستگاههای وارد شده در حوزه Compact،  دید. البته شرکت‌های تولید کننده خارجی که عمدتا در کشورهای جنوب شرق و شرق آسیا هستند، جزو شرکت‌های مطرح در این زمینه هستند که بازارهای خوبی هم در کشورهای توسعه یافته‌ای چون آمریکا پیدا کرده‌اند.

در این بین برای عقب نماندن از تکنولوژی‌های جدید بوجود آمده در حوزه دات نت مانند WCF این مقاله کمکی هر چند کوچک برای استفاده از این قابلیت موثر در فریمورک کامپکت می‌تواند باشد.

پیشنیاز‌های لازم:

- Microsoft Visual Studio 2008 + Service Pack 1

- نصب Power Toys for .NET Compact Framework 3.5


پیاده سازی سرویس (بر روی سیستمی غیر از ویندوز کامپکت):  

در ویژوال استودیو 2008 سرویس پک یک، پروژه ای از نوعclass library  را  ایجاد کرده و سرویسی تستی را برای استفاده ایجاد میکنیم:  
[ServiceContract(Namespace = "http://samples.wcf.cfnet.sample")]
    public interface ICalculator
    {
        [OperationContract]
        int Add(int a, int b);
    }

و پیاده سازی آن:

public class CalculatorService : ICalculator
    {
        public static int count;

        public int Add(int a, int b)
        {
            count++;
            Console.WriteLine(string.Format("{3}\tReceived 'Add({0}, {1})' returning {2}", a, b, a + b, count));
            return a + b;
        }

سرور سرویس:

برای هاست این سرویس از یک برنامه‌ی کنسول که در سلوشن ایجاد میکنیم استفاده میکنیم. البته امکان‌های دیگر برای هاست سرویس در هر پروسس دات نتی را میتوان یاد آور شد. برای هاست کردن شروع یک سرویس WCF باید یک IP درون شبکه را که قابل دسترسی از سمت ویندوز کامپکت بوده و به سیستم انتساب داده شده، دریافت و استفاده کنیم:  

var addressList = Dns.GetHostEntry(Dns.GetHostName());

string hostIP = addressList.AddressList.Single(x=>x.ToString().StartsWith("192.168.10.")).ToString();
Uri address = new Uri(string.Format("http://{0}:8000/Calculator", hostIP));

در قطعه بالا IP در رنج مناسب و قابل دسترسی انتخاب میشود چون ویندوز کامپکت (فارق از اینکه در شبیه ساز باشد یا واقعی) از طریق شبکه به سرور دسترسی پیدا میکند باید IP مناسب انتساب داده شده انتخاب شود.

ServiceHost serviceHost = new ServiceHost(typeof(CalculatorService),address);
serviceHost.AddServiceEndpoint(typeof(ICalculator), new BasicHttpBinding(), "Calculator");

در ادامه یک سرویس هاست را new کرده و سرویس و بایندینگ را به آن در سازنده پاس میدهیم.

var serviceMetadataBehavior =
new ServiceMetadataBehavior { HttpGetEnabled = true };
serviceHost.Description.Behaviors.Add(serviceMetadataBehavior);

این قسمت برای ادامه کارکرد سرویس لازم نیست ولی در ادامه‌ی مقاله برای تولید کدهای سمت کلاینت باید این قابلیت فعال باشد و پس از آن دیگر احتیاجی نیست و میتوان این چند خط کد را کامنت کرد.

serviceHost.Open();
Console.WriteLine("CalculatorService is running at " + address.ToString());
Console.WriteLine("Press <ENTER> to terminate");
Console.ReadLine();
serviceHost.Close();

و در نهایت، شروع سرویس با فرمان Open و خاتمه آن با فرمان Close .


کلاینت سرویس (در داخل ویندوز کامپکت):

همراه با ارائه دات نت فریمورک 3.5 برای کار با سرویس WCF که از آن یک نسخه‌ی ارائه شده برای کامپکت نیز تهیه شده‌است، ابزاری مانند netcfSvcUtil.exe که در SDK نسخه‌ی کامپکت موجود است و کاربرد هندل کردن بعضی از موارد مانند تولید کد پروکسی‌های سمت کلاینت را دارد که در ادامه طرز استفاده از آن را بررسی خواهیم کرد. بعد از اجرای سرویس WCF با رفتار HttpGetEnabled = true برای بررسی سریع کارکرد صحیح سرویس، آدرس آن را در مرورگر میبینیم. تصویر زیر نتیجه‌ی آن در مرورگر است:



در خط فرمان به آدرس مربوط به این ابزار رفته (بسته به نسخه‌ی سیستم عامل ممکن است در پوشه‌های زیر یافت شود ( :

(Windows Drive)\Program Files (x86)\Microsoft.NET\SDK\CompactFramework\v3.5\bin
(Windows Drive)\Program Files\Microsoft.NET\SDK\CompactFramework\v3.5\bin

و فرمان زیر را اجرا میکنیم:

netcfSvcUtil.exe /language:C# /target:code /directory:D:\GeneratedCode\CF\CaculatorService http://192.168.10.189:8000/BooksService.svc?wsdl

البته ذکر IP شبکه در اینجا الزامی نیست؛ زیرا در صورت استفاده از آدرسهای داخلی سیستم، این فرمان به مشکلی بر نخواهد خورد. در این فرمان تولید کد با زبان c# و تولید کد که بصورت پیش فرض نیز وجود دارد و محل ذخیره سازی کدهای تولیدی را مشخص میکنیم و بعد از اجرای این فرمان، باید دو فایل در مسیر اشاره شده در فرمان تولید شود که اساس کار ما در سمت کلاینت خواهد بود:


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

var addressList = Dns.GetHostEntry(Dns.GetHostName());
var localAddress = addressList.AddressList.Single(x => x.ToString().StartsWith("192.168.10.")).ToString();

دوباره IP مناسب در شبکه جاری استخراج میشود. بایندیگ مورد نیاز برای ارتباط با سرور ساخته میشود:

var binding = CalculatorClient.CreateDefaultBinding();

نکته‌ای که دراین قسمت باید مدنظر قرار گیرد این است که در زمان تولید کدها اگر از localhost یا 127.0.0.1 و یا آدرسهای دیگر انتساب داده شده به سرور استفاده کرده باشید در متد CreateDefaultBinding از همان آدرس استفاده میشود و برای اصلاح آن بصورت زیر عمل میکنیم:

string remoteAddress = CalculatorClient.EndpointAddress.Uri.ToString();
remoteAddress = remoteAddress.Replace("localhost", serviceAddress.Text);

یک EndpointAddress با استفاده از این آدرس ساخته و به‌همراه بایندینگ، یک آبجکت از جنس CalculatorClient که در کدهای تولیدی داریم میسازیم:

CalculatorClient _client = new CalculatorClient(binding, endpoint);

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

var result = _client.Add(82, 18).ToString(CultureInfo.InvariantCulture);

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


 
مطالب
چک لیست امنیتی پروژه های نرم افزاری تحت وب
 مقدمه:

امروزه یکی از بزرگترین دغدغه‌های فعالان حوزه آی تی، برقراری امنیت اطلاعات می‌باشد. با پدید آمدن بانک‌های داده‌ای آماری و مالی، حساسیت مسئله صد چندان می‌شود. در ادامه چک لیستی را ارائه می‌نمایم که با کمک آن می‌توانید تا حدود بسیار خوبی امنیت نرم افزار تحت وب خود را برقرار نمایید. در برخی از موارد مثال‌هایی از تکنولوژی مایکروسافت آورده شده است که این بدلیل تخصص نویسنده در تکنولوژی‌های مایکروسافت می‌باشد. در صورتیکه شما از تکنولوژی‌ها و زبان‌های سورس باز بهره می‌برید، می‌بایست معادل مورد ذکر شده را در زبان مورد استفاده خود بیابید .
ابتدا اجازه دهید مقداری با حملات آشنا شویم و سپس راه مقابله را در کنار هم بررسی نماییم.
 

مهمترین و خطرناک‌ترین حملات سطح وب :

حمله XSS

این نوع حملات بدین صورت است که هکر با استفاده از فرم‌های عمومی یا خصوصی (پنل‌های سایت) اقدام به ثبت کدهای مخرب جاوااسکریپت درون دیتابیس شما می‌نماید. همانطور که می‌دانید پایه اصلی سیستم‌های احراز هویت، ساخت فایل کوکی بر روی کامپیوتر کاربران می‌باشد. زمانی که مطلب ثبت شده‌ی هکر برای کاربران شما نمایش داده می‌شود، کدهای جاوا اسکریپت هکر روی مرورگر کاربر، اجرا شده و اطلاعات کوکی‌های کاربر به راحتی برای سایت هکر ارسال می‌شود (معمولا هکر یک صفحه روی وب می‌سازد تا بتواند اطلاعات دریافتی از کدهای جاوا اسکریپت خود را دریافت و در جایی ذخیره کند).
حال هکر به راحتی کوکی را بر روی مرورگر خودش تنظیم می‌کند و بعد وارد سایت شما می‌شود. سیستم شما او را با کاربر شما اشتباه می‌گیرد و به راحتی هکر به اطلاعات پنل کاربری کاربر(ان) شما دست پیدا می‌کند.
 

حمله SQL Injection

این حمله معروفترین حمله است که تقریبا با قدرت می‌توانم بگویم که درتکنولوژی ASP.Net با امکانات فوق العاده‌ای که بصورت توکار در دات نت در نظر گرفته شده است، بصورت کامل به فراموشی سپرده شده است. فقط 2 تا نکته‌ی ریز هست که باید در کدهایتان رعایت کنید و تمام.
این حمله بدین صورت است که هکر یک سری دستورات SQL را در کوئری استرینگ، به صفحات تزریق می‌کند و بدین صورت می‌تواند در کدهای کوئری TSQL شما اختلال ایجاد کند و اطلاعات جداول شما را بدست بیاورد. در این نوع حمله، هکر از طریق باگ سطح کد نویسی کدهای نرم افزار، به دیتابیس حمله می‌کند و اطلاعاتی مثل نام کاربری و کلمه‌ی عبور ادمین یا کاربران را می‌دزد و بعد می‌رود داخل پنل و خرابکاری می‌کند.
 

حمله CSRF

این حمله یکی از جالب‌ترین و جذاب‌ترین نوع حملات است که هوش بالای دوستان هکر را نشون می‌دهد. عبارت CSRF مخفف Cross Site Request Forgery است (احتمالا دوستان ام وی سی کار، این عبارت برایشان آشناست).
در این نوع حمله هکر یک فایل برای کاربر شما از طریق ایمیل یا روش‌های دیگر ارسال می‌کند و کاربر را به این سمت سوق می‌دهد که فایل را باز کند. کاربر یک فایل به ظاهر معمولی مثل عکس یا ... را می‌بیند و فایل را باز می‌کند. وقتی فایل باز می‌شود دیتای خاصی دیده نمی‌شود و گاهی هم اروری مبنی بر ناقص بودن فایل یا ... به کاربر نمایش داده می‌شود و کاربر فکر می‌کند که فایل، ناقص برای ارسال شده ...
اما در حقیقت با کلیک بر روی فایل و باز کردن آن یک درخواست POST از کامپیوتر کاربر برای سایت شما ارسال می‌شود و در صورتیکه کاربر در آن زمان در سایت شما لاگین باشد، سایت درخواست را با روی باز می‌پذیرد و درخواست را اجرا می‌کند. بدین صورت هکر می‌تواند درخواست‌هایی را به سرویس‌های سایت شما که مثلا برای حذف یک سری داده است، ارسال کند و اطلاعات کاربر را حذف کند.
 

حمله Brute Force

در این حمله، هکر از یک سری برنامه برای ارسال درخواست‌های مکرر به فرم‌های سایت شما استفاده می‌کند و بدین صورت فرم‌های عمومی سایت شما مورد حجوم انبوهی از درخواست‌ها قرار می‌گیرد که این امر در بهترین حالت موجب ثبت کلی دیتای اسپم در دیتابیس شما و در بدترین حالت موجب داون شدن سایت شما می‌شود.
 

حمله DDOS

این نوع حمله مانند حمله Brute Force است؛ با این تفاوت که درخواست به همه‌ی صفحات شما ارسال می‌شود و معمولا درخواست‌ها از چندین سرور مختلف برای سایت شما ارسال می‌شوند و حجم درخواست‌ها به قدری زیاد است که عملا سرور شما هنگ می‌کند و کاملا از دسترس خارج می‌شود. این نوع حمله در سطح کد راه حل زیادی ندارد و در سطح سرور و فایروال باید حل شود و حل آن هم بدین صورت است که درخواست‌های بیش از حد طبیعی از یک آی پی خاص تشخیص داده شده و به سرعت، آی پی بلاک می‌شود و از آن به بعد درخواست‌های آن آی پی در فایروال از بین می‌رود و دیگه به سرور نمیرسد.


حمله SHELL

شل فایلی است خطرناک که اگر بر روی سرور سایت شما آپلود و اجرا شود، هکر از طریق آن دسترسی کاملی به کل سرور سایت شما خواهد داشت. فایل‌های دیگری با نام بک‌دور [1] نیز وجود دارند که نویسنده تمایل دارد آنها را نیز از نوع حمله SHELL معرفی نماید. این نوع از فایل‌ها به مراتب بسیار خطرناک‌تر از فایل‌های شل می‌باشند؛ تا جایی که ممکن است سال‌ها هکر به سروی دسترسی داشته باشد و مدیر سرور کاملا از آن بی خبر باشد. اینجاست که باید شدیدا مراقب فایل‌هایی که روی سایت شما آپلود می‌شوند باشید. نویسنده به تمامی خوانندگان پیشنهاد می‌نماید، در صورتیکه نرم افزار حساسی دارند، حتما از سرور اختصاصی استفاده نمایند؛ چرا که در هاست‌های اشتراکی که در آنها فضا و امکانات یک سرور بصورت اشتراکی در اختیار چندین سایت قرار می‌گیرد، وجود باگ امنیتی در سایر سایت‌های موجود بر روی سرور اشتراکی می‌تواند امنیت سایت شما را نیز به مخاطره بیاندازد. نویسنده تهیه‌ی سرور اختصاصی را شدیدا به توسعه دهندگان سایت‌های دارای تراکنش‌های بانکی بالا (داخلی یا خارجی) پیشنهاد می‌نماید. زیرا درگاه تراکنش‌های بانکی بر روی آی پی هاست شما قفل می‌شوند و در صورتیکه سرور بصورت اختصاصی تهیه شده باشد، آی پی سرور شما فقط و فقط در اختیار شماست و هکر نمی‌تواند با تهیه هاستی بر روی سرور اشتراکی شما، به راحتی آی پی قفل شده در درگاه بانکی شما را در اختیار داشته باشد. بدیهی است تنها در اختیار داشتن آی پی سرور شما جهت انجام خرابکاری در درگاه بانکی شما کافی نیست. ولی به نظر نویسنده این مورد در بدترین حالت ممکن 30% کار هکر می‌باشد. البته بحث حمله شل به سطح مهارت متخصصان سرورها نیز بستگی دارد. نویسنده اظهار می‌دارد اطلاعات دقیقی از تنظیماتی که بتواند جلوی اجرای انواع شل و یا جلوی دسترسی فایل‌های شل را بگیرد، ندارد. بنابراین از متخصصان این حوزه دعویت می‌نماید اطلاعاتی درباره این موضوع ارائه نمایند.
 

حمله SNIFF

در این نوع حملات، هکر پکت‌های رد و بدل شده‌ی بین کاربران و سرور شما را شنود می‌نماید و به راحتی می‌تواند اطلاعات مهمی مثل نام کاربری و رمز عبور کاربران شما را بدست آورد.



چک لیست امنیتی پروژه‌های نرم افزاری تحت وب

- بررسی کامل ورودی‌های دریافتی از فرم‌های سایت؛ هم در سمت کلاینت و هم در سطح سرور .
- در تکنولوژی دات نت به منظور تمیز سازی ورودی‌ها و حذف تگهای خطرناکی همچون تگ script، کتابخانه‌ای با نام Microsoft.Security.Application وجود دارد. کتابخانه‌های سورس باز دیگری نیز وجود دارند که نمونه آن کتابخانه AntiXss [2] سایت نوگت [3] می‌باشد.
- بررسی کامل ورودی‌های دریافتی از کوئری استرینگ‌های [4] سایت. اگر از ASP.Net MVC استفاده می‌نمایید، تا حدی زیادی نیاز به نگرانی نخواهد داشت، زیرا تبدیلات [5] در سیستم Model Binding انجام می‌پذیرد و این موضوع تا حد زیادی شما را در برابر حملات SQL Injection مقاوم می‌نماید.
- حتما در فرم‌های عمومی سایتتان از تصویر کپچا با امنیت بالا استفاده نمایید. این موضوع جهت شناخت روبات‌ها از انسان‌ها می‌باشد و شما را در برابر حملات Brute Force مقاوم می‌نماید.
-  حتما سیستم شخصی سازی صفحات ارور را فعال نمایید و از نمایش صفحات ارور حاوی اطلاعات مهمی مانند صفحات ارور ASP.Net جلوگیری نمایید. این موضوع بسیار حساس می‌باشد و می‌تواند نقاط ضعف نرم افزار شما را برای هکر نمایان کند. حتی ممکن است اطلاعات حساسی مانند نام بانک اطلاعاتی، نام کاربری اتصال به بانک اطلاعاتی و نام جداول بانک اطلاعاتی شما را در اختیار هکر قرار دهد.
- استفاده از ORM ها یا استفاده از پروسیجرهای پارامتریک. این موضوع کاملا شما را در برابر حملات SQL Injection مقاوم می‌نماید. کما اینکه ORM ها، سطحی از کش را بصورت توکار دارا می‌باشند و این موضوع در سرعت دستیابی به داده‌ها نیز بسیار تاثیر گذار است. از طرف دیگر بانک اطلاعاتی SQL نیز امکانات توکاری جهت کش نمودن پرس و جو‌های [6] پارامتریک دارد.
- لاگ کردن ارورهای سطح کد و سطح روتینگ [7] . یکی از مهمترین خصیصه‌های پروژه‌های با کیفیت، لاگ شدن خطاهای سطح کد می‌باشد. این امر شما را با نقاط حساس و ضعف‌های نرم افزار آگاه می‌سازد و به شما اجازه می‌دهد به سرعت در جهت رفع آنها اقدام نمایید. لاگ نمودن خطاهای سطح روتینگ شما را از فعالیت‌های هکر‌ها جهت یافتن صفحات لاگین و صفحات مدیریتی پنل مدیریتی سایت اگاه می‌نماید، همچنین شما را از حملات SQL Injection نیز آگاه می‌نماید.
- جلوگیری از ایندکس شدن صفحات لاگین پنل مدیریت سایت در موتورهای جستجو. بخش مهمی از عملیات هکر ها، قرار دادن روبات‌های تشخیص رمز بر روی صفحات لاگین می‌باشد که به نوعی می‌توان این نوع حملات را در دسته حملات Brute Force قرار داد. موتورهای جستجو یکی از ابزارهای مهم هکرها می‌باشد. عملیات هایی مانند یافتن صفحات لاگین پنل مدیریتی یکی از کاربردهای موتورهای جستجو برای هکرها می‌باشد.
- لاگ کردن ورود و خروج افراد به همراه تاریخ، زمان، آی پی افراد و وضعیت لاگین. با کمک این موضوع شما می‌توانید ورود و خروج کاربران نرم افزار خود را کنترل نمایید و موارد غیر طبیعی و مشکوک را در سریعترین زمان مورد بررسی قرار دهید.
- استفاده از روال‌های استاندارد جهت بخش "فراموشی کلمه عبور". همیشه از استاندارهای نرم افزارهای بزرگ پیروی نمایید. بدیهی است استاندارهای استفاده شده در این نرم افزارها بارها و بارها تست شده و سپس بعنوان یک روال استاندارد در همه‌ی نرم افزارهای بزرگ بکار گرفته شده است. استاندارد جهانی بخش "فراموشی کلمه عبور" که در اغلب نرم افزارهای معروف جهان بکار گرفته شده است، عبارت است از دریافت آدرس ایمیل کاربر، احراز هویت ایمیل وارد شده، ارسال یک نامه‌ی الکترونیکی [8] حاوی نام کاربری و لینک تنظیم کلمه عبور جدید به ایمیل کاربر. بهتر است لینک ارسال شده به ایمیل کاربر بصورت یکبار مصرف باشد. کاربر پس از کلیک بر روی لینک تنظیم کلمه عبور جدید، وارد یکی از صفحات سایت شده و می‌تواند کلمه‌ی عبور جدیدی را برای خود ثبت نماید. در پایان، کاربر به صفحه‌ی ورود سایت هدایت شده و پیامی مبنی بر موفقیت آمیز بودن عملیات تغییر کلمه‌ی عبور به او نمایش داده می‌شود. البته روال ذکر شده حداقل رول استانداردی می‌باشد و می‌توان در کنار آن از روال‌های تکمیل کننده‌ای مانند پرسش‌های امنیتی و غیره نیز استفاده نمود.
- قراردادن امکاناتی جهت بلاک نمودن آی پی‌ها و غیر فعال نمودن حساب کاربری اعضای سایت. در نرم افزار باید این امکان وجود داشته باشد که آی پی هایی که بصورت غیر طبیعی در سایت فعالیت می‌نمایند و یا مکررا اقدام به ورود به پنل مدیریتی و پنل کاربران می‌نمایند را بلاک نماییم. همچنین در صورت تخلف کاربران باید بتوان حساب کاربری کاربر خاطی را مسدود نمود. این موضوع می‌تواند بسته به اندازه پروژه و یا سلیقه تیم توسعه بصورت خودکار، دستی و یا هر دو روش در نرم افزار در تعبیه شود.
- امن سازی سرویس‌های ای جکس و چک کردن ای جکس بودن درخواست ها. حتما جلوی اجرای سرویس‌های درون نرم افزاری از بیرون از نرم افزار را بگیرید. سرویس‌های ای جکس یکی از این نوع سرویس‌ها می‌باشند که در نرم افزار‌ها جهت استفاده‌های داخلی در نظر گرفته می‌شوند. در این نوع سرویس‌ها حتما نوع درخواست را بررسی نمایید و از پاسخگویی سرویس‌ها به درخواست‌های غیر ای جکسی جلوگیری نمایید. در ASP.Net MVC این امر توسط متد Request.IsAjaxRequest انجام می‌پذیرد .
- محدود کردن سرویس‌های حساس به درخواست‌های POST. حتما از دسترسی به سرویس هایی از نوع Insert,Update و Delete از طریق فعل GET جلوگیری نمایید. در ASP.Net MVC این سرویس‌ها را به فعل POST محدود نموده و در ASP.Net Web API این سرویس‌ها را به افعال POST,PUT و DELETE محدود نمایید.
- عدم استفاده از آی دی در پنل‌های کاربران بالاخص در آدرس صفحات (کوئری استرینگ) و استفاده از کد غیر قابل پیش بینی مثل GUID به جای آن. حتی الامکان بررسی مالکیت داده‌ها در همه بخش‌های پنل‌های کاربری سایت را جهت محکم کاری بیشتر انجام دهید تا خدای نکرده کاربر با تغییر اطلاعات کوئری استرینگ صفحات نتوانند به داده‌های یک کاربر دیگه دسترسی داشته باشند.
- حتی الامکان پنل مدیران را از کاربران بصورت فیزیکی جدا نمایید. این مورد جهت جلوگیری از خطاهایی است که ممکن است توسط توسعه دهنده در سطح سیستم مدیریت نقش رخ دهد و موجب دسترسی داشتن کاربران به بخش هایی از پنل مدیریتی شود.
- استفاده از الگوریتم‌های کدگذاری ترکیبی و کد کردن اطلاعات حساس قبل از ذخیره سازی در بانک اطلاعاتی. اطلاعات حساسی مانند کلمات عبور را حتما توسط چند الگوریتم کدگذاری، کدگذاری نمایید و سپس درون بانک اطلاعاتی ذخیره نمایید.
- تنظیمات حساس نرم افزار را درون فایل web.config قرار دهید و حتی الامکان آنها را نیز کدگذاری نمایید. بصورتی که اطلاعات قابلیت دیکد شدن را داشته باشند.
- ساخت پروژه بصورت چند لایه. این موضوع جهت جلوگیری از دستیابی هکر به ساختار لایه‌های پروژه‌های شما می‌باشد. به بیان دیگر اگر نهایتا هکر بتواند به اطلاعات FTP هاست شما دست یابد، استفاده از تکنولوژی چند لایه در بدترین حالت هکر را از دستیابی به اطاعات لایه‌های زیرین نرم افزار باز می‌دارد. البته این کار برای هکر‌ها غیر ممکن نیست، اما بسیار سخت و زمان بر می‌باشد.
- اشتراک گذاری اینترفیس در سرویس‌های خارج برنامه ای و عدم اشتراک گذاری کلاس اصلی. این موضوع از دستیابی هکر به بدنه سرویس‌ها و پیاده سازی‌های آنها جلوگیری می‌نماید.
- استفاده از تکنیک‌های مقابله با CSRF در همه سرویس‌های POST. در ASP.NET MVC اتریبیوتی با نام AntiForgery جهت مقاوم سازی سرویس‌ها از حملات CSRF وجود دارد. مکانیزم بدین صورت است که در تمامی فرم‌های سایت یک کد منحصر به فرد تولید می‌گردد که همراه درخواست GET به کامپیوتر کاربر ارسال می‌شود و در هنگام ارسال درخواست POST به سرور، صحت کد مورد نظر بررسی شده و در صورت صحت، اجازه‌ی اجرای سرویس به درخواست داده می‌شود. بدین صورت وقتی کاربر سایت شما فایل آلوده‌ای را باز می‌نماید، در خواست ارسالی هکر که توسط فایل باز شده، به سرور سایت ما ارسال می‌گردد، فاقد کد منحصر به فرد بوده و از اجرای سرویس جلو گیری می‌شود.
- استفاده از سیستم‌های مدیریت نقش امن مانند IDENTITY در ASP.Net MVC و یا استفاده از امکانات توکار دات نت در سیستم‌های مدیریت نقش شخصی سازی شده [9] . بدیهی است امنیت این سیستم‌ها بارها و بارها تست شده است.
- بررسی فرمت و پسوند فایل‌های آپلود شده. توجه نمایید که بررسی پسوند فایل‌ها کافی نبوده و فرمت فایل‌ها نیز می‌بایست بررسی شود. حتی نویسنده پیشنهاد می‌نماید فایل‌ها را به نوع‌های مرتبطشان تبدیل [10] نمایید. در حوزه هک بایند نمودن انواع ویروس، تروجان، شل و بک دور [11] به فایل‌های تصویری و متنی یک امر بسیار رایج است. بنابراین حساسیت زیادی روی این موضوع قرار دهید. نویسنده توصیه می‌نماید کتابخانه‌های کاملی برای این موضوع تدارک ببینید تا در تمامی پروژه‌ها نیاز به ایجاد مجدد آنها نداشته باشید و سعی نمایید در هر پروژه این کتابخانه‌ها را تکمیل‌تر و بهتر نمایید.
- تنظیم IIS  جهت جلوگیری از اجرای فایل‌های اجرایی در مسیر آپلود فایل‌ها. شاید جمله بیان شده به نظر ترسناک و یا سخت برسد، اما این کار با نوشتن چند تگ ساده در فایل Web.Config به راحتی قابل انجام است و نیاز به هیچ نوع کدنویسی ندارد.
- آپلود فایل‌ها در پوشه App_Data و دسترسی به فایل‌ها از طریق سرویس‌های خود شما. پوشه App_Data پوشه‌ای امن است و دسترسی مستقیم از طریق آدرس بار مرورگر به فایل‌های درون آن توسط IIS داده نمی‌شود و افراد فقط از طریق سرویس‌های خود شما می‌توانند به فایل‌های داخل این پوشه دسترسی داشته باشند. بدین صورت در سرویس‌های خود می‌توانید با تبدیل نمودن [12] فایل‌ها به نوع خودشان (تصویر. پی دی اف یا ...) هکر را نا امید نمایید. این موضوع شما را در مقابل حملات SHELL مقاوم می‌نماید.
- استفاده از تکنیک‌های لاگین چند سطحی برای پنل ادمین. در این روش شما حتی با داشتن نام کاربری و کلمه‌ی عبور ادمین، قادر نخواهید بود وارد پنل ادمین شوید. نویسنده ابزار می‌دارد که این روش، یک روش ابداعی می‌باشد که از ترکیبی از احرا هویت ساده توسط نام کاربری و کلمه‌ی عبور به همراه تکنیک‌های احراز هویت ایمیل و موبایل مدیریت سایت می‌باشد.
- استفاده از SSL بسیار اهمیت دارد. بالاخص اگر نرم افزار شما Service Oriented باشد و نرم افزار شما سرویس هایی جهت اتصال به اپلیکیشن‌های خارجی مثل اپلیکیشن اندروید دارد. این مورد در صفحات لاگین نیز بسیار مهم است و موجب می‌شود نام کاربری و کلمه عبور کاربران شما بصورت هش شده بین کامپیوتر کاربر و سرور شما رد و بدل شود و عملا شنود پکت‌ها فایده ای برای هکر نخواهد داشت، زیرا داده‌ها توسط الگوریتم‌های امنیتی که بین سرور و مرورگر کاربران توافق می‌شود کدگذاری شده و سپس رد و بدل می‌شوند.



[1] Back Door
[2] https://www.nuget.org/packages/AntiXss/
[3] www. Nuget.org
[4] Query String
[5] Casting
[6] Procedure
[7] Routing
[8] Email
[9] Custom Role Provider
[10] Cast
[11] Back Door
[12] Cast
مطالب
بلاگ‌ها و مطالب مطالعه شده در هفته قبل (هفته سوم آبان)

وبلاگ‌ها و سایت‌های ایرانی


ASP. Net


طراحی وب


به روز رسانی‌ها


ابزارها


سی‌شارپ


عمومی دات نت


دلفی



ویندوز


متفرقه

  • کدام سایت‌ها مطالب شما را کپی کرده‌اند؟! (البته شبیه به این کار را با Google alerts هم می‌شود انجام داد. فقط کافی است آدرس سایت خودتان را در گوگل alert اضافه کنید. هر جایی لینکی به شما داده شود یا امثال آن، یک ایمیل آنی یا روزانه بسته به تنظیمات برای شما ارسال خواهد کرد.)