Skip to main content
GET
/
analytics
/
jobs
curl -X GET \
  "https://api.kardow.com/analytics/jobs?jobIds=123e4567-e89b-12d3-a456-426614174000,123e4567-e89b-12d3-a456-426614174001&period=30d" \
  -H "x-api-key: your-api-key-here"
{
  "data": {
    "visitors": {
      "123e4567-e89b-12d3-a456-426614174000": 150,
      "123e4567-e89b-12d3-a456-426614174001": 320
    }
  },
  "meta": {
    "period": "30d",
    "total_jobs": 2
  }
}

Authentication

This endpoint requires API key authentication. Include your API key in the request header:
x-api-key: your-api-key-here
You can generate API keys from your organization settings in the Kardow dashboard under Settings > API Keys.

Query Parameters

jobIds
string
required
Comma-separated list of job UUIDs to fetch visitor counts for. Maximum 100 job IDs per request.Example: 123e4567-e89b-12d3-a456-426614174000,123e4567-e89b-12d3-a456-426614174001
period
string
default:"30d"
Time period for analytics data. Must be one of:
  • 7d - Last 7 days
  • 30d - Last 30 days
  • 6mo - Last 6 months
  • 12mo - Last 12 months

Response

data
object
The analytics data for the requested jobs
meta
object
Metadata about the request
curl -X GET \
  "https://api.kardow.com/analytics/jobs?jobIds=123e4567-e89b-12d3-a456-426614174000,123e4567-e89b-12d3-a456-426614174001&period=30d" \
  -H "x-api-key: your-api-key-here"
{
  "data": {
    "visitors": {
      "123e4567-e89b-12d3-a456-426614174000": 150,
      "123e4567-e89b-12d3-a456-426614174001": 320
    }
  },
  "meta": {
    "period": "30d",
    "total_jobs": 2
  }
}

Security

This endpoint implements multiple security layers:
  1. API Key Authentication - Only valid API keys can access the endpoint
  2. Organization Scoping - You can only access jobs belonging to your organization
  3. Job Ownership Validation - All requested job IDs are verified to belong to your organization
  4. Domain Validation - Analytics are fetched only from your organization’s verified domain

Rate Limits

API requests are subject to rate limits:
  • 100 requests per minute per API key
  • 10 concurrent requests maximum
When you exceed the rate limit, you’ll receive a 429 Too Many Requests response.

Best Practices

Batch Multiple Jobs

Instead of making individual requests for each job, batch multiple job IDs in a single request:
// Making 50 requests
for (const jobId of jobIds) {
  await fetch(`https://api.kardow.com/analytics/jobs?jobIds=${jobId}`);
}

Implement Error Handling

Always implement proper error handling with retries:
async function getAnalyticsWithRetry(jobIds, maxRetries = 3) {
  let lastError;

  for (let i = 0; i < maxRetries; i++) {
    try {
      const response = await fetch(
        `https://api.kardow.com/analytics/jobs?jobIds=${jobIds.join(',')}`,
        { headers: { 'x-api-key': apiKey } }
      );

      if (response.status === 429) {
        // Rate limited - wait and retry
        await new Promise(resolve => setTimeout(resolve, 2000 * (i + 1)));
        continue;
      }

      if (!response.ok) {
        const error = await response.json();
        throw new Error(error.error.message);
      }

      return await response.json();
    } catch (error) {
      lastError = error;
      if (i < maxRetries - 1) {
        await new Promise(resolve => setTimeout(resolve, 1000 * (i + 1)));
      }
    }
  }

  throw lastError;
}

Cache Results

Cache analytics data to reduce API calls:
const cache = new Map();
const CACHE_TTL = 5 * 60 * 1000; // 5 minutes

async function getCachedAnalytics(jobIds) {
  const cacheKey = jobIds.sort().join(',');
  const cached = cache.get(cacheKey);

  if (cached && Date.now() - cached.timestamp < CACHE_TTL) {
    return cached.data;
  }

  const data = await getJobAnalytics(jobIds);
  cache.set(cacheKey, { data, timestamp: Date.now() });
  return data;
}

Common Use Cases

Dashboard Integration

Display visitor analytics in your custom dashboard:
async function buildJobDashboard(jobIds) {
  const analytics = await getJobAnalytics(jobIds);

  return jobIds.map(jobId => ({
    jobId,
    visitors: analytics.data.visitors[jobId] || 0,
    // Add other job data
  }));
}

Weekly Performance Reports

Generate automated reports of job performance:
async function generateWeeklyReport() {
  const jobs = await getAllActiveJobs();
  const jobIds = jobs.map(j => j.id);

  const analytics = await getJobAnalytics(jobIds);

  const report = {
    period: analytics.meta.period,
    totalVisitors: Object.values(analytics.data.visitors)
      .reduce((a, b) => a + b, 0),
    topJobs: Object.entries(analytics.data.visitors)
      .sort(([, a], [, b]) => b - a)
      .slice(0, 10)
      .map(([jobId, visitors]) => ({
        job: jobs.find(j => j.id === jobId),
        visitors
      }))
  };

  return report;
}

Comparative Analysis

Compare performance across different time periods:
async function comparePerformance(jobIds) {
  const [last7Days, last30Days] = await Promise.all([
    getJobAnalytics(jobIds, '7d'),
    getJobAnalytics(jobIds, '30d')
  ]);

  return jobIds.map(jobId => ({
    jobId,
    last7Days: last7Days.data.visitors[jobId] || 0,
    last30Days: last30Days.data.visitors[jobId] || 0,
    averageDaily: (last30Days.data.visitors[jobId] || 0) / 30
  }));
}

Site Analytics

Get comprehensive analytics with filtering options

List Jobs

Retrieve your job listings

Authorizations

x-api-key
string
header
required

API key for authentication. Get yours from Settings > API Keys in the Kardow dashboard.

Query Parameters

jobIds
string
required

Comma-separated list of job UUIDs (max 100)

Example:

"123e4567-e89b-12d3-a456-426614174000,123e4567-e89b-12d3-a456-426614174001"

period
enum<string>
default:30d

Time period for analytics

Available options:
7d,
30d,
6mo,
12mo

Response

Success

data
object
meta
object