<?xml version="1.0" encoding="UTF-8"?><rss version="2.0"><channel><title>نوشته های XDIA | ایکس‌دیا</title><link>https://virgool.ir/feed/@xdia</link><description>مرکز توسعه کسب‌وکارهای آنلاین. اول مسئله کسب‌وکار را می‌فهمیم، بعد سراغ فناوری می‌رویم. اینجا درباره مهندسی نرم‌افزار، طراحی  محصول، سیستم‌سازی و رشد دیجیتال می‌نویسیم. xdia.ir</description><language>fa</language><pubDate>2026-11-10 15:04:15</pubDate><image><url>https://files.virgool.ir/upload/users/4953979/avatar/H6OJw4.png</url><title>XDIA | ایکس‌دیا</title><link>https://virgool.ir/@xdia</link></image><item><title>معماری یک وب‌اپلیکیشن حرفه‌ای؛ از React و Django تا پایگاه داده و استقرار</title><link>https://virgool.ir/@xdia/web-app-architecture-react-django-gau6onbryled</link><description>تصویر مفهومی؛ ساخته‌شده با هوش مصنوعیمعماری نرم‌افزار را می‌شود این‌طور تعریف کرد: مجموعه تصمیم‌هایی که عوض کردنشان بعداً گران است. انتخاب زبان و فریم‌ورک، نحوه تقسیم کد به ماژول‌ها، مدل داده، روش احراز هویت و نحوه استقرار، همه از این جنس‌اند. بقیه چیزها را معمولاً می‌شود در مسیر اصلاح کرد.در این یادداشت یک وب‌اپلیکیشن واقعی را لایه‌به‌لایه می‌سازیم و در هر لایه توضیح می‌دهیم چه تصمیمی گرفته می‌شود و چرا. پشته فنی مثال‌ها React و Django است، اما بیشتر اصول به پشته‌های دیگر هم منتقل می‌شوند. این نوشته نسخه‌ای «درست برای همه» نیست؛ هر بخش جایی که انتخاب به شرایط پروژه بستگی دارد، این را صریح گفته است.مثال ما: پنل سفارش عمده برای یک پخش‌کنندهیک سناریوی فرضی ولی معمول را در نظر بگیرید: یک شرکت پخش می‌خواهد مشتریانش (فروشگاه‌ها) سفارش‌هایشان را آنلاین ثبت کنند. تیم فروش سفارش‌ها را بررسی و تأیید می‌کند، انبار موجودی را می‌بیند و آماده‌سازی را شروع می‌کند، و مدیر گزارش فروش می‌خواهد. سه نوع کاربر، چند فرایند به‌هم‌وابسته و داده‌ای که نباید خراب شود. مثال خوبی است، چون تقریباً همه مسائل یک سیستم سازمانی در آن هست.نمای کلی اجزای سیستم در مثال این نوشته؛ همه در قالب یک مونولیت ماژولار.نمای کلیدر ساده‌ترین شکل حرفه‌ای، اجزای سیستم این‌ها هستند:کلاینت: اپلیکیشن React که در مرورگر اجرا می‌شود.لبه: Nginx به‌عنوان reverse proxy که HTTPS را مدیریت می‌کند، فایل‌های استاتیک را سرو می‌کند و درخواست‌های API را به بک‌اند می‌فرستد.بک‌اند: Django و Django REST Framework که روی Gunicorn اجرا می‌شوند.پایگاه داده: PostgreSQL به‌عنوان منبع اصلی حقیقت.کارهای پس‌زمینه: Celery با Redis به‌عنوان صف، برای کارهایی مثل ارسال پیامک و ساخت گزارش.ذخیره فایل: فضای ذخیره‌سازی جدا از سرور برنامه، برای فاکتورها و تصاویر.مشاهده‌پذیری: لاگ، ثبت خطا و متریک، تا بدانیم سیستم در عمل چه می‌کند.نکته مهم این است که همه این‌ها می‌توانند داخل یک «مونولیت ماژولار» باشند: یک پروژه Django، یک پایگاه داده، یک بار استقرار. شروع با میکروسرویس برای چنین سیستمی معمولاً پیچیدگی‌ای اضافه می‌کند که هنوز هیچ مسئله‌ای را حل نکرده است.فرانت‌اند: React، اما کدام نوع؟اولین تصمیم این است که صفحه‌ها در مرورگر ساخته شوند (SPA) یا روی سرور (SSR). برای پنلی که پشت صفحه ورود است و موتور جست‌وجو قرار نیست آن را ببیند، یک SPA ساده با Vite کافی و کم‌هزینه است. اگر بخشی از سیستم عمومی است و باید در گوگل دیده شود، مثلاً کاتالوگ محصولات، فریم‌ورکی مثل Next.js که رندر سمت سرور دارد منطقی‌تر است.دو اصل در فرانت‌اند بیشترین اثر را روی نگهداری‌پذیری دارند:داده سرور را از وضعیت رابط کاربری جدا کنید. لیست سفارش‌ها مال سرور است و باید با ابزاری مثل TanStack Query کش، تازه‌سازی و هماهنگ شود. باز یا بسته بودن یک منو مال رابط کاربری است. قاطی کردن این دو، منشأ بخش بزرگی از باگ‌های «داده قدیمی» است.قانون کسب‌وکار فقط در فرانت‌اند نباشد. اعتبارسنجی فرم در مرورگر برای تجربه کاربری خوب است، اما هر قانونی که اهمیت دارد، مثل سقف اعتبار مشتری، باید در بک‌اند هم بررسی شود. هر چیزی که در مرورگر است، قابل دور زدن است.بک‌اند: ماژول‌ها بر اساس حوزه کسب‌وکاراپ‌های Django را بر اساس مفاهیم کسب‌وکار تقسیم کنید، نه لایه‌های فنی: customers، catalog، orders، inventory، billing. هر ماژول مدل‌ها، منطق و API خودش را دارد و وابستگی‌های بین ماژول‌ها باید کم و آگاهانه باشد.منطق کسب‌وکار را هم در view یا serializer پخش نکنید. یک لایه سرویس، یعنی توابع ساده پایتون که یک عملیات کامل کسب‌وکار را انجام می‌دهند، هم تست کردن را راحت می‌کند و هم اجازه می‌دهد همان منطق از API، پنل ادمین یا یک کار پس‌زمینه صدا زده شود. مثلاً ثبت سفارش و رزرو موجودی:# orders/services.py&#xA;from django.db import transaction&#xA;from django.db.models import F&#xA;&#xA;from inventory.models import Stock&#xA;from .models import Order&#xA;&#xA;&#xA;class OutOfStock(Exception):&#xA;    pass&#xA;&#xA;&#xA;def place_order(*, customer, items):&#xA;    with transaction.atomic():&#xA;        # Lock the stock rows so two concurrent orders can&#39;t oversell&#xA;        stocks = {&#xA;            s.product_id: s&#xA;            for s in Stock.objects.select_for_update().filter(&#xA;                product_id__in=[i.product_id for i in items]&#xA;            )&#xA;        }&#xA;        for item in items:&#xA;            stock = stocks.get(item.product_id)&#xA;            if stock is None or stock.quantity &lt; item.quantity:&#xA;                raise OutOfStock(item.product_id)&#xA;&#xA;        order = Order.objects.create(customer=customer)&#xA;        for item in items:&#xA;            order.lines.create(product_id=item.product_id, quantity=item.quantity)&#xA;            Stock.objects.filter(pk=stocks[item.product_id].pk).update(&#xA;                quantity=F(&#34;quantity&#34;) - item.quantity&#xA;            )&#xA;    return orderدو نکته در همین چند خط هست: همه تغییرات در یک تراکنش انجام می‌شوند، پس یا کل سفارش ثبت می‌شود یا هیچ‌چیز. و select_for_update ردیف‌های موجودی را قفل می‌کند تا دو سفارش هم‌زمان نتوانند آخرین کالای انبار را هر دو بخرند. این نوع خطا در محیط توسعه تقریباً هیچ‌وقت دیده نمی‌شود و در محیط واقعی، در شلوغ‌ترین روز سال سر می‌زند.طراحی APIAPI قرارداد بین فرانت‌اند و بک‌اند است و هرچه پایدارتر باشد، دو تیم مستقل‌تر کار می‌کنند. چند تصمیمی که ارزش دارد از روز اول گرفته شود:منابع و افعال روشن: GET /api/v1/orders/ برای فهرست، POST /api/v1/orders/ برای ثبت. عملیات‌هایی که در قالب CRUD نمی‌گنجند، مثل تأیید سفارش، می‌توانند endpoint جدا داشته باشند: POST /api/v1/orders/{id}/approve/.نسخه‌بندی: پیشوند v1 هزینه‌ای ندارد و روزی که لازم شود قرارداد را بشکنید، کمکتان می‌کند.صفحه‌بندی برای همه فهرست‌ها: فهرستی که امروز پنجاه ردیف دارد، دو سال بعد پنجاه هزار ردیف دارد.قالب خطای یکسان: فرانت‌اند باید بتواند همه خطاها را به یک شکل بخواند و نمایش دهد.Idempotency برای عملیات حساس: اگر کاربر دکمه پرداخت را دو بار زد یا شبکه درخواست را تکرار کرد، نباید دو تراکنش ثبت شود. یک کلید یکتا که کلاینت همراه درخواست می‌فرستد، این مشکل را حل می‌کند.مستندات خودکار: ابزاری مثل drf-spectacular از روی کد، مستند OpenAPI می‌سازد و مستندات را با واقعیت هماهنگ نگه می‌دارد.پایگاه داده: آخرین خط دفاعکد عوض می‌شود، اما داده می‌ماند. به همین دلیل قواعد مهم داده باید در خود پایگاه داده هم تعریف شوند، نه فقط در کد. اگر فردا اسکریپتی مستقیم روی دیتابیس اجرا شد یا باگی از اعتبارسنجی کد رد شد، دیتابیس جلوی داده نامعتبر را می‌گیرد:class OrderLine(models.Model):&#xA;    order = models.ForeignKey(Order, related_name=&#34;lines&#34;, on_delete=models.CASCADE)&#xA;    product = models.ForeignKey(&#34;catalog.Product&#34;, on_delete=models.PROTECT)&#xA;    quantity = models.IntegerField()&#xA;&#xA;    class Meta:&#xA;        constraints = [&#xA;            models.UniqueConstraint(&#xA;                fields=[&#34;order&#34;, &#34;product&#34;], name=&#34;uniq_product_per_order&#34;&#xA;            ),&#xA;            # Django 5.1+; older versions use check= instead of condition=&#xA;            models.CheckConstraint(&#xA;                condition=models.Q(quantity__gt=0), name=&#34;line_quantity_positive&#34;&#xA;            ),&#xA;        ]چند اصل دیگر:ایندکس را بر اساس کوئری‌های واقعی بسازید، نه حدس. فیلترهای پرتکرار، مثل وضعیت سفارش و تاریخ، اولین نامزدها هستند.مراقب مسئله N+1 باشید. نمایش صد سفارش همراه با نام مشتری نباید صد و یک کوئری بزند. select_related و prefetch_related در Django برای همین ساخته شده‌اند.حذف واقعی را با احتیاط انجام دهید. on_delete=PROTECT برای محصولی که در سفارش‌های قبلی آمده، جلوی پاک شدن ناخواسته تاریخچه را می‌گیرد.احراز هویت: سشن یا توکن؟این یکی از بحث‌برانگیزترین تصمیم‌هاست و جواب درست به نوع کلاینت بستگی دارد. اگر فرانت‌اند و API روی یک دامنه (یا زیردامنه‌های یک دامنه) هستند، سشن‌های خود Django با کوکی HttpOnly و محافظت CSRF ساده و امن است؛ جاوااسکریپت به کوکی دسترسی ندارد و ابطال نشست هم ساده است.توکن‌ها، مثل JWT، وقتی مزیت دارند که کلاینت‌های متنوع دارید: اپ موبایل، سرویس‌های دیگر یا API عمومی. در این حالت عمر توکن دسترسی را کوتاه نگه دارید و توکن را در localStorage ذخیره نکنید، چون هر آسیب‌پذیری XSS می‌تواند آن را بخواند. انتخاب JWT فقط به این دلیل که «مدرن‌تر است»، معمولاً پیچیدگی ابطال و نوسازی توکن را بی‌دلیل به پروژه اضافه می‌کند.برای ورود با کد یکبارمصرف پیامکی هم، محدودیت تعداد درخواست (rate limit) برای هر شماره و هر IP ضروری است؛ هم برای امنیت، هم برای قبض پنل پیامک.مجوزدهی: چه کسی به چه چیزی دسترسی دارداحراز هویت می‌گوید کاربر کیست؛ مجوزدهی می‌گوید چه کاری مجاز است. در مثال ما، کنترل دسترسی مبتنی بر نقش (RBAC) نقطه شروع خوبی است: فروشنده، انباردار، مدیر. اما RBAC به‌تنهایی کافی نیست. فروشنده‌ای که اجازه دیدن سفارش‌ها را دارد، فقط باید سفارش‌های مشتریان خودش یا سازمان خودش را ببیند. این «دسترسی در سطح شیء» است و بهترین جایش، محدود کردن queryset در خود بک‌اند است:class HasRole(BasePermission):&#xA;    &#34;&#34;&#34;Roles per action are declared on the view; undeclared actions are denied.&#34;&#34;&#34;&#xA;&#xA;    def has_permission(self, request, view):&#xA;        allowed = getattr(view, &#34;required_roles&#34;, {}).get(view.action, [])&#xA;        return request.user.groups.filter(name__in=allowed).exists()&#xA;&#xA;&#xA;class OrderViewSet(viewsets.ModelViewSet):&#xA;    serializer_class = OrderSerializer&#xA;    permission_classes = [IsAuthenticated, HasRole]&#xA;    required_roles = {&#xA;        &#34;list&#34;: [&#34;sales&#34;, &#34;manager&#34;],&#xA;        &#34;retrieve&#34;: [&#34;sales&#34;, &#34;manager&#34;],&#xA;        &#34;create&#34;: [&#34;sales&#34;, &#34;manager&#34;],&#xA;        &#34;partial_update&#34;: [&#34;manager&#34;],&#xA;        &#34;destroy&#34;: [&#34;manager&#34;],&#xA;    }&#xA;&#xA;    def get_queryset(self):&#xA;        # Scope every query to the user&#39;s organization&#xA;        return (&#xA;            Order.objects.filter(organization=self.request.user.organization)&#xA;            .select_related(&#34;customer&#34;)&#xA;            .prefetch_related(&#34;lines__product&#34;)&#xA;        )به پیش‌فرض این کد دقت کنید: اگر برای عملیاتی نقشی تعریف نشده باشد، دسترسی رد می‌شود. پیش‌فرض «بسته» یعنی فراموش کردن یک خط، به‌جای حفره امنیتی، یک خطای ۴۰۳ می‌سازد که سریع دیده و اصلاح می‌شود. مخفی کردن دکمه‌ها در فرانت‌اند خوب است، اما امنیت نیست.کارهای پس‌زمینههر کاری که کند است یا به سرویس بیرونی وابسته است، نباید کاربر را منتظر نگه دارد: ارسال پیامک تأیید سفارش، ساخت فایل گزارش ماهانه، همگام‌سازی با نرم‌افزار حسابداری. این کارها به صف Celery می‌روند. دو قاعده را فراموش نکنید: کارها باید قابل تکرار بدون اثر جانبی (idempotent) باشند، چون ممکن است دو بار اجرا شوند؛ و برای خطاهای موقت مثل قطعی سرویس پیامک، تلاش مجدد با فاصله رو به افزایش تعریف کنید.استقرارهدف استقرار خوب این است که انتشار نسخه جدید یک کار عادی و کم‌استرس باشد، نه یک رویداد. چند جزء اصلی:کانتینر: Docker محیط اجرای یکسان می‌سازد؛ چیزی که روی سیستم توسعه‌دهنده کار می‌کند، روی سرور هم کار می‌کند.تنظیمات و رمزها بیرون از کد: رمز پایگاه داده، کلیدهای API و SECRET_KEY از متغیرهای محیطی یا یک مدیر رمز خوانده شوند و هیچ‌وقت در مخزن کد نباشند.CI: هر تغییر قبل از ادغام، تست‌ها را پاس کند. استقرار از شاخه اصلی و با یک فرمان یا خودکار.مهاجرت‌های سازگار با عقب: اگر قرار است ستونی را تغییر نام دهید، اول ستون جدید را اضافه کنید، کد را طوری منتشر کنید که با هر دو کار کند، داده را منتقل کنید و در انتشار بعدی ستون قدیمی را حذف کنید. این الگو اجازه می‌دهد بدون قطعی منتشر کنید و در صورت نیاز به نسخه قبل برگردید.پشتیبان و تست بازیابی: پشتیبانی که هیچ‌وقت بازیابی‌اش آزمایش نشده، فقط یک فرض است.امنیت: فهرست حداقلیبیشتر رخنه‌ها از اشتباه‌های ساده می‌آیند، نه حمله‌های پیچیده. این فهرست جای ممیزی امنیتی را نمی‌گیرد، اما حداقلی است که هر وب‌اپلیکیشنی باید داشته باشد:HTTPS همه‌جا، و DEBUG = False و ALLOWED_HOSTS درست در محیط تولید.اتکا به ORM برای کوئری‌ها؛ هرجا SQL خام لازم شد، فقط با پارامتر، هرگز با چسباندن رشته.React خروجی را به‌طور پیش‌فرض escape می‌کند؛ هر استفاده از dangerouslySetInnerHTML باید دلیل و پاک‌سازی داشته باشد.محدودیت نرخ درخواست برای ورود، فراموشی رمز و ارسال کد.به‌روزرسانی منظم وابستگی‌ها و بررسی آسیب‌پذیری‌های شناخته‌شده آن‌ها.ثبت رویدادهای حساس، مثل تغییر نقش کاربران، برای پیگیری بعدی.مقیاس‌پذیری: اول اندازه بگیریدبیشتر سیستم‌های سازمانی هیچ‌وقت به مرزی نمی‌رسند که یک سرور خوب و یک پایگاه داده تنظیم‌شده از پسش برنیاید. بیشتر پروژه‌ها زیر بار پیچیدگی از پا درمی‌آیند، نه زیر بار ترافیک. پس به‌جای طراحی برای میلیون‌ها کاربر خیالی، سیستم را طوری بسازید که اگر روزی لازم شد، بشود مقیاسش را بالا برد:سرورهای برنامه بی‌حالت (stateless) باشند تا بشود چند نسخه از آن‌ها را پشت load balancer گذاشت.فایل‌ها روی دیسک سرور برنامه ذخیره نشوند.کش فقط برای جاهایی که اندازه‌گیری نشان داده کند هستند؛ کش زودهنگام، باگ «داده قدیمی» می‌سازد.پایگاه داده معمولاً آخرین گلوگاه است: اول کوئری و ایندکس، بعد سخت‌افزار، بعد نسخه‌های فقط‌خواندنی.تست و مانیتورینگهرم تست هنوز راهنمای خوبی است: تعداد زیادی تست واحد برای لایه سرویس، که سریع اجرا می‌شوند و منطق کسب‌وکار را پوشش می‌دهند؛ تست‌های API با APIClient برای بررسی مجوزها و قرارداد پاسخ‌ها؛ و چند تست سرتاسری با ابزاری مثل Playwright فقط برای مسیرهای حیاتی، مثل ثبت و تأیید سفارش. تست مجوزها را جدی بگیرید: «فروشنده سازمان الف نباید سفارش سازمان ب را ببیند» دقیقاً همان تستی است که بعداً جانتان را نجات می‌دهد.بعد از استقرار، مانیتورینگ جای تست را می‌گیرد. سه چیز لازم دارید: لاگ ساخت‌یافته که بشود در آن جست‌وجو کرد، ثبت خطا با جزئیات (ابزاری مثل Sentry که نسخه خودمیزبان هم دارد)، و چند متریک کلیدی مثل زمان پاسخ، نرخ خطا و طول صف کارهای پس‌زمینه. هشدارها را هم فقط برای چیزهایی تعریف کنید که واقعاً باید کسی را بیدار کنند؛ هشداری که هر روز بی‌دلیل می‌آید، روزی که دلیل دارد هم نادیده گرفته می‌شود.خلاصه تصمیم‌ها: از ساده شروع کنیدساختار کلی: مونولیت ماژولار. وقتی تیم‌های مستقل یا نیاز مقیاس جداگانه پیدا شد، سراغ جدا کردن سرویس‌ها بروید.فرانت‌اند: SPA برای پنل‌های پشت ورود؛ SSR برای صفحه‌هایی که باید در جست‌وجو دیده شوند.احراز هویت: سشن روی دامنه یکسان؛ توکن وقتی کلاینت موبایل یا سرویس بیرونی دارید.مجوزدهی: نقش‌ها به‌علاوه محدود کردن داده در سطح شیء، با پیش‌فرض بسته.پایگاه داده: یک PostgreSQL با قیدهای درست. نسخه فقط‌خواندنی وقتی اندازه‌گیری گفت لازم است.کارهای کند: صف پس‌زمینه با کارهای idempotent.استقرار: کانتینر، CI و مهاجرت‌های سازگار با عقب، از همان نسخه اول.معماری خوب، معماری‌ای نیست که همه این‌ها را از روز اول داشته باشد. معماری‌ای است که هر تصمیمش دلیل روشنی دارد، جاهایی که ممکن است عوض شوند را باز نگه می‌دارد و بقیه را تا جای ممکن ساده می‌گیرد. اگر قرار است فقط یک جمله از این نوشته در ذهنتان بماند، این باشد: پیچیدگی را وقتی اضافه کنید که مسئله‌اش را دیده‌اید، نه وقتی که تصورش را کرده‌اید.</description><category>XDIA | ایکس‌دیا</category><author>XDIA | ایکس‌دیا</author><pubDate>Sat, 10 Oct 2026 00:30:29 +0330</pubDate></item><item><title>قبل از سفارش طراحی سایت، این ۱۰ سؤال را از خودتان بپرسید</title><link>https://virgool.ir/@xdia/10-questions-before-ordering-a-website-fvtnq4tlmpci</link><description>تصویر مفهومی؛ ساخته‌شده با هوش مصنوعیبیشتر پروژه‌های طراحی سایتی که به دردسر می‌افتند، از جلسه اول مشکل داشته‌اند؛ فقط مشکل دیر دیده شده است. سفارش‌دهنده تصور روشنی از نتیجه داشته، طراح تصور روشن دیگری، و هیچ‌کدام آن را روی کاغذ نیاورده‌اند. چند ماه بعد، هر دو طرف حس می‌کنند حقشان خورده شده.خبر خوب این است که بخش بزرگی از این سوءتفاهم‌ها با چند سؤال ساده قبل از شروع کار برطرف می‌شود. سؤال‌هایی که تیم طراحی خوب به‌هرحال از شما می‌پرسد، اما اگر خودتان از قبل جوابشان را بدانید، هم انتخاب تیم راحت‌تر می‌شود و هم پروژه با تصمیم‌های بهتری شروع می‌شود.برای هر سؤال یک توضیح کوتاه، یک مثال و یک کار عملی آورده‌ایم. مثال‌ها فرضی‌اند، اما از موقعیت‌هایی گرفته شده‌اند که در پروژه‌های وب رایج‌اند.۱. این سایت قرار است کدام مسئله کسب‌وکار را حل کند؟«سایت می‌خواهیم» هدف نیست؛ وسیله است. هدف چیزی است که بعد از راه‌اندازی سایت باید عوض شود: تعداد درخواست مشاوره، فروش آنلاین، کم شدن تماس‌های تکراری با پشتیبانی، یا اعتبار در چشم مشتریان سازمانی.مثال: یک آموزشگاه زبان می‌گوید سایت می‌خواهد. با کمی سؤال معلوم می‌شود مشکل اصلی‌اش این است که منشی روزانه ده‌ها بار به سؤال «کلاس بعدی کِی شروع می‌شود و هزینه‌اش چقدر است؟» جواب می‌دهد. این یعنی صفحه تقویم کلاس‌ها و ثبت‌نام آنلاین از گالری عکس مهم‌تر است.کار عملی: هدف سایت را در یک جمله بنویسید که یک عدد یا رفتار قابل مشاهده در آن باشد. اگر نشد، هنوز برای سفارش آماده نیستید.۲. مخاطب اصلی کیست و قبل از تصمیم چه چیزی باید بداند؟سایتی که برای «همه» طراحی شود، معمولاً با هیچ‌کس درست حرف نمی‌زند. مخاطب اصلی را مشخص کنید و ببینید او قبل از تماس گرفتن یا خرید، به چه سؤال‌هایی باید جواب بگیرد.مثال: یک تولیدکننده قطعات صنعتی دو مخاطب دارد: مدیر خرید که دنبال مشخصات فنی، گواهی‌ها و زمان تحویل است، و مدیرعامل که می‌خواهد بداند شرکت چقدر قابل اتکاست. سایت باید برای هر دو مسیر جدا داشته باشد.کار عملی: پنج سؤالی را که مشتری‌ها معمولاً پشت تلفن می‌پرسند فهرست کنید. سایت باید به همین‌ها جواب بدهد.۳. کدام امکانات واقعاً ضروری‌اند؟فهرست امکانات معمولاً با نگاه به سایت رقبا بلند می‌شود: چت آنلاین، وبلاگ، باشگاه مشتریان، دو زبانه بودن. هر کدام هزینه ساخت و هزینه نگهداری دارد. امکاناتی که کسی از آن استفاده نکند، فقط سایت را سنگین‌تر می‌کند.مثال: بخش وبلاگ برای کسب‌وکاری که هیچ‌کس را برای نوشتن ندارد، بعد از سه پست رها می‌شود و آخرین تاریخ انتشارش، بیشتر از نبودِ وبلاگ به اعتبار سایت ضربه می‌زند.کار عملی: امکانات را در سه ستون بنویسید: «بدون این راه‌اندازی نمی‌کنیم»، «مفید است»، «بعداً». نسخه اول فقط ستون اول را لازم دارد.۴. محتوای سایت را چه کسی و تا کی آماده می‌کند؟یکی از رایج‌ترین دلایل تأخیر در پروژه‌های وب، نه برنامه‌نویسی است و نه طراحی؛ محتواست. متن صفحه‌ها، عکس محصولات، مشخصات فنی، نمونه‌کارها. وقتی مشخص نباشد چه کسی مسئول آماده کردن این‌هاست، پروژه هفته‌ها منتظر می‌ماند.مثال: طراحی یک فروشگاه آنلاین تمام شده، اما عکس‌های ۲۰۰ محصول هنوز گرفته نشده‌اند. سایت یا با عکس‌های بی‌کیفیت باز می‌شود، یا اصلاً باز نمی‌شود.کار عملی: قبل از قرارداد روشن کنید تولید متن و عکس با شماست یا با تیم طراحی، و برای تحویل محتوا هم مثل بقیه کار، تاریخ بگذارید.۵. بودجه و دامنه کار چطور با هم جفت می‌شوند؟بودجه بدون دامنه کار مشخص، عدد بی‌معنایی است و دامنه کار بدون بودجه، فهرست آرزوهاست. این دو باید کنار هم تعریف شوند. اگر بودجه محدود است، بهتر است دامنه را کوچک کنید تا کیفیت را.مثال: دو پیشنهاد قیمت با اختلاف زیاد معمولاً دو کار متفاوت را قیمت داده‌اند: یکی قالب آماده با کمی شخصی‌سازی، دیگری طراحی اختصاصی با تحلیل نیاز. مقایسه عددی آن‌ها بدون مقایسه شرح کار گمراه‌کننده است.کار عملی: از هر پیشنهاددهنده بخواهید شرح کارش را به تفکیک بنویسد و بپرسید درخواست تغییرات خارج از قرارداد چطور قیمت‌گذاری می‌شود.۶. سایت باید با چه سیستم‌هایی ارتباط داشته باشد؟سایت تنها نیست. درگاه پرداخت، پنل پیامک، نرم‌افزار حسابداری، انبار، CRM یا حتی یک جدول ساده که تیم فروش با آن کار می‌کند. هر اتصال باید از اول دیده شود، چون اضافه کردنش بعد از راه‌اندازی معمولاً گران‌تر است.مثال: فروشگاهی که موجودی‌اش را در نرم‌افزار حسابداری نگه می‌دارد و این دو به هم وصل نیستند، دیر یا زود کالایی را می‌فروشد که در انبار ندارد.کار عملی: فهرست ابزارهایی را که امروز استفاده می‌کنید بنویسید و برای هر کدام مشخص کنید چه اطلاعاتی باید بین آن و سایت رد و بدل شود.۷. شش ماه و دو سال بعد چه تغییری انتظار دارید؟سایت را برای امروز می‌سازید، اما باید بتواند فردا هم تغییر کند: محصول جدید، شهر جدید، زبان دوم، پنل نمایندگان. لازم نیست امروز همه این‌ها را بسازید؛ کافی است ساختار جلوی آن‌ها را نبندد. پیچیده کردن پروژه برای آینده‌ای که شاید هیچ‌وقت نیاید، به همان اندازه اشتباه است.مثال: اگر احتمال می‌دهید سال بعد فروش عمده هم داشته باشید، کافی است از حالا مدل کاربران طوری طراحی شود که بعداً بشود نوع «مشتری عمده» با قیمت متفاوت به آن اضافه کرد.کار عملی: سه تغییر محتمل در دو سال آینده را با تیم طراحی در میان بگذارید و بپرسید هرکدام بعداً چقدر هزینه دارد.۸. مالکیت دامنه، کد، هاست و داده‌ها با کیست؟این سؤال کمتر از بقیه پرسیده می‌شود و وقتی اهمیتش معلوم می‌شود که رابطه کاری تمام شده است. اگر دامنه به نام مجری ثبت شده باشد، رمز هاست فقط دست او باشد یا کد سایت به شما تحویل نشود، عملاً بدون او نمی‌توانید سایت خودتان را جابه‌جا یا توسعه دهید.مثال: کسب‌وکاری که می‌خواهد تیم توسعه‌اش را عوض کند، متوجه می‌شود دامنه .ir با شناسه ایرنیک مجری قبلی ثبت شده و برای انتقالش باید با او هماهنگ کند.کار عملی: در قرارداد بنویسید دامنه به نام چه کسی ثبت می‌شود، کد منبع و دسترسی‌های مدیریتی کِی و چطور تحویل می‌شوند، و داده‌های مشتریان متعلق به کیست. این بند برای هر دو طرف شفافیت می‌آورد.۹. نگهداری و پشتیبانی بعد از تحویل چطور انجام می‌شود؟سایت بعد از راه‌اندازی تمام نمی‌شود. به‌روزرسانی‌های امنیتی، پشتیبان‌گیری، رفع خطا و تغییرات کوچک همیشگی‌اند. اگر مشخص نباشد چه کسی و با چه هزینه‌ای مسئول این‌هاست، سایت آرام‌آرام فرسوده می‌شود.مثال: افزونه‌ای که دو سال به‌روز نشده، راه نفوذ به سایت را باز می‌کند و تازه آن موقع معلوم می‌شود هیچ نسخه پشتیبان سالمی وجود ندارد.کار عملی: بپرسید پشتیبان‌ها کجا و هر چند وقت یک بار گرفته می‌شوند، آخرین بار کِی بازیابی آن‌ها آزمایش شده، و زمان پاسخ به یک خطای جدی چقدر است.۱۰. پروژه را با چه معیاری «تحویل‌شده» و با چه معیاری «موفق» می‌دانید؟این دو یکی نیستند. معیار تحویل یعنی چه چیزهایی باید ساخته و کار کند تا قرارداد تمام شده حساب شود. معیار موفقیت یعنی بعد از چند ماه، چه چیزی در کسب‌وکار باید بهتر شده باشد. اولی را باید در قرارداد نوشت؛ دومی را باید با هم دنبال کرد.مثال: «سایت روی موبایل و دسکتاپ بدون خطا کار کند و فرم‌ها به پنل فروش برسند» معیار تحویل است. «درخواست‌های آنلاین در سه ماه اول از تماس تلفنی بیشتر شود» معیار موفقیت است.کار عملی: یک فهرست کوتاه از معیارهای پذیرش بنویسید که بشود تک‌تک آن‌ها را آزمایش کرد، و جدا از آن، یکی دو عدد را انتخاب کنید که می‌خواهید بعد از راه‌اندازی دنبالشان کنید.چک‌لیست پیش از سفارشاگر وقت ندارید همه متن را دوباره بخوانید، قبل از امضای قرارداد این فهرست را مرور کنید:هدف سایت در یک جمله، همراه با یک عدد یا رفتار قابل اندازه‌گیری، نوشته شده است.مخاطب اصلی و پنج سؤال پرتکرارش مشخص است.امکانات به «ضروری»، «مفید» و «بعداً» تقسیم شده‌اند.مسئول و تاریخ تحویل محتوا روشن است.شرح کار تفکیکی است و نحوه قیمت‌گذاری تغییرات مشخص شده.سیستم‌هایی که باید به سایت وصل شوند فهرست شده‌اند.تغییرات محتمل دو سال آینده با تیم طراحی مطرح شده است.مالکیت دامنه، کد، دسترسی‌ها و داده‌ها در قرارداد آمده است.برنامه پشتیبان‌گیری، به‌روزرسانی و پشتیبانی بعد از تحویل معلوم است.معیارهای پذیرش و شاخص‌های موفقیت جداگانه تعریف شده‌اند.هیچ‌کدام از این سؤال‌ها فنی نیست و برای جواب دادن به آن‌ها لازم نیست برنامه‌نویسی بلد باشید. اما همین‌ها هستند که تعیین می‌کنند سایت شما بعد از راه‌اندازی به کار کسب‌وکار می‌آید یا فقط یک هزینه انجام‌شده است. و اگر تیمی که با آن صحبت می‌کنید خودش این سؤال‌ها را نپرسید، همین هم نشانه خوبی برای تصمیم‌گیری است.</description><category>XDIA | ایکس‌دیا</category><author>XDIA | ایکس‌دیا</author><pubDate>Sat, 10 Oct 2026 00:23:42 +0330</pubDate></item><item><title>بعد از کلیک روی «ارسال» چه می‌شود؟ چرا سایت خوب به‌تنهایی فروش نمی‌سازد</title><link>https://virgool.ir/@xdia/website-alone-does-not-sell-qjktke0vm9o0</link><description>تصویر مفهومی؛ ساخته‌شده با هوش مصنوعیفرض کنید یک کارگاه مبلمان تازه سایتش را عوض کرده است. (مثال فرضی است، اما احتمالاً برایتان آشناست.) طراحی تمیز است، عکس‌ها حرفه‌ای‌اند و سایت روی موبایل هم خوب باز می‌شود. چند ماه بعد، مدیر کارگاه حس می‌کند چیزی تغییر نکرده: سفارش‌ها هنوز بیشتر از دایرکت اینستاگرام و تلفن می‌آیند و هیچ‌کس دقیق نمی‌داند فرم «درخواست مشاوره» سایت در این مدت چند بار پر شده و چه بر سر آن درخواست‌ها آمده است.اولین واکنش معمولاً این است که «لابد طراحی ایراد دارد». گاهی هم دارد. اما در بیشتر موارد مشکل جای دیگری است: سایت ساخته شده، ولی به فرایند فروش وصل نشده است. سایت یک حلقه از زنجیره است و اگر حلقه‌های قبل و بعدش درست کار نکنند، بهترین طراحی هم کار زیادی از پیش نمی‌برد.در این یادداشت همین زنجیره را باز می‌کنیم: سایت دقیقاً چه کاری باید بکند، بعد از کلیک روی دکمه «ارسال» چه باید اتفاق بیفتد و چه چیزهایی را باید اندازه گرفت تا بدانیم سایت واقعاً به رشد کسب‌وکار کمک می‌کند یا نه.سایت قرار است کدام کار را انجام بدهد؟اگر از صاحبان کسب‌وکار بپرسید چرا سایت می‌خواهند، جواب‌ها معمولاً کلی است: «برای اعتبار»، «همه دارند»، «برای سئو». هیچ‌کدام غلط نیست، اما هیچ‌کدام هم به تیم طراحی نمی‌گوید دقیقاً چه چیزی باید ساخته شود.برای بیشتر کسب‌وکارها، سایت سه کار مشخص دارد:پیدا شدن: کسی که دنبال راه‌حل مشکلش می‌گردد، باید به شما برسد؛ از گوگل، از لینکی که دوستش فرستاده یا از تبلیغ.قانع کردن: بازدیدکننده باید سریع بفهمد شما دقیقاً چه کاری می‌کنید، برای چه کسی، و چرا می‌شود به شما اعتماد کرد.هدایت به قدم بعد: خرید، تماس، رزرو یا درخواست پیش‌فاکتور. هر سایتی باید یک «قدم بعدی» روشن داشته باشد.یک آزمون ساده: اگر نمی‌توانید در یک جمله بگویید «بازدیدکننده‌ای که از صفحه اول ما راضی است، بعدش چه کاری می‌کند؟»، سایت شما احتمالاً بیشتر ویترین است تا ابزار فروش. ویترین بد نیست؛ فقط نباید از آن انتظار فروشنده داشت.نشانه‌هایی که می‌گویند سایت فقط ویترین استاین نشانه‌ها در کسب‌وکارهای کوچک و متوسط رایج‌اند. اگر بیشتر از دو مورد برایتان صدق می‌کند، احتمالاً مشکل اصلی «طراحی» نیست:نمی‌دانید فرم‌های تماس سایت به ایمیل یا پنل چه کسی می‌رود و چه کسی مسئول جواب دادن به آن‌هاست.نمی‌دانید از هر صد بازدیدکننده، چند نفر تماس می‌گیرند یا فرم پر می‌کنند.تیم فروش نمی‌داند مشتری از کدام صفحه یا کدام تبلیغ آمده است.محتوای سایت از روز راه‌اندازی تقریباً دست نخورده است.آخرین تصمیمی را که بر اساس داده‌های سایت گرفته‌اید، به خاطر نمی‌آورید.مسیر واقعی: از غریبه تا مشتریبهتر است به‌جای «سایت»، به مسیری فکر کنیم که یک نفر از اولین آشنایی تا خرید، و حتی خرید دوباره، طی می‌کند. این مسیر در هر کسب‌وکاری شکل خودش را دارد، اما اسکلتش معمولاً همین است:آشنایی: جست‌وجو در گوگل، شبکه‌های اجتماعی، معرفی یا تبلیغ.بررسی: صفحه خدمات یا محصول، قیمت، نمونه‌کار، تجربه مشتریان قبلی.اقدام: پر کردن فرم، تماس یا افزودن به سبد خرید.پیگیری: پاسخ تیم فروش، مذاکره، ارسال پیش‌فاکتور.تحویل: انجام سفارش یا ارائه خدمت.بازگشت: خرید دوباره و معرفی به دیگران.سایت معمولاً فقط مرحله‌های دوم و سوم را پوشش می‌دهد و در بهترین حالت روی مرحله اول هم اثر دارد. اما فروش در مرحله چهارم بسته می‌شود؛ جایی که اغلب هیچ ارتباطی با سایت ندارد. بیشترِ مشتری‌ها همین‌جا گم می‌شوند.مسیر از غریبه تا مشتری: سایت معمولاً مرحله‌های بررسی و اقدام را پوشش می‌دهد؛ ریزش اصلی در مرحله پیگیری است.بعد از کلیک روی «ارسال»یک فرم «درخواست مشاوره» را در نظر بگیرید. از دید بازدیدکننده، کار تمام شده است. از دید کسب‌وکار، تازه شروع شده. چند سؤال ساده نشان می‌دهد این بخش چقدر جدی گرفته شده است:درخواست به کجا می‌رود؟ ایمیلی که هفته‌ای یک بار باز می‌شود، یا جایی که تیم فروش واقعاً هر روز با آن کار می‌کند؟چقدر طول می‌کشد تا کسی جواب بدهد؟ مشتری‌ای که امروز فرم پر کرده، ممکن است هم‌زمان با رقیب‌های شما هم تماس گرفته باشد.اگر مسئول پاسخ‌گویی مرخصی باشد، چه کسی درخواست را می‌بیند؟بعد از اولین تماس، پیگیری بعدی کِی و توسط چه کسی انجام می‌شود؟آیا بعداً می‌شود فهمید این مشتری از کدام صفحه یا کدام کمپین آمده بود؟جواب این سؤال‌ها ربطی به رنگ دکمه‌ها ندارد؛ ربطش به فرایند است. سایتی که فرم‌هایش در یک صندوق ایمیل شلوغ گم می‌شوند، عملاً بخشی از تقاضای واقعی بازار را دور می‌ریزد، بدون اینکه این ضرر در هیچ گزارشی دیده شود.CRM لازم نیست از روز اول پیچیده باشدوقتی حرف از ثبت و پیگیری مشتری می‌شود، خیلی‌ها فوراً به نرم‌افزارهای بزرگ CRM فکر می‌کنند. برای یک کسب‌وکار کوچک، شروع می‌تواند خیلی ساده‌تر باشد: یک جدول مشترک که هر درخواست با تاریخ، منبع، مسئول پیگیری و وضعیتش در آن ثبت شود. همین جدول ساده سه چیز به شما می‌دهد که قبلاً نداشتید: هیچ درخواستی گم نمی‌شود، مسئولیت‌ها مشخص است و بعد از چند ماه داده‌ای دارید که می‌شود به آن نگاه کرد.وقتی این نشانه‌ها پیدا شد، سراغ CRM واقعی بروید: تعداد درخواست‌ها از توان جدول بیرون زده، چند نفر هم‌زمان روی یک مشتری کار می‌کنند، یا اطلاعات مشتری باید بین فروش، انبار و حسابداری جابه‌جا شود.اتوماسیون؛ برای کارهای تکراری، نه برای حذف آدم‌هااتوماسیون در این مرحله یعنی کارهایی را که هر بار به یک شکل تکرار می‌شوند به سیستم بسپارید تا آدم‌ها برای گفت‌وگو با مشتری وقت داشته باشند. چند نمونه رایج:ارسال خودکار پیامک تأیید به مشتری بعد از ثبت فرم، همراه با زمان تقریبی تماس.سپردن خودکار درخواست به یک فروشنده بر اساس نوع خدمت یا شهر.یادآوری به فروشنده، اگر درخواستی بیشتر از یک روز بی‌پاسخ ماند.ثبت خودکار منبع ورود مشتری (مثلاً پارامترهای UTM کمپین) کنار اطلاعات او.هیچ‌کدام از این‌ها پروژه بزرگی نیست، اما هرکدام یک نقطه نشت را می‌بندد.تجربه کاربری یعنی کم کردن اصطکاکتجربه کاربری را گاهی با سلیقه بصری یکی می‌گیرند. در عمل، بخش بزرگی از آن یعنی پیدا کردن جاهایی که کاربر بی‌دلیل اذیت می‌شود. چند نمونه آشنا:فرمی با ده‌ها فیلد برای یک درخواست ساده، در حالی که برای اولین تماس، نام و شماره کافی است.شماره تلفنی که روی موبایل قابل لمس نیست و کاربر باید آن را حفظ یا کپی کند.نبود هیچ نشانه‌ای از قیمت یا بازه قیمت. کاربری که نمی‌داند با چه رقمی طرف است، اغلب تماس نمی‌گیرد؛ فقط می‌رود.صفحه‌هایی که روی اینترنت موبایل کند باز می‌شوند، چون تصاویرشان بهینه نشده‌اند.اصلاح هرکدام از این موارد معمولاً از بازطراحی کامل ارزان‌تر است و اثرش زودتر دیده می‌شود.سئو کانال است، نه افزونهسئو را نمی‌شود بعد از ساخت سایت «نصب» کرد. ساختار صفحه‌ها، سرعت، آدرس‌ها و از همه مهم‌تر محتوایی که به سؤال واقعی مخاطب جواب می‌دهد، از همان ابتدا روی دیده شدن سایت در جست‌وجو اثر می‌گذارند. سئوی فنی مانع‌ها را برمی‌دارد، اما جای «جواب خوب» را نمی‌گیرد.دو نکته را هم باید صادقانه گفت: نتیجه سئو زمان‌بر است و هیچ‌کس نمی‌تواند رتبه مشخصی را در گوگل تضمین کند. و ترافیک جست‌وجو فقط وقتی ارزش دارد که به همان مسیری وصل باشد که بالاتر گفتیم. هزار بازدید از کسانی که هیچ‌وقت مشتری نمی‌شوند، چیزی را عوض نمی‌کند.چه چیزی را بسنجیم؟بدون اندازه‌گیری، هر بحثی درباره سایت به بحث سلیقه‌ها تبدیل می‌شود. لازم نیست ده‌ها شاخص را دنبال کنید؛ چند عدد درست کافی است:نرخ تبدیل بازدید به درخواست: از هر صد بازدید، چند فرم یا تماس ثبت می‌شود؟ این عدد را برای صفحه‌های مهم جداگانه ببینید.منبع درخواست‌ها: گوگل، اینستاگرام، تبلیغ یا معرفی. کدام منبع درخواست بیشتری می‌آورد و کدام مشتری بهتری؟زمان پاسخ: فاصله ثبت درخواست تا اولین تماس.نرخ تبدیل درخواست به مشتری: از هر ده درخواست، چندتا به فروش رسید؟هزینه جذب هر مشتری: برای کانال‌های پولی، کل هزینه تقسیم بر تعداد مشتری‌های واقعی؛ نه تعداد کلیک.نکته جالب اینکه بیشتر این اعداد را نمی‌شود فقط از ابزارهای تحلیل سایت درآورد. نیمی از آن‌ها از همان جدول یا CRM می‌آید. یعنی سایت و فرایند فروش، از نظر داده هم به هم وابسته‌اند.چه زمانی سراغ توسعه اختصاصی برویم؟با همه این حرف‌ها، جواب همیشه «یک سیستم اختصاصی بسازید» نیست. ابزارهای آماده، از سیستم‌های مدیریت محتوا تا CRMهای آماده، برای بسیاری از کسب‌وکارها کافی‌اند و ارزان‌ترند. نشانه‌هایی که می‌گویند وقت توسعه اختصاصی رسیده، معمولاً این‌هاست:فرایند کسب‌وکار شما با منطق ابزارهای آماده جور درنمی‌آید و مدام مجبورید دورش بزنید.اطلاعات بین چند سیستم دستی کپی می‌شود و خطای انسانی هزینه‌ساز شده است.داده‌های مهم در چند جای مختلف پراکنده‌اند و هیچ تصویر یکپارچه‌ای از مشتری ندارید.بخشی از مزیت رقابتی شما دقیقاً در همان فرایندی است که ابزارهای عمومی پشتیبانی نمی‌کنند.اگر هیچ‌کدام صدق نمی‌کند، احتمالاً بهترین سرمایه‌گذاری بهتر کردن همان چیزی است که دارید. ساده‌ترین راه‌حلی که مسئله را واقعاً حل کند، تقریباً همیشه از پیچیده‌ترین راه‌حل بهتر است.جمع‌بندی: قبل از بازطراحی، این چهار سؤال را بپرسیددفعه بعد که به نظرتان رسید «سایت باید عوض شود»، قبل از هر کاری به این‌ها جواب بدهید:قدم بعدی بازدیدکننده در سایت ما دقیقاً چیست؟بعد از برداشتن آن قدم، درخواست به دست چه کسی می‌رسد و چقدر طول می‌کشد تا جواب بگیرد؟کدام‌یک از عددهای بالا را امروز می‌دانیم؟مشتری‌ها کجای مسیر بیشتر از همه ریزش دارند؟گاهی جواب این سؤال‌ها نشان می‌دهد که سایت واقعاً باید عوض شود. اما خیلی وقت‌ها معلوم می‌شود که سایت سر جایش است و آنچه کم است، پلِ بین سایت و بقیه کسب‌وکار است.</description><category>XDIA | ایکس‌دیا</category><author>XDIA | ایکس‌دیا</author><pubDate>Sat, 10 Oct 2026 00:08:46 +0330</pubDate></item></channel></rss>