فرض کنید یک API با Django ساختهاید و همهچیز هم بهدرستی کار میکند. با اجرای دستور زیر پروژه بالا میآید:
python manage.py runserver
و API شما مثلاً روی این آدرس در دسترس است:
http://127.0.0.1:8000/api/hello/مشکل اینجاست که این آدرس فقط روی کامپیوتر خودتان قابل دسترسی است. اگر لینک را برای دوست، همکار، کارفرما یا برنامهنویس فرانتاند بفرستید، طبیعتاً چیزی برای او باز نمیشود.
یک راه این است که پروژه را روی یک سرور واقعی Deploy کنید. اما اگر فقط میخواهید API را چند ساعت تست کنید، یک Webhook دریافت کنید، خروجی پروژه را به شخص دیگری نشان دهید یا یک برنامه موبایل را به بکاند لپتاپتان متصل کنید، راهاندازی سرور کار اضافهای است.
اینجاست که ngrok به کارمان میآید.
با ngrok میتوانیم سرویسی که روی localhost لپتاپ اجرا شده را از طریق یک آدرس عمومی HTTPS روی اینترنت در دسترس قرار دهیم. ngrok برای این کار یک Endpoint عمومی ایجاد میکند و درخواستها را از طریق یک اتصال امن به سرویس محلی ما Forward میکند.
در این مقاله این کار را مرحلهبهمرحله با Django انجام میدهیم.
نکته مهم: ngrok جایگزین سرور Production نیست. هدف اصلی این آموزش، تست، توسعه، دمو، Webhook و دسترسی موقت به پروژهای است که روی سیستم خودمان اجرا میشود. خود Django نیز صراحتاً اعلام میکند که runserver یک Development Server است و برای محیط Production مناسب نیست.ngrok دقیقاً چه کاری انجام میدهد؟
قبل از نصب ngrok بهتر است مکانیزم آن را خیلی ساده درک کنیم.
زمانی که Django را با دستور زیر اجرا میکنیم:
python manage.py runserver
بهصورت پیشفرض سرور توسعه Django روی این آدرس اجرا میشود:
127.0.0.1:8000این آدرس متعلق به کامپیوتر خودمان است.
حالا ngrok را اجرا میکنیم و به آن میگوییم:
هر درخواستی که از اینترنت دریافت کردی، به پورت 8000 کامپیوتر من بفرست.
برای این کار کافی است بعداً دستور زیر را اجرا کنیم:
ngrok http 8000
ngrok یک URL عمومی شبیه این به ما میدهد:
https://your-name.ngrok-free.appدر نتیجه اگر شخص دیگری این آدرس را باز کند:
https://your-name.ngrok-free.app/api/hello/درخواست تقریباً این مسیر را طی میکند:
کاربر اینترنت
↓
آدرس HTTPS مربوط به ngrok
↓
تونل ngrok
↓
localhost:8000
↓
Django
↓
API مایعنی Django همچنان روی لپتاپ خودمان اجرا میشود؛ ngrok فقط یک مسیر عمومی برای رسیدن درخواستهای اینترنت به آن ایجاد کرده است.
در حال بارگذاری تصویر...

ساخت یک API ساده در Django
اگر در حال حاضر یک پروژه Django دارید و چند URL روی localhost شما کار میکنند، این بخش را رد کنید. مهم نیست API شما با Django REST Framework نوشته شده، JsonResponse استفاده کردهاید یا حتی یک پروژه بزرگ دارید.
تنها چیزی که برای ادامه نیاز داریم این است که یک آدرس مثل این روی لپتاپ شما کار کند:
http://127.0.0.1:8000/api/...اما برای اینکه آموزش قابل اجرا باشد، یک API بسیار ساده هم میسازیم.
فرض میکنیم از قبل یک پروژه Django دارید. یک App به نام api میسازیم:
python manage.py startapp api
سپس آن را در settings.py اضافه کنید:
INSTALLED_APPS = [
# ...
"api",
]در فایل api/views.py یک View ساده مینویسیم:
from django.http import JsonResponse
from django.views.decorators.http import require_GET
@require_GET
def hello(request):
return JsonResponse({
"message": "Hello from my laptop!",
"status": "ok",
})حالا فایل api/urls.py را ایجاد کنید:
from django.urls import path
from .views import hello
urlpatterns = [
path("hello/", hello, name="hello"),
]و در فایل اصلی urls.py پروژه، URLهای این App را اضافه کنید:
from django.contrib import admin
from django.urls import include, path
urlpatterns = [
path("admin/", admin.site.urls),
path("api/", include("api.urls")),
]پروژه را اجرا کنید:
python manage.py runserver
حالا باید بتوانید آدرس زیر را باز کنید:
http://127.0.0.1:8000/api/hello/و خروجی تقریباً چنین چیزی باشد:
{
"message": "Hello from my laptop!",
"status": "ok"
}تا اینجا هیچ ارتباطی با ngrok نداریم. API ما فقط بهصورت Local اجرا شده است.
نصب ngrok
روش نصب ngrok در سیستمعاملهای مختلف کمی متفاوت است. ابتدا ویندوز را بررسی میکنیم و سپس سراغ macOS و Linux میرویم.
این آموزش بر اساس روش نصب و CLI فعلی ngrok در زمان نگارش مقاله نوشته شده است. خود ngrok برای Windows استفاده از Microsoft Store را بهعنوان یکی از روشهای اصلی نصب ارائه میکند، برای macOS نصب با Homebrew و برای Linux نیز بستههای رسمی از جمله Apt در دسترس هستند.
نصب ngrok در ویندوز
برای ویندوز سادهترین روش این است که وارد صفحه رسمی دانلود ngrok شوید و نسخه Windows را نصب کنید.
ngrok در حال حاضر روش نصب از طریق Microsoft Store را نیز ارائه میکند و در مستندات رسمی آن را گزینه امن پیشنهادی برای Windows معرفی کرده است.
بعد از نصب، PowerShell، Command Prompt یا Windows Terminal را باز کنید و دستور زیر را اجرا کنید:
ngrok version
اگر نسخه ngrok نمایش داده شد، نصب موفق بوده است.
مثلاً خروجی ساختاری شبیه این خواهد داشت:
ngrok version 3.x.xعدد نسخه ممکن است با زمان مطالعه این مقاله متفاوت باشد.
اگر ngrok را بهصورت فایل مستقل نصب کردهاید و نه از Package Manager، میتوانید برای بررسی و نصب نسخه Stable جدید از این دستور استفاده کنید:
ngrok update
مستندات ngrok توصیه میکنند در صورتی که برنامه را با Package Manager نصب کردهاید، بهجای ngrok update از همان Package Manager برای آپدیت استفاده کنید.
اگر دستور ngrok شناخته نشد
اگر با چنین خطایی مواجه شدید:
'ngrok' is not recognized...یا:
ngrok: command not foundاحتمالاً فایل اجرایی ngrok داخل PATH سیستم قرار نگرفته است.
اگر نسخه مستقل ngrok.exe را دانلود کردهاید، میتوانید آن را در پوشهای مثل:
C:\Tools\ngrok\قرار دهید و این پوشه را به Environment Variable مربوط به PATH ویندوز اضافه کنید.
بعد از تغییر PATH، Terminal را ببندید و دوباره باز کنید.
نصب ngrok در macOS
اگر Homebrew روی سیستم نصب است، نصب ngrok بسیار ساده است:
brew install ngrok
این همان روش نصب ارائهشده در مستندات رسمی ngrok برای macOS است.
بعد از نصب:
ngrok version
برای آپدیت نسخهای که با Homebrew نصب شده نیز از Homebrew استفاده کنید:
brew upgrade ngrok
نصب ngrok در Linux
ngrok برای Linux روشهای مختلفی مثل Apt، Snap و دانلود مستقیم ارائه میکند.
اگر توزیع شما مبتنی بر Debian یا Ubuntu است، میتوانید از Repository رسمی ngrok استفاده کنید:
curl -sSL https://ngrok-agent.s3.amazonaws.com/ngrok.asc \| sudo tee /etc/apt/trusted.gpg.d/ngrok.asc >/dev/null \&& echo "deb https://ngrok-agent.s3.amazonaws.com bookworm main" \| sudo tee /etc/apt/sources.list.d/ngrok.list \&& sudo apt update \&& sudo apt install ngrok
این دستور مطابق روش Apt ارائهشده در مستندات رسمی ngrok است.
بعد از نصب:
ngrok version
ساخت حساب ngrok و دریافت Authtoken
بعد از نصب باید ngrok را به حساب خود متصل کنیم.
یک حساب در ngrok ایجاد کنید و سپس در Dashboard وارد بخش مربوط به Authtoken شوید.
توکنی شبیه این دریافت خواهید کرد:
2abcDEFxxxxxxxxxxxxxxxxxxxxحالا در Terminal دستور زیر را اجرا کنید:
ngrok config add-authtoken YOUR_AUTHTOKEN
برای مثال:
ngrok config add-authtoken 2abcDEFxxxxxxxxxxxxxxxxxxxx
البته مقدار بالا فقط مثال است و باید Token واقعی خودتان را جایگزین کنید.
این دستور Authtoken را در فایل تنظیمات ngrok ذخیره میکند. ngrok برای احراز هویت Agent از Authtoken استفاده میکند.
Authtoken یک اطلاعات محرمانه است.
آن را داخل GitHub، فایلهای پروژه، اسکرینشات عمومی یا مقاله قرار ندهید.
آنلاین کردن Django با ngrok
حالا به قسمت اصلی آموزش رسیدیم.
در Terminal اول Django را اجرا کنید:
python manage.py runserver 8000
مطمئن شوید آدرس Local شما کار میکند:
http://127.0.0.1:8000/api/hello/حالا یک Terminal جدید باز کنید.
Django باید همچنان در Terminal اول در حال اجرا باشد.
در Terminal دوم بنویسید:
ngrok http 8000
معنای این دستور خیلی ساده است:
برای سرویس HTTP که روی پورت 8000 سیستم من اجرا شده، یک Endpoint عمومی ایجاد کن.
ngrok نیز در مستندات CLI خود دقیقاً از همین ساختار ngrok http PORT برای Forward کردن یک سرویس HTTP محلی استفاده میکند.
بعد از اجرای دستور، آدرسی شبیه این مشاهده خواهید کرد:
https://your-assigned-name.ngrok-free.appدر پلن رایگان فعلی ngrok یک Development Domain اختصاصیافته به حساب در اختیار کاربر قرار میگیرد. جزئیات محدودیتهای پلن ممکن است در آینده تغییر کند.
حالا اگر API ما این بود:
http://127.0.0.1:8000/api/hello/نسخه عمومی آن میشود:
https://your-assigned-name.ngrok-free.app/api/hello/اما احتمال زیادی وجود دارد که در اولین درخواست با یک خطای Django مواجه شوید.
حل خطای DisallowedHost در Django
فرض کنید URL عمومی ngrok شما این باشد:
https://codingyar-demo.ngrok-free.appاگر آن را باز کنید ممکن است Django این خطا را نمایش دهد:
DisallowedHost
Invalid HTTP_HOST headerعلت این خطا ngrok نیست.
Django درخواست را دریافت کرده، اما Domain جدید را نمیشناسد.
Django برای محافظت در برابر حملات مرتبط با Host header، مقدار Host درخواست را با تنظیم ALLOWED_HOSTS مقایسه میکند.
بنابراین وارد settings.py شوید و Domain مربوط به ngrok را اضافه کنید:
ALLOWED_HOSTS = [
"127.0.0.1",
"localhost",
"codingyar-demo.ngrok-free.app",
]دقت کنید که داخل ALLOWED_HOSTS فقط نام Host را قرار میدهیم.
اشتباه:
ALLOWED_HOSTS = [
"https://codingyar-demo.ngrok-free.app",
]درست:
ALLOWED_HOSTS = [
"codingyar-demo.ngrok-free.app",
]حالا Django را Restart کنید:
python manage.py runserver 8000
و دوباره API را از URL عمومی باز کنید:
https://codingyar-demo.ngrok-free.app/api/hello/این بار باید همان JSON مربوط به لپتاپ خودتان را دریافت کنید:
{
"message": "Hello from my laptop!",
"status": "ok"
}تبریک! در این لحظه API که روی لپتاپ شما اجرا شده، از اینترنت قابل دسترسی است.
اگر این لینک را برای شخص دیگری بفرستید، تا زمانی که لپتاپ شما روشن باشد و Django و ngrok در حال اجرا باشند، او نیز میتواند API را فراخوانی کند.
آیا میتوانیم .ngrok-free.app را کامل داخل ALLOWED_HOSTS قرار دهیم؟
Django اجازه میدهد Hostهایی که با یک نقطه شروع میشوند تمام Subdomainهای آن دامنه را Match کنند. بنابراین از نظر فنی میتوان تنظیمی شبیه این داشت:
ALLOWED_HOSTS = [
"127.0.0.1",
"localhost",
".ngrok-free.app",
]اما در حالت عادی اضافه کردن Domain دقیق خودتان انتخاب بهتری است:
ALLOWED_HOSTS = [
"127.0.0.1",
"localhost",
"codingyar-demo.ngrok-free.app",
]هرچه ALLOWED_HOSTS محدودتر باشد، رفتار پروژه قابلکنترلتر است.
از این تنظیم هم برای راحتی استفاده نکنید:
ALLOWED_HOSTS = ["*"]خصوصاً زمانی که برنامه را واقعاً روی اینترنت قرار دادهاید.
هدف ALLOWED_HOSTS یک کنترل امنیتی واقعی در Django است، نه خطایی که لازم باشد به هر روشی از شر آن خلاص شویم.
تست API عمومی با curl
تا اینجا API را احتمالاً با مرورگر تست کردهایم.
اما برای اینکه مطمئن شویم واقعاً از طریق اینترنت قابل فراخوانی است، میتوانیم curl استفاده کنیم.
curl https://codingyar-demo.ngrok-free.app/api/hello/
در Windows اگر PowerShell شما curl را به Command دیگری Alias کرده است، میتوانید بنویسید:
curl.exe https://codingyar-demo.ngrok-free.app/api/hello/
خروجی:
{"message":"Hello from my laptop!","status":"ok"}حتی بهتر است آدرس را روی موبایل و با اینترنت سیمکارت امتحان کنید.
در این حالت دیگر موبایل روی شبکه Wi-Fi لپتاپ نیست و مطمئن میشوید درخواست واقعاً از اینترنت به پروژه شما رسیده است.
در حال بارگذاری تصویر...

آیا برای هر URL باید یک ngrok جدا اجرا کنیم؟
خیر.
فرض کنید پروژه Django شما این Endpointها را دارد:
/api/users/
/api/products/
/api/orders/
/api/login/همه آنها روی یک سرور Django و پورت 8000 اجرا میشوند:
http://localhost:8000کافی است فقط یک بار اجرا کنید:
ngrok http 8000
اگر Domain عمومی شما این باشد:
https://codingyar-demo.ngrok-free.appتمام Endpointها به شکل زیر قابل دسترسی میشوند:
https://codingyar-demo.ngrok-free.app/api/users/
https://codingyar-demo.ngrok-free.app/api/products/
https://codingyar-demo.ngrok-free.app/api/orders/
https://codingyar-demo.ngrok-free.app/api/login/ngrok کل سرویس روی آن پورت را Public میکند، نه فقط یک URL خاص را.
اگر Django روی پورت دیگری اجرا شود چه؟
هیچ مشکلی نیست.
مثلاً:
python manage.py runserver 9000
در این حالت Django روی پورت 9000 است، پس ngrok را نیز برای همان پورت اجرا میکنیم:
ngrok http 9000
یا اگر برنامه دیگری روی پورت 3000 دارید:
ngrok http 3000
قاعده کلی این است:
ngrok http PORT
Port باید همان پورتی باشد که سرویس Local شما روی آن Listen میکند.
HTTPS از کجا آمد؟
نکته جالب این است که Django روی لپتاپ ما معمولاً با HTTP اجرا شده:
http://localhost:8000ولی URL عمومی ngrok میتواند HTTPS باشد:
https://codingyar-demo.ngrok-free.appngrok اتصال عمومی HTTPS را مدیریت کرده و سپس Traffic را از طریق تونل خود به سرویس Local Forward میکند. HTTPS Endpoint و Automatic Certificates از قابلیتهای ngrok هستند.
بنابراین برای یک تست ساده لازم نیست روی Django Development Server خودتان SSL Certificate نصب کنید.
تفاوت ALLOWED_HOSTS، CORS و CSRF
این قسمت یکی از مهمترین بخشهای مقاله است، چون این سه مفهوم زیاد با هم اشتباه گرفته میشوند.
ALLOWED_HOSTS
ALLOWED_HOSTS مشخص میکند Django اجازه دارد درخواستهایی با چه Hostهایی را قبول کند.
وقتی ngrok برای ما Domain جدید ایجاد میکند:
codingyar-demo.ngrok-free.appباید آن Domain را به Django معرفی کنیم:
ALLOWED_HOSTS = [
"localhost",
"127.0.0.1",
"codingyar-demo.ngrok-free.app",
]اگر این کار را انجام ندهیم معمولاً DisallowedHost میگیریم.
CORS
CORS داستان متفاوتی دارد.
فرض کنید Frontend شما روی این آدرس اجرا شده:
https://frontend.example.comو JavaScript داخل مرورگر میخواهد به API شما درخواست بزند:
https://codingyar-demo.ngrok-free.app/api/products/این دو Origin متفاوت دارند.
در چنین حالتی مرورگر قوانین CORS را اعمال میکند.
ngrok مانع CORS نیست؛ برنامه شما باید Headerهای مناسب CORS را برگرداند. خود مستندات ngrok نیز تأکید میکنند که Application باید CORS headers مناسب را ارائه کند.
اگر API را از Postman، curl یا یک Backend دیگر صدا بزنید، محدودیت CORS مرورگر را ندارید.
تنظیم CORS در Django
یکی از ابزارهای رایج برای این کار django-cors-headers است:
python -m pip install django-cors-headers
سپس:
INSTALLED_APPS = [
# ...
"corsheaders",
]Middleware را نیز اضافه کنید:
MIDDLEWARE = [
"corsheaders.middleware.CorsMiddleware",
"django.middleware.common.CommonMiddleware",
# ...
]و Origin واقعی Frontend را مجاز کنید:
CORS_ALLOWED_ORIGINS = [
"https://frontend.example.com",
]برای Development ممکن است نمونههایی مثل این ببینید:
CORS_ALLOW_ALL_ORIGINS = Trueاما این تنظیم را بدون دلیل روی یک API عمومی رها نکنید.
در زمان نگارش این مقاله، نسخه 4.9.0 پکیج django-cors-headers در PyPI بهعنوان آخرین Release ثبت شده و پشتیبانی رسمی آن در Metadata تا Django 6.0 اعلام شده است؛ اگر از نسخه جدیدتری از Django استفاده میکنید، Compatibility نسخه فعلی پکیج را قبل از نصب بررسی کنید.
CSRF_TRUSTED_ORIGINS
CSRF_TRUSTED_ORIGINS هم با ALLOWED_HOSTS یکی نیست.
Django برای درخواستهای Unsafe مثل:
POST
PUT
PATCH
DELETEدر سناریوهایی که CSRF Protection فعال است، Origin درخواست را بررسی میکند. طبق مستندات Django، اگر درخواست Origin داشته باشد، Origin باید با Host مورد انتظار تطابق داشته باشد یا در فهرست Trusted Origins قرار گرفته باشد.
اگر هم Frontend و هم API از همان ngrok URL استفاده کنند، معمولاً نیازی نیست صرفاً بهدلیل استفاده از ngrok چیزی به CSRF_TRUSTED_ORIGINS اضافه کنید.
اما فرض کنید Frontend روی این Origin است:
https://frontend.example.comو با Cookie یا Session به Django درخواست POST ارسال میکند.
در صورت نیاز میتوانید همان Origin فرستنده درخواست را Trust کنید:
CSRF_TRUSTED_ORIGINS = [
"https://frontend.example.com",
]نکته مهم همین است:
CSRF_TRUSTED_ORIGINS را کورکورانه با تمام دامنههای ngrok پر نکنید. ابتدا ببینید Origin واقعی درخواست چیست و چرا Django آن را Reject کرده است.
یک تنظیم پیشنهادی برای settings.py
برای یک پروژه آزمایشی که فقط قرار است با ngrok تست شود، تنظیمات میتواند چیزی شبیه این باشد:
ALLOWED_HOSTS = [
"localhost",
"127.0.0.1",
"codingyar-demo.ngrok-free.app",
]اگر Frontend جداگانهای دارید:
CORS_ALLOWED_ORIGINS = [
"https://frontend.example.com",
]و اگر Session/CSRF در درخواست Cross-Origin مطرح باشد:
CSRF_TRUSTED_ORIGINS = [
"https://frontend.example.com",
]این سه تنظیم سه مسئله متفاوت را حل میکنند.
مشاهده درخواستهایی که از ngrok عبور میکنند
یکی از امکانات بسیار کاربردی ngrok این است که میتوانید Requestهایی که به API شما میرسند را Inspect کنید.
Traffic Inspector به شما کمک میکند مواردی مثل موارد زیر را بررسی کنید:
- Method درخواست
- URL
- Headerها
- Status Code
- مدت زمان پاسخ
- Request و Response در حالت Capture مناسب
- Replay کردن Request در شرایط پشتیبانیشده
ngrok یک Traffic Inspector در Dashboard دارد و Agent مستقل نیز معمولاً رابط Local Inspection را روی آدرس زیر ارائه میکند:
http://localhost:4040مستندات فعلی ngrok، Traffic Inspector ابری Dashboard را نیز برای بررسی و Replay ترافیک ارائه میکنند.
این قابلیت مخصوصاً هنگام تست Webhookها فوقالعاده مفید است.
مثلاً سرویس خارجی یک درخواست POST برای لپتاپ شما ارسال میکند، اما Django خطای 400 یا 500 میدهد.
بهجای حدس زدن میتوانید درخواست ورودی را Inspect کنید.
نکته امنیتی درباره Traffic Inspector
اگر Full Capture را فعال کنید، Body و Headerهای Request و Response ممکن است در Traffic Inspector ذخیره شوند.
پس در زمان کار با اطلاعات حساسی مثل Password، Token، اطلاعات شخصی یا داده واقعی کاربران، تنظیمات Capture را با دقت بررسی کنید. مستندات ngrok نیز درباره ذخیره دادههای حساس در Full Capture هشدار میدهند.
یک کاربرد واقعی: تست Webhook روی لپتاپ
یکی از بهترین کاربردهای ngrok تست Webhook است.
فرض کنید یک درگاه پرداخت یا سرویس خارجی بعد از انجام عملیات باید درخواست زیر را ارسال کند:
POST /api/payment/callback/سرویس خارجی نمیتواند به این آدرس دسترسی داشته باشد:
http://127.0.0.1:8000/api/payment/callback/چون 127.0.0.1 برای خود لپتاپ شماست.
ngrok را اجرا میکنیم:
ngrok http 8000
و آدرس عمومی میگیریم:
https://codingyar-demo.ngrok-free.appحالا Callback URL را در سرویس خارجی میگذاریم:
https://codingyar-demo.ngrok-free.app/api/payment/callback/درخواست سرویس خارجی وارد ngrok میشود و در نهایت به Django روی لپتاپ شما میرسد.
بدون خرید VPS، تنظیم Nginx، گرفتن Domain یا Deploy کردن پروژه میتوانیم Webhook واقعی را تست کنیم.
یک کاربرد دیگر: اتصال برنامه موبایل به Django لپتاپ
فرض کنید شما Backend پروژه را با Django نوشتهاید و یکی از اعضای تیم در حال ساخت اپلیکیشن Android یا iOS است.
Backend روی سیستم شما اجرا شده:
http://localhost:8000برنامه موبایل هم طبیعتاً نمیتواند از اینترنت به localhost کامپیوتر شما دسترسی داشته باشد.
با ngrok:
ngrok http 8000
میتوانید Base URL موقت API را در اختیار برنامهنویس موبایل قرار دهید:
https://codingyar-demo.ngrok-free.app/api/حالا اپ موبایل میتواند Endpointهای واقعی Django لپتاپ شما را فراخوانی کند.
برای پروژههای تیمی کوچک و تست سریع، این روش بسیار کاربردی است.
آیا ngrok باعث میشود لپتاپ ما سرور شود؟
از یک نظر، برنامه روی لپتاپ شما در حال پاسخ دادن به درخواستهای اینترنت است.
اما نباید نتیجه بگیریم که حالا دیگر نیازی به Deployment نداریم.
تا زمانی که این موارد برقرار باشند API کار میکند:
لپتاپ روشن باشد
+
اتصال اینترنت برقرار باشد
+
Django اجرا باشد
+
ngrok اجرا باشداگر یکی از آنها قطع شود، API دیگر در دسترس نیست.
بنابراین ngrok برای مواردی مثل این عالی است:
- تست API
- دمو به مشتری یا همکار
- تست Webhook
- توسعه Frontend و Backend بهصورت جداگانه
- اتصال موقت اپ موبایل
- تست سرویسهای خارجی
- Debug کردن Callbackها
- نمایش سریع یک نمونه اولیه
اما برای سرویس Production با کاربران واقعی، همچنان باید از معماری Deployment مناسب استفاده کنید.
نکات امنیتی بسیار مهم
زمانی که دستور زیر را اجرا میکنید:
ngrok http 8000
دیگر نباید با پروژه مثل یک localhost خصوصی رفتار کنید.
شما یک مسیر عمومی از اینترنت به برنامه ساختهاید.
۱. API بدون احراز هویت را بیدلیل عمومی نکنید
اگر Endpoint حساسی دارید:
/api/users/
/api/orders/
/api/admin-data/صرفاً به این دلیل که URL ngrok را کسی نمیداند، نباید آن را امن فرض کنید.
Authentication و Authorization پروژه باید همچنان فعال باشند.
۲. DEBUG را جدی بگیرید
در Development معمولاً داریم:
DEBUG = Trueاگر Exception رخ دهد، Django ممکن است اطلاعات Debug زیادی نمایش دهد.
وقتی پروژه از طریق ngrok عمومی شده، این اطلاعات دیگر فقط روی لپتاپ خودتان دیده نمیشوند.
برای Demo عمومی یا دسترسی افراد ناشناس، DEBUG=True انتخاب امنی نیست.
ضمن اینکه Django Development Server اساساً برای Production طراحی نشده است.
۳. Authtoken را منتشر نکنید
این دستور:
ngrok config add-authtoken YOUR_AUTHTOKEN
حاوی یک Credential مربوط به حساب ngrok شماست.
آن را در فایل پروژه ننویسید و Commit نکنید.
۴. اطلاعات واقعی کاربران را برای تست استفاده نکنید
اگر فقط در حال تست هستید، تا حد ممکن از اطلاعات Mock یا Test استفاده کنید.
Public کردن لپتاپ توسعه نباید باعث شود دیتابیس حاوی اطلاعات حساس ناخواسته در معرض Endpointهای آزمایشی قرار بگیرد.
۵. بعد از پایان تست ngrok را ببندید
برای متوقف کردن آن کافی است در Terminal مربوط به ngrok:
Ctrl + Cرا بزنید.
وقتی دیگر به Endpoint عمومی نیاز ندارید، باز نگه داشتن آن فایدهای ندارد.
محدودیت پلن رایگان ngrok
ngrok پلن رایگان هم دارد و برای سناریوی این مقاله معمولاً همین پلن کافی است.
در وضعیت فعلی پلن Free، یک Development Domain اختصاصیافته، تا 3 Online Endpoint، سقف 20 هزار HTTP/S Request در ماه و 1 گیگابایت Data Transfer Out در نظر گرفته شده است. این اعداد متعلق به زمان نگارش مقاله هستند و ممکن است بعداً تغییر کنند.
برای تست API معمولاً مسئلهای ایجاد نمیشود، اما اگر قرار است ترافیک واقعی و مداوم داشته باشید، ngrok رایگان یا Development Server Django راهحل Production محسوب نمیشوند.
صفحه هشدار ngrok در مرورگر چیست؟
ممکن است در پلن رایگان هنگام باز کردن بعضی URLها در مرورگر با صفحهای از سمت ngrok روبهرو شوید که قبل از ورود به سایت یک هشدار نمایش میدهد.
این Interstitial برای کاهش سوءاستفادههایی مثل Phishing استفاده میشود.
طبق مستندات فعلی ngrok، این صفحه برای Browser Traffic مربوط به HTML اعمال میشود و روی APIهایی که بهصورت Programmatic فراخوانی میشوند تأثیر مشابهی ندارد. همچنین کلاینت در صورت نیاز میتواند Header زیر را ارسال کند:
ngrok-skip-browser-warningبا یک مقدار دلخواه.
بنابراین اگر هدف شما API و فراخوانی آن با fetch، Postman، curl یا برنامه موبایل باشد، رفتار با باز کردن مستقیم یک صفحه HTML در مرورگر میتواند متفاوت باشد.
خطاهای رایج ngrok و Django
خطای DisallowedHost
اگر دیدید:
DisallowedHost
Invalid HTTP_HOST headerDomain مربوط به ngrok را در ALLOWED_HOSTS اضافه کنید:
ALLOWED_HOSTS = [
"localhost",
"127.0.0.1",
"codingyar-demo.ngrok-free.app",
]ngrok باز میشود ولی API پاسخ نمیدهد
اول بررسی کنید Django هنوز در حال اجراست:
python manage.py runserver 8000
سپس Local URL را تست کنید:
http://127.0.0.1:8000/api/hello/اگر Local URL هم کار نمیکند، مشکل از ngrok نیست.
پورت اشتباه است
اگر Django روی 8080 اجرا شده:
python manage.py runserver 8080
نباید بنویسید:
ngrok http 8000
باید بنویسید:
ngrok http 8080
خطای CORS در مرورگر
اگر Console مرورگر چیزی درباره CORS میگوید، احتمالاً خود Tunnel سالم است.
باید CORS را در Application تنظیم کنید.
ngrok بهتنهایی CORS Policy اپلیکیشن Django شما را حل نمیکند.
خطای CSRF Failed
اگر Requestهای POST یا سایر Requestهای Unsafe با خطای CSRF مواجه میشوند، موارد زیر را بررسی کنید:
- Origin درخواست چیست؟
- آیا از Session Authentication استفاده میکنید؟
- Frontend روی Domain دیگری است؟
CSRF_TRUSTED_ORIGINSواقعاً برای آن Origin لازم است؟- CSRF Token ارسال میشود؟
مشکل CSRF را با csrf_exempt روی همه Viewها «حل» نکنید؛ ابتدا علت خطا را پیدا کنید.
دستور ngrok پیدا نمیشود
اگر:
ngrok: command not foundدریافت کردید، نصب یا PATH را بررسی کنید.
با این دستور هم میتوانید نصب را تست کنید:
ngrok version
ngrok به سرویس متصل نمیشود
خود ngrok دستور عیبیابی دارد:
ngrok diagnose
این Command برای بررسی مشکلات Connectivity Agent در CLI رسمی ngrok در دسترس است.
آیا لازم است Port Forwarding مودم انجام دهیم؟
خیر، و این یکی از دلایل جذاب بودن ngrok است.
در روشهای سنتی ممکن بود نیاز باشد:
- IP عمومی داشته باشید
- NAT را بررسی کنید
- Port Forwarding مودم انجام دهید
- Firewall را تنظیم کنید
- SSL Certificate بگیرید
اما Agent مربوط به ngrok از داخل سیستم شما یک اتصال خروجی امن به سرویس ngrok ایجاد میکند. مستندات ngrok اعلام میکنند اتصال Agent به سرویس ngrok از طریق پورت 443 برقرار میشود.
در نتیجه در سناریوی معمول این مقاله نیازی نیست پورت 8000 مودم خود را مستقیماً به اینترنت باز کنید.
کل فرایند در چند دستور
اگر پروژه Django شما از قبل آماده است، کل آموزش در عمل به چند مرحله خلاصه میشود.
ابتدا Django:
python manage.py runserver 8000
تست Local:
http://127.0.0.1:8000/api/hello/یک بار Authtoken را تنظیم کنید:
ngrok config add-authtoken YOUR_AUTHTOKEN
سپس:
ngrok http 8000
URL دریافتشده را در settings.py قرار دهید:
ALLOWED_HOSTS = [
"localhost",
"127.0.0.1",
"YOUR_DOMAIN.ngrok-free.app",
]Django را Restart کنید و API عمومی را باز کنید:
https://YOUR_DOMAIN.ngrok-free.app/api/hello/همین.
جمعبندی
برای اینکه دیگران بتوانند به API روی لپتاپ ما دسترسی داشته باشند، لزوماً لازم نیست همان لحظه پروژه را روی VPS یا یک سرویس Cloud Deploy کنیم.
اگر هدف تست، دمو یا توسعه است، ngrok میتواند بین اینترنت و localhost ما یک مسیر عمومی ایجاد کند.
در مثال این مقاله Django روی:
http://localhost:8000اجرا شد و با دستور:
ngrok http 8000
یک آدرس عمومی HTTPS برای آن ایجاد کردیم.
سپس با اضافه کردن Domain ngrok به:
ALLOWED_HOSTSتوانستیم API را از خارج از کامپیوتر خودمان فراخوانی کنیم.
نکتهای که باید به خاطر بسپارید این است:
ngrok = دسترسی موقت و سریع به سرویس Localو نه:
ngrok + runserver = Deployment واقعی Productionبرای تست Webhook، اتصال اپ موبایل، همکاری Frontend و Backend، نمایش سریع پروژه و Debug کردن API، ngrok یکی از ابزارهایی است که میتواند مقدار زیادی از دردسرهای راهاندازی یک سرور موقت را حذف کند.
سوالات متداول
آیا ngrok رایگان است؟
بله، ngrok در حال حاضر پلن رایگان دارد که برای تست و Development قابل استفاده است، البته محدودیتهایی در تعداد Request، Data Transfer و Endpointها دارد.
آیا برای ngrok باید سرور بخریم؟
خیر. در سناریوی این مقاله برنامه روی لپتاپ خودتان اجرا میشود و ngrok یک Endpoint عمومی برای دسترسی به آن ایجاد میکند.
آیا لپتاپ باید روشن بماند؟
بله. چون خود Django روی لپتاپ شما اجرا میشود، با خاموش شدن لپتاپ یا توقف Django/ngrok، API هم از دسترس خارج میشود.
آیا میتوان Django REST Framework را هم با ngrok آنلاین کرد؟
بله. برای ngrok تفاوت خاصی ندارد که API با JsonResponse نوشته شده باشد یا Django REST Framework. چیزی که اهمیت دارد آدرس و Port سرویس Local است.
مثلاً:
ngrok http 8000
آیا ngrok مشکل CORS را حل میکند؟
خیر. ngrok API را قابل دسترس میکند، ولی CORS مربوط به Browser و Headerهای پاسخ Application است. اگر Frontend روی Origin دیگری قرار دارد باید CORS را در Django یا لایه مناسب دیگری تنظیم کنید.
چرا Django خطای DisallowedHost میدهد؟
چون Domain ایجادشده توسط ngrok داخل ALLOWED_HOSTS پروژه نیست. Domain دقیق را به ALLOWED_HOSTS اضافه کنید.
آیا میتوان از ngrok برای Production استفاده کرد؟
خود ngrok امکانات Production نیز ارائه میدهد، اما چیزی که در این مقاله ساختهایم یعنی ngrok در مقابل python manage.py runserver روی لپتاپ شخصی معماری Production نیست. runserver از طرف Django فقط برای Development در نظر گرفته شده است.

















