Insights
Insights endpoints of the URLCrop API: 6 operations. Analytics served from hourly/daily rollups; raw recent events; CSV exports.
Time series of one or more metrics
GET/insights/timeseries
- Scope insights:read
Served from hourly/daily rollups. interval=hour is limited to a 7-day range. Ranges beyond the plan's retention are truncated (truncated_to_retention: true).
Parameters
| Name | In | Type | Description |
|---|---|---|---|
| X-Workspace-Id | header | string | Workspace to act on. Required for session requests on workspace-scoped routes; optional for API keys (must equal the key's workspace, otherwise 403 workspace_mismatch). For a session, a workspace the user is not an active member of (another tenant, a removed membership, a malformed or unknown id) answers 404 resource_not_found, never 403. |
| metricsrequired | query | string | Comma-separated. conversions and revenue are Phase 2. |
| interval | query | string | One of: hour, day, week, month |
| from | query | string | Start of the period (inclusive). YYYY-MM-DD or RFC 3339. Default 30 days ago. |
| to | query | string | End of the period (inclusive). Default now. |
| timezone | query | string | IANA timezone for bucketing. Default is the workspace timezone. |
| include_bots | query | boolean | When true, flagged bot events are added into click, scan and view counts (the rollups' bots column). Default false excludes them. unique_visitors never includes bots. |
| compare | query | string | previous adds the previous period of equal length (a whole calendar month compares with the previous calendar month). timeseries returns a previous series and per-metric deltas; top-links returns a delta per row.Value: previous |
| link_id | query | string | |
| qr_code_id | query | string | |
| page_id | query | string | |
| campaign_id | query | string | |
| domain | query | string | |
| country | query | string | Served from the country dimension rows of the rollups; one of country / device at a time (both → 422 unsupported_in_phase), combinable with one scope filter. A malformed code → 400 invalid_query. With interval=hour it reads the raw events of the last 7 days and the response is marked truncated_to_retention: true when from is cut. |
| device | query | string | Served from the device_type dimension rows of the rollups; one of country / device at a time (both → 422 unsupported_in_phase), combinable with one scope filter. With interval=hour it reads the raw events of the last 7 days and the response is marked truncated_to_retention: true when from is cut.One of: mobile, desktop, tablet |
Request example
curl 'https://api.urlcrop.com/v1/insights/timeseries?metrics=clicks%2Cscans%2Cunique_visitors' \
-H 'Authorization: Bearer uc_live_…'Responses
200 response
Time series
InsightsTimeseries schema and example
Field Type Description objectrequired string Value: timeseriesintervalrequired string One of: hour,day,week,monthfromrequired string ISO 8601 UTC with milliseconds.Format: date-time torequired string ISO 8601 UTC with milliseconds.Format: date-time timezonerequired string metricsrequired array of string truncated_to_retention boolean True when fromwas moved forward to the plan's retention window.over_quota_events integer Over-quota events (counted without detail) in the UTC months overlapping the range; not part of data.previous object Only with compare=previous. Same buckets asdata, shifted to the previous period (index-aligned).previous. fromrequired string ISO 8601 UTC with milliseconds.Format: date-time previous. torequired string ISO 8601 UTC with milliseconds.Format: date-time previous. datarequired array of InsightsTimeseriesPoint previous. data[]. timestamprequired string ISO 8601 UTC with milliseconds.Format: date-time previous. data[]. clicks integer previous. data[]. scans integer previous. data[]. views integer previous. data[]. unique_visitors integer previous. data[]. conversions integer previous. data[]. revenue integer Minor units in the workspace currency (Phase 2). deltas object Only with compare=previous. One entry per requested metric.datarequired array of InsightsTimeseriesPoint data[]. timestamprequired string ISO 8601 UTC with milliseconds.Format: date-time data[]. clicks integer data[]. scans integer data[]. views integer data[]. unique_visitors integer data[]. conversions integer data[]. revenue integer Minor units in the workspace currency (Phase 2). 200 response: dailyJSON{ "object": "timeseries", "interval": "day", "from": "2026-12-01T00:00:00.000Z", "to": "2026-12-03T23:59:59.999Z", "timezone": "Asia/Kolkata", "metrics": [ "clicks", "scans" ], "truncated_to_retention": false, "data": [ { "timestamp": "2026-11-30T18:30:00.000Z", "clicks": 1200, "scans": 140 }, { "timestamp": "2026-12-01T18:30:00.000Z", "clicks": 1380, "scans": 162 }, { "timestamp": "2026-12-02T18:30:00.000Z", "clicks": 990, "scans": 121 } ] }304 response
The
If-None-MatchETag matches; no body. Sent for cacheable aggregate reads (Cache-Control: private, max-age=30, weakETag).400 response
Malformed request (
invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand). Any credentialed operation can return it: a credential in the query string (api_key,access_token) isinvalid_query, and a session request withoutX-Workspace-Idon a workspace-scoped route ismissing_header.Error codes:
invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expandError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 400 response: missing headerJSON{ "error": { "type": "invalid_request_error", "code": "missing_header", "message": "The X-Workspace-Id header is required for session requests.", "param": "X-Workspace-Id", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#missing_header" } }401 response
Missing or invalid credentials. Always
code: unauthenticated;details[0].codegives the reason (missing_credentials,invalid_api_key,api_key_revoked,api_key_expired,session_expired,publishable_key_not_allowed).Error codes:
unauthenticatedError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 401 response: unauthenticatedJSON{ "error": { "type": "authentication_error", "code": "unauthenticated", "message": "The API key is not valid.", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#unauthenticated", "details": [ { "path": "Authorization", "code": "invalid_api_key", "message": "No key matches this secret" } ] } }403 response
Permitted credential but not allowed:
insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,two_factor_required(also Owner/Admin writes on Business+ after the 14-day 2FA grace,details[0].grace_ends_at),step_up_required,email_verification_required,signups_paused(sign-up while the platform setting is on),write_blocked_past_due,workspace_suspended,content_policy_hold,origin_not_allowed, or a plan limit (type: plan_limit_error—feature_not_in_plan,plan_limit_reachedwithparamnaming the plan limit key). Any credentialed operation can return it: an API key on a session-only route isinsufficient_scope, a session write without an allowedOriginisorigin_not_allowed, and an API key whose plan has no API access isfeature_not_in_plan.Error codes:
two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,feature_not_in_plan,plan_limit_reachedError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 403 response: plan limit reachedJSON{ "error": { "type": "plan_limit_error", "code": "plan_limit_reached", "message": "You have created 2,000 of 2,000 links this billing period. Upgrade or buy a pack to continue.", "param": "links_per_month", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/pricing", "details": [ { "code": "plan_limit_reached", "message": "Monthly link quota reached", "limit": 2000, "used": 2000, "resets_at": "2026-12-01T00:00:00.000Z", "upgrade_to": "business" } ] } }403 response: feature not in planJSON{ "error": { "type": "plan_limit_error", "code": "feature_not_in_plan", "message": "The public API is available on the Pro plan and above.", "param": "api_requests_per_day", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/pricing", "details": [ { "code": "feature_not_in_plan", "message": "Upgrade to Pro", "upgrade_to": "pro" } ] } }403 response: email verification requiredJSON{ "error": { "type": "permission_error", "code": "email_verification_required", "message": "Verify your email address to create links.", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#email_verification_required" } }403 response: step up requiredJSON{ "error": { "type": "permission_error", "code": "step_up_required", "message": "Confirm your password or 2FA code to continue.", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#step_up_required" } }404 response
Unknown id, or the resource belongs to another workspace (never distinguished). Also returned when a session's
X-Workspace-Idnames a workspace the user is not an active member of.Error codes:
resource_not_foundError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 404 response: not foundJSON{ "error": { "type": "not_found_error", "code": "resource_not_found", "message": "No link with id lnk_01JB4N8ZK3Q9WXYZ0123456789.", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#resource_not_found" } }422 response
Validation failure (
validation_failed,destination_invalid,destination_blocked(details[0].codeispolicy_violation, with the category, for content-policy blocks),slug_invalid,slug_reserved,slug_not_allowed,handle_not_allowed,title_not_allowed,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,policy_acceptance_required, …).Error codes:
validation_failed,destination_invalid,destination_blocked,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,policy_acceptance_requiredError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 422 response: validation failedJSON{ "error": { "type": "validation_error", "code": "validation_failed", "message": "The request body is invalid.", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#validation_failed", "details": [ { "path": "destination_url", "code": "invalid_string", "message": "Must be an absolute http(s) URL" } ] } }422 response: destination blockedJSON{ "error": { "type": "validation_error", "code": "destination_blocked", "message": "This destination was flagged as unsafe and cannot be shortened.", "param": "destination_url", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#destination_blocked" } }429 response
Burst limit, daily plan quota or endpoint limit exceeded.
Error codes:
rate_limitedError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 429 response: rate limitedJSON{ "error": { "type": "rate_limit_error", "code": "rate_limited", "message": "Daily API quota of 50,000 requests exhausted. Resets at 00:00 UTC.", "param": "daily_quota", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/rate-limits" } }
Break one metric down by a dimension
GET/insights/breakdown
- Scope insights:read
Parameters
| Name | In | Type | Description |
|---|---|---|---|
| X-Workspace-Id | header | string | Workspace to act on. Required for session requests on workspace-scoped routes; optional for API keys (must equal the key's workspace, otherwise 403 workspace_mismatch). For a session, a workspace the user is not an active member of (another tenant, a removed membership, a malformed or unknown id) answers 404 resource_not_found, never 403. |
| dimensionrequired | query | string | hour_of_day (keys 0..23) and day_of_week (keys mon..sun) are bucketed in the request timezone, always return every slot (zeros included) and ignore limit. page and campaign rows use the public id as key and the title / name as label.One of: country, city, device, os, browser, referrer, language, link, qr_code, page, campaign, domain, utm_source, utm_medium, utm_campaign, hour_of_day, day_of_week |
| metricrequired | query | string | One of: clicks, scans, views, unique_visitors, conversions, revenue |
| from | query | string | Start of the period (inclusive). YYYY-MM-DD or RFC 3339. Default 30 days ago. |
| to | query | string | End of the period (inclusive). Default now. |
| timezone | query | string | IANA timezone for bucketing. Default is the workspace timezone. |
| include_bots | query | boolean | When true, flagged bot events are added into click, scan and view counts (the rollups' bots column). Default false excludes them. unique_visitors never includes bots. |
| link_id | query | string | |
| qr_code_id | query | string | Served from qr rollups; alone only (with link_id, campaign_id, domain or page_id → 422 unsupported_in_phase). |
| page_id | query | string | Served from page rollups; alone only (with link_id, qr_code_id, campaign_id or domain → 422 unsupported_in_phase). |
| campaign_id | query | string | |
| domain | query | string | |
| country | query | string | ISO 3166-1 alpha-2 code. Combines with the attribute dimensions (city, device, os, browser, referrer, language, utm_*) and with the other scope filters. For city it selects the rollup rows of that country (CC|City keys) for any range (no truncation); for the other attribute dimensions rollup rows carry one dimension each, so it reads the raw events of the last 7 days (from is moved forward to that window and the response is marked truncated_to_retention: true). link, domain, qr_code, page, campaign, hour_of_day and day_of_week with country → 422 unsupported_in_phase. A malformed code → 400 invalid_query. |
| device | query | string | Not served for breakdowns yet (422 unsupported_in_phase).One of: mobile, desktop, tablet |
| limit | query | integer |
Request example
curl 'https://api.urlcrop.com/v1/insights/breakdown?dimension=country&metric=clicks' \
-H 'Authorization: Bearer uc_live_…'Responses
200 response
Breakdown
InsightsBreakdown schema and example
Field Type Description objectrequired string Value: breakdowndimensionrequired string hour_of_day(keys0..23) andday_of_week(keysmon..sun) are bucketed in the requesttimezone, always return every slot (zeros included) and ignorelimit.pageandcampaignrows use the public id askeyand the title / name aslabel.One of:country,city,device,os,browser,referrer,language,link,qr_code,page,campaign,domain,utm_source,utm_medium,utm_campaign,hour_of_day,day_of_weekmetricrequired string One of: clicks,scans,views,unique_visitors,conversions,revenuefromrequired string ISO 8601 UTC with milliseconds.Format: date-time torequired string ISO 8601 UTC with milliseconds.Format: date-time totalrequired number truncated_to_retention boolean datarequired array of BreakdownRow data[]. keyrequired string Dimension value (ISO country code, device class, referrer host, link id…). data[]. label string data[]. valuerequired number data[]. share number Fraction of the total (0–1). 200 response: countryJSON{ "object": "breakdown", "dimension": "country", "metric": "clicks", "from": "2026-11-05T00:00:00.000Z", "to": "2026-12-05T23:59:59.999Z", "total": 13620, "truncated_to_retention": false, "data": [ { "key": "IN", "label": "India", "value": 11170, "share": 0.82 }, { "key": "AE", "label": "United Arab Emirates", "value": 1090, "share": 0.08 } ] }304 response
The
If-None-MatchETag matches; no body. Sent for cacheable aggregate reads (Cache-Control: private, max-age=30, weakETag).400 response
Malformed request (
invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand). Any credentialed operation can return it: a credential in the query string (api_key,access_token) isinvalid_query, and a session request withoutX-Workspace-Idon a workspace-scoped route ismissing_header.Error codes:
invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expandError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 400 response: missing headerJSON{ "error": { "type": "invalid_request_error", "code": "missing_header", "message": "The X-Workspace-Id header is required for session requests.", "param": "X-Workspace-Id", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#missing_header" } }401 response
Missing or invalid credentials. Always
code: unauthenticated;details[0].codegives the reason (missing_credentials,invalid_api_key,api_key_revoked,api_key_expired,session_expired,publishable_key_not_allowed).Error codes:
unauthenticatedError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 401 response: unauthenticatedJSON{ "error": { "type": "authentication_error", "code": "unauthenticated", "message": "The API key is not valid.", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#unauthenticated", "details": [ { "path": "Authorization", "code": "invalid_api_key", "message": "No key matches this secret" } ] } }403 response
Permitted credential but not allowed:
insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,two_factor_required(also Owner/Admin writes on Business+ after the 14-day 2FA grace,details[0].grace_ends_at),step_up_required,email_verification_required,signups_paused(sign-up while the platform setting is on),write_blocked_past_due,workspace_suspended,content_policy_hold,origin_not_allowed, or a plan limit (type: plan_limit_error—feature_not_in_plan,plan_limit_reachedwithparamnaming the plan limit key). Any credentialed operation can return it: an API key on a session-only route isinsufficient_scope, a session write without an allowedOriginisorigin_not_allowed, and an API key whose plan has no API access isfeature_not_in_plan.Error codes:
two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,feature_not_in_plan,plan_limit_reachedError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 403 response: plan limit reachedJSON{ "error": { "type": "plan_limit_error", "code": "plan_limit_reached", "message": "You have created 2,000 of 2,000 links this billing period. Upgrade or buy a pack to continue.", "param": "links_per_month", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/pricing", "details": [ { "code": "plan_limit_reached", "message": "Monthly link quota reached", "limit": 2000, "used": 2000, "resets_at": "2026-12-01T00:00:00.000Z", "upgrade_to": "business" } ] } }403 response: feature not in planJSON{ "error": { "type": "plan_limit_error", "code": "feature_not_in_plan", "message": "The public API is available on the Pro plan and above.", "param": "api_requests_per_day", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/pricing", "details": [ { "code": "feature_not_in_plan", "message": "Upgrade to Pro", "upgrade_to": "pro" } ] } }403 response: email verification requiredJSON{ "error": { "type": "permission_error", "code": "email_verification_required", "message": "Verify your email address to create links.", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#email_verification_required" } }403 response: step up requiredJSON{ "error": { "type": "permission_error", "code": "step_up_required", "message": "Confirm your password or 2FA code to continue.", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#step_up_required" } }404 response
Unknown id, or the resource belongs to another workspace (never distinguished). Also returned when a session's
X-Workspace-Idnames a workspace the user is not an active member of.Error codes:
resource_not_foundError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 404 response: not foundJSON{ "error": { "type": "not_found_error", "code": "resource_not_found", "message": "No link with id lnk_01JB4N8ZK3Q9WXYZ0123456789.", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#resource_not_found" } }422 response
Validation failure (
validation_failed,destination_invalid,destination_blocked(details[0].codeispolicy_violation, with the category, for content-policy blocks),slug_invalid,slug_reserved,slug_not_allowed,handle_not_allowed,title_not_allowed,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,policy_acceptance_required, …).Error codes:
validation_failed,destination_invalid,destination_blocked,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,policy_acceptance_requiredError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 422 response: validation failedJSON{ "error": { "type": "validation_error", "code": "validation_failed", "message": "The request body is invalid.", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#validation_failed", "details": [ { "path": "destination_url", "code": "invalid_string", "message": "Must be an absolute http(s) URL" } ] } }422 response: destination blockedJSON{ "error": { "type": "validation_error", "code": "destination_blocked", "message": "This destination was flagged as unsafe and cannot be shortened.", "param": "destination_url", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#destination_blocked" } }429 response
Burst limit, daily plan quota or endpoint limit exceeded.
Error codes:
rate_limitedError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 429 response: rate limitedJSON{ "error": { "type": "rate_limit_error", "code": "rate_limited", "message": "Daily API quota of 50,000 requests exhausted. Resets at 00:00 UTC.", "param": "daily_quota", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/rate-limits" } }
Top links by a metric, optionally with period-over-period delta
GET/insights/top-links
- Scope insights:read
Same range, time-zone and filter semantics as timeseries. With compare=previous every row carries a delta.
Parameters
| Name | In | Type | Description |
|---|---|---|---|
| X-Workspace-Id | header | string | Workspace to act on. Required for session requests on workspace-scoped routes; optional for API keys (must equal the key's workspace, otherwise 403 workspace_mismatch). For a session, a workspace the user is not an active member of (another tenant, a removed membership, a malformed or unknown id) answers 404 resource_not_found, never 403. |
| metric | query | string | One of: clicks, scans, views, unique_visitors, conversions, revenue |
| from | query | string | Start of the period (inclusive). YYYY-MM-DD or RFC 3339. Default 30 days ago. |
| to | query | string | End of the period (inclusive). Default now. |
| timezone | query | string | IANA timezone for bucketing. Default is the workspace timezone. |
| include_bots | query | boolean | When true, flagged bot events are added into click, scan and view counts (the rollups' bots column). Default false excludes them. unique_visitors never includes bots. |
| compare | query | string | previous adds the previous period of equal length (a whole calendar month compares with the previous calendar month). timeseries returns a previous series and per-metric deltas; top-links returns a delta per row.Value: previous |
| link_id | query | string | |
| qr_code_id | query | string | |
| page_id | query | string | |
| campaign_id | query | string | |
| domain | query | string | |
| country | query | string | Served from the country dimension rows of the rollups; one of country / device at a time (both → 422 unsupported_in_phase), combinable with one scope filter. A malformed code → 400 invalid_query. With interval=hour it reads the raw events of the last 7 days and the response is marked truncated_to_retention: true when from is cut. |
| device | query | string | Served from the device_type dimension rows of the rollups; one of country / device at a time (both → 422 unsupported_in_phase), combinable with one scope filter. With interval=hour it reads the raw events of the last 7 days and the response is marked truncated_to_retention: true when from is cut.One of: mobile, desktop, tablet |
| limit | query | integer |
Request example
curl 'https://api.urlcrop.com/v1/insights/top-links' \
-H 'Authorization: Bearer uc_live_…'Responses
200 response
Top links
InsightsTopLinks schema and example
Field Type Description objectrequired string Value: top_linksmetricrequired string One of: clicks,scans,views,unique_visitors,conversions,revenuefromrequired string ISO 8601 UTC with milliseconds.Format: date-time torequired string ISO 8601 UTC with milliseconds.Format: date-time truncated_to_retention boolean previous object Only with compare=previous.previous. fromrequired string ISO 8601 UTC with milliseconds.Format: date-time previous. torequired string ISO 8601 UTC with milliseconds.Format: date-time datarequired array of object data[]. link_idrequired string data[]. short_urlrequired string Format: uri data[]. title string | null data[]. valuerequired number data[]. delta InsightsDelta Only with compare=previous.data[]. delta. valuerequired number data[]. delta. previousrequired number data[]. delta. delta_pctrequired number | null 200 response: 200 responseJSON{ "object": "top_links", "metric": "clicks", "from": "2026-12-05T10:15:30.000Z", "to": "2026-12-05T10:15:30.000Z", "truncated_to_retention": false, "previous": { "from": "2026-12-05T10:15:30.000Z", "to": "2026-12-05T10:15:30.000Z" }, "data": [ { "link_id": "string", "short_url": "https://example.com", "title": "string", "value": 0, "delta": { "value": 0, "previous": 0, "delta_pct": 0 } } ] }Example generated from the schema. 304 response
The
If-None-MatchETag matches; no body. Sent for cacheable aggregate reads (Cache-Control: private, max-age=30, weakETag).400 response
Malformed request (
invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand). Any credentialed operation can return it: a credential in the query string (api_key,access_token) isinvalid_query, and a session request withoutX-Workspace-Idon a workspace-scoped route ismissing_header.Error codes:
invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expandError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 400 response: missing headerJSON{ "error": { "type": "invalid_request_error", "code": "missing_header", "message": "The X-Workspace-Id header is required for session requests.", "param": "X-Workspace-Id", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#missing_header" } }401 response
Missing or invalid credentials. Always
code: unauthenticated;details[0].codegives the reason (missing_credentials,invalid_api_key,api_key_revoked,api_key_expired,session_expired,publishable_key_not_allowed).Error codes:
unauthenticatedError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 401 response: unauthenticatedJSON{ "error": { "type": "authentication_error", "code": "unauthenticated", "message": "The API key is not valid.", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#unauthenticated", "details": [ { "path": "Authorization", "code": "invalid_api_key", "message": "No key matches this secret" } ] } }403 response
Permitted credential but not allowed:
insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,two_factor_required(also Owner/Admin writes on Business+ after the 14-day 2FA grace,details[0].grace_ends_at),step_up_required,email_verification_required,signups_paused(sign-up while the platform setting is on),write_blocked_past_due,workspace_suspended,content_policy_hold,origin_not_allowed, or a plan limit (type: plan_limit_error—feature_not_in_plan,plan_limit_reachedwithparamnaming the plan limit key). Any credentialed operation can return it: an API key on a session-only route isinsufficient_scope, a session write without an allowedOriginisorigin_not_allowed, and an API key whose plan has no API access isfeature_not_in_plan.Error codes:
two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,feature_not_in_plan,plan_limit_reachedError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 403 response: plan limit reachedJSON{ "error": { "type": "plan_limit_error", "code": "plan_limit_reached", "message": "You have created 2,000 of 2,000 links this billing period. Upgrade or buy a pack to continue.", "param": "links_per_month", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/pricing", "details": [ { "code": "plan_limit_reached", "message": "Monthly link quota reached", "limit": 2000, "used": 2000, "resets_at": "2026-12-01T00:00:00.000Z", "upgrade_to": "business" } ] } }403 response: feature not in planJSON{ "error": { "type": "plan_limit_error", "code": "feature_not_in_plan", "message": "The public API is available on the Pro plan and above.", "param": "api_requests_per_day", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/pricing", "details": [ { "code": "feature_not_in_plan", "message": "Upgrade to Pro", "upgrade_to": "pro" } ] } }403 response: email verification requiredJSON{ "error": { "type": "permission_error", "code": "email_verification_required", "message": "Verify your email address to create links.", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#email_verification_required" } }403 response: step up requiredJSON{ "error": { "type": "permission_error", "code": "step_up_required", "message": "Confirm your password or 2FA code to continue.", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#step_up_required" } }404 response
Unknown id, or the resource belongs to another workspace (never distinguished). Also returned when a session's
X-Workspace-Idnames a workspace the user is not an active member of.Error codes:
resource_not_foundError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 404 response: not foundJSON{ "error": { "type": "not_found_error", "code": "resource_not_found", "message": "No link with id lnk_01JB4N8ZK3Q9WXYZ0123456789.", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#resource_not_found" } }422 response
Validation failure (
validation_failed,destination_invalid,destination_blocked(details[0].codeispolicy_violation, with the category, for content-policy blocks),slug_invalid,slug_reserved,slug_not_allowed,handle_not_allowed,title_not_allowed,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,policy_acceptance_required, …).Error codes:
validation_failed,destination_invalid,destination_blocked,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,policy_acceptance_requiredError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 422 response: validation failedJSON{ "error": { "type": "validation_error", "code": "validation_failed", "message": "The request body is invalid.", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#validation_failed", "details": [ { "path": "destination_url", "code": "invalid_string", "message": "Must be an absolute http(s) URL" } ] } }422 response: destination blockedJSON{ "error": { "type": "validation_error", "code": "destination_blocked", "message": "This destination was flagged as unsafe and cannot be shortened.", "param": "destination_url", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#destination_blocked" } }429 response
Burst limit, daily plan quota or endpoint limit exceeded.
Error codes:
rate_limitedError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 429 response: rate limitedJSON{ "error": { "type": "rate_limit_error", "code": "rate_limited", "message": "Daily API quota of 50,000 requests exhausted. Resets at 00:00 UTC.", "param": "daily_quota", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/rate-limits" } }
Raw recent events (last 7 days, ≤ 10,000 rows per query)
GET/insights/events
- Scope insights:read
Reads the partitioned events table directly; from is clamped to the last 7 days, a query returns at most 10,000 rows across its pages, and the dashboard's live strip polls it every 10 s. Use exports for anything older or larger. Visitor hashes are never returned.
Parameters
| Name | In | Type | Description |
|---|---|---|---|
| X-Workspace-Id | header | string | Workspace to act on. Required for session requests on workspace-scoped routes; optional for API keys (must equal the key's workspace, otherwise 403 workspace_mismatch). For a session, a workspace the user is not an active member of (another tenant, a removed membership, a malformed or unknown id) answers 404 resource_not_found, never 403. |
| cursor | query | string | Opaque cursor from pagination.next_cursor. |
| limit | query | integer | |
| type | query | string | One of: click, scan, view, conversion |
| click_id | query | string | |
| include_bots | query | boolean | |
| since | query | string | RFC 3339 instant, at most 7 days old; only events at or after it are returned (the live strip asks for the last 60 s). |
| from | query | string | Start of the period (inclusive). YYYY-MM-DD or RFC 3339. Default 30 days ago. |
| to | query | string | End of the period (inclusive). Default now. |
| timezone | query | string | IANA timezone for bucketing. Default is the workspace timezone. |
| link_id | query | string | |
| qr_code_id | query | string | |
| page_id | query | string | |
| campaign_id | query | string | |
| domain | query | string | |
| country | query | string | |
| device | query | string | One of: mobile, desktop, tablet |
Request example
curl 'https://api.urlcrop.com/v1/insights/events' \
-H 'Authorization: Bearer uc_live_…'Responses
200 response
Events, newest first
InsightsEventList schema and example
Field Type Description datarequired array of InsightsEvent data[]. event_typerequired string One of: click,scan,view,conversiondata[]. occurred_atrequired string ISO 8601 UTC with milliseconds.Format: date-time data[]. link_id string | null data[]. qr_code_id string | null data[]. page_id string | null data[]. campaign_id string | null data[]. country string | null data[]. region string | null data[]. city string | null data[]. device string | null data[]. os string | null data[]. browser string | null data[]. referrer_domain string | null data[]. referrer_class string | null One of: direct,search,social,email,referral,other,nulldata[]. is_botrequired boolean data[]. click_id string | null paginationrequired Pagination pagination. limitrequired integer pagination. has_morerequired boolean pagination. next_cursorrequired string | null Pass as cursorto fetch the next page.nullon the last page.pagination. total integer Only with include_total=true; estimated above 10,000.200 response: 200 responseJSON{ "data": [ { "event_type": "click", "occurred_at": "2026-12-05T10:15:30.000Z", "link_id": "string", "qr_code_id": "string", "page_id": "string", "campaign_id": "string", "country": "string", "region": "string", "city": "string", "device": "string", "os": "string", "browser": "string", "referrer_domain": "string", "referrer_class": "direct", "is_bot": false, "click_id": "clk_01JB59XQ0P1N2M3L4K5J6H7G8F" } ], "pagination": { "limit": 0, "has_more": false, "next_cursor": "string", "total": 0 } }Example generated from the schema. 400 response
Malformed request (
invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand). Any credentialed operation can return it: a credential in the query string (api_key,access_token) isinvalid_query, and a session request withoutX-Workspace-Idon a workspace-scoped route ismissing_header.Error codes:
invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expandError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 400 response: missing headerJSON{ "error": { "type": "invalid_request_error", "code": "missing_header", "message": "The X-Workspace-Id header is required for session requests.", "param": "X-Workspace-Id", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#missing_header" } }401 response
Missing or invalid credentials. Always
code: unauthenticated;details[0].codegives the reason (missing_credentials,invalid_api_key,api_key_revoked,api_key_expired,session_expired,publishable_key_not_allowed).Error codes:
unauthenticatedError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 401 response: unauthenticatedJSON{ "error": { "type": "authentication_error", "code": "unauthenticated", "message": "The API key is not valid.", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#unauthenticated", "details": [ { "path": "Authorization", "code": "invalid_api_key", "message": "No key matches this secret" } ] } }403 response
Permitted credential but not allowed:
insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,two_factor_required(also Owner/Admin writes on Business+ after the 14-day 2FA grace,details[0].grace_ends_at),step_up_required,email_verification_required,signups_paused(sign-up while the platform setting is on),write_blocked_past_due,workspace_suspended,content_policy_hold,origin_not_allowed, or a plan limit (type: plan_limit_error—feature_not_in_plan,plan_limit_reachedwithparamnaming the plan limit key). Any credentialed operation can return it: an API key on a session-only route isinsufficient_scope, a session write without an allowedOriginisorigin_not_allowed, and an API key whose plan has no API access isfeature_not_in_plan.Error codes:
two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,feature_not_in_plan,plan_limit_reachedError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 403 response: plan limit reachedJSON{ "error": { "type": "plan_limit_error", "code": "plan_limit_reached", "message": "You have created 2,000 of 2,000 links this billing period. Upgrade or buy a pack to continue.", "param": "links_per_month", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/pricing", "details": [ { "code": "plan_limit_reached", "message": "Monthly link quota reached", "limit": 2000, "used": 2000, "resets_at": "2026-12-01T00:00:00.000Z", "upgrade_to": "business" } ] } }403 response: feature not in planJSON{ "error": { "type": "plan_limit_error", "code": "feature_not_in_plan", "message": "The public API is available on the Pro plan and above.", "param": "api_requests_per_day", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/pricing", "details": [ { "code": "feature_not_in_plan", "message": "Upgrade to Pro", "upgrade_to": "pro" } ] } }403 response: email verification requiredJSON{ "error": { "type": "permission_error", "code": "email_verification_required", "message": "Verify your email address to create links.", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#email_verification_required" } }403 response: step up requiredJSON{ "error": { "type": "permission_error", "code": "step_up_required", "message": "Confirm your password or 2FA code to continue.", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#step_up_required" } }404 response
Unknown id, or the resource belongs to another workspace (never distinguished). Also returned when a session's
X-Workspace-Idnames a workspace the user is not an active member of.Error codes:
resource_not_foundError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 404 response: not foundJSON{ "error": { "type": "not_found_error", "code": "resource_not_found", "message": "No link with id lnk_01JB4N8ZK3Q9WXYZ0123456789.", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#resource_not_found" } }422 response
Validation failure (
validation_failed,destination_invalid,destination_blocked(details[0].codeispolicy_violation, with the category, for content-policy blocks),slug_invalid,slug_reserved,slug_not_allowed,handle_not_allowed,title_not_allowed,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,policy_acceptance_required, …).Error codes:
validation_failed,destination_invalid,destination_blocked,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,policy_acceptance_requiredError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 422 response: validation failedJSON{ "error": { "type": "validation_error", "code": "validation_failed", "message": "The request body is invalid.", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#validation_failed", "details": [ { "path": "destination_url", "code": "invalid_string", "message": "Must be an absolute http(s) URL" } ] } }422 response: destination blockedJSON{ "error": { "type": "validation_error", "code": "destination_blocked", "message": "This destination was flagged as unsafe and cannot be shortened.", "param": "destination_url", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#destination_blocked" } }429 response
Burst limit, daily plan quota or endpoint limit exceeded.
Error codes:
rate_limitedError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 429 response: rate limitedJSON{ "error": { "type": "rate_limit_error", "code": "rate_limited", "message": "Daily API quota of 50,000 requests exhausted. Resets at 00:00 UTC.", "param": "daily_quota", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/rate-limits" } }
Start a CSV export (async, 10/hour, ≤ 5 M rows)
POST/insights/exports
- Scope insights:read
Runs in jobs against raw events within the plan's retention (scope: events) or the workspace series (scope: workspace, daily rows from the rollups; filters.device or filters.country select that dimension's rollup rows, one at a time, both together → 422 unsupported_in_phase; filters.type stays unsupported there). The file is emailed to the requester and listed in the app; the signed URL is valid 24 h. Poll GET /insights/exports/{id}.
Parameters
| Name | In | Type | Description |
|---|---|---|---|
| X-Workspace-Id | header | string | Workspace to act on. Required for session requests on workspace-scoped routes; optional for API keys (must equal the key's workspace, otherwise 403 workspace_mismatch). For a session, a workspace the user is not an active member of (another tenant, a removed membership, a malformed or unknown id) answers 404 resource_not_found, never 403. |
| Idempotency-Key | header | string | Unique string (UUID v4 recommended, ≤ 255 chars). Repeating a POST with the same key and body within 24 hours replays the original response with Idempotent-Replayed: true. One-time secrets are never cached: a replay returns them as null with Idempotent-Redacted: secret. |
Request body application/json
| Field | Type | Description |
|---|---|---|
| formatrequired | string | Value: csv |
| scope | string | One of: events, workspace |
| fromrequired | string | YYYY-MM-DD or RFC 3339. |
| torequired | string | |
| timezone | string | |
| filters | object | |
| filters. | string | |
| filters. | string | |
| filters. | string | |
| filters. | string | |
| filters. | string | |
| filters. | string | |
| filters. | string | One of: mobile, desktop, tablet |
| filters. | string | One of: click, scan, view, conversion |
| filters. | boolean | |
| columns | array of string | Subset of the scope's columns, in output order. Column lists per scope are fixed by the contract; hashes are never exportable. |
{
"format": "csv",
"scope": "events",
"from": "2026-11-01",
"to": "2026-11-30",
"timezone": "Asia/Kolkata",
"filters": {
"campaign_id": "cmp_01JB4N0DIWALI2026XXXXXXXXX",
"type": "click"
}
}Request example
curl -X POST 'https://api.urlcrop.com/v1/insights/exports' \
-H 'Authorization: Bearer uc_live_…' \
-H 'Content-Type: application/json' \
-d '{
"format": "csv",
"scope": "events",
"from": "2026-11-01",
"to": "2026-11-30",
"timezone": "Asia/Kolkata",
"filters": {
"campaign_id": "cmp_01JB4N0DIWALI2026XXXXXXXXX",
"type": "click"
}
}'Responses
202 response
Queued (
status: queued)InsightsExport schema and example
Field Type Description idrequired string objectrequired string Value: exportstatusrequired string expiredonceexpires_athas passed (the file is deleted within the hour); nodownload_urlafter that.One of:queued,running,done,failed,expiredformat string Value: csvscoperequired string One of: events,workspacefrom string to string rows integer | null bytes integer | null download_url string | null Signed file URL, valid 24 h; only when statusisdone.Format: uriexpires_at string | null Format: date-time error_code string | null truncated boolean True when the export stopped at the 5,000,000-row cap; the file holds the first rows of the range. created_atrequired string ISO 8601 UTC with milliseconds.Format: date-time completed_at string | null Format: date-time 202 response: 202 responseJSON{ "id": "exp_01JB4PF6G7H8J9K0L1M2N3P4Q5", "object": "export", "status": "queued", "format": "csv", "scope": "events", "from": "string", "to": "string", "rows": 0, "bytes": 0, "download_url": "https://example.com", "expires_at": "2026-12-05T10:15:30.000Z", "error_code": "string", "truncated": false, "created_at": "2026-12-05T10:15:30.000Z", "completed_at": "2026-12-05T10:15:30.000Z" }Example generated from the schema. 400 response
Malformed request (
invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand). Any credentialed operation can return it: a credential in the query string (api_key,access_token) isinvalid_query, and a session request withoutX-Workspace-Idon a workspace-scoped route ismissing_header.Error codes:
invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expandError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 400 response: missing headerJSON{ "error": { "type": "invalid_request_error", "code": "missing_header", "message": "The X-Workspace-Id header is required for session requests.", "param": "X-Workspace-Id", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#missing_header" } }401 response
Missing or invalid credentials. Always
code: unauthenticated;details[0].codegives the reason (missing_credentials,invalid_api_key,api_key_revoked,api_key_expired,session_expired,publishable_key_not_allowed).Error codes:
unauthenticatedError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 401 response: unauthenticatedJSON{ "error": { "type": "authentication_error", "code": "unauthenticated", "message": "The API key is not valid.", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#unauthenticated", "details": [ { "path": "Authorization", "code": "invalid_api_key", "message": "No key matches this secret" } ] } }403 response
Permitted credential but not allowed:
insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,two_factor_required(also Owner/Admin writes on Business+ after the 14-day 2FA grace,details[0].grace_ends_at),step_up_required,email_verification_required,signups_paused(sign-up while the platform setting is on),write_blocked_past_due,workspace_suspended,content_policy_hold,origin_not_allowed, or a plan limit (type: plan_limit_error—feature_not_in_plan,plan_limit_reachedwithparamnaming the plan limit key). Any credentialed operation can return it: an API key on a session-only route isinsufficient_scope, a session write without an allowedOriginisorigin_not_allowed, and an API key whose plan has no API access isfeature_not_in_plan.Error codes:
two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,feature_not_in_plan,plan_limit_reachedError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 403 response: plan limit reachedJSON{ "error": { "type": "plan_limit_error", "code": "plan_limit_reached", "message": "You have created 2,000 of 2,000 links this billing period. Upgrade or buy a pack to continue.", "param": "links_per_month", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/pricing", "details": [ { "code": "plan_limit_reached", "message": "Monthly link quota reached", "limit": 2000, "used": 2000, "resets_at": "2026-12-01T00:00:00.000Z", "upgrade_to": "business" } ] } }403 response: feature not in planJSON{ "error": { "type": "plan_limit_error", "code": "feature_not_in_plan", "message": "The public API is available on the Pro plan and above.", "param": "api_requests_per_day", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/pricing", "details": [ { "code": "feature_not_in_plan", "message": "Upgrade to Pro", "upgrade_to": "pro" } ] } }403 response: email verification requiredJSON{ "error": { "type": "permission_error", "code": "email_verification_required", "message": "Verify your email address to create links.", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#email_verification_required" } }403 response: step up requiredJSON{ "error": { "type": "permission_error", "code": "step_up_required", "message": "Confirm your password or 2FA code to continue.", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#step_up_required" } }404 response
Unknown id, or the resource belongs to another workspace (never distinguished). Also returned when a session's
X-Workspace-Idnames a workspace the user is not an active member of.Error codes:
resource_not_foundError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 404 response: not foundJSON{ "error": { "type": "not_found_error", "code": "resource_not_found", "message": "No link with id lnk_01JB4N8ZK3Q9WXYZ0123456789.", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#resource_not_found" } }409 response
State conflict (
slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use).Error codes:
slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_useError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 409 response: slug takenJSON{ "error": { "type": "conflict_error", "code": "slug_taken", "message": "The slug \"diwali\" is already in use on crop.sh.", "param": "slug", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#slug_taken" } }422 response
Validation failure (
validation_failed,destination_invalid,destination_blocked(details[0].codeispolicy_violation, with the category, for content-policy blocks),slug_invalid,slug_reserved,slug_not_allowed,handle_not_allowed,title_not_allowed,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,policy_acceptance_required, …).Error codes:
validation_failed,destination_invalid,destination_blocked,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,policy_acceptance_requiredError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 422 response: validation failedJSON{ "error": { "type": "validation_error", "code": "validation_failed", "message": "The request body is invalid.", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#validation_failed", "details": [ { "path": "destination_url", "code": "invalid_string", "message": "Must be an absolute http(s) URL" } ] } }422 response: destination blockedJSON{ "error": { "type": "validation_error", "code": "destination_blocked", "message": "This destination was flagged as unsafe and cannot be shortened.", "param": "destination_url", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#destination_blocked" } }429 response
Burst limit, daily plan quota or endpoint limit exceeded.
Error codes:
rate_limitedError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 429 response: rate limitedJSON{ "error": { "type": "rate_limit_error", "code": "rate_limited", "message": "Daily API quota of 50,000 requests exhausted. Resets at 00:00 UTC.", "param": "daily_quota", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/rate-limits" } }
Export status and download URL
GET/insights/exports/{id}
- Scope insights:read
Parameters
| Name | In | Type | Description |
|---|---|---|---|
| idrequired | path | string | Prefixed ULID (<prefix>_<26 Crockford base32 chars>). |
| X-Workspace-Id | header | string | Workspace to act on. Required for session requests on workspace-scoped routes; optional for API keys (must equal the key's workspace, otherwise 403 workspace_mismatch). For a session, a workspace the user is not an active member of (another tenant, a removed membership, a malformed or unknown id) answers 404 resource_not_found, never 403. |
Request example
curl 'https://api.urlcrop.com/v1/insights/exports/lnk_01JB4N8ZK3Q9WXYZ0123456789' \
-H 'Authorization: Bearer uc_live_…'Responses
200 response
Export
InsightsExport schema and example
Field Type Description idrequired string objectrequired string Value: exportstatusrequired string expiredonceexpires_athas passed (the file is deleted within the hour); nodownload_urlafter that.One of:queued,running,done,failed,expiredformat string Value: csvscoperequired string One of: events,workspacefrom string to string rows integer | null bytes integer | null download_url string | null Signed file URL, valid 24 h; only when statusisdone.Format: uriexpires_at string | null Format: date-time error_code string | null truncated boolean True when the export stopped at the 5,000,000-row cap; the file holds the first rows of the range. created_atrequired string ISO 8601 UTC with milliseconds.Format: date-time completed_at string | null Format: date-time 200 response: 200 responseJSON{ "id": "exp_01JB4PF6G7H8J9K0L1M2N3P4Q5", "object": "export", "status": "queued", "format": "csv", "scope": "events", "from": "string", "to": "string", "rows": 0, "bytes": 0, "download_url": "https://example.com", "expires_at": "2026-12-05T10:15:30.000Z", "error_code": "string", "truncated": false, "created_at": "2026-12-05T10:15:30.000Z", "completed_at": "2026-12-05T10:15:30.000Z" }Example generated from the schema. 400 response
Malformed request (
invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand). Any credentialed operation can return it: a credential in the query string (api_key,access_token) isinvalid_query, and a session request withoutX-Workspace-Idon a workspace-scoped route ismissing_header.Error codes:
invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expandError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 400 response: missing headerJSON{ "error": { "type": "invalid_request_error", "code": "missing_header", "message": "The X-Workspace-Id header is required for session requests.", "param": "X-Workspace-Id", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#missing_header" } }401 response
Missing or invalid credentials. Always
code: unauthenticated;details[0].codegives the reason (missing_credentials,invalid_api_key,api_key_revoked,api_key_expired,session_expired,publishable_key_not_allowed).Error codes:
unauthenticatedError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 401 response: unauthenticatedJSON{ "error": { "type": "authentication_error", "code": "unauthenticated", "message": "The API key is not valid.", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#unauthenticated", "details": [ { "path": "Authorization", "code": "invalid_api_key", "message": "No key matches this secret" } ] } }403 response
Permitted credential but not allowed:
insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,two_factor_required(also Owner/Admin writes on Business+ after the 14-day 2FA grace,details[0].grace_ends_at),step_up_required,email_verification_required,signups_paused(sign-up while the platform setting is on),write_blocked_past_due,workspace_suspended,content_policy_hold,origin_not_allowed, or a plan limit (type: plan_limit_error—feature_not_in_plan,plan_limit_reachedwithparamnaming the plan limit key). Any credentialed operation can return it: an API key on a session-only route isinsufficient_scope, a session write without an allowedOriginisorigin_not_allowed, and an API key whose plan has no API access isfeature_not_in_plan.Error codes:
two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,feature_not_in_plan,plan_limit_reachedError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 403 response: plan limit reachedJSON{ "error": { "type": "plan_limit_error", "code": "plan_limit_reached", "message": "You have created 2,000 of 2,000 links this billing period. Upgrade or buy a pack to continue.", "param": "links_per_month", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/pricing", "details": [ { "code": "plan_limit_reached", "message": "Monthly link quota reached", "limit": 2000, "used": 2000, "resets_at": "2026-12-01T00:00:00.000Z", "upgrade_to": "business" } ] } }403 response: feature not in planJSON{ "error": { "type": "plan_limit_error", "code": "feature_not_in_plan", "message": "The public API is available on the Pro plan and above.", "param": "api_requests_per_day", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/pricing", "details": [ { "code": "feature_not_in_plan", "message": "Upgrade to Pro", "upgrade_to": "pro" } ] } }403 response: email verification requiredJSON{ "error": { "type": "permission_error", "code": "email_verification_required", "message": "Verify your email address to create links.", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#email_verification_required" } }403 response: step up requiredJSON{ "error": { "type": "permission_error", "code": "step_up_required", "message": "Confirm your password or 2FA code to continue.", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#step_up_required" } }404 response
Unknown id, or the resource belongs to another workspace (never distinguished). Also returned when a session's
X-Workspace-Idnames a workspace the user is not an active member of.Error codes:
resource_not_foundError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 404 response: not foundJSON{ "error": { "type": "not_found_error", "code": "resource_not_found", "message": "No link with id lnk_01JB4N8ZK3Q9WXYZ0123456789.", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#resource_not_found" } }422 response
Validation failure (
validation_failed,destination_invalid,destination_blocked(details[0].codeispolicy_violation, with the category, for content-policy blocks),slug_invalid,slug_reserved,slug_not_allowed,handle_not_allowed,title_not_allowed,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,policy_acceptance_required, …).Error codes:
validation_failed,destination_invalid,destination_blocked,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,policy_acceptance_requiredError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 422 response: validation failedJSON{ "error": { "type": "validation_error", "code": "validation_failed", "message": "The request body is invalid.", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#validation_failed", "details": [ { "path": "destination_url", "code": "invalid_string", "message": "Must be an absolute http(s) URL" } ] } }422 response: destination blockedJSON{ "error": { "type": "validation_error", "code": "destination_blocked", "message": "This destination was flagged as unsafe and cannot be shortened.", "param": "destination_url", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/errors#destination_blocked" } }429 response
Burst limit, daily plan quota or endpoint limit exceeded.
Error codes:
rate_limitedError schema and example
Field Type Description errorrequired object error. typerequired string One of: invalid_request_error,authentication_error,permission_error,plan_limit_error,not_found_error,conflict_error,validation_error,rate_limit_error,api_errorerror. coderequired string Complete error-code catalogue. @urlcrop/shared/errorsis tested against this list.paramon plan_limit_error responses is always a plan limit key.One of:invalid_json,invalid_query,missing_header,invalid_cursor,invalid_sort,invalid_expand,unauthenticated,two_factor_required,step_up_required,email_verification_required,signups_paused,insufficient_scope,insufficient_role,workspace_mismatch,wrong_environment,workspace_suspended,write_blocked_past_due,content_policy_hold,origin_not_allowed,turnstile_failed,second_approver_required,view_as_read_only,support_access_approval_required,feature_not_in_plan,plan_limit_reached,resource_not_found,route_not_found,slug_taken,domain_already_exists,member_already_exists,invitation_pending,idempotency_in_progress,state_conflict,resource_in_use,payload_too_large,unsupported_media_type,validation_failed,destination_invalid,destination_blocked,destination_unreachable,slug_invalid,slug_reserved,domain_not_active,domain_proxied,idempotency_key_reused,unsupported_qr_type,qr_unreadable,invalid_routing_rule,invalid_currency,csv_invalid,attribution_key_missing,policy_acceptance_required,rate_limited,internal_error,upstream_unavailable,service_unavailable,timeouterror. messagerequired string Human-readable, safe to show to end users. error. param string Field, header or scope the error refers to, when applicable. error. request_idrequired string error. doc_urlrequired string Format: uri error. details array of object error. details[]. path string error. details[]. coderequired string Zod issue code, unsupported_in_phase, a destination safety reason, or a 401 reason.error. details[]. messagerequired string error. details[]. limit integer | null Plan limit in force (plan_limit_error only; null = unlimited). error. details[]. used integer Current usage (plan_limit_error only). error. details[]. resets_at string When a periodic limit resets (plan_limit_error only).Format: date-time error. details[]. upgrade_to string Plan slug that lifts a plan limit (plan_limit_error only). 429 response: rate limitedJSON{ "error": { "type": "rate_limit_error", "code": "rate_limited", "message": "Daily API quota of 50,000 requests exhausted. Resets at 00:00 UTC.", "param": "daily_quota", "request_id": "req_01JB4N8ZK3Q9WXYZ0123456789", "doc_url": "https://urlcrop.com/docs/api/rate-limits" } }