Bulk Sync API

Pre-register multiple monitors at once with the sync endpoint. Essential for framework integrations that auto-discover recurring jobs (Hangfire, Laravel, Celery).


What is Sync?

The sync endpoint allows you to register multiple monitors in a single API call. This is used by:

  • Framework integrations: Hangfire, Quartz.NET, Laravel, Celery auto-discover jobs and sync them on app startup
  • CI/CD pipelines: Register all scheduled jobs during deployment
  • Dynamic job systems: Programmatically manage monitors based on configuration

Endpoint

POST /api/sync

Content-Type: application/json

Authentication

Use any of the supported authentication methods (see Authentication docs). Basic Auth recommended:

curl -X POST -u YOUR_API_KEY: \
  -H "Content-Type: application/json" \
  https://cron.life/api/sync \
  -d @monitors.json

Request Format

{
  "source": "hangfire",
  "monitors": [
    {
      "key": "daily-backup",
      "name": "Daily Database Backup",
      "schedule": "0 2 * * *",
      "gracePeriod": 300
    },
    {
      "key": "hourly-sync",
      "name": "Hourly Data Sync",
      "schedule": "0 * * * *",
      "gracePeriod": 60
    },
    {
      "key": "process-payments",
      "name": "Process Payment Queue",
      "schedule": "*/15 * * * *",
      "gracePeriod": 120
    }
  ]
}

Request Fields

FieldTypeRequiredDescription
sourcestringYesSource identifier (e.g., "hangfire", "laravel", "celery", "manual")
monitorsarrayYesArray of monitor objects (max 100 per request)

Monitor Object Fields

FieldTypeRequiredDescription
keystringYesMonitor key (lowercase, alphanumeric, hyphens, underscores)
namestringNoHuman-readable name (auto-generated from key if not provided)
schedulestringYesCron expression (5 or 6 fields, or special strings like @hourly)
gracePeriodintegerNoGrace period in seconds (default: 60)

Response

Success Response (200 OK)

{
  "status": "success",
  "synced": 3,
  "created": 2,
  "updated": 1,
  "errors": []
}

Response Fields

FieldDescription
syncedTotal monitors successfully synced
createdNumber of new monitors created
updatedNumber of existing monitors updated
errorsArray of error objects for failed monitors

Partial Success Response

If some monitors fail validation, sync continues for valid ones:

{
  "status": "partial",
  "synced": 2,
  "created": 2,
  "updated": 0,
  "errors": [
    {
      "key": "invalid-job",
      "error": "Invalid cron expression: '0 25 * * *' (hour must be 0-23)"
    }
  ]
}

Code Examples

curl -X POST -u YOUR_API_KEY: \
  -H "Content-Type: application/json" \
  https://cron.life/api/sync \
  -d '{
    "source": "manual",
    "monitors": [
      {
        "key": "backup-prod",
        "name": "Production Backup",
        "schedule": "0 2 * * *",
        "gracePeriod": 300
      }
    ]
  }'

Idempotency

Sync is fully idempotent - safe to call multiple times:

  • First call: Creates all monitors (e.g., 5 created, 0 updated)
  • Subsequent calls: Updates existing monitors (e.g., 0 created, 5 updated)
  • Changed schedules: Updates take effect immediately
  • Removed monitors: Not deleted (manual deletion only)

Rate Limits

  • Sync endpoint: 10 requests per minute per API key
  • Max monitors per request: 100
  • Recommended frequency: Once per app startup (not in a loop)

Need higher limits? Contact support@cronradar.com.


Best Practices

1. Use Descriptive Source IDs

Source IDs help you filter monitors in the dashboard:

"source": "hangfire-production"    ✓ Good
"source": "hangfire-staging"      ✓ Good
"source": "manual"                ✓ Good
"source": "app"                   ✗ Too vague

2. Normalize Keys

Always convert job IDs to lowercase, replace spaces with hyphens:

// Good normalization
"Send Welcome Email""send-welcome-email"
"Backup_DB""backup-db"
"ProcessPayments""process-payments"

3. Generate Readable Names

If keys are machine-readable, provide human-friendly names:

{
  "key": "send-welcome-email",
  "name": "Send Welcome Email",
  ...
}

4. Call on App Startup

Framework integrations should call sync during application initialization:

// .NET Hangfire example
services.AddHangfire(config =>
{
    config.UseStorage(...);
    config.MonitorAll("api_key"); // Calls sync internally
});

Next Steps

Was this page helpful?