ابرووا
شروع رایگان
☰ فهرست مستندات · SDK نود

SDK برای Node.js

ردیابی خطای سمت سرور برای برنامه‌های Node.js با middleware برای Express، breadcrumb، context محدود به یک بلوک و پشتیبانی از TypeScript.

Node.js 0.2.4Node 14+Express 4+ (optional)به‌روزرسانی: ۵ آبان ۱۴۰۵
ردیابی خطای سمت سرور

پایش کامل خطاها در برنامه‌های Node.js

ثبت خودکار خطا

exceptionهای مدیریت‌نشده و promiseهای rejectشده‌ی بی‌پاسخ را می‌گیرد

Middleware برای Express.js

middleware داخلی برای مدیریت درخواست‌ها و خطاها در Express.js

Breadcrumb

رویدادهای پیش از خطا را برای درک بهتر شرایط ثبت می‌کند

Context محدود

با withScope برای یک بلوک کد به‌طور موقت context تعیین کنید

اطلاعات کاربر

خطاها را به اطلاعات کاربر مرتبط کنید

فیلتر کردن خطا

با beforeSend، ignoredExceptions و ignoredPaths رویدادها را فیلتر یا اصلاح کنید

پشتیبانی از TypeScript

تعریف‌های کامل TypeScript همراه بسته است

نصب#

بسته‌ها از Abrova Center نصب می‌شوند. دو مرحله دارد:

۱. رجیستری ابرووا را اضافه کنید به فایل .npmrc در ریشه‌ی پروژه (npm، yarn و pnpm همگی آن را می‌خوانند):

# .npmrc
@abrova-trace:registry=https://center.abrova.ir/api/packages/abrova/npm/

۲. بسته را نصب کنید:

bash
npm install @abrova-trace/nodejs-sdk
# or
yarn add @abrova-trace/nodejs-sdk
# or
pnpm add @abrova-trace/nodejs-sdk

شروع سریع#

javascript
const AbrovaTrace = require('@abrova-trace/nodejs-sdk');

// Initialize AbrovaTrace
AbrovaTrace.init({
  apiKey: 'ab_live_your_api_key',            // project API key
  serverSecret: process.env.ABROVA_SERVER_SECRET, // ab_srv_... (required)
  environment: 'production',
  release: '1.0.0'
});

// Capture exceptions
try {
  throw new Error('Something went wrong!');
} catch (error) {
  AbrovaTrace.captureException(error);
}

// Capture messages
AbrovaTrace.captureMessage('User completed checkout');

ثبت خطاها#

ثبت exceptionها

javascript
AbrovaTrace.captureException(error, {
  extra: {
    userId: 123,
    feature: 'checkout'
  }
});

ثبت پیام‌ها

javascript
AbrovaTrace.captureMessage('Something happened', {
  level: 'warning',                   // 'debug' | 'info' (default) | 'warning' | 'error'
  extra: { context: 'additional info' },
  tags: { feature: 'checkout' }
});
پیام‌ها کجا نمایش داده می‌شوند.

پیام‌ها در کنسول، در بخش ابرووا تریس › پیام‌ها همراه با سطح، پلتفرم، داده‌های اضافه و breadcrumbها نمایش داده می‌شوند. پیام هیچ‌وقت مشکل (issue) نمی‌سازد. سطح 'warn' به‌صورت warning، سطح 'fatal' به‌صورت error و سطح 'trace' به‌صورت debug فرستاده می‌شود؛ هر مقدار دیگری info می‌شود. پیام را برای چیزهایی به کار ببرید که برنامه عمداً گزارش می‌دهد («checkout شروع شد»، «همگام‌سازی تمام شد»)؛ برای عیب‌یابی پرحجم از Logs استفاده کنید.

Breadcrumbها رویدادهای پیش از خطا را ثبت می‌کنند تا بفهمید قبل از وقوع خطا چه اتفاقی افتاده است.

Breadcrumb دستی

javascript
AbrovaTrace.addBreadcrumb({
  message: 'User clicked checkout',
  category: 'user-action',
  level: 'info',
  data: { cartTotal: 99.99 }
});

توابع کمکی Breadcrumb

javascript
const { Breadcrumb } = require('@abrova-trace/nodejs-sdk');

// HTTP request breadcrumb
AbrovaTrace.addBreadcrumb(Breadcrumb.http('POST', '/api/order', 200, 150));

// Database query breadcrumb
AbrovaTrace.addBreadcrumb(Breadcrumb.database('SELECT * FROM users', 25));

