وب سرور برای فایل های استاتیک | Nginx from stratch
۷ تیر ۱۴۰۴
یک وب سرور برای فایل های static ایجاد میکنیم , با فایل های مهم nginx آشنا میشیم و یکسری از دستورات اولیه رو مرور میکنیم.
فرض کنید یکسری فایل داریم و میخواهیم آنها را از طریق سرور با استفاده از یک آدرس وب با کاربرهای خودمون به اشتراک بزاریم. ما میتونیم از nginx استفاده کنیم و اون رو طوری تنظیم کنیم که فایل ها رو روی ادرس مورد نظر ما برای کاربرها لود کنه.
در قسمت قبل با بررسی فایل /etc/nginx/nginx.conf
متوجه شدیم هر فایلی که با پسوند conf
در مسیر /etc/nginx/conf.d/
ایجاد کنیم به عنوان تنظیمات در بلاک HTTP لود میشود. بنابراین ما میتونیم فایل های استاتیک خودمون رو در پوشه ای به نام public در یک مسیر دلخواه قرار بدیم و تنظیمات وب سرور خودمون رو با ایجاد یک فایل با پسوند conf در مسیر /etc/nginx/conf.d
ذخیره کنیم.
من اسم فایل تنظیمات خودم رو static01.conf
میزارم و درون این فایل دستورات زیر رو قرار میدم و سپس با استفاده از سیگنال reload
که در قسمت قبل باهاش آشنا شدیم به nginx میگم که تنظیمات رو دوباره بخونه و خودشو مطابق با اون تنظیم کنه.
در دستورات بالا اولین خط server
است یعنی ما میخواهیم یک سرور ایجاد کنیم. سپس با استفاده از {
و }
بدنه دستورات server
را مشخص میکنیم.
دستور listen
مشخص میکند که سرور ما به کدام پورت برای دریافت درخواست ها باید گوش دهد. در اینجا پورت 8000 رو مشخص کنیم و با استفاده از default_server
مشخص میکنیم که تمامی درخواست هایی که روی این پورت بیاد به صورت دیفالت توسط این سرور مدیریت میشه.
با استفاده از دستور location
میتونیم یک نوع روتینگ انجام بدیم. تمامی ادرس های وب دارای بخشی به نام path هستن. به قسمتی که بعد از host قرار میگیره path میگیم.
برای مثال , در آدرس بالا lets/go/to/the/moon
همون path یا مسیر درخواست است.
ما در تنظیمات خودمون از /
استفاده کردیم. هر وقت در انتهای آدرسی که برای location
مشخص کرده ایم /
داشته باشیم, آن ادرس و تمامی زیر ادرس های آن تطبیق داده میشوند. root
یعنی اینکه درخواست ها رو به این مسیر روی هارد دیسک بفرست و index
فایل پیش فرضی که باید لود شود را مشخص میکند.
دستور root در Nginx برای مشخص کردن مسیر فایلهای استاتیک روی سیستم استفاده میشود, وقتی از root استفاده میکنی، مسیر درخواست به مسیر فایل اضافه میشود. یعنی مسیر (path) درخواستی که location با آن تطبیق میکند به انتهای مسیری که در root
مشخص کردیم اضافه میشود و سپس نتیجه نهایی آدرسی است که فایل ها با توجه به آن از روی دیسک باید خوانده شوند. برای مثال اگر کاربر آدرس زیر را درخواست بدهد:
nginx دنبال فایل زیر روی دیسک میگردد:
پس یعنی مسیر تطبیق داده شده با location به مسیر root اضافه میشود.
من یکسری عکس توی پوشه public قرار دادم و یک فایل index.html ایجاد کردم و توی تنظیمات به عنوان فایل پیش فرض برای لود شدن معرفی کردم. پس اگه کاربر توی آدرسی که وارد میکنه مستقیم به فایلی اشاره نکنه index.html براش باز میشه. (فایل هایی که من توی این مثال استفاده کردم را از Github دانلود کنید.)
اگر با استفاده از مرورگر خود به آدرس localhost:8000
یا 127.0.0.1:8000
برید باید فایل index.html برای شما نمایش داده شود. اگر از فایل هایی که من در گیت هاب قرار دادم استفاده کرده باشید, باید چیزی شبیه زیر در مرورگر خودتون ببینید:
در صورتی که docker و make رو نصب کردین: میتونید فایل های مربوط به مثال بالا رو از گیت هاب دانلود کنید. سپس به درون پوشه 01-serving-static-content
برید و دستور make up
رو درون خط فرمان اجرا کنید. این دستور یک nginx توسط داکر اجرا میکند و تنظیماتی که در قسمت قبل به آن اشاره کردیم رو نیز انجام میدهد. سپس در پورت 8000 روی localhost
یا 127.0.0.1
باید تصویر بالا رو بتونید ببینید. وقتی دیگه nginx رو لازم ندارید میتونید درون پوشه ای که گفته شد دستور make down
رو بزنید تا داکر اون رو قطع و حذف کند.
دستور alias و تفاوت آن با root
ممکن است در مواقعی بخوایم فایل ها دقیقا آدرسی که روی دیسک مشخص کردیم خوانده شوند و مسیر درخواستِ تطبیق داده شده به مسیری که ما برای فایل ها مشخص کردیم اضافه شود اما قسمتی که در location مشخص کردیم از آن حذف شود. در چنین مواقعی میتوان بجای root
از alias
استفاده کرد. برای مثال اگر کاربر ادرس زیر را باز کند:
ما میخواهیم فایل ها را از آدرس زیر لود کنیم:
برای اینکار, یه فایل جدید با پسوند conf بسازید و تنظیمات زیر رو درون اون قرار بدید:
پورت رو از 8000
به 8001
تغییر دادیم و بجای root
از alias
استفاده کردیم, همچنین توی این مثال فقط به درخواست هایی که روی آدرس /home
ارسال میشن پاسخ میدیم. حالا وب سرور ما روی دوتا پورت 8000
و 8001
به درخواست های ما گوش میده. کافیه آدرس localhost:8001/home
رو باز کنید تا نتیجه رو ببینید. اگر روی یکی از تصاویری که میبینید کلیک کنید متوجه خواهید شد با اینکه ادرس با home
شروع میشود اما تصاویر از مسیر درستی خوانده میشوند.
نمایش لیست فایل ها توسط وب سرور
در مثال های قبل اگر توی مسیری برید که وجود ندارد با صفحه 404
مواجه میشید. اما اگه مسیری رو برید که وجود داشته باشه ولی در آدرس شما, دقیقا فایل خاصی رو مشخص نکرده باشید با صفحه 403 access forbidden
مواجهه میشوید.
ما میخوایم در حالتی که مسیر مورد نظر ما وجود داشت, لیست فایل ها و فولدر های درون اون مسیر به ما نمایش داده شود. برای اینکار کافیست autoindex
را on
کنیم.
در مثال بالا ما autoindex on
رو اضافه کردیم که باعث میشه اگه کاربر به آدرسی بره که وجود داره, بجای 403 access forbidden
لیست فایل ها و پوشه های موجود رو نشون بدیم.
ریدایرکت کردن توسط وب سرور
هدایت کاربر از یک آدرس یا مسیر به آدرس یا مسیر دیگر را "ریدایرکت (redirect)" مینامند.
برای ریدایرکت کردن میتونید از دستور return
به همراه یک عدد و آدرس مورد نظر استفاده کرد. برای ریدایرکت کردن عددی که مشخص میکنید باید 3xx باشد (بزرگتر مساوی 300 و کمتر از 400) میتونید راجب HTTP redirect status code
جستجو کنید و مطالعه کنید. هرکدام از کدها معنی خاصی دارند. اگه قرار است ریدارکت شما دائمی باشد بهتر است از 301 و اگر دائمی نیست بهتر است از 302 استفاده کنید.
در مثال بالا یک redirect روی آدرس /
مشخص کردیم. اگر شما هر آدرسی رو باز کنید که با /home
شروع نشود, درخواست شما به /home
ریدایرکت خواهد شد. برای اینکه بهتر متوجه بشید میتونید یکی از آدرس هایی که در زیر ذکر شده رو باز کنید و نتیجه رو ببینید:
گوش دادن به چندین پورت
اگه میخواید یه سرور راه بندازید که همزمان روی چند پورت به درخواستها جواب بده، دو راه دارید, یا پورتها رو با ویرگول از هم جدا کنید و به صورت لیست بدید، یا برای هر پورت جداگانه یک بار دستور listen
رو بنویسید.
برای مشخص کردن یک بازه از پورتها، میتوان از نماد خط تیره (-
) استفاده کرد. در این روش، شماره پورت ابتدایی و انتهایی را با خط تیره از یکدیگر جدا میکنید. بدین ترتیب، پورت شروع، پورت پایان و تمامی پورتهای مابین آنها در بازه مورد نظر قرار میگیرند.
همچنین دو مثال قبلی رو میشه باهم ترکیب کرد. یعنی شما هم میتونید یک listen برای رنج پورت مورد نظر مشخص کنید و همچنین دوباره listen را برای یک پورت خاص دیگر تکرار کنید.
نمونه کد تمامی مثال هایی که در این قسمت داشتیم را میتونید همچنین در Github ببینید.
قسمت قبل: معماری و تنظیمات اولیه | Nginx from stratch
قسمت بعد: لود بالانس | Nginx from scratch