ارتقاء به ASP.NET Core 1.0 - قسمت 22 - توزیع برنامه توسط IIS
اندازه‌ی قلم متن
تخمین مدت زمان مطالعه‌ی مطلب: ده دقیقه

روش کار برنامه‌های ASP.NET Core در IIS کاملا متفاوت است با تمام نگارش‌های پیشین ASP.NET؛ از این جهت که برنامه‌های ASP.NET Core در اصل یک برنامه‌ی متکی به خود از نوع Console می‌باشند. به همین جهت برای هاست شدن نیازی به IIS ندارند. این نوع برنامه‌ها به همراه یک self-hosted Web server ارائه می‌شوند (به نام Kestrel) و این وب سرور توکار است که تمام درخواست‌های رسیده را دریافت و پردازش می‌کند. هرچند در اینجا می‌توان از IIS صرفا به عنوان یک «front end proxy» استفاده کرد؛ از این جهت که Kestrel تنها یک وب سرور خام است و تمام امکانات و افزونه‌های مختلف IIS را شامل نمی‌شود.
بر روی ماشین‌های ویندوزی و ویندوزهای سرور، استفاده‌ی از IIS به عنوان پروکسی درخواست‌ها و ارسال آن‌ها به Kestrel، روش توصیه شده‌است؛ از این جهت که حداقل قابلیت‌هایی مانند «port 80/443 forwarding»، مدیریت طول عمر برنامه، مدیریت مجوزهای SLL آن و خیلی از موارد دیگر توسط Kestrel پشتیبانی نمی‌شود.


معماری پردازش نگارش‌های پیشین ASP.NET در IIS


در نگارش‌های پیشین ASP.NET، همه چیز داخل پروسه‌‌ای به نام w3wp.exe و یا IIS Worker Process پردازش می‌شود که در اصل چیزی نیست بجز همان IIS Application Pool. این AppPoolها، برنامه‌های ASP.NET شما را هاست می‌کنند و همچنین سبب وهله سازی و اجرای آن‌ها نیز خواهند شد.
در اینجا درایور http.sys ویندوز، درخواست‌های رسیده را دریافت کرده و سپس آن‌ها را به سمت سایت‌هایی نگاشت شده‌ی به AppPoolهای مشخص، هدایت می‌کند.


معماری پردازش برنامه‌های ASP.NET Core در IIS

روش اجرای برنامه‌های ASP.NET Core با نگارش‌های پیشین آن‌ها کاملا متفاوت هستند؛ از این جهت که داخل پروسه‌ی w3wp.exe اجرا نمی‌شوند. این برنامه‌ها در یک پروسه‌ی مجزای کنسول خارج از پروسه‌ی w3wp.exe اجرا می‌شوند و حاوی وب سرور توکاری به نام کسترل (Kestrel) هستند.


 این وب سرور، وب سروری است تماما دات نتی و به شدت برای پردازش تعداد بالای درخواست‌ها بهینه سازی شده‌است؛ تا جایی که کارآیی آن در این یک مورد چند 10 برابر IIS است. هرچند این وب سرور فوق العاده سریع است، اما «تنها» یک وب سرور خام است و به همراه سرویس‌های مدیریت وب، مانند IIS نیست.


در تصویر فوق مفهوم «پروکسی» بودن IIS را در حین پردازش برنامه‌های ASP.NET Core بهتر می‌توان درک کرد. ابتدا درخواست‌های رسیده به IIS می‌رسند و سپس IIS آن‌ها را به طرف Kestrel هدایت می‌کند.
برنامه‌های ASP.NET Core، برنامه‌های کنسول متکی به خودی هستند که توسط دستور خط فرمان dotnet اجرا می‌شوند. این اجرا توسط ماژولی ویژه به نام AspNetCoreModule در IIS انجام می‌شود.


همانطور که در تصویر نیز مشخص است، AspNetCoreModule یک ماژول بومی IIS است و هنوز برای اجرا نیاز به IIS Application Pool دارد؛ با این تفاوت که در تنظیم AppPoolهای برنامه‌های ASP.NET Core، باید NET CLR Version. را به No managed code تنظیم کرد.


اینکار از این جهت صورت می‌گیرد که IIS در اینجا تنها نقش یک پروکسی هدایت درخواست‌ها را به پروسه‌ی برنامه‌ی حاوی وب سرور Kestrel، دارد و کار آن وهله سازی NET Runtime. نیست. کار AspNetCoreModule این است که با اولین درخواست رسیده‌ی به برنامه‌ی شما، آن‌را بارگذاری کند. سپس درخواست‌های رسیده را دریافت و به سمت برنامه‌ی ASP.NET Core شما هدایت می‌کند (به این عملیات reverse proxy هم می‌گویند).


اگر دقت کرده باشید، برنامه‌های ASP.NET Core، هنوز دارای فایل web.config ایی با محتوای ذیل هستند:
<?xml version="1.0" encoding="utf-8"?>
<configuration>
  <system.webServer>
    <handlers>
      <add name="aspNetCore" path="*" verb="*"
           modules="AspNetCoreModule" resourceType="Unspecified"/>
    </handlers>
    <aspNetCore processPath="%LAUNCHER_PATH%"
                arguments="%LAUNCHER_ARGS%" stdoutLogEnabled="false"
                stdoutLogFile=".\logs\stdout" forwardWindowsAuthToken="false"/>
  </system.webServer>
