Android SDK
SDK نیتیو Kotlin برای اندروید با تشخیص خودکار کرش، تشخیص ANR، یکپارچگی با OkHttp و مانیتورینگ عملکرد.
با Kotlin ساخته شده و از API 19 به بالا (Android 4.4 به بالا) پشتیبانی میکند
exceptionهای مدیریتنشده را میگیرد، و روی Android 11 به بالا کرشهای نیتیو را هم
مشکلهای «برنامه پاسخ نمیدهد» (Application Not Responding) را تشخیص میدهد
مسیر کاربر را پیش از وقوع خطا ثبت میکند
ردیابی خودکار درخواستهای HTTP
ردیابی تأخیر API با interceptorهای OkHttp
جمعآوری خودکار اطلاعات دستگاه، سیستمعامل و برنامه
نصب#
SDK از Abrova Center نصب میشود. در دو مرحله:
۱. مخزن ابرووا را اضافه کنید در settings.gradle.kts (یا settings.gradle):
dependencyResolutionManagement {
repositories {
google()
mavenCentral()
maven { url = uri("https://center.abrova.ir/api/packages/abrova/maven") }
}
}برای Groovy: maven { url "https://center.abrova.ir/api/packages/abrova/maven" }
۲. وابستگی را اضافه کنید به build.gradle.kts برنامه:
dependencies {
implementation("ir.abrova.trace:abrova-trace-android-sdk:0.2.3")
}سپس پروژه را با فایلهای Gradle همگام (sync) کنید. پیشنیازها: Android 4.4 (API 19) یا بالاتر؛ گزارش کرشهای نیتیو به Android 11 (API 30) یا بالاتر نیاز دارد.
شروع سریع#
AbrovaTrace را در کلاس Application راهاندازی کنید:
import android.app.Application
import ir.abrova.trace.sdk.AbrovaTrace
import ir.abrova.trace.sdk.AbrovaTraceConfig
class MyApp : Application() {
override fun onCreate() {
super.onCreate()
val config = AbrovaTraceConfig.Builder("ab_live_YOUR_API_KEY")
.environment(if (BuildConfig.DEBUG) "development" else "production")
.release(BuildConfig.VERSION_NAME)
.debug(BuildConfig.DEBUG)
.captureUncaughtExceptions(true)
.captureSignalCrashes(true)
.captureAnr(true)
.anrTimeoutMs(5000L)
.build()
AbrovaTrace.init(this, config)
}
override fun onTerminate() {
AbrovaTrace.close()
super.onTerminate()
}
}متد onTerminate() روی دستگاه واقعی هیچوقت صدا زده نمیشود؛ پس close() را در Activity اصلی هم صدا بزنید. close() لاگهای بافرشده را میفرستد، watchdog مربوط به ANR را متوقف میکند و کلاینت شبکه را میبندد. کلید API باید با ab_live_ شروع شود؛ در غیر این صورت config خطا میدهد.
class MainActivity : AppCompatActivity() {
override fun onDestroy() {
if (isFinishing) {
AbrovaTrace.close() // Flush logs, stop the ANR watchdog
}
super.onDestroy()
}
}ثبت خطاها#
ثبت exceptionها
try {
someRiskyOperation()
} catch (e: Exception) {
AbrovaTrace.captureException(e)
}ثبت با اطلاعات تکمیلی
AbrovaTrace.captureException(
throwable = exception,
message = "Failed to load user profile",
extra = mapOf("user_id" to userId, "screen" to "ProfileActivity"),
tags = mapOf("feature" to "user_profile")
)ثبت پیامها
import ir.abrova.trace.sdk.models.MessageLevel
// Info message
AbrovaTrace.captureMessage("User completed onboarding", MessageLevel.INFO)
// Warning message
AbrovaTrace.captureMessage("API rate limit approaching", MessageLevel.WARNING)
// Error message with extra data
AbrovaTrace.captureMessage(
message = "Payment failed",
level = MessageLevel.ERROR,
extra = mapOf("amount" to 99.99)
)پیامها در کنسول، در بخش ابرووا تریس › پیامها، همراه با سطح، پلتفرم، دادههای تکمیلی و breadcrumbها نمایش داده میشوند. پیام هیچوقت مشکل (issue) نمیسازد. سطحها: MessageLevel.DEBUG، INFO (پیشفرض)، WARNING و ERROR. سطح FATAL هم پذیرفته میشود و با سطح error ذخیره میشود. پیام را برای چیزهایی به کار ببرید که برنامه عمداً گزارش میدهد («پرداخت شروع شد»، «همگامسازی تمام شد»)؛ برای عیبیابی پرحجم از لاگها استفاده کنید.
Breadcrumbها#
Breadcrumbها کمک میکنند بفهمید پیش از وقوع خطا چه اتفاقی افتاده است. برای جابهجایی بین Activityها، رفتن برنامه به پیشزمینه و پسزمینه، و رویدادهای سیستم بهطور خودکار اضافه میشوند.
import ir.abrova.trace.sdk.models.BreadcrumbType
// User action
AbrovaTrace.addUserBreadcrumb("Added item to cart", mapOf("product_id" to "abc"))
// Navigation
AbrovaTrace.addNavigationBreadcrumb(from = "MainActivity", to = "ProductDetailActivity")
// HTTP request
AbrovaTrace.addHttpBreadcrumb(
method = "POST",
url = "https://api.example.com/orders",
statusCode = 201,
duration = 342L
)
// Custom breadcrumb
AbrovaTrace.addBreadcrumb("Order placed", BreadcrumbType.INFO, mapOf(
"order_id" to "12345",
"total" to 99.99
))یکپارچگی با OkHttp#
درخواستهای HTTP را بهطور خودکار بهصورت breadcrumb ثبت کنید و خطاهای HTTP را بگیرید:
راهاندازی پایه
import ir.abrova.trace.sdk.network.AbrovaTraceInterceptor
import okhttp3.OkHttpClient
val client = OkHttpClient.Builder()
.addInterceptor(AbrovaTraceInterceptor())
.build()همراه با ثبت خطا
import ir.abrova.trace.sdk.network.AbrovaTraceInterceptor
import ir.abrova.trace.sdk.network.AbrovaTraceErrorInterceptor
import okhttp3.OkHttpClient
val client = OkHttpClient.Builder()
.addInterceptor(AbrovaTraceInterceptor()) // Adds breadcrumbs
.addInterceptor(AbrovaTraceErrorInterceptor()) // Captures HTTP errors
.build()کلاس AbrovaTraceErrorInterceptor هر پاسخ 5xx را بهصورت یک پیام با سطح error میفرستد (ابرووا تریس › پیامها). پاسخهای 4xx بهطور پیشفرض خاموشاند؛ با AbrovaTraceErrorInterceptor(captureClientErrors = true) روشنشان کنید (با سطح warning فرستاده میشوند). خطاهای شبکه (وقتی پاسخی نمیرسد) بهصورت exception ثبت میشوند.
تشخیص کرش#
ابرووا تریس کرشها را درون خود برنامه تشخیص میدهد و روی Android 11 به بالا، از سوابق خروج خود سیستم هم میخواند.
- exceptionهای Java/Kotlin: بهصورت لحظهای با یک handler برای exceptionهای مدیریتنشده (
captureUncaughtExceptions) گرفته میشوند. گزارش پیش از بسته شدن برنامه، روی هر threadی از جمله main thread، فرستاده میشود؛ اگر سرور ظرف ۲ ثانیه آن را نپذیرد، روی دستگاه نگه داشته میشود و در اجرای بعدی فرستاده میشود. به نسخهی 0.2.2 یا جدیدتر نیاز دارد. - رویدادهای ANR: یک thread نگهبان (watchdog) تشخیص میدهد که main thread بیش از
anrTimeoutMsمسدود مانده است (captureAnr) - کرشهای نیتیو: سیگنالهایی مثل SIGSEGV و SIGABRT که در اجرای بعدی گزارش میشوند (فقط Android 11 / API 30 به بالا،
captureSignalCrashes)
نحوهی کار
- در هر اجرا (API 30 به بالا)، ابرووا تریس سوابق
ApplicationExitInfoاندروید را برای برنامهی شما میخواند - خروجهایی که از اجرای قبلی تا حالا با دلیل کرش JVM، کرش نیتیو یا ANR رخ دادهاند به گزارش کرش تبدیل میشوند؛ برای کرشهای نیتیو، tombstone هم ضمیمه میشود
- زمان آخرین رکورد فرستادهشده ذخیره میشود تا هر کرش فقط یک بار گزارش شود؛ اگر ارسال ناموفق باشد، در اجرای بعدی دوباره تلاش میشود. کرش Java/Kotlinی که handler درون برنامه قبلاً گزارش داده، اینجا نادیده گرفته میشود
- روی Android 10 و پایینتر این مرحله کاری انجام نمیدهد؛ کرشهای JVM همچنان با handler درون برنامه گرفته میشوند
مانیتورینگ عملکرد (APM)#
تأخیر API و عملکرد درخواستهای HTTP را بهطور خودکار ردیابی کنید.
ردیابی خودکار عملکرد HTTP با OkHttp
import ir.abrova.trace.sdk.network.AbrovaTraceInterceptor
import ir.abrova.trace.sdk.network.AbrovaTracePerformanceInterceptor
import okhttp3.OkHttpClient
import okhttp3.Request
val client = OkHttpClient.Builder()
.addInterceptor(AbrovaTraceInterceptor()) // Breadcrumbs
.addInterceptor(AbrovaTracePerformanceInterceptor()) // APM tracking
.build()
// All API calls are automatically tracked!
val request = Request.Builder()
.url("https://api.example.com/users")
.build()
client.newCall(request).execute().use { response ->
// Duration, status code, and errors are automatically reported
val users = response.body?.string()
}استفاده با Retrofit
import ir.abrova.trace.sdk.network.AbrovaTraceInterceptor
import ir.abrova.trace.sdk.network.AbrovaTracePerformanceInterceptor
import okhttp3.OkHttpClient
import retrofit2.Retrofit
import retrofit2.converter.gson.GsonConverterFactory
val okHttpClient = OkHttpClient.Builder()
.addInterceptor(AbrovaTraceInterceptor())
.addInterceptor(AbrovaTracePerformanceInterceptor())
.build()
val retrofit = Retrofit.Builder()
.baseUrl("https://api.example.com/")
.client(okHttpClient)
.addConverterFactory(GsonConverterFactory.create())
.build()
val api = retrofit.create(MyApiService::class.java)
// All API calls through this Retrofit instance are automatically trackedردیابی عملیات دلخواه
import ir.abrova.trace.sdk.AbrovaTrace
val result = AbrovaTrace.trackOperation("load_user_profile") {
val user = fetchUserFromApi()
cacheUserLocally(user)
user
}گزارش دستی span
import ir.abrova.trace.sdk.models.PerformanceSpan
// HTTP request span
AbrovaTrace.reportPerformanceSpan(
PerformanceSpan.fromHttpRequest(
method = "GET",
url = "https://api.example.com/products",
statusCode = 200,
durationMs = 245L,
startTime = System.currentTimeMillis() - 245
)
)
// Database query span
AbrovaTrace.reportPerformanceSpan(
PerformanceSpan.forDbQuery(
queryType = "SELECT",
tableName = "products",
durationMs = 15L,
startTime = System.currentTimeMillis() - 15,
rowsAffected = 50
)
)
// Custom operation span
AbrovaTrace.reportPerformanceSpan(
PerformanceSpan.custom(
operation = "image_processing",
durationMs = 1250L,
startTime = System.currentTimeMillis() - 1250,
tags = mapOf("format" to "png")
)
)لاگها#
ارسال لاگ ساختیافته با دستهبندی (batching) و تلاش مجدد خودکار. یک بار فعالش کنید و سپس از هر جای برنامه از متدهای سطحها استفاده کنید:
// Enable logging after AbrovaTrace.init()
AbrovaTrace.enableLogging(sourceId = "my-android-app")
AbrovaTrace.info("User login successful", mapOf("user_id" to "user_123"))برای جزئیات کامل این مسیر (دستهبندی، سطحهای لاگ، مدیریت چرخهی عمر، ارسال دستی و تنظیمات) صفحهی لاگها در Android SDK را ببینید.
گزینههای تنظیمات#
val config = AbrovaTraceConfig.Builder("ab_live_YOUR_API_KEY")
.environment("production") // Environment name
.release("1.0.0") // App version
.debug(false) // Enable debug logging
.enabled(true) // Enable/disable SDK
.sampleRate(1.0f) // Error sample rate (0.0 - 1.0)
.maxBreadcrumbs(20) // Max breadcrumbs to keep
.httpTimeout(30) // HTTP request timeout (seconds)
.enableOfflineStorage(true) // Keep unsent errors on the device while offline
.captureUncaughtExceptions(true) // Catch uncaught exceptions
.captureSignalCrashes(true) // Detect native signal crashes
.captureAnr(true) // Detect ANR issues
.anrTimeoutMs(5000L) // ANR detection timeout
.apiUrl("https://trace.abrova.ir") // Server URL (self-hosted override)
.build()| گزینه | نوع | اجباری | توضیح |
|---|---|---|---|
| apiKey | String | بله | کلید API پروژه (باید با ab_live_ شروع شود) |
| environment | String | خیر | نام محیط (پیشفرض: "production") |
| release | String | خیر | شناسهی نسخهی برنامه |
| debug | Boolean | خیر | فعال کردن لاگهای debug (پیشفرض: false) |
| enabled | Boolean | خیر | فعال/غیرفعال کردن SDK (پیشفرض: true) |
| sampleRate | Float | خیر | نرخ نمونهبرداری ۰٫۰ تا ۱٫۰ برای captureException (پیشفرض: 1.0) |
| maxBreadcrumbs | Int | خیر | حداکثر تعداد breadcrumbهای نگهداشتهشده (پیشفرض: 20) |
| httpTimeout | Int | خیر | مهلت درخواست HTTP به ثانیه (پیشفرض: 30) |
| enableOfflineStorage | Boolean | خیر | خطاهایی را که هنگام آفلاین بودن دستگاه فرستاده نشدهاند (تا ۱۰۰ مورد) نگه میدارد و بعداً میفرستد (پیشفرض: true) |
| captureUncaughtExceptions | Boolean | خیر | گرفتن exceptionهای مدیریتنشده (پیشفرض: true) |
| captureSignalCrashes | Boolean | خیر | گزارش کرشهای نیتیو و دیگر کرشها و ANRهایی که سیستم ثبت کرده، در اجرای بعدی، API 30 به بالا (پیشفرض: true) |
| captureAnr | Boolean | خیر | تشخیص رویدادهای ANR (پیشفرض: true) |
| anrTimeoutMs | Long | خیر | مهلت تشخیص ANR به میلیثانیه (پیشفرض: 5000) |
| apiUrl | String | خیر | آدرس سرور Trace (پیشفرض: "https://trace.abrova.ir") |
وقتی خطایی به دلیل قطع بودن اتصال دستگاه فرستاده نشود، SDK آن را در فضای خصوصی برنامه نگه میدارد و بعداً میفرستد: در اجرای بعدی، و به محض اینکه خطای دیگری با موفقیت فرستاده شود. حداکثر ۱۰۰ خطا نگه داشته میشود؛ با رسیدن به این سقف، قدیمیترینها حذف میشوند. این فقط شامل خطاهاست: captureException، exceptionهای مدیریتنشده و گزارشهای ANR. پیامها، لاگها و دادههای عملکرد ذخیره نمیشوند. اگر نمیخواهید چیزی روی دستگاه بماند، enableOfflineStorage(false) را تنظیم کنید.
ProGuard / R8#
قوانین ProGuard بهطور خودکار همراه SDK هستند. اگر به قوانین سفارشی نیاز دارید، آنها را به proguard-rules.pro اضافه کنید:
-keep class ir.abrova.trace.sdk.** { *; }
-keepattributes SourceFile,LineNumberTable
-keepattributes *Annotation*سازگاری با دستگاهها#
- Android 4.4 KitKat: API 19
- Android 5.0 Lollipop: API 21
- Android 8.0 Oreo: API 26
- Android 10: API 29
- Android 12: API 31
- Android 14: API 34
Context و تگها#
متادیتای ثابت را به همهی خطاها و پیامهایی که SDK ثبت میکند پیوست کنید (تگها به spanهای عملکرد هم اضافه میشوند). این کار برای فیلتر کردن بر اساس تیم، منطقه، پرچم ویژگی یا گروه آزمایش در کنسول ابرووا مفید است. گزارشهای ANR و گزارشهای کرشی که در اجرای بعدی از سیستم خوانده میشوند این اطلاعات را ندارند.
extraهای سراسری
extraها جفتهای کلید/مقدار دلخواه هستند (کلید رشتهای، هر مقدار قابل serialize) که بهطور خودکار در همهی رویدادها ادغام میشوند:
// Set individual extras
AbrovaTrace.setExtra("organizationId", "org-123")
AbrovaTrace.setExtra("feature", "checkout-v2")
// Set multiple at once
AbrovaTrace.setExtras(mapOf(
"organizationId" to "org-123",
"feature" to "checkout-v2",
"experiment" to "new-flow"
))
// Clear when no longer needed (e.g. on logout)
AbrovaTrace.clearExtras()تگها
تگها جفتهای کلید/مقدار فقط رشتهای هستند که به همهی خطاها و پیامها پیوست میشوند:
AbrovaTrace.setTag("team", "payments")
AbrovaTrace.setTag("region", "us-east")
AbrovaTrace.setTags(mapOf("team" to "payments", "version" to "2.1"))
AbrovaTrace.clearTags()از تگها برای فیلترهای دستهای با تنوع کم (تیم، منطقه، build flavor) استفاده کنید. از extraها برای context غنیتر هر رویداد (شناسهی کاربر، بدنهی درخواست، مقادیر محاسبهشده).
مرجع API#
فهرست کامل متدهای AbrovaTrace و PerformanceSpan. امضای متدها به سبک Kotlin نوشته شده و پارامترهای اختیاری با ? مشخص شدهاند.
AbrovaTrace: راهاندازی و چرخهی عمر
| گزینه | نوع | اجباری | توضیح |
|---|---|---|---|
| init(context, config) | - | - | راهاندازی SDK با یک AbrovaTraceConfig کامل |
| init(context, apiKey) | - | - | راهاندازی SDK فقط با کلید API (با مقادیر پیشفرض) |
| isInitialized() | - | - | اگر SDK راهاندازی شده باشد true برمیگرداند |
| close() | - | - | ارسال لاگهای بافرشده، توقف watchdog مربوط به ANR و بستن کلاینت شبکه |
ثبت خطا
| گزینه | نوع | اجباری | توضیح |
|---|---|---|---|
| captureException(throwable, message?, extra?, tags?, callback?) | - | - | ثبت یک exception با متادیتای اختیاری |
| captureMessage(message, level?, extra?, tags?, callback?) | - | - | ارسال یک پیام با سطح مشخص به ابرووا تریس › پیامها (مشکل نمیسازد) |
کاربر و نشست
| گزینه | نوع | اجباری | توضیح |
|---|---|---|---|
| setUserId(id) | - | - | تنظیم شناسهی کاربر فعلی |
| getUserId() | - | - | دریافت شناسهی کاربر فعلی |
context سراسری (extraها)
| گزینه | نوع | اجباری | توضیح |
|---|---|---|---|
| setExtra(key, value) | - | - | تنظیم یک extra |
| setExtras(extras) | - | - | تنظیم چند extra بهصورت یکجا |
| clearExtras() | - | - | پاک کردن همهی extraها |
تگها
| گزینه | نوع | اجباری | توضیح |
|---|---|---|---|
| setTag(key, value) | - | - | تنظیم یک تگ |
| setTags(tags) | - | - | تنظیم چند تگ بهصورت یکجا |
| clearTags() | - | - | پاک کردن همهی تگها |
Breadcrumbها
| گزینه | نوع | اجباری | توضیح |
|---|---|---|---|
| addBreadcrumb(message, type?, data?) | - | - | افزودن یک breadcrumb عمومی |
| addNavigationBreadcrumb(from, to) | - | - | افزودن یک breadcrumb ناوبری |
| addUserBreadcrumb(action, data?) | - | - | افزودن یک breadcrumb برای اقدام کاربر |
| addHttpBreadcrumb(method, url, statusCode?, duration?) | - | - | افزودن یک breadcrumb برای HTTP |
| clearBreadcrumbs() | - | - | پاک کردن همهی breadcrumbها |
مانیتورینگ عملکرد
| گزینه | نوع | اجباری | توضیح |
|---|---|---|---|
| reportPerformanceSpan(method, url, statusCode, durationMs, startTime, errorMessage?, tags?) | - | - | گزارش یک span برای HTTP |
| reportPerformanceSpan(span, callback?) | - | - | گزارش یک PerformanceSpan ساختهشده |
| reportPerformanceSpanBatch(spans, callback?) | - | - | گزارش چند span بهصورت یکجا |
| trackOperation(operation, operationType?, tags?, block) | - | - | زمانگیری یک بلوک و گزارش آن بهصورت span |
| performanceInterceptor(minDurationMs?) | - | - | ساخت یک interceptor برای OkHttp جهت زمانسنجی HTTP |
لاگها
| گزینه | نوع | اجباری | توضیح |
|---|---|---|---|
| enableLogging(sourceId?, sourceName?, batchSize?, flushIntervalMs?) | - | - | روشن کردن مسیر ارسال لاگ |
| log(message, level?, metadata?) | - | - | لاگ با سطح مشخص |
| trace(message, metadata?) | - | - | لاگ با سطح trace |
| logDebug(message, metadata?) | - | - | لاگ با سطح debug |
| info(message, metadata?) | - | - | لاگ با سطح info |
| warn(message, metadata?) | - | - | لاگ با سطح warn |
| logError(message, metadata?) | - | - | لاگ با سطح error |
| fatal(message, metadata?) | - | - | لاگ با سطح fatal |
| flushLogs(callback?) | - | - | ارسال فوری لاگهای بافرشده |
| getPendingLogCount() | - | - | تعداد لاگهایی که هنوز در بافر ماندهاند |
متدهای سازندهی PerformanceSpan
| گزینه | نوع | اجباری | توضیح |
|---|---|---|---|
| PerformanceSpan.fromHttpRequest(...) | - | - | ساخت span از یک درخواست/پاسخ HTTP |
| PerformanceSpan.forDbQuery(...) | - | - | ساخت span برای یک کوئری پایگاه داده |
| PerformanceSpan.custom(...) | - | - | ساخت یک span کاملاً سفارشی |
| PerformanceSpan.generateTraceId() | - | - | تولید یک trace ID تصادفی |
| PerformanceSpan.generateSpanId() | - | - | تولید یک span ID تصادفی |
نمونهی کامل#
import android.app.Application
import android.os.Bundle
import androidx.appcompat.app.AppCompatActivity
import ir.abrova.trace.sdk.AbrovaTrace
import ir.abrova.trace.sdk.AbrovaTraceConfig
import ir.abrova.trace.sdk.models.MessageLevel
import ir.abrova.trace.sdk.network.AbrovaTraceInterceptor
import okhttp3.OkHttpClient
class MyApp : Application() {
override fun onCreate() {
super.onCreate()
val config = AbrovaTraceConfig.Builder("ab_live_YOUR_API_KEY")
.environment(if (BuildConfig.DEBUG) "development" else "production")
.release(BuildConfig.VERSION_NAME)
.debug(BuildConfig.DEBUG)
.captureUncaughtExceptions(true)
.captureSignalCrashes(true)
.captureAnr(true)
.anrTimeoutMs(5000L)
.maxBreadcrumbs(20)
.enableOfflineStorage(true)
.build()
AbrovaTrace.init(this, config)
}
override fun onTerminate() {
AbrovaTrace.close()
super.onTerminate()
}
}
class MainActivity : AppCompatActivity() {
private val httpClient = OkHttpClient.Builder()
.addInterceptor(AbrovaTraceInterceptor())
.build()
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
AbrovaTrace.setUserId("user_123")
AbrovaTrace.addUserBreadcrumb("Viewed home screen")
}
private fun handlePurchase() {
try {
processPurchase()
AbrovaTrace.captureMessage(
message = "Purchase successful",
level = MessageLevel.INFO,
extra = mapOf("amount" to 99.99)
)
} catch (e: Exception) {
AbrovaTrace.captureException(
throwable = e,
message = "Purchase failed",
extra = mapOf("user_id" to "user_123", "screen" to "MainActivity")
)
}
}
override fun onDestroy() {
if (isFinishing) {
AbrovaTrace.close()
}
super.onDestroy()
}
private fun processPurchase() { /* ... */ }
}توصیهها#
ابرووا تریس را در متد onCreate() کلاس Application راهاندازی کنید تا همهی خطاها از لحظهی شروع برنامه گرفته شوند
لاگهای بافرشده را میفرستد و watchdog مربوط به ANR را متوقف میکند
شناسهی کاربر، نام صفحه و دادههای مرتبط را در پارامتر extra بگذارید
خطاهای production، staging و development را با تنظیم environment از هم جدا کنید
در زمان توسعه debug(true) را تنظیم کنید تا لاگهای SDK را ببینید و درستی یکپارچگی را بررسی کنید
برای breadcrumbهای HTTP از AbrovaTraceInterceptor و برای گزارش خطاهای HTTP از AbrovaTraceErrorInterceptor استفاده کنید
enableLogging() را بلافاصله بعد از init() صدا بزنید تا همهی رویدادهای برنامه ثبت شوند