Invoice Analytics
Retrieve comprehensive analytics and metrics for your invoices, including KPIs, status breakdowns, aging analysis, top customers, and revenue trends.
Endpoints
Summary Analytics
GET
/api/v1/invoices/analytics/summaryGet comprehensive invoice analytics including KPIs, status counts, aging buckets, and top customers.
Revenue Timeseries
GET
/api/v1/invoices/analytics/revenue-timeseriesGet revenue trends over time aggregated by day, week, or month.
Summary Analytics Endpoint
Query Parameters
| Field | Type | Required | Description | Example |
|---|---|---|---|---|
| from | string | Required | Start date for analytics (ISO 8601 format) | 2025-11-01T00:00:00Z |
| to | string | Required | End date for analytics (ISO 8601 format) | 2025-11-30T23:59:59Z |
Code Examples
import requestsurl = "http://localhost:8000/api/v1/invoices/analytics/summary"headers = {"Authorization": "Bearer your-api-key"}params = {"from": "2025-11-01T00:00:00Z","to": "2025-11-30T23:59:59Z"}response = requests.get(url, headers=headers, params=params)analytics = response.json()print(analytics)
Response Structure
{
"summary": {
"status_counts": {
"draft": 5,
"sent": 20,
"paid": 45,
"overdue": 3,
"canceled": 2
},
"total_invoiced": "5000.00",
"total_paid": "4200.00",
"total_outstanding": "700.00",
"total_overdue": "300.00",
"collection_rate": 0.857,
"avg_time_to_pay_days": 5.2
},
"aging": {
"days_0_30": "400.00",
"days_31_60": "200.00",
"days_61_90": "100.00",
"days_90_plus": "0.00"
},
"top_customers": [
{
"customer_name": "Acme Corp",
"customer_email": "[email protected]",
"invoice_count": 10,
"total_invoiced": "1500.00",
"total_paid": "1400.00"
}
]
}
Summary Fields
| Field | Type | Required | Description | Example |
|---|---|---|---|---|
| status_counts | object | Required | Count of invoices by status | {"draft": 5, "sent": 20, "paid": 45, "overdue": 3, "canceled": 2} |
| total_invoiced | string (Decimal) | Required | Total amount invoiced (status: sent, paid, or overdue) in the date range | 5000.00 |
| total_paid | string (Decimal) | Required | Total amount paid in the date range | 4200.00 |
| total_outstanding | string (Decimal) | Required | Total amount outstanding (status: sent or overdue) | 700.00 |
| total_overdue | string (Decimal) | Required | Total amount overdue | 300.00 |
| collection_rate | float | Required | Collection rate calculated as: total_paid / (total_paid + total_outstanding). Range: 0.0 to 1.0 | 0.857 |
| avg_time_to_pay_days | float | null | Optional | Average number of days from invoice issued_at to paid_at for paid invoices | 5.2 |
Aging Fields
| Field | Type | Required | Description | Example |
|---|---|---|---|---|
| days_0_30 | string (Decimal) | Required | Amount overdue for 0-30 days | 400.00 |
| days_31_60 | string (Decimal) | Required | Amount overdue for 31-60 days | 200.00 |
| days_61_90 | string (Decimal) | Required | Amount overdue for 61-90 days | 100.00 |
| days_90_plus | string (Decimal) | Required | Amount overdue for 90+ days | 0.00 |
Top Customers Fields
| Field | Type | Required | Description | Example |
|---|---|---|---|---|
| customer_name | string | Required | Customer name | Acme Corp |
| customer_email | string | null | Optional | Customer email address | [email protected] |
| invoice_count | integer | Required | Number of invoices for this customer | 10 |
| total_invoiced | string (Decimal) | Required | Total amount invoiced to this customer | 1500.00 |
| total_paid | string (Decimal) | Required | Total amount paid by this customer | 1400.00 |
Revenue Timeseries Endpoint
Query Parameters
| Field | Type | Required | Description | Example |
|---|---|---|---|---|
| from | string | Required | Start date for analytics (ISO 8601 format) | 2025-11-01T00:00:00Z |
| to | string | Required | End date for analytics (ISO 8601 format) | 2025-11-30T23:59:59Z |
| granularity | string | Optional | Time granularity for aggregation: 'day', 'week', or 'month' | day |
Code Examples
import requestsurl = "http://localhost:8000/api/v1/invoices/analytics/revenue-timeseries"headers = {"Authorization": "Bearer your-api-key"}params = {"from": "2025-11-01T00:00:00Z","to": "2025-11-30T23:59:59Z","granularity": "day"}response = requests.get(url, headers=headers, params=params)timeseries = response.json()print(timeseries)
Response Structure
{
"timeseries": [
{
"bucket": "2025-11-01",
"paid_amount": "500.00",
"paid_count": 5
},
{
"bucket": "2025-11-02",
"paid_amount": "300.00",
"paid_count": 3
}
]
}
Timeseries Fields
| Field | Type | Required | Description | Example |
|---|---|---|---|---|
| bucket | string | Required | Date bucket (YYYY-MM-DD format for day, YYYY-MM-DD for week/month representing the start of the period) | 2025-11-01 |
| paid_amount | string (Decimal) | Required | Total amount paid in this time bucket | 500.00 |
| paid_count | integer | Required | Number of invoices paid in this time bucket | 5 |
Metrics Explanation
Collection Rate
The collection rate measures payment efficiency:
collection_rate = total_paid / (total_paid + total_outstanding)
- Range: 0.0 to 1.0 (0% to 100%)
- Higher values indicate better collection performance
- Only considers invoices that were sent (status: sent, paid, or overdue)
Average Time to Pay
Average number of days between invoice issued_at and paid_at:
- Calculated only for paid invoices
- Excludes invoices without both
issued_atandpaid_attimestamps - Returns
nullif no paid invoices exist in the date range
Aging Buckets
Aging analysis groups outstanding invoices by days overdue:
- 0-30 days: Recently overdue invoices
- 31-60 days: Moderately overdue
- 61-90 days: Significantly overdue
- 90+ days: Severely overdue
Only includes invoices with status sent or overdue that have a due_at date.
Error Scenarios
400 Bad Request
- Invalid date format (must be ISO 8601)
fromdate is aftertodate- Invalid
granularityvalue (must be 'day', 'week', or 'month')
401 Unauthorized
- Missing or invalid API key
- API key does not have permission to access analytics
500 Internal Server Error
- Database query failure
- Service error during analytics calculation