دیباگ در توسعه موبایل — ماهیت، حالت‌های اشکال‌زدایی و نحوه کارکرد

نویسنده: IT Sectr منتشر شده: 2026-05-06 زمان مطالعه: 8 دقیقه

دیباگ (حالت اشکال‌زدایی) — پیکربندی کمپیلاسیون برنامه موبایل است که در آن کمپایلر اطلاعات سمبلیک را وارد می‌کند، بهینه‌سازی کد را غیرفعال می‌کند و برای تجزیه و تحلیل گام‌به‌گام دیباگر را متصل می‌کند. به گزارش Android Developers، بیلد Debug شامل سمبل‌های اشکال‌زدایی است، منابع را فشرده نمی‌کند و امکان اتصال بازرسی پایگاه داده و درخواست‌های شبکه را فراهم می‌کند. حالت Debug در مقابل بیلد Release قرار می‌گیرد: در Debug توسعه‌دهنده برای شفافیت اجرای کد، عملکرد را قربان می‌دهد.

نکات کلیدی

  • دیباگ — پیکربندی کمپیلاسیون با اطلاعات اشکال‌زدایی، بهینه‌سازی غیرفعال و دسترسی به دیباگر
  • دیباگر امکان قرار دادن نقاط توقف، مشاهده متغیرها و اجرای گام‌به‌گام کد را فراهم می‌کند
  • بیلد Debug با گواهینامه اشکال‌زدایی امضا می‌شود و قابل انتشار در فروشگاه‌های برنامه نیست
  • LLDB — دیباگر اصلی برای iOS/macOS، و LLDB در Android Studio — برای Android
  • عملکرد بیلد Debug به دلیل نبود بهینه‌سازی‌های کمپایلر از Release پایین‌تر است

ماهیت حالت Debug در توسعه موبایل

Debug (اشکال‌زدایی) — صرفا یک علم کمپایلر نیست، بلکه مجموعه‌ای از تنظیمات است که برنامه را برای توسعه‌دهنده شفاف می‌کند. در حالت Debug، کمپایلر جدول اسامی سمبولیک (DWARF) را به فایل اجرایی اضافه می‌کند که کد ماشین را با سطور منبع مرتبط می‌سازد. بدون این جدول، دیباگر نمی‌تواند نشان دهد که کدام سطر کد در حال حاضر اجرا می‌شود.

دیباگر — برنامه‌ای است که برنامه شما را در یک محیط کنترل شده اجرا می‌کند. می‌توانید اجرا را در هر سطری (breakpoint) متوقف کنید، مقادیر تمام متغیرها را در حوزه جاری مشاهده کنید، آن‌ها را در حال اجرا تغییر دهید و اجرا را ادامه دهید. برای پلتفرم‌های موبایل، دیباگر استاندارد LLDB است — کامپوننت LLVM که هم در Xcode و هم در Android Studio استفاده می‌شود.

حالت Debug همچنین بررسی‌های افزوده را که در Release غیرفعال هستند فعال می‌کند: تأکیدها (assertions)، بررسی مرزهای آرایه، آشکارساز‌های نشت حافظه و ثبت گسترده. این بررسی‌ها کار برنامه را کند می‌کنند، اما خطاها را در مراحل اولیه توسعه — قبل از اینکه کد به کاربر برسد — شناسایی می‌کنند.

Debug و Release: تفاوت‌های کلیدی بیلدها

تفاوت بین بیلدهای Debug و Release اساسی است: این‌ها دو مجموعه متفاوت از علم‌های کمپایلر، تنظیمات امضا و تنظیمات بسته‌بندی هستند. درک این تفاوت‌ها از وضعیت‌هایی که «در شبیه‌ساز کار می‌کند، اما روی دستگاه واقعی نه» جلوگیری می‌کند.

پارامترDebugRelease
بهینه‌سازیغیرفعال (-O0)فعال (-Os یا -O2)
سمبل‌هاجدول کامل DWARFسمبل‌های Stripped (حذف شده)
امضاگواهینامه Developmentگواهینامه Distribution
پروفایل‌هاDebug provisioning profileApp Store / Ad Hoc profile
ثبت رویدادکامل (تمام سطوح)غیرفعال یا حداقل
ابهام‌سازیغیرفعالفعال (ProGuard/R8)
اندازه .apk/.ipaبزرگ‌تر (سمبل‌ها + بدون فشردگی)کوچک‌تر (R8 + منابع)