// User action breadcrumb
AbrovaTrace.addBreadcrumb(Breadcrumb.user('clicked_button', { buttonId: 'submit' }));

اطلاعات کاربر#

javascript
AbrovaTrace.setUser({
  id: 123,
  email: 'user@example.com',
  username: 'john_doe'
});

Context محدود به یک بلوک#

با context محدود می‌توانید کاربر و مقادیر اضافه را فقط برای یک بلوک کد همگام (synchronous) تعیین کنید. وقتی callback برمی‌گردد، کاربر و مقادیر اضافه به حالت قبل برمی‌گردند؛ breadcrumbهایی که داخل بلوک اضافه شده‌اند باقی می‌مانند.

javascript
AbrovaTrace.withScope((scope) => {
  scope.setUser({ id: 456 });
  scope.setExtra('operation', 'bulk_import');
  scope.addBreadcrumb({ message: 'Starting import' });

  // Errors captured here include this context
  AbrovaTrace.captureException(new Error('Import failed'));
});
// Context is restored after the block

یکپارچگی با Express.js#

middleware داخلی برای ردیابی خودکار درخواست‌ها و مدیریت خطا در برنامه‌های Express.js.

javascript
const express = require('express');
const AbrovaTrace = require('@abrova-trace/nodejs-sdk');

const app = express();

// Initialize
AbrovaTrace.init({
  apiKey: 'ab_live_your_api_key',
  serverSecret: process.env.ABROVA_SERVER_SECRET,
  environment: process.env.NODE_ENV
});

// Add middleware
const middleware = AbrovaTrace.expressMiddleware();
app.use(middleware.requestHandler());

// Your routes
app.get('/api/users/:id', async (req, res) => {
  // Your route logic
});

// Error handler (must be last)
app.use(middleware.errorHandler());

app.listen(3000);
مهم: جای error handler.

middleware مدیریت خطا باید بعد از همه‌ی routeها اضافه شود. Express لازم می‌داند که middlewareهای مدیریت خطا آخر از همه تعریف شوند. پیش از AbrovaTrace.expressMiddleware() تابع AbrovaTrace.init() را صدا بزنید: middlewareی که پیش از init() ساخته شود هیچ کاری نمی‌کند.

خطاهایی که errorHandler() گزارش می‌دهد شامل متد درخواست، URL، path، route منطبق (مثلاً /api/users/:id)، پارامترهای query و route، user agent، آدرس IP و وضعیت پاسخ هستند (اگر err.status / err.statusCode در محدوده‌ی 4xx یا 5xx باشد همان، وگرنه 500). headerها و body درخواست هرگز فرستاده نمی‌شوند. پارامترهای query و route که نامشان حساس به نظر برسد (password، token، secret، auth، API key، session، cookie، signature، OTP، code) به‌صورت [REDACTED] فرستاده می‌شوند. همین قاعده برای آدرس درخواستی که همراه خطاها و breadcrumbها فرستاده می‌شود هم برقرار است: مقدار پارامترهای query حساس در آن با [REDACTED] جایگزین می‌شود (مثلاً /reset?token=[REDACTED]&page=2)، اما نام پارامترها و بقیه‌ی مقادیر حفظ می‌شوند (از نسخه‌ی 0.2.3).

ردیابی کوئری‌های پایگاه داده#

javascript
const AbrovaTrace = require('@abrova-trace/nodejs-sdk');

async function executeQuery(sql, params) {
  const startTime = Date.now();

  try {
    AbrovaTrace.addBreadcrumb({
      message: 'Executing query',
      category: 'database',
      data: { sql: sql.substring(0, 100) }
    });

    const results = await db.query(sql, params);

    AbrovaTrace.addBreadcrumb({
      message: 'Query completed',
      category: 'database',
      data: { duration_ms: Date.now() - startTime }
    });

    return results;
  } catch (error) {
    AbrovaTrace.captureException(error, {
      extra: { sql, duration_ms: Date.now() - startTime }
    });
    throw error;
  }
}

فیلتر کردن خطاها#

با hook به نام beforeSend می‌توانید رویدادها را پیش از ارسال به ابرووا تریس فیلتر یا اصلاح کنید. این hook برای exceptionها و رویدادهای captureMessage() اجرا می‌شود؛ برای حذف یک رویداد null برگردانید. برای نادیده گرفتن کامل یک کلاس exception یا یک path درخواست، به‌جای آن از گزینه‌های ignoredExceptions و ignoredPaths استفاده کنید.

javascript
AbrovaTrace.init({
  apiKey: 'ab_live_your_api_key',
  serverSecret: process.env.ABROVA_SERVER_SECRET,
  beforeSend(event) {
    // Don't send network errors
    if (event.message.includes('ECONNREFUSED')) {
      return null;
    }

    // Add custom data (errors are AbrovaTraceError objects; messages from
    // captureMessage() arrive as plain objects without setExtra)
    if (typeof event.setExtra === 'function') {
      event.setExtra('server_id', process.env.SERVER_ID);
    }

    return event;
  }
});

خاموش شدن تمیز#

خطاها، پیام‌ها، لاگ‌ها و spanهای عملکرد در پس‌زمینه فرستاده می‌شوند. تابع flush() هر چیزی را که هنوز در صف است می‌فرستد؛ پس پیش از پایان پروسه صدایش بزنید: قبل از process.exit()، در پایان handler یک تابع serverless و در handlerهای خاموش شدن.

javascript
process.on('SIGTERM', async () => {
  console.log('Shutting down...');
  const sent = await AbrovaTrace.flush(2000); // false if 2 seconds pass before everything is sent
  await AbrovaTrace.close();                  // Sends buffered logs and performance spans, then resets the SDK
  process.exit(0);
});

تابع flush(timeout) یک timeout بر حسب میلی‌ثانیه می‌گیرد (پیش‌فرض: 5000) و یک Promise<boolean> برمی‌گرداند: اگر ارسال در مهلت تمام شود true و اگر مهلت زودتر تمام شود false. این Promise هیچ‌وقت reject نمی‌شود. close() هم یک Promise برمی‌گرداند؛ لاگ‌ها و spanهای عملکردِ در بافر را می‌فرستد، اما منتظر خطاها و پیام‌هایی که هنوز در حال ارسال‌اند نمی‌ماند؛ پس اول flush() را صدا بزنید. بعد از close()، پیش از استفاده‌ی دوباره از SDK باید init() را دوباره صدا بزنید.

در یک تابع serverless، پیش از برگشتن handler عمل flush را انجام دهید:

javascript
exports.handler = async (event) => {
  try {
    return await processEvent(event);
  } catch (error) {
    AbrovaTrace.captureException(error);
    throw error;
  } finally {
    await AbrovaTrace.flush();
  }
};

Source mapها#

اگر از TypeScript، bundlerها (webpack، esbuild) یا Babel استفاده می‌کنید، برای stack trace دقیق source mapها را فعال کنید:

bash
node --enable-source-maps app.js

یا از داخل کد برنامه:

javascript
process.setSourceMapsEnabled(true);

لاگ‌گیری#

لاگ ساختاریافته‌ی سمت سرور، به‌صورت دسته‌ای و با backoff نمایی و بدون هیچ وابستگی. لاگ‌ها به ابرووا تریس › Logs می‌روند و از captureMessage() (بخش پیام‌ها) جدا هستند. بعد از init()، یک بار لاگ‌گیری را فعال کنید و از هر جای برنامه لاگ بنویسید:

javascript
AbrovaTrace.enableLogging({ sourceId: 'api-server' });

AbrovaTrace.info('Server started on port 3000');
AbrovaTrace.warn('Database connection slow', { latency: 2500 });
AbrovaTrace.logError('Failed to process payment', { orderId: '12345' });

برای جزئیات کامل این مسیر — سطح‌های لاگ، یکپارچگی با Express، ارسال دسته‌ای و خاموش شدن تمیز — صفحه‌ی لاگ‌گیری در SDK برای Node.js را ببینید.

گزینه‌های پیکربندی#

javascript
AbrovaTrace.init({
  apiKey: 'ab_live_your_api_key',        // Required
  serverSecret: 'ab_srv_your_secret',     // Required
  environment: 'production',              // Default: NODE_ENV or 'development'
  release: '1.0.0',                       // Default: npm_package_version or '1.0.0'
  enabled: true,                          // Default: true
  debug: false,                           // Default: false
  timeout: 5000,                          // Default: 5000ms
  captureUncaughtExceptions: true,        // Default: true
  captureUnhandledRejections: true,       // Default: true
  maxBreadcrumbs: 50,                     // Default: 50 (max 100)
  sampleRate: 1.0,                        // Default: 1.0 (captureException and captureMessage)
  ignoredExceptions: ['ValidationError'], // Error class, error.name, or RegExp
  ignoredPaths: ['/health*'],             // Express paths not reported
  beforeSend: (event) => event,           // Filter/modify events
});
گزینهنوعاجباریتوضیح
apiKeystringبلهکلید API پروژه (ab_live_xxx)
serverSecretstringبلهکلید سرور (ab_srv_xxx)؛ فقط روی سرور نگهش دارید
environmentstringخیرنام محیط (پیش‌فرض: NODE_ENV یا "development")
releasestringخیرنسخه‌ی برنامه (پیش‌فرض: npm_package_version یا "1.0.0")
enabledbooleanخیرروشن/خاموش کردن ردیابی (پیش‌فرض: true)
debugbooleanخیرفعال کردن لاگ عیب‌یابی (پیش‌فرض: false)
timeoutnumberخیرمهلت HTTP بر حسب میلی‌ثانیه، 1000 تا 30000 (پیش‌فرض: 5000)
captureUncaughtExceptionsbooleanخیرثبت خودکار exceptionهای مدیریت‌نشده (پیش‌فرض: true)
captureUnhandledRejectionsbooleanخیرثبت خودکار rejectionهای مدیریت‌نشده (پیش‌فرض: true)
maxBreadcrumbsnumberخیرحداکثر تعداد breadcrumbهای نگه‌داشته‌شده، تا ۱۰۰ (پیش‌فرض: 50). ۱۰ مورد آخر همراه هر رویداد فرستاده می‌شوند
sampleRatenumberخیرسهم رویدادهای captureException() و captureMessage() که فرستاده می‌شوند، 0.0 تا 1.0 (پیش‌فرض: 1.0)
ignoredExceptionsarrayخیرexceptionهایی که captureException() و error handler مربوط به Express گزارش نمی‌کنند: یک کلاس خطا (با instanceof مقایسه می‌شود)، رشته‌ای برابر با error.name، یا یک RegExp که روی error.name آزموده می‌شود. exceptionهای مدیریت‌نشده و rejectionهای مدیریت‌نشده همیشه گزارش می‌شوند
ignoredPathsarrayخیرpathهای درخواستی که middleware مربوط به Express از آن‌ها می‌گذرد: glob، path دقیق یا RegExp
beforeSendfunctionخیرhook برای فیلتر یا اصلاح خطاها و پیام‌ها پیش از ارسال؛ برای حذف، null برگردانید

آمار SDK#

javascript
const stats = AbrovaTrace.getStats();
console.log(stats);
// {
//   isEnabled: true,
//   breadcrumbCount: 5,
//   rateLimiter: { totalErrorsInWindow: 3, uniqueErrorsInWindow: 2, totalLimit: 100, errorLimit: 10, windowMs: 60000 },
//   config: { environment: 'production', release: '1.0.0', apiKey: 'ab_live_abc1234...' }
// }

پشتیبانی از TypeScript#

SDK تعریف‌های کامل TypeScript را همراه دارد. هر typeی را که لازم دارید import کنید:

typescript
import AbrovaTrace, {
  AbrovaTraceInitOptions,
  AbrovaTraceError,
  Breadcrumb,
  BreadcrumbOptions,
  UserContext
} from '@abrova-trace/nodejs-sdk';

پیش‌نیازها#

  • Node.js — >= 14.0.0
  • Express (اختیاری) — >= 4.0.0

مرجع API#

AbrovaTrace

  • init(config) — راه‌اندازی SDK
  • captureException(error, options?) — ثبت یک خطا
  • captureMessage(message, options?) — ارسال پیام به ابرووا تریس › پیام‌ها (options: level، extra، tags)
  • addBreadcrumb(breadcrumb) — افزودن یک breadcrumb
  • setUser(user) — تعیین اطلاعات کاربر
  • setRequestContext(context) — تعیین context درخواست که به رویدادهای ثبت‌شده پیوست می‌شود
  • withScope(callback) — اجرای کد با scope جداگانه
  • expressMiddleware() — گرفتن middleware برای Express.js
  • flush(timeout?) — ارسال خطاها، پیام‌ها، لاگ‌ها و spanهای عملکرد در صف؛ timeout بر حسب میلی‌ثانیه (پیش‌فرض: 5000). خروجی Promise<boolean> است: اگر مهلت زودتر تمام شود false
  • close() — ارسال لاگ‌ها و spanهای عملکرد و سپس پاک‌سازی (یک Promise برمی‌گرداند)
  • getStats() — گرفتن آمار SDK
  • enableLogging(options?)، log()، trace()، logDebug()، info()، warn()، logError()، fatal()، flushLogs() — لاگ‌گیری (صفحه‌ی لاگ‌گیری در SDK برای Node.js را ببینید)
  • trackOperation(name, fn, options?)، reportPerformanceSpan(span)، reportPerformanceSpanBatch(spans)، flushPerformance() — spanهای عملکرد

توابع کمکی Breadcrumb

  • Breadcrumb.http(method, url, status?, duration?) — breadcrumb برای درخواست HTTP
  • Breadcrumb.database(query, duration, error?) — breadcrumb برای کوئری پایگاه داده
  • Breadcrumb.user(action, data?) — breadcrumb برای کار کاربر
  • Breadcrumb.console(level, message, ...args) — breadcrumb برای خروجی console
  • Breadcrumb.navigation(from, to, method?) — breadcrumb برای جابه‌جایی بین صفحه‌ها
  • Breadcrumb.custom(message, category, data?) — breadcrumb با دسته‌بندی دلخواه

Middleware برای Express

  • requestHandler() — middleware ردیابی درخواست را برمی‌گرداند
  • errorHandler() — middleware مدیریت خطا را برمی‌گرداند
  • userMiddleware() — اطلاعات کاربر را از req.user (id، email، username) تعیین می‌کند
  • transactionMiddleware(name) — برای یک route نام‌دار، breadcrumbهای شروع و پایان (مدت و وضعیت) اضافه می‌کند

نمونه‌ی کامل#

javascript
const express = require('express');
const AbrovaTrace = require('@abrova-trace/nodejs-sdk');
const { Breadcrumb } = require('@abrova-trace/nodejs-sdk');

// Initialize AbrovaTrace
AbrovaTrace.init({
  apiKey: 'ab_live_your_api_key',
  serverSecret: process.env.ABROVA_SERVER_SECRET,
  environment: process.env.NODE_ENV || 'development',
  release: '1.0.0',
  captureUncaughtExceptions: true,
  captureUnhandledRejections: true,
  maxBreadcrumbs: 50,
  debug: process.env.NODE_ENV === 'development',
});

const app = express();

// Add AbrovaTrace middleware
const middleware = AbrovaTrace.expressMiddleware();
app.use(middleware.requestHandler());

app.use(express.json());

// Set user context from auth
app.use((req, res, next) => {
  if (req.user) {
    AbrovaTrace.setUser({
      id: req.user.id,
      email: req.user.email,
    });
  }
  next();
});

app.get('/api/users/:id', async (req, res) => {
  AbrovaTrace.addBreadcrumb(Breadcrumb.user('view_user', {
    userId: req.params.id,
  }));

  try {
    const user = await db.query('SELECT * FROM users WHERE id = ?', [req.params.id]);
    AbrovaTrace.addBreadcrumb(Breadcrumb.database('SELECT * FROM users', 15));
    res.json(user);
  } catch (error) {
    AbrovaTrace.captureException(error, {
      extra: { userId: req.params.id },
    });
    res.status(500).json({ error: 'Internal Server Error' });
  }
});

// Error handler (must be last)
app.use(middleware.errorHandler());

// Graceful shutdown
process.on('SIGTERM', async () => {
  await AbrovaTrace.flush(2000);
  await AbrovaTrace.close();
  process.exit(0);
});

app.listen(3000, () => console.log('Server running on port 3000'));

توصیه‌ها#

زود راه‌اندازی کنید

ابرووا تریس را در ابتدای نقطه‌ی ورود برنامه راه‌اندازی کنید تا همه‌ی خطاها ثبت شوند

از middleware برای Express استفاده کنید

برای ردیابی کامل در Express.js، request handler را اول و error handler را آخر اضافه کنید

اطلاعات کاربر را تعیین کنید

خطاها را به اطلاعات کاربر مرتبط کنید تا عیب‌یابی آسان‌تر شود

از context محدود استفاده کنید

با withScope برای یک بلوک همگام context موقت تعیین کنید؛ context در SDK برای کل پروسه مشترک است، برای همین وقتی callback برمی‌گردد به حالت قبل برمی‌گردد

Breadcrumb اضافه کنید

کارهای مهم (کوئری‌های پایگاه داده، درخواست‌های HTTP، کارهای کاربر) را به‌صورت breadcrumb ثبت کنید

خاموش شدن تمیز

در SIGTERM/SIGINT منتظر flush() و close() بمانید تا خطاها، لاگ‌ها و spanهای در صف فرستاده شوند

Source mapها را فعال کنید

برای stack trace دقیق در برنامه‌های TypeScript یا bundleشده از --enable-source-maps استفاده کنید

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

خطاهای پرسروصدا را فیلتر کنید و داده‌ی خطا را با context دلخواه غنی کنید

این صفحه مفید بود؟
گزارش مشکل