Smart Library Docs

Dashboard Endpoints

Detailed API reference for the dashboard endpoints — aggregate statistics and trend analytics for system monitoring.

Dashboard Endpoints

Base path: /api/v1/dashboard Authentication: Requires a valid JWT token.


GET /dashboard/stats

Returns aggregate system statistics used to populate the admin dashboard overview cards.

Access Control

  • Allowed roles: Any authenticated user

Request

GET /api/v1/dashboard/stats
Authorization: Bearer <token>

Response — 200 OK

{
  "totalBooks": 1247,
  "activeLoans": 89,
  "totalUsers": 432,
  "totalFines": 12,
  "totalRevenue": 1540.00
}

Metric Definitions

MetricQueryDescription
totalBooksBookCopy.countDocuments()Total number of physical book copies in the system (not unique titles)
activeLoansTransaction.countDocuments({ returnedAt: null })Number of currently checked-out books (unreturned transactions)
totalUsersUser.countDocuments({ isActive: true })Number of active user accounts (excludes deactivated)
totalFinesFine.countDocuments({ status: 'UNPAID' })Number of outstanding unpaid fines
totalRevenueFine.aggregate([{ $match: { status: 'PAID' } }, { $group: { _id: null, total: { $sum: '$amount' } } }])Total dollar amount collected from paid fines

Performance Notes

Each metric executes a countDocuments() query independently. The totalRevenue metric uses a MongoDB aggregation pipeline. For high-traffic deployments, consider:

  • Caching these values with a TTL (e.g., Redis)
  • Using Promise.all() to parallelize the queries
  • Adding MongoDB indexes on returnedAt, isActive, and status fields

GET /dashboard/analytics

Returns time-series trend data for the last 6 months. Used to render charts on the dashboard.

Access Control

  • Allowed roles: Any authenticated user

Request

GET /api/v1/dashboard/analytics
Authorization: Bearer <token>

Response — 200 OK

{
  "loansTrend": [
    { "month": "2026-02", "count": 45 },
    { "month": "2026-03", "count": 67 },
    { "month": "2026-04", "count": 52 },
    { "month": "2026-05", "count": 78 },
    { "month": "2026-06", "count": 61 },
    { "month": "2026-07", "count": 34 }
  ],
  "revenueTrend": [
    { "month": "2026-02", "revenue": 120.00 },
    { "month": "2026-03", "revenue": 245.50 },
    { "month": "2026-04", "revenue": 180.00 },
    { "month": "2026-05", "revenue": 310.00 },
    { "month": "2026-06", "revenue": 195.00 },
    { "month": "2026-07", "revenue": 85.00 }
  ]
}

Data Definitions

DatasetAggregationDescription
loansTrendGroups Transaction.issuedAt by year/month for the last 6 monthsMonthly count of new book checkouts
revenueTrendGroups Fine.updatedAt by year/month where status === 'PAID'Monthly sum of paid fine amounts

Aggregation Pipeline

Loans Over Time:

Transaction.aggregate([
  { $match: { issuedAt: { $gte: sixMonthsAgo } } },
  { $group: {
      _id: { year: { $year: "$issuedAt" }, month: { $month: "$issuedAt" } },
      count: { $sum: 1 }
  }},
  { $sort: { "_id.year": 1, "_id.month": 1 } }
]);

Revenue Over Time:

Fine.aggregate([
  { $match: { status: 'PAID', updatedAt: { $gte: sixMonthsAgo } } },
  { $group: {
      _id: { year: { $year: "$updatedAt" }, month: { $month: "$updatedAt" } },
      revenue: { $sum: "$amount" }
  }},
  { $sort: { "_id.year": 1, "_id.month": 1 } }
]);

Frontend Usage

The analytics data feeds into Recharts line/bar charts on the dashboard:

const res = await api.get('/dashboard/analytics');
const { loansTrend, revenueTrend } = res.data;

Health Check (Non-API)

While not under the /api/v1/ prefix, the server also exposes a health check:

GET /health

GET /health

Response — 200 OK

{
  "status": "ok",
  "message": "SLMS API is running"
}

This endpoint requires no authentication and is intended for infrastructure monitoring (load balancers, uptime checks, CI/CD pipelines).


Route Summary

MethodPathAuthDescription
GET/dashboard/statsAggregate stat cards
GET/dashboard/analytics6-month trend data
GET/healthServer health check

On this page