کی از کدام استفاده کنیم

بیلد Debug در تمام مراحل توسعه و آزمایش روی دستگاه‌های محلی استفاده می‌شود. بیلد Release پیش از ارسال به App Store Connect یا Google Play Console ساخته می‌شود. اجرای اشکال‌زدایی روی بیلد Release از نظر فنی ممکن است، اما به دلیل تغییر نام متدها (R8) و نبود symbolication برای گزارش‌های کراش، بسیار ناراحت است.

مشکلات تغییر حالت

یکی از مشکلات رایج کدی است که در Debug کار می‌کند اما در Release دچار شکست می‌شود. علت آن UB (رفتار تعریف‌نشده) در کد است که کمپایلر در سطح بهینه‌سازی‌های مختلف به صورت متفاوت با آن برخورد می‌کند. مثال تیپیک: خواندن متغیر اهلیت‌سازی نشده یا نقض strict aliasing. برای شناسایی چنین خطاهایی، پیش از هر بیلد Release از تحلیلگر استاتیک (Clang Static Analyzer، ktlint) استفاده کنید.

ابزارهای اشکال‌زدایی: LLDB، نقاط توقف و بازرس‌ها

LLDB — یک دیباگر با عملکرد بالا بر پایه LLVM است که از C، C++، Objective-C، Swift و Kotlin/Native پشتیبانی می‌کند. LLDB رابط REPL را فراهم می‌کند که در آن می‌توان عبارات دلخواه را اجرا کرد، مقادیر متغیرها را تغییر داد و در زمینه برنامه متوقف شده، توابع را فراخوانی کرد.

نقاط توقف و انواع آنها

Breakpoint — ابزار کلیدی دیباگر. شما روی یک سطر کد نقطه‌ای قرار می‌دهید و برنامه وقتی اجرا به آن سطر می‌رسد متوقف می‌شود. LLDB چند نوع نقطه را پشتیبانی می‌کند: شرطی (فقط در صورت تحقق شرط فعال می‌شوند)، سمبولیک (بر روی فراخوانی تابع) و یکبارمصرف (یکبار فعال شده و خودکار حذف می‌شوند).

Watchpoint‌ها و بازرس‌های حافظه

Watchpoint — نقطه مشاهده تغییر متغیر. شما یک آدرس حافظه را مشخص می‌کنید و دیباگر در هر نوشتن به آن آدرس، اجرا را متوقف می‌کند. این ابزار در جستجوی مسابقه داده‌ها و تغییرات نادرست اشیاء مشترک ضروری است. برای مشاهده سلسلمراتب UIKit از UIView Inspector موجود در Xcode استفاده کنید.

lldb
// تنظیم breakpoint شرطی
(lldb) breakpoint set --name "viewDidLoad" --condition "self.isViewLoaded == false"

// Watchpoint بر ویژگی
(lldb) watchpoint set variable self->_loadingState

// اجرای کد در زمینه توقف
(lldb) expr self.view.backgroundColor = UIColor.redColor

بازرس‌های Xcode و Android Studio

هر دو IDE بازرس‌های گرافیکی بر پایه LLDB تولید می‌کنند. Android Studio شامل Layout Inspector (مشاهده سلسلمراتب View)، Network Inspector (ردیابی درخواست‌های HTTP) و Database Inspector (SQLite بلافاصله) است. Xcode Debug Memory Graph (تحلیل نشت حافظه) و View Debugger (نمایش 3D لایه‌های UIKit) را فراهم می‌کند.

اشکال‌زدایی از راه دور و اشکال‌زدایی از طریق Wi-Fi

