دوره توسعه asp.net mvc
در ادامه دوره مقدماتی mvc که قبلا در سایت به اشتراک گذاشته شده بود.دوره جدیدی رو مایکروسافت منتشر کرده با عنوان توسعه برنامههای MVC که سرفصلهای آن را در بخش زیر مشاهده میکنید:
Mod 01: Introduction to MVC 4 Mod 02: Developing ASP.NET MVC 4 Models Mod 03: Developing MVC 4 Controllers Mod 04: Developing ASP.NET MVC 4 Views Mod 05: Integrating JavaScript and MVC 4 Mod 06: Implementing Web APIs Mod 07: Deploying to Windows Azure Mod 08: Visual Studio 2013/MVC 5 Sneak Peek
داخل یک Image چیست؟
در قسمت قبل دریافتیم که یک Image، از کل User Space مورد نیاز جهت اجرای یک برنامه تشکیل میشود. در ادامه میخواهیم بررسی کنیم، این ادعا تا چه حد صحت دارد و یک Image، واقعا از چه اجزائی تشکیل میشود.
با استفاده از دستور docker images میتوان لیست imageهای دریافت شده را به همراه tagهای مرتبط با هر کدام، مشاهده کرد. سپس با استفاده از دستور docker save میتوان image ای خاص را export کرد؛ برای مثال:
docker save microsoft/iis:nanoserver -o iis.tar
البته ویندوز در حالت استاندارد آن، قابلیت کار با فایلهای tar را ندارد. هرچند میتوان از نرم افزارهای ثالثی مانند win-rar و یا 7zip برای انجام اینکار استفاده کرد، اما تمام Linux Containers، به همراه ابزار کمکی tar، برای استخراج محتوای این نوع فایلها نیز هستند. بنابراین نیاز است از حالت Windows Containers به Linux Containers سوئیچ کرد. برای اینکار فقط کافی بر روی آیکن Docker در قسمت Tray Icons ویندوز کلیک راست نمود و گزینهی Switch to Linux Containers را انتخاب کرد. اکنون اگر دستور docker images را صادر کنیم، تنها لیست imageهای لینوکسی از پیش دریافت شده را میتوان مشاهده کرد.
در ادامه، image یکی از سبکترین توزیعهای لینوکسی را به نام alpine، دریافت میکنیم که فقط 5 مگابایت حجم دارد؛ چون آنچنان فایلی در user space آن وجود ندارد. به همین جهت برای دریافت آن، دستور docker pull alpine را صادر میکنیم. اکنون اگر دستور docker images را صادر کنیم، این image جدید در لیست خروجی آن قابل مشاهدهاست.
سپس چون میخواهیم یک shell را در داخل این container اجرا کنیم (مانند اجرای کنسول PowerShell قسمت قبل)، نیاز است دستور docker run آنرا با سوئیچ it اجرا کنیم:
docker run -it alpine sh
اکنون میخواهیم به فایل iis.tar ای که export کردیم از اینجا دسترسی پیدا کنیم. این فایل نیز بر روی فایل سیستم ویندوز 10 تولید شدهاست. به همین جهت نیاز است بتوان به این فایل خارج از container جاری دسترسی پیدا کرد.
روش به اشتراک گذاری فایل سیستم میزبان با کانتینرها
برای اینکه از داخل یک container به فایلی در خارج از آن دسترسی پیدا کنیم، باید درایو آن فایل خارجی را اصطلاحا mount کرد؛ دقیقا مانند اتصال یک USB Stick به سیستم و اضافه شدن آن به صورت یک درایو جدید. در Docker، اینکار توسط مفهومی به نام Volumes انجام میشود. برای این منظور بر روی آیکن Docker در قسمت Tray Icons ویندوز کلیک راست کرده و گزینهی Settings را انتخاب کنید. البته این تصویر را در حالت کار با Linux Containers مشاهده میکنید:
در اینجا درایو C را انتخاب و Apply کنید و سپس نام کاربری و کلمهی عبور ویندوز خود را وارد نمائید، تا مجوز دسترسی به این درایو، به این Container داده شود.
سپس دستور زیر را اجرا کنید:
docker run --rm -v c:/Users:/data alpine ls /data
- عبارت c:/Users:/data به این معنا است که پوشهی C:\users ویندوز را به مسیر data/ داخل container لینوکسی نگاشت کن. به همین جهت بین این دو قسمت یک : وجود دارد و مسیرهای لینوکسی فاقد نام درایو خاصی هستند.
در این دستور میتوان پوشهای خاص مانند c:/Users/Vahid:/data و یا فایلی خاص را مانند c:/Users/Vahid/iis.tar:/data نیز نگاشت کرد. مزیت آن کاهش سطح دسترسی Container به فایلهای سیستم میزبان است.
- این دستور با اجرای دستور ls، محتوای پوشهی C:\users را لیست میکند.
کار با فایلهای سیستم میزبان از داخل یک Container
در ادامه دستور فوق را به صورت زیر اجرا میکنیم که در آن فایل iis.tar میزبان، در داخل container در مسیر data/ آن قابل دسترسی شدهاست و همچنین بجای ls، دستور sh صادر شدهاست تا به shell آن دسترسی پیدا کنیم. به همین جهت نیاز به سوئیچ it نیز وجود دارد:
docker run --rm -it -v c:/Users/vahid/iis.tar:/data alpine sh
tar -tf /data/iis.tar
در اینجا حداقل هفت پوشه را مشاهده میکنید که داخل هر کدام فایلی به نام layer.tar قرار دارد؛ لایههایی که این image را ایجاد میکنند.
پس از این، اگر دستور استخراج این فایلها را صادر کنیم (t برای نمایش لیست محتویات است و x برای استخراج آنها):
mkdir /data/extract tar -xf /data/iis.tar -C /data/extract
انتقال فایلها از Container به سیستم میزبان
البته نکتهی مهم اینجا است که این پوشهی /data/extract/ صرفا داخل دیسک مجازی این container ایجاد شدهاست و در سمت ویندوز قابل دسترسی و مشاهده نیست.
برای رفع این مشکل، اینبار دستور tar -xf را به صورت زیر اجرا میکنیم:
docker run --rm -it -v c:/Users/vahid/:/data alpine tar -xf /data/iis.tar -C /data/iis
در اینجا اگر دستور tar را بر روی این لایهها اجرا کنیم، در نهایت به یک چنین خروجیهایی خواهیم رسید:
که بسیار شبیه به درایو C یک سیستم ویندوزی است. بنابراین این لایه، همان OS Apps & Libs را به همراه دارد که در قسمت قبل با آن آشنا شدیم.
یک مثال دیگر: اجرای ffmpeg توسط docker
اگر خاطرتان باشد بحث docker را در قسمت اول با معرفی ffmpeg و سخت بودن اجرای آن آغاز کردیم. در ادامه میخواهیم image آنرا دریافت و سپس با تبدیل آن به یک container، کار تبدیل فرمتهای ویدیویی را انجام دهیم:
docker run --rm --volume ${pwd}:/output jrottenberg/ffmpeg -i http://site.com/file.mp4 /output/file.gif
- سوئیچ rm کار حذف container ایجاد شده را پس از اتمام کار آن انجام میدهد.
- سپس مسیرجاری (پوشهی جاری در سیستم میزبان که دستور فوق را اجرا میکند) به مسیر output/ کانتینر نگاشت شدهاست.
- در ادامه مخزن dockerhub ای که ffmpeg قرار است از آن دریافت و اجرا شود، مشخص شدهاست.
- در آخر پارامترهای کار با ffmpeg برای دریافت یک فایل mp4 آنلاین و تبدیل آن به یک فایل animated gif محلی، ذکر شدهاند. این فایل در مسیر output کانتینر ایجاد میشود که در نهایت با میزبان، به اشتراک گذاشته خواهد شد.
- خروجی نهایی تولید شده را در سیستم میزبان در همان پوشهای که دستور فوق را صادر کردهاید، مشاهده خواهید کرد.
ایندکسهای XML ایی
ایندکسهای XML ایی، ایندکسهای خاصی هستند که بر روی ستونهایی از نوع XML تعریف میشوند. هدف از تعریف آنها، بهینه سازی اعمال مبتنی بر XQuery، بر روی دادههای این نوع ستونها است. چهار نوع XML Index قابل تعریف هستند؛ اما primary xml index باید ابتدا ایجاد شود. در این حالت جدولی که دارای ستون XML ایی است نیز باید دارای یک clustered index باشد. هدف از primary XML indexها، ارائهی تخمینهای بهتری است به بهینه ساز کوئریها در SQL Server.
جزئیات primary XML indexها
زمانیکه یک primary xml index را ایجاد میکنیم، node table یاد شده در قسمت قبل را، بر روی سخت دیسک ذخیره خواهیم کرد (بجای هربار محاسبه در زمان اجرا). متادیتای این اطلاعات ذخیره شده را در جداول سیستمی sys.indexes و sys.columns میتوان مشاهده کرد. باید دقت داشت که تهیهی این ایندکسها، فضای قابل توجهی را از سخت دیسک به خود اختصاص خواهند داد؛ چیزی حدود 2 تا 5 برابر حجم اطلاعات اولیه. بدیهی است تهیهی این ایندکسها که نتیجهی تجزیهی اطلاعات XML ایی است، بر روی سرعت insert تاثیر خواهند گذاشت. Node table دارای ستونهایی مانند نام تگ، آدرس تگ، نوع داده آن، مسیر و امثال آن است.
زمانیکه یک Primary XML Index تعریف میشود، اگر به Query Plan حاصل دقت کنید، دیگر خبری از XML Readerها مانند قبل نخواهد بود. در اینجا Clustered index seek قابل مشاهدهاست.
ایجاد primary XML indexها
همان مثال قسمت قبل را که دو جدول از آن به نامهای xmlInvoice و xmlInvoice2 ایجاد کردیم، درنظر بگیرید. اینبار یک xmlInvoice3 را با همان ساختار و همان 6 رکوردی که معرفی شدند، ایجاد میکنیم. بنابراین برای آزمایش جاری، در مثال قبل، هرجایی xmlInvoice مشاهده میکنید، آنرا به xmlInvoice3 تغییر داده و مجددا جدول مربوطه و دادههای آنرا ایجاد کنید.
اکنون برای ایجاد primary XML index بر روی ستون invoice آن میتوان نوشت:
CREATE PRIMARY XML INDEX invoice_idx ON xmlInvoice3(invoice) SELECT * FROM sys.internal_tables
در ادامه علاقمند هستیم که بدانیم داخل آن چه چیزی ذخیره شدهاست:
SELECT * FROM sys.xml_index_nodes_325576198_256000
اگر به این جدول دقت کنید، 6 ردیف اطلاعات XML ایی، به حدود 100 ردیف اطلاعات ایندکس شده، تبدیل گردیدهاست. با استفاده از دستور ذیل میتوان حجم ایندکس تهیه شده را نیز مشاهده کرد:
sp_spaceused 'xmlInvoice3'
--DROP INDEX invoice_idx ON xmlInvoice3
تاثیر primary XML indexها بر روی سرعت اجرای کوئریها
همان 10 کوئری قسمت قبل را درنظر بگیرید. اینبار برای مقایسه میتوان به نحو ذیل عمل کرد:
SELECT * FROM xmlInvoice WHERE invoice.exist('/Invoice[@InvoiceId = "1003"]') = 1 SELECT * FROM xmlInvoice3 WHERE invoice.exist('/Invoice[@InvoiceId = "1003"]') = 1
چند نکته در این تصویر حائز اهمیت است:
- Query plan کوئری انجام شده بر روی جدول دارای primary XML index، مانند قسمت قبل، حاوی XML Readerها نیست.
- هزینهی انجام کوئری بر روی جدول دارای XML ایندکس نسبت به حالت بدون ایندکس، تقریبا نزدیک به صفر است. (بهبود کارآیی فوق العاده)
اگر کوئریهای دیگر را نیز با هم مقایسه کنید، تقریبا به نتیجهی کمتر از یک سوم تا یک چهارم حالت بدون ایندکس خواهید رسید.
همچنین اگر برای حالت دارای Schema collection نیز ایندکس ایجاد کنید، اینبار کوئری پلن آن اندکی (چند درصد) بهبود خواهد یافت ولی نه آنچنان.
ایندکسهای XMLایی ثانویه یا secondary XML indexes
سه نوع ایندکس XML ایی ثانویه نیز قابل تعریف هستند:
- VALUE : کار آن بهینه سازی کوئریهای content و wildcard است.
- PATH : بهینه سازی انتخابهای مبتنی بر XPath را انجام میدهد.
- Property: برای بهینه سازی انتخاب خواص و ویژگیها بکار میرود.
این ایندکسها یک سری non-clustered indexes بر روی node tables هستند. برای ایجاد سه نوع ایندکس یاد شده به نحو ذیل میتوان عمل کرد:
CREATE XML INDEX invoice_path_idx ON xmlInvoice3(invoice) USING XML INDEX invoice_idx FOR PATH
پس از ایجاد ایندکس ثانویه بر روی مسیرها، اگر اینبار کوئری دوم را اجرا کنیم، به Query Plan ذیل خواهیم رسید:
همانطور که مشاهده میکنید، نسبت به حالت primary index، وضعیت clustered index seek به index seek تغییر کردهاست و همچنین دقیقا مشخص است که از کدام ایندکس استفاده شدهاست.
در ادامه دو نوع ایندکس دیگر را نیز ایجاد میکنیم:
CREATE XML INDEX invoice_value_idx ON xmlInvoice3(invoice) USING XML INDEX invoice_idx FOR VALUE CREATE XML INDEX invoice_prop_idx ON xmlInvoice3(invoice) USING XML INDEX invoice_idx FOR PROPERTY
سؤال: اکنون پس از تعریف 4 ایندکس یاد شده، کوئری دوم از کدام ایندکس استفاده خواهد کرد؟
در اینجا مجددا کوئری دوم را اجرا کرده و به قسمت Query Plan آن دقت خواهیم کرد:
برای مشاهده دقیق نام ایندکس مورد استفاده، کرسر ماوس را بر روی index seek قرار میدهیم. در اینجا اگر به قسمت object گزارش ارائه شده دقت کنیم، نام invoice_value_idx یا همان value index ایجاد شده، قابل مشاهدهاست؛ به این معنا که در کوئری دوم، اهمیت مقادیر بیشتر است از اهمیت مسیرها.
کوئریهایی مانند کوئری ذیل از property index استفاده میکنند:
SELECT * FROM xmlInvoice3 WHERE invoice.exist('/Invoice//CustomerName[text() = "Vahid"]') = 1
SELECT * FROM xmlInvoice3 WHERE invoice.exist('/Invoice//CustomerName[. = "Vahid"]') = 1
خلاصه نکات بهبود کارآیی برنامههای مبتنی بر فیلدهای XML
- در حین استفاده از XPath، ذکر محور parent یا استفاده از .. (دو دات)، سبب ایجاد مراحل اضافهای در Query Plan میشوند. تا حد امکان از آن اجتناب کنید و یا از روشهایی مانند cross apply و xml.nodes برای مدیریت اینگونه موارد تو در تو استفاده نمائید.
- ordinals را به انتهای Path منتقل کنید (مانند ذکر [1] جهت مشخص سازی نودی خاص).
- از ذکر predicates در وسط یک Path اجتناب کنید.
- اگر اسناد شما fragment با چند root elements نیستند، بهتر است document بودن آنها را در حین ایجاد ستون XML مشخص کنید.
- xml.value را به xml.query ترجیح دهید.
- عملیات casting در XQuery سنگین بوده و استفاده از ایندکسها را غیرممکن میکند. در اینجا استفاده از اسکیما میتواند مفید باشد.
- نوشتن sub queryها بهتر هستند از چندین XQuery در یک عبارت SQL.
- در ترکیب اطلاعات رابطهای و XML، استفاده از متدهای xml.exist و sql:column نسبت به xml.value جهت استخراج و مقایسه اطلاعات، بهتر هستند.
- اگر قصد تهیه خروجی XML از جدولی رابطهای را دارید، روش select for xml کارآیی بهتری را نسبت به روش FLOWR دارد. روش FLOWR برای کار با اسناد XML موجود طراحی و بهینه شدهاست؛ اما روش select for xml در اصل برای کار با اطلاعات رابطهای بهینه سازی گردیدهاست.
کتاب رایگان LINQPad Succinctly
LINQPad Succinctly offers IT professionals a detailed examination of how and why LINQPad can improve development lifecycle and deliver applications in less time. Author José Roberto Olivas Mendoza begins with a detailed overview of LINQPad's features, then delves into the installation process, including necessary prerequisites. Readers then get instruction on how to get the most out of LINQPad, such as how to query data bases and using LINQPad as a code scratchpad, which allows users to save significant time and effort on application delivery.
- Introduction
- Installing LINQPad
- Beginning with LINQPad
- LINQPad Basics
- Querying Databases with LINQ-to-SQL
- LINQPad as a Code Scratchpad
- General Summary
- General Conclusions about LINQPad
- Appendix
اسکیوال سرور ۲۰۱۹ نسخه نهایی ریلیز شد
15.0.2070.41 | 2019.150.2070.41 | 4517790 Servicing Update (GDR1) for SQL Server 2019 RTM | 2019-11-04 *new |
15.0.2000.5 | 2019.150.2000.5 | Microsoft SQL Server 2019 RTM RTM | 2019-11-04 |
کتاب رایگان ساخت Mobile Websites با MVC4
علت چیست؟ پرداختن بیش از حد به وارز شما را از تولید محتوا دور میکند و صرفا تبدیل خواهید شد به یک مصرف کننده ساده نهایی.
هنر این است که مثلا از محصولات تلریک استفاده میکنید؟ آیا میتونید در مورد نحوه طراحی API اون نصف صفحه مطلب بنویسید؟ یا اینکه نه، فقط یک مصرف کننده جزء هستید که به دنبال کرک و برنامه مفت.
آیا میتونید از 10 تا کتاب سی شارپی که در مورد پردازش موازی دانلود کردید 5 تا مقاله دربیارید؟
از 100 گیگ فیلم آموزشی که دانلود کردید 10 تا مطلب منتشر کنید؟
هدف کلی این سایت هم همین است. آیا میتونید محتوا تولید کنید؟ یا اینکه فقط کوش، فقط میخوام، فقط نیست. فقط زود باش.
پ.ن.
مادر تمام سایتهای وارز مرتبط با برنامه نویسی، سایتی است با آدرس «board4allcz.eu». اگر کمی دقت کنید، تعداد ایرانیهای فعال در آن هم بسیار زیاد است! ولی واقعا ضرورتی نداره کار یک سایت دیگر رو ما اینجا تکرار کنیم.
Vue.js 3.0 منتشر شد
Today we are proud to announce the official release of Vue.js 3.0 "One Piece". This new major version of the framework provides improved performance, smaller bundle sizes, better TypeScript integration, new APIs for tackling large scale use cases, and a solid foundation for long-term future iterations of the framework.
IdentityServer4 v2 منتشر شد
Wow – this was probably our biggest update ever! Version 2.0 of IdentityServer4 is not only incorporating all the feedback we got over the last year, it also includes the necessary updates for ASP.NET Core 2 – and also has a couple of brand new features. See the release notes for a complete list as well as links to issues and PRs.
لیست جدید کتابهای رایگان Microsoft
Largest FREE Microsoft eBook Giveaway! I’m Giving Away MILLIONS of FREE Microsoft eBooks again, including: Windows 10, Office 365, Office 2016, Power BI, Azure, Windows 8.1, Office 2013, SharePoint 2016, SharePoint 2013, Dynamics CRM, PowerShell, Exchange Server, System Center, Cloud, SQL Server and more!