</configuration>
توسط این تنظیمات است که AspNetCoreModule فایل‌های dll برنامه‌ی شما را یافته و سپس برنامه را به عنوان یک برنامه‌ی کنسول بارگذاری می‌کند (با توجه به اینکه حاوی کلاس Program و متد Main هستند).
یک نکته: در زمان publish برنامه، تنظیم و تبدیل مقادیر LAUNCHER_PATH و LAUNCHER_ARGS به معادل‌های اصلی آن‌ها صورت می‌گیرد (در ادامه مطلب بحث خواهد شد).


آیا واقعا هنوز نیازی به استفاده‌ی از IIS وجود دارد؟

هرچند می‌توان Kestrel را توسط یک IP و پورت مشخص، عمومی کرد و استفاده نمود، اما حداقل در ویندوز چنین توصیه‌ای نمی‌شود و بهتر است از IIS به عنوان یک front end proxy استفاده کرد؛ به این دلایل:
- اگر می‌خواهید چندین برنامه را بر روی یک وب سرور که از طریق پورت‌های 80 و 443 ارائه می‌شوند داشته باشید، نمی‌توانید از Kestrel  به صورت مستقیم استفاده کنید؛ زیرا از مفهوم host header routing که قابلیت ارائه‌ی چندین برنامه را از طریق پورت 80 و توسط یک IP میسر می‌کند، پشتیبانی نمی‌کند. برای اینکار نیاز به IIS و یا در حقیقت درایور http.sys ویندوز است.
- IIS خدمات قابل توجهی را به برنامه‌ی شما ارائه می‌کند. برای مثال با اولین درخواست رسیده، به صورت خودکار آن‌را اجرا و بارگذاری می‌کند؛ به همراه تمام مدیریت‌های پروسه‌ای که در اختیار برنامه‌های ASP.NET در طی سالیان سال قرار داشته‌است. برای مثال اگر پروسه‌ی برنامه‌ی شما در اثر استثنایی کرش کرد، دوباره با درخواست بعدی رسیده، حتما برنامه را بارگذاری و آماده‌ی خدمات دهی مجدد می‌کند.
- در اینجا می‌توان تنظیمات SSL را بر روی IIS انجام داد و سپس درخواست‌های معمولی را به Kestrel  ارسال کرد. به این ترتیب با یک مجوز می‌توان چندین برنامه‌ی Kestrel را مدیریت کرد.
- IISهای جدید به همراه ماژول‌های بومی بسیار بهینه و کم مصرفی برای مواردی مانند gzip compression of static content, static file caching, Url Rewriting هستند که با فعال سازی آن‌ها می‌توان از این قابلیت‌ها، در برنامه‌های ASP.NET Core نیز استفاده کرد.


نحوه‌ی توزیع برنامه‌های ASP.NET Core به IIS

روش اول: استفاده از دستور خط فرمان dotnet publish

برای این منظور به ریشه‌ی پروژه‌ی خود وارد شده و دستور dotnet publish را با توجه به پارامترهای ذیل اجرا کنید:
 dotnet publish --framework netcoreapp1.0 --output "c:\temp\mysite" --configuration Release
در اینجا برنامه کامپایل شده و همچنین مراحلی که در فایل project.json نیز ذکر شده‌اند، اعمال می‌شود. برای مثال در اینجا پوشه‌ها و فایل‌هایی که در قسمت include ذکر شده‌اند به خروجی کپی خواهند شد. همچین در قسمت scripts تمام مراحل ذکر شده مانند یکی کردن و فشرده سازی اسکریپت‌ها نیز انجام خواهد شد. قسمت postpublish تنها کاری را که انجام می‌دهد، ویرایش فایل web.config برنامه و تنظیم LAUNCHER_PATH و LAUNCHER_ARGS آن به مقادیر واقعی آن‌ها است.
{

    "publishOptions": {
        "include": [
            "wwwroot",
            "Features",
            "appsettings.json",
            "web.config"
        ]
    },
 
    "scripts": {
        "precompile": [
            "dotnet bundle"
        ],
        "prepublish": [
            //"bower install"
        ],
        "postpublish": [ "dotnet publish-iis --publish-folder %publish:OutputPath% --framework %publish:FullTargetFramework%" ]
    }
}
و در نهایت اگر به پوشه‌ی output ذکر شده‌ی در فرمان فوق مراجعه کنید، این خروجی نهایی است که باید به صورت دستی به وب سرور خود برای اجرا انتقال دهید که به همراه تمام DLLهای مورد نیاز برای برنامه نیز هست.


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


برنامه‌های ASP.NET Core باید به AppPool ایی تنظیم شوند که NET CLR Version. آن‌ها No Managed Code است. همچنین بهتر است به ازای هر برنامه‌ی جدید یک AppPool مجزا را ایجاد کنید تا کرش یک برنامه تاثیر منفی را بر روی برنامه‌ی دیگری نگذارد.

روش دوم: استفاده از ابزار Publish خود ویژوال استودیو

اگر علاقمند هستید که روش خط فرمان فوق را توسط ابزار publish ویژوال استودیو انجام دهید، بر روی پروژه در solution explorer کلیک راست کرده و گزینه‌ی publish را انتخاب کنید. در صفحه‌ای که باز می‌شود، بر روی گزینه‌ی custom کلیک کرده و نامی را وارد کنید. از این نام پروفایل، جهت ساده سازی مراحل publish، در دفعات آتی فراخوانی آن استفاده می‌شود.


در صفحه‌ی بعدی اگر گزینه‌ی file system را انتخاب کنید، دقیقا همان مراحل روش اول تکرار می‌شوند:


سپس می‌توانید فریم ورک برنامه و نوع ارائه را مشخص کنید:


و در آخر کار، Publish به این پوشه‌ی مشخص شده که به صورت پیش فرض در ذیل پوشه‌ی bin برنامه‌است، صورت می‌گیرد.


روش عیب یابی راه اندازی اولیه‌ی برنامه‌های ASP.NET Core

در اولین سعی در اجرای برنامه‌ی ASP.NET Core بر روی IIS به این خطا رسیدم:


در event viewer ویندوز چیزی ثبت نشده بود. اولین کاری را که در این موارد می‌توان انجام داد به این صورت است. از طریق خط فرمان به پوشه‌ی publish برنامه وارد شوید (همان پوشه‌ای که توسط IIS عمومی شده‌است). سپس دستور dotnet prog.dll را صادر کنید. در اینجا prog.dll نام dll اصلی برنامه یا همان نام پروژه است:


همانطور که مشاهده می‌کنید، برنامه به دنبال پوشه‌ی bower_components ایی می‌گردد که کار publish آن انجام نشده‌است (این پوشه در تنظیمات آغازین برنامه عمومی شده‌است و در لیست include قسمت publishOptions فایل project.json فراموش شده‌است).

روش دوم، فعال سازی stdoutLogEnabled موجود در فایل وب کانفیگ، به true است. در اینجا web.config نهایی تولیدی توسط عملیات publish را مشاهده می‌کنید که در آن پارامترهای  processPath و arguments مقدار دهی شده‌اند (همان قسمت postpublish فایل project.json). در اینجا مقدار stdoutLogEnabled به صورت پیش فرض false است. اگر true شود، همان خروجی تصویر فوق را در پوشه‌ی logs خواهید یافت:

<?xml version="1.0" encoding="utf-8"?>
<configuration>
  <system.webServer>
    <handlers>
      <add name="aspNetCore" path="*" verb="*" modules="AspNetCoreModule" resourceType="Unspecified" />
    </handlers>
    <aspNetCore processPath="dotnet" arguments=".\Core1RtmEmptyTest.dll" stdoutLogEnabled="true" stdoutLogFile=".\logs\stdout" forwardWindowsAuthToken="false" />
  </system.webServer>
</configuration>
البته اگر کاربر منتسب به AppPool برنامه، دسترسی نوشتن در این پوشه را نداشته باشد، خطای ذیل را در event viewer ویندوز مشاهده خواهید کرد:
 Warning: Could not create stdoutLogFile \\?\D:\Prog\1395\Core1RtmEmptyTest\src\Core1RtmEmptyTest\bin\Release\PublishOutput\logs\stdout_10064_201672893654.log, ErrorCode = -2147024893.
همچنین پوشه‌ی logs را هم باید خودتان از پیش ایجاد کنید. به عبارتی کاربر منتسب به AppPool برنامه باید دسترسی نوشتن در پوشه‌ی logs واقع در ریشه‌ی برنامه را داشته باشد. این کاربر  IIS AppPool\DefaultAppPool نام دارد.



حداقل‌های یک هاست ویندوزی که می‌خواهد برنامه‌های ASP.NET Core را ارائه دهد

پس از نصب IIS، نیاز است ASP.NET Core Module نیز نصب گردد. برای این‌کار اگر بسته‌ی NET Core Windows Server Hosting. را نصب کنید، کافی است:
https://go.microsoft.com/fwlink/?LinkId=817246

این بسته به همراه NET Core Runtime, .NET Core Library. و ASP.NET Core Module است. همچنین همانطور که عنوان شد، برنامه‌های ASP.NET Core باید به AppPool ایی تنظیم شوند که NET CLR Version. آن‌ها No Managed Code است. این‌ها حداقل‌های راه اندازی یک برنامه‌ی ASP.NET Core بر روی سرورهای ویندوزی هستند.


هنوز فایل app_offline.htm نیز در اینجا معتبر است

یکی از خواص ASP.NET Core Module، پردازش فایل خاصی است به نام app_offline.htm. اگر این فایل را در ریشه‌ی سایت قرار دهید، برنامه پردازش تمام درخواست‌های رسیده را قطع خواهد کرد و سپس پروسه‌ی برنامه خاتمه می‌یابد. هر زمانیکه این فایل حذف شد، مجددا با درخواست بعدی رسیده، برنامه آماده‌ی پاسخگویی می‌شود.
    • #
      ‫۷ سال و ۱۱ ماه قبل، چهارشنبه ۱۴ مهر ۱۳۹۵، ساعت ۱۰:۱۷
      بازخوردها و خطاها پس از نصب :
      بنده سرور مجازی 2008 رو مورد آزمایش قرار دادم :
      با خطای 502.5 مواجه شدم


      که طبق نکاتی که در لینک پایین تصویر وجود داشت :

      Hosting bundle not installed or server not restarted

      • Browser: 502.3 Bad Gateway: There was a connection error while trying to route the request.
      • Application Log: Process ‘0’ failed to start. Port = PORT, Error Code = ‘-2147024894’.
      • ASP.NET Core Module Log: Log file created but empty 

      و تغییری که در فایل webconfig جهت log کردن انجام دادم مورد زیر از توضیحات بالا مشاهده شد :
      ASP.NET Core Module Log: Log file created but empty

      که پس از Restart ویندوز سرور - مشکل خالی بودن فایل‌های لاگ برطرف شد و اینبار در فایل‌های لاگ با متن خطای زیر مواجه شدم:
       Failed to load the dll from [C:\Program Files\dotnet\host\fxr\1.0.1\hostfxr.dll], HRESULT: 0x80070057

      در حال حاضر در صدد رفع این مشکل هستم.
      • #
        ‫۷ سال و ۱۱ ماه قبل، چهارشنبه ۱۴ مهر ۱۳۹۵، ساعت ۱۲:۰۶
        - زمانیکه یک DLL قابل بارگذاری نیست یعنی یکسری از وابستگی‌های آن نصب نشدند. این لیست را هم باید نصب کنید:
        Windows dependencies 
        - وابستگی ویندوز سرور آن علاوه بر نصب NET Core.، نصب Visual C++ Redistributable for Visual Studio 2015 است. بسته‌ای را که در اینجا لینک دادند، قدیمی است. آدرس بسته‌ی به روز و جدید آن (با شماره نگارش 14.0.24215 ^) 
        • #
          ‫۶ سال و ۷ ماه قبل، شنبه ۱۴ بهمن ۱۳۹۶، ساعت ۲۰:۴۳
          موقعی که از آدرس دامنه رو میزنم چنین خطایی میگیرم و موارد گفته شده نصب هست و نتیجه فایل stdlog خالی هست همچنین نتیجه اجرا از طریق کامند و دستور dotnet  x.dll  روی سرور مشکلی نداره و روی پورت 5000 باز میشه.
          ولی Event Viewer خطای زیر رو میده که نمیتونه دستور رو اجرا کنه
          Application 'MACHINE/WEBROOT/APPHOST/BWIN.PLUSTEAM.IR' with physical root 'C:\Inetpub\vhosts\plusteam.ir\bwin.plusteam.ir\' failed to start process with commandline 'dotnet .\BetWin.dll', ErrorCode = '0x80070002 : 0.
      • #
        ‫۷ سال و ۱۰ ماه قبل، شنبه ۶ آذر ۱۳۹۵، ساعت ۱۵:۰۰
        من هم همین مشکل را داشتم و ثبت log هم انجام نمی‌شد،که با افزودن SERVICE با دسترسی Full control به پوشه publish مورد نظر، از طریق Tab Security مشکل برطرف شد و ثبت log هم انجام شد.


  • #
    ‫۷ سال و ۶ ماه قبل، دوشنبه ۷ فروردین ۱۳۹۶، ساعت ۰۱:۰۸
    به روز رسانی
    با حذف فایل project.json در VS 2017، اکنون با کلیک راست بر روی گروه نام پروژه (فایل csproj)، گزینه‌ی Edit آن ظاهر شده و مداخل ذکر شده‌ی در مطلب فوق، چنین تعاریفی را پیدا می‌کنند:
    <Project Sdk="Microsoft.NET.Sdk.Web">
       <PropertyGroup>
          <TargetFramework>netcoreapp1.1</TargetFramework>
       </PropertyGroup>
    </Project>
    به فرامین dotnet publish-iis  هم نیازی نیست و Sdk.Web کار مدیریت آن‌ها را انجام می‌دهد.
  • #
    ‫۶ سال و ۱۲ ماه قبل، دوشنبه ۳ مهر ۱۳۹۶، ساعت ۲۰:۰۰
    آیا راهکاری برای اجرا و تست برنامه در زمان توسعه بر روی Local IIS، بدون توزیع، توسط دیگر سیستم‌ها (کاربران دیگر) وجود دارد؟ به بیان دیگر آیا از طریق Local IIS می‌توان برنامه را همانند برنامه‌های Web Forms, MVC، دیباگ کرد و با اجرای برنامه در Visual Studio، یک آدرس share شده در Local IIS، در مرورگر اجرا شده و به برنامه اشاره کند؟ 
    یا اینکه حتما باید توزیع برنامه انجام شود تا بتوان آنرا از طریق Local IIS در اختیار دیگر کاربران قرار داد؟
    • #
      ‫۶ سال و ۱۲ ماه قبل، دوشنبه ۳ مهر ۱۳۹۶، ساعت ۲۲:۴۲
      راه‌کاری وجود ندارد؛ از این جهت که پوشه‌ی توسعه‌ی برنامه‌های ASP.NET Core به همراه تمام فایل‌های لازم برای ارائه‌ی توسط IIS نیست. به همین جهت publish آن ضروری است. ضمن اینکه همانطور که در متن توضیح داده شد، برنامه‌های ASP.NET Core اصلا وابستگی به IIS ندارند و در پروسه‌ی IIS اجرا نمی‌شوند. این برنامه‌ها در پروسه‌ی کنسول مجزایی که توسط Kestrel web server ارائه می‌شود، توسط IIS در معرض دید عموم قرار می‌گیرند. بنابراین اگر قصد توزیع محلی آن‌را دارید، فرمان dotnet run را در ریشه‌ی پروژه اجرا کنید تا برنامه بر روی پورت 5000 در اختیار عموم قرار گیرد. یا dotnet watch run را اجرا کنید تا اگر در همان لحظه تغییری را اعمال کردید، به صورت خودکار برنامه مجددا کامپایل و ارائه شود. البته این مورد نیاز به تنظیمات Microsoft.DotNet.Watcher.Tools را در فایل csproj برنامه دارد. این روش (استفاده از NET Core CLI.) برای آزمایش این نوع برنامه‌ها، روش پیش‌فرض هست.
    • #
      ‫۶ سال و ۴ ماه قبل، یکشنبه ۹ اردیبهشت ۱۳۹۷، ساعت ۱۹:۰۵
      با توجه به این مطلب با فعالسازی Development time IIS support  در نصاب Visual Studio و انجام تنظیمات در Solution > Properties > Debug امکان اجرا و تست برنامه‌های مبتنی بر Asp.Net Core در هنگام توسعه بر روی IIS و دسترسی به آن از طریق دیگر کلاینت‌ها با آدرس تعریف شده وجود دارد:

      که معادل است با استفاده از فایل launchSettings.json با تنظیمات زیر:

      {
          "iisSettings": {
              "windowsAuthentication": false,
              "anonymousAuthentication": true,
              "iis": {
                  "applicationUrl": "http://localhost/WebApplication2",
                  "sslPort": 0
              }
          },
          "profiles": {
              "IIS": {
                  "commandName": "IIS",
                  "launchBrowser": "true",
                  "launchUrl": "http://localhost/WebApplication2",
                  "environmentVariables": {
                      "ASPNETCORE_ENVIRONMENT": "Development"
                  }
              }
          }
      }


  • #
    ‫۶ سال و ۷ ماه قبل، شنبه ۱۴ بهمن ۱۳۹۶، ساعت ۱۲:۳۰
    بهبود کارآیی برنامه‌های ASP.NET Core 2.1 هاست شده‌ی در IIS

    تا پیش از نگارش 2.1، تمام درخواست‌های رسیده‌ی به IIS توسط یک پروکسی معکوس به نام ASP.NET Core Module به Kestrel ارسال می‌شدند:


    در نگارش 2.1، می‌توان کل برنامه را داخل IIS worker process یا همان w3wp.exe هاست کرد تا تاثیر منفی این پروکسی معکوس حذف شود. با بررسی‌های انجام شده، این روش بهبود کارآیی بیش از 4 برابری را به همراه دارد؛ نسبت به حالت out-of-process فعلی (تصویر فوق).
    برای فعالسازی آن یا فایل web.config را به صورت ذیل جهت تعیین hostingModel ویرایش کنید:
     <aspNetCore processPath="%LAUNCHER_PATH%" arguments="%LAUNCHER_ARGS%" hostingModel="inprocess" />
    و یا فایل csproj برنامه را به صورت زیر تنظیم نمائید:
     <PropertyGroup>
        <AspNetCoreModuleHostingModel>inprocess</AspNetCoreModuleHostingModel>
    </PropertyGroup>
    
      • #
        ‫۵ سال و ۷ ماه قبل، شنبه ۲۷ بهمن ۱۳۹۷، ساعت ۱۲:۴۴
        یک نکته‌ی تکمیلی: برای فعالسازی IIS InProcess hosting در ASP.NET Core 2.2
         
        ابتدا باید TargetFramework متناسبی را در فایل csproj انتخاب کرد:
        <TargetFramework>netcoreapp2.2</TargetFramework>
        سپس شماره نگارش را از Microsoft.AspNetCore.App حذف کنید:
        <PackageReference Include="Microsoft.AspNetCore.App"  />
        و در آخر فایل web.config به صورت زیر تغییر می‌کند:
        <configuration> 
          <system.webServer> 
            <handlers> 
             <add name="aspNetCore" path="*" verb="*" modules="AspNetCoreModuleV2" resourceType="Unspecified" /> 
            </handlers> 
            <aspNetCore processPath="dotnet" arguments=".\MyApp.dll" hostingModel="InProcess" /> 
           </system.webServer> 
        </configuration>
        که در آن AspNetCoreModuleV2 و hostingModel جدید هستند.
        • #
          ‫۳ سال و ۴ ماه قبل، یکشنبه ۲۲ فروردین ۱۴۰۰، ساعت ۱۴:۳۷
          اگر پروژه به صورت InProcess بر روی IIS اجرا شود باید از UseIIS استفاده کنیم. در Asp.Net Core 2.2
          public static IWebHostBuilder CreateWebHostBuilder(string[] args) =>
              WebHost.CreateDefaultBuilder(args)
                  .UseApplicationInsights()
                  .UseStartup<Startup>()
                  .UseIIS();
          اما اگر پروژه به صورت OutOfProcess باشد باید از UseIISIntegration استفاده کنیم.
          public static IWebHostBuilder CreateWebHostBuilder(string[] args) =>
              WebHost.CreateDefaultBuilder(args)
                  .UseApplicationInsights()
                  .UseStartup<Startup>()
                  .UseIISIntegration();

          • #
            ‫۳ سال و ۴ ماه قبل، یکشنبه ۲۲ فروردین ۱۴۰۰، ساعت ۱۶:۴۶
            - این مورد در فایل csproj هم قابل تنظیم است:
            <PropertyGroup>
              <AspNetCoreHostingModel>InProcess</AspNetCoreHostingModel>
            </PropertyGroup>
            البته از زمان ASP.NET Core 3.1 به بعد دیگر نیازی به تنظیم آن نیست و حالت پیش‌فرض است.
            - همچنین دیگر نیازی هم به ذکر UseIIS نیست؛ چون جزئی از متد CreateDefaultBuilder است.
  • #
    ‫۶ سال و ۶ ماه قبل، یکشنبه ۲۷ اسفند ۱۳۹۶، ساعت ۱۷:۴۹
    من روی سرور یک پروژه core دارم و بدون مشکل اجرا میشه ولی روی همون سرور پروژه دیگری دارم که از طریق دامنه اجرا نمیشه و خطای 500 میده. متاسفانه نه لاگی در پوشه لاگ دیدم و نه در event viewer ویندوز. همچنین وقتی ریموت میزنم  سایت از طریق دستور dotnet در ابتدای نام dll روی سرور اجرا می‌شود. در این موارد برای رسیدگی به مشکل چه کارهایی می‌شود انجام داد؟
    • #
      ‫۶ سال و ۶ ماه قبل، یکشنبه ۲۷ اسفند ۱۳۹۶، ساعت ۱۸:۰۷
      اگر جزئیات هیچ خطایی را مشاهده نمی‌کنید، به صورت زیر عمل کنید:
      - در فایل web.config، محیط کاری را به صورت موقت به حالت توسعه تنظیم کنید:
      <aspNetCore ...... > 
        <environmentVariables>
          <environmentVariable name="ASPNETCORE_ENVIRONMENT" value="Development" /> 
        </environmentVariables> 
      </aspNetCore>
      - سپس در ابتدای متد Configure فایل آغازین برنامه، تنظیم نمایش خطاهای توسعه دهندگان را قرار دهید:
      public void Configure(IApplicationBuilder app, IHostingEnvironment env) 
      {    
          if (env.IsDevelopment()) 
          {     
              app.UseDeveloperExceptionPage(); 
          }
      • #
        ‫۶ سال و ۶ ماه قبل، یکشنبه ۲۷ اسفند ۱۳۹۶، ساعت ۱۸:۱۹
        اینکار را انجام دادم ولی همچنان IIS خطای 500 رو برمیگردونه به نظرم تنظیمات IIS هست که مورد داره. حتی از طریق program.cs هم تنظیماتی رو برای حالت توسعه انجام دادم.
        در مرحله اول pool رو روی no managed Code تنظیم کردم و سپس Identity را روی ApplicationPoolIdentity تنظیم نمودم.
        • #
          ‫۶ سال و ۶ ماه قبل، یکشنبه ۲۷ اسفند ۱۳۹۶، ساعت ۱۸:۳۸
          این 2 خط رو هم به BuildWebHost در Program.cs  اضافه کنید و سپس تست کنید:
            public static IWebHost BuildWebHost(string[] args) =>
                      WebHost.CreateDefaultBuilder(args)
                       ...
                          .CaptureStartupErrors(true)
                          .UseSetting("detailedErrors", "true")
                        ...
                          .Build();

        • #
          ‫۶ سال و ۶ ماه قبل، یکشنبه ۲۷ اسفند ۱۳۹۶، ساعت ۱۸:۳۸
          - آیا این application pool به برنامه نسبت داده شده‌است؟
          - آیا خطای 500 خالی هست یا 500 به همراه یک شماره؟
          • #
            ‫۶ سال و ۶ ماه قبل، یکشنبه ۲۷ اسفند ۱۳۹۶، ساعت ۱۸:۵۱
            خیر فقط از طریق IIS به پول نسبت دادم.
            نه خالی است و شماره ای ندارد.
            موقعی که پول را نسبت نداده باشم 502.5 را دریافت میکنم.
            پی نوشت: سیستم را به پولی که سایت قبلی روی آن بدون مشکل کار میکرد انتقال دادم و بدون مشکل اجرا شد. مشخصا مشکل از پول ایجاد شده است.
            • #
              ‫۶ سال و ۶ ماه قبل، یکشنبه ۲۷ اسفند ۱۳۹۶، ساعت ۲۲:۲۴
              در مورد خالی بودن فایل لاگ گزینه stdoutLogFile
              <aspNetCore stdoutLogEnabled="true" stdoutLogFile=".\logs\stdout" />
              - اگر این مورد به مسیر logs\stdout\. تنظیم شده‌است، باید پوشه‌ی logs را در ریشه‌ی پروژه به صورت دستی ایجاد کنید؛ و گرنه IIS آن‌را به صورت خودکار ایجاد نخواهد کرد.
              - کاربر App Pool برنامه (با نام پیش‌فرض «
              IIS AppPool\DefaultAppPool») باید دسترسی نوشتن در این پوشه را داشته باشد؛ وگرنه فایل لاگی در آن ایجاد نخواهد شد.
              - همچنین اگر با رعایت تمام این موارد، محتوای این فایل تولید شده باز هم خالی بود، یکبار IIS را ری‌استارت کنید. ممکن است IIS کار نوشتن در فایل لاگ را تمام نکرده باشد و با این کار مجبور به تکمیل و بستن فایل می‌شود.
    • #
      ‫۶ سال و ۶ ماه قبل، دوشنبه ۲۸ اسفند ۱۳۹۶، ساعت ۰۳:۵۴
      مشکل برطرف شد. با قرار دادن Identity بر روی Local System سایت بالا آمد و متوجه شدم مشکل از مجوزهای داخلی پول هست. به همین دلیل مجددا تنظیم رو روی Application Pool Identity گذاشتم و اینبار مجوز Service را به دایرکتوری دامنه دادم که قبلا تنها به دایرکتوری logs داده بودم. مشکل برطرف شد. سوال اینجاست که تفاوت مجوز‌های Local system و Application Pool Identity تا چه حد متفاوت است و Local System میتواند مشکلات امنیتی داشته باشد یا خیر؟
      • #
        ‫۶ سال و ۶ ماه قبل، دوشنبه ۲۸ اسفند ۱۳۹۶، ساعت ۰۴:۵۳
        مطلقا نباید از Local System استفاده کنید. در این حالت کاربر وارد شده‌ی به سایت توسط برنامه‌ی وب جاری، دسترسی مدیریتی بر روی سیستم عامل جاری را پیدا می‌کند و اگر باگی در برنامه پیدا شود، قادر به اعمال هر نوع تغییری بر روی کل سیستم عامل خواهد بود.
  • #
    ‫۶ سال و ۲ ماه قبل، پنجشنبه ۱۴ تیر ۱۳۹۷، ساعت ۲۰:۲۰
    آیا می‌توان یک برنامه‌ی ASP.NET Core را به صورت Virtual Directory درون یک برنامه‌ی ASP.NET Core دیگر میزبانی کرد؟ در اینحالت سیستم مسیریابی درون Child با Parent تداخل ایجاد نمی‌کند؟
    • #
      ‫۶ سال و ۲ ماه قبل، جمعه ۱۵ تیر ۱۳۹۷، ساعت ۰۱:۰۴
      خیر. نمی‌توان. چندین Application جدید در IIS می‌توانند از یک App Pool استفاده کنند. اما به Virtual Directory نمی‌توان App Pool ایی را نسبت داد و بیشتر برای ارائه‌ی محتوای استاتیک از آن استفاده می‌شود.
  • #
    ‫۵ سال و ۱۰ ماه قبل، یکشنبه ۲۰ آبان ۱۳۹۷، ساعت ۱۴:۴۹
    فایل‌های خروجی publish برنامه بصورت زیر درآمده

    تا قبل از این اتفاق همیشه 76 فایل بود. 
    ولی الان به 256 فایل رسیده.
    فولدرهایی با نام (de, es, fr, it, ja, ko, ru, zh-Hans, zh-Hant) اضافه شده. 
    مشخصا بیشتر شدن تعداد فایل‌های بدلیل اضافه شدن dll یا پکیج‌های ناگت و... است، منتها چیزی به پروژه اضافه نشده است.
    ASP.NET Core 2.0, DNT.Identity
    • #
      ‫۵ سال و ۱۰ ماه قبل، یکشنبه ۲۰ آبان ۱۳۹۷، ساعت ۱۵:۲۱
      علت اینجا است که وابستگی‌های مورد استفاده‌ی قسمت‌های مختلف solution شما، از نگارش‌های مختلفی از بسته‌ی Microsoft.AspNetCore.App، استفاده می‌کنند. به همین جهت لیست بسته‌های پایه‌ای مانند *.Microsoft.AspNetCore را هم مشاهده می‌کنید که نباید حضور داشته باشند (چون توسط run-time store تامین می‌شوند؛ اگر ... تمام وابستگی‌های شما یک دست باشند). بنابراین اگر نکته‌ی «روش صحیح به روز رسانی وابستگی‌های پروژه‌های NET Core.» را رعایت کنید، خروجی DNT Identity فعلی، که مبتنی بر آخرین نگارش SDK موجود است، 41 فایل بیشتر ندارد:

  • #
    ‫۵ سال و ۱ ماه قبل، جمعه ۲۵ مرداد ۱۳۹۸، ساعت ۱۴:۲۷
    ارتقاء به ASP.NET Core 3.0

    اگر در تنظیمات web.config خود، سطر زیر را در مورد تنظیم AspNetCoreModule دارید:
    <add name="aspNetCore" path="*" verb="*" modules="AspNetCoreModule" resourceType="Unspecified" />
    و یا در تنظیمات فایل csproj خود، ماژول نگارش 1 درج شده‌است:
    <AspNetCoreModuleName>AspNetCoreModule</AspNetCoreModuleName>
    برنامه‌ی شما اجرا نخواهد شد. ماژول نگارش 1 از بسته‌ی هاستینگ برنامه‌های ASP.NET Core 3.0 حذف شده‌است و باید از نگارش 2 استفاده کنید:
    <add name="aspNetCore" path="*" verb="*" modules="AspNetCoreModuleV2" resourceType="Unspecified"/>
  • #
    ‫۴ سال و ۹ ماه قبل، جمعه ۱۵ آذر ۱۳۹۸، ساعت ۲۰:۲۸
    برای دیتابیس چه کاری انجام میدید؟ یعنی برنامه ای که با EF6 نوشته شده بود میتونست خودش بانک اطلاعات ایجاد کنه. حالا dotnet core چه جایگزینی داره؟ نمیشه از همین دستورات EF Core در هاست هم کمک گرفت تا دیتابیس در آنجا ساخته شود؟
    • #
      ‫۴ سال و ۹ ماه قبل، جمعه ۱۵ آذر ۱۳۹۸، ساعت ۲۱:۳۲
      dotnet ef --startup-project ../TechnicalDiagnosis.WebApp/ migrations script | out-file ./script.sql 
      این دستور در power shall باعث تولید sql دیتابیس میشه. فقط چند خط اول پاک کنید و دستی یک دیتابیس ایجاد کنید و این sql روی اون اجرا کنید.
      • #
        ‫۴ سال و ۹ ماه قبل، جمعه ۱۵ آذر ۱۳۹۸، ساعت ۲۳:۱۹
        - مطالب مختص به آن، به همراه نکات به روز رسانی‌های تا EF Core 3x: ^ و ^
        + پروژه‌ای که از این نکات برای ایجاد بانک اطلاعاتی به صورت خودکار استفاده می‌کند: ^
  • #
    ‫۳ سال و ۴ ماه قبل، شنبه ۲۱ فروردین ۱۴۰۰، ساعت ۱۴:۰۱
    یک نکته‌ی تکمیلی: ساده‌تر شدن به روز رسانی برنامه‌ها در ASP.NET Core 6x
    تا پیش از دات نت 6، فایل‌های باینری برنامه‌های ASP.NET Core توسط IIS قفل می‌شوند و امکان جایگزینی آن‌ها بدون متوقف کردن برنامه، میسر نیست. برای رفع این مشکل، پشتیبانی از shadow copy به ASP.NET Core Module for IIS جدید، اضافه شده که روش فعالسازی آن با انجام تغییراتی در Web.Config به صورت زیر است:
    <?xml version="1.0" encoding="utf-8"?>
    <configuration>
      <!-- To customize the asp.net core module uncomment and edit the following section. 
      For more info see https://go.microsoft.com/fwlink/?linkid=838655 -->
    
      <system.webServer>
        <handlers>
          <remove name="aspNetCore"/>
          <add name="aspNetCore" path="*" verb="*" modules="AspNetCoreModulev2" resourceType="Unspecified"/>
        </handlers>
        <aspNetCore processPath="%LAUNCHER_PATH%" arguments="%LAUNCHER_ARGS%" stdoutLogEnabled="false" stdoutLogFile=".\logs\stdout">
          <handlerSettings>
            <handlerSetting name="experimentalEnableShadowCopy" value="true" />
            <handlerSetting name="shadowCopyDirectory" value="../ShadowCopyDirectory/" />
            <!-- Only enable handler logging if you encounter issues-->
            <!--<handlerSetting name="debugFile" value=".\logs\aspnetcore-debug.log" />-->
            <!--<handlerSetting name="debugLevel" value="FILE,TRACE" />-->
          </handlerSettings>
        </aspNetCore>
      </system.webServer>
    </configuration>
    • #
      ‫۲ سال و ۴ ماه قبل، شنبه ۳ اردیبهشت ۱۴۰۱، ساعت ۱۷:۴۷
      یک نکته: experimentalEnableShadowCopy دات نت 6، در دات نت 7، دیگر experimental نیست و دات نت 7 از shadow copy جهت توزیع ساده‌تر برنامه‌های ASP.NET Core، بدون نیاز به offline کردن آن‌ها پشتیبانی می‌کند.
      <?xml version="1.0" encoding="utf-8"?>
      <configuration>
        <system.webServer>
          <handlers>
            <remove name="aspNetCore"/>
            <add name="aspNetCore" path="*" verb="*" modules="AspNetCoreModuleV2" resourceType="Unspecified"/>
          </handlers>
          <aspNetCore processPath="%LAUNCHER_PATH%" arguments="%LAUNCHER_ARGS%" stdoutLogEnabled="false" stdoutLogFile=".logsstdout">
            <handlerSettings>
              <handlerSetting name="enableShadowCopy" value="true" />
              <!-- Ensure that the IIS ApplicationPool identity has permission to this directory -->
              <handlerSetting name="shadowCopyDirectory" value="../ShadowCopyDirectory/" />
            </handlerSettings>
          </aspNetCore>
        </system.webServer>
      </configuration>