از Android 11 به بعد، اشکال‌زدایی از طریق Wi-Fi بدون اتصال USB کار می‌کند: کافی است کد QR را از Android Studio اسکن کنید. iOS از Xcode 9+ به بعد از اشکال‌زدایی Wi-Fi پشتیبانی می‌کند — دستگاه یک بار از طریق USB متصل می‌شود، پس از آن جلسه‌های اشکال‌زدایی می‌توانند از طریق شبکه انجام شوند. برای سرورهای CI، اشکال‌زدایی از طریق Wi-Fi به دلیل تأخیرهای غیرقابل پیش‌بینی و از دست رفتن بسته، مناسب نیست، بنابراین در پایپلاین‌های خودکار همیشه از USB استفاده می‌شود. با این حال، برای توسعه محلی، اشکال‌زدایی Wi-Fi بسیار راحت‌تر است — توسعه‌دهنده به کابل وابسته نیست و می‌تواند برنامه را روی دستگاهی در آن سمت اتاق آزمایش کند.

Debug در Android: Android Studio و اشکال‌زدایی از طریق ADB

Android Debug Bridge (ADB) — ابزاری جهت تعامل با دستگاه Android از خط فرمان است. از طریق ADB می‌توان برنامه را نصب کرد، اشکال‌زدایی را آغاز کرد، فایل‌ها را کپی کرد، دستورات shell را اجرا کرد و گزارش‌ها را مشاهده کرد. Android Studio از ADB در پشت صحنه برای تمام عملیات اشکال‌زدایی استفاده می‌کند.

اتصال دیباگر در Android Studio

Android Studio از دو حالت اشکال‌زدایی پشتیبانی می‌کند: Run (عمل عادی) و Debug (عمل با دیباگر متصل). در حالت Debug می‌توانید مستقیماً در ویرایشگر breakpoint قرار دهید، متغیرها را در Debug Tool Window مشاهده کنید و عبارات را در Evaluate Expression ارزیابی کنید. برای اشکال‌زدایی فرآیندهای پس‌زمینه (Service، BroadcastReceiver) از Attach Debugger to Android Process استفاده کنید.

kotlin
class MainActivity : AppCompatActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)

        // Breakpoint در اینجا اجرا را متوقف می‌کند
        val button = findViewById<Button>(R.id.btn_debug)
        button.setOnClickListener {
            startDebugProcess()
        }
    }

    private fun startDebugProcess() {
        val data = fetchDataFromApi()
        Log.d("Debug", "Data loaded: $data")
    }
}

ADB shell و بازرسی پایگاه داده

دستورات ADB shell بدون دسترسی root به سیستم فایلی دستگاه دسترسی می‌دهند. می‌توانید محتوای پوشه databases را مشاهده کرده، فایل .db را به کامپیوتر کپی کرده و آن را با هر کلینت SQLite باز کرد. Android Studio Database Inspector این فرآیند را خودکار می‌کند: شما داده‌های زنده پایگاه را در زمان واقعی می‌بینید و می‌توانید مستقیماً از IDE پرسجوهای SQL را اجرا کنید.

Debug در iOS: Xcode، دیباگر و تشخیص

Xcode محیط اشکال‌زدایی یکپارچه بر پایه LLDB فراهم می‌کند. توسعه‌دهنده می‌تواند برنامه را روی شبیه‌ساز یا دستگاه فیزیکی اجرا کند، breakpoint قرار دهد و از Debug Navigator برای کنترل جریان‌های اجرا استفاده کند. بر خلاف Android، iOS بدون تنظیمات ویژه اجازه اجرای دو بیلد Debug به صورت همزمان روی یک دستگاه را نمی‌دهد.

اشکال‌زدایی در شبیه‌ساز و دستگاه

شبیه‌ساز برنامه را به عنوان یک فرآیند ماتیو macOS اجرا می‌کند که سریع‌ترین چرخه اشکال‌زدایی را فراهم می‌کند. در دستگاه فیزیکی، اشکال‌زدایی از طریق USB یا Wi-Fi (از iOS 16 به بعد) انجام می‌شود و LLDB با debugserver روی دستگاه ارتباط برقرار می‌کند. عملکرد اشکال‌زدایی روی دستگاه به دلیل پهنای باند محدود USB 2.0 پایین‌تر است، اما تنها دستگاه فیزیکی امکان آزمایش سناریوهای واقعی را فراهم می‌کند: اعلام‌های push، دوربین، حسگرها.

swift
import UIKit

class ViewController: UIViewController {
    override func viewDidLoad() {
        super.viewDidLoad()
        setupUI()
    }

    private func setupUI() {
        let label = UILabel()
        label.text = "Debug Mode"
        label.textColor = .systemBlue
        view.addSubview(label)
    }
}

تشخیص و گزارش‌های کراش

Xcode Organizer گزارش‌های کراش را از دستگاه‌های آزمایشگران از طریق Crash Logs جمع‌آوری می‌کند. برای symbolication (تبدیل آدرس‌ها به نام‌های توابع) فایل .dSYM مورد نیاز است که در هر بیلد Debug تولید می‌شود. در بیلد Release نیز dSYM ایجاد می‌شود، اما گزارش‌های کراش از App Store را باید دستی یا از طریق خدمات bitcode به Organizer بارگذاری کرد.

سوالات متداول

آیا می‌توان بیلد Debug را روی دستگاه کاربر اجرا کرد؟

از نظر فنی بله — از طریق Ad Hoc با گواهینامه Debug، اما Apple و Google این کار را توصیه نمی‌کنند. بیلد Debug حاوی سمبل‌های اشکال‌زدایی و عملکرد پایینتری است که UX را بدتر کرده و اندازه برنامه را 2–3 برابر افزایش می‌دهد.

چرا بیلد Debug از Release کندتر کار می‌کند؟

دلیل — بهینه‌سازی کمپایلر غیرفعال (-O0). کمپایلر توابع را درون‌کابی نمی‌کند، کد مرده را حذف نمی‌کند و تمام متغیرهای وسطی را نگه می‌دارد. به علاوه، Debug بررسی‌های تأکید و مرزهای آرایه را که در Release وجود ندارند فعال می‌کند.

چگونه اشکال‌زدایی Wi-Fi را برای iOS تنظیم کنیم؟

در Xcode Window → Devices and Simulators را انتخاب کرده و گزینه «Connect via network» را برای دستگاه خود فعال کنید. دستگاه و Mac باید در یک شبکه Wi-Fi باشند. پس از یک بار اتصال از طریق USB، اشکال‌زدایی در عملکردهای بعدی از طریق Wi-Fi کار خواهد کرد.

«Attach to process» در Android Studio چیست؟

Attach to process امکان اتصال دیباگر به یک فرآیند در حال اجرا را بدون راه‌اندازی مجدد برنامه فراهم می‌کند. این برای اشکال‌زدایی Service، BroadcastReceiver یا فرآیندهایی که توسط رویداد سیستم آغاز می‌شوند، مفید است جایی که Debug Run استاندارد قابل استفاده نیست.

چگونه NSLog و print را در بیلد Release ببینیم؟

NSLog و print به صورت پیش‌فرض فقط در تنظیمات Debug خروجی را نشان می‌دهند. برای Release از os_log با علم OSLogType.default استفاده کنید — پیام‌ها را در Unified Logging System ذخیره می‌کند و از طریق Console.app روی Mac قابل دسترس است.

خلاصه

  • بیلد Debug شامل سمبل‌های اشکال‌زدایی، بهینه‌سازی را غیرفعال کرده و از گواهینامه development استفاده می‌کند
  • LLDB — دیباگر اصلی برای هر دو پلتفرم، از breakpoint، watchpoint و REPL پشتیبانی می‌کند
  • تفاوت‌های Debug و Release شامل بهینه‌سازی، سمبل‌ها، امضا، ابهام‌سازی و اندازه بیلد می‌شوند
  • ADB برای Android و debugserver برای iOS ارتباط IDE را با دستگاه تأمین می‌کنند
  • عملکرد بیلد Debug به دلیل بهینه‌سازی‌های غیرفعال 2–5 برابر پایین‌تر است
  • گزارش‌های کراش بیلد Debug شامل نام‌های خوانا توابع هستند، Release برای symbolication به dSYM نیاز دارد

ما یک اپلیکیشن موبایل به صورت کلید در دست توسعه خواهیم داد

IT Sectr از سال 2017 برنامه‌های iOS و Android را برای استارتاپ‌ها و کسب‌وکارها ایجاد می‌کند. ما به شما مشاوره می‌دهیم و بهترین راه‌حل را پیشنهاد خواهیم کرد.

بحث درباره پروژه

همچنین بخوانید