Skip to main content
Use the upload service to create many field boundaries at once from shapefiles, GeoJSON, or KML/KMZ files. This page covers the upload endpoints, supported formats, status values, and the follow-up calls you use to inspect results. For conceptual background, see Uploading Boundaries.

Base URL

https://api.withleaf.io/services/uploadservice/api

Endpoints

EndpointMethodPath
Upload a field filePOST/upload
Get all uploadsGET/upload
Get an uploadGET/upload/{uploadId}
Get upload entriesGET/upload/{uploadId}/entries

Supported formats

You can upload field boundaries in the following formats:
  • Shapefile — packaged as a .zip containing .shp, .shx, .dbf, and optionally .prj
  • GeoJSON.json or .geojson
  • KML / KMZ.kml or .kmz
Leaf reprojects all uploaded geometries to WGS 84 (EPSG:4326).

Upload limits

ConstraintLimit
Maximum file size3 GB
Maximum fields per upload100

Upload and entry statuses

Each upload progresses through the following statuses:
Upload statusDescription
RECEIVEDThe file has been received and is queued for processing.
PROCESSEDAll files in the upload have finished processing, and at least one recognized file created fields successfully.
FAILEDThe upload did not generate any field boundaries successfully.
Individual entries within an upload have their own statuses:
Entry statusDescription
PROCESSINGThe entry is being converted and validated.
CONVERTEDThe geometry has been converted and is pending field creation.
FINISHEDThe field has been created from this entry.
FAILEDThe entry could not be processed.
PARTIALLY_FINISHEDSome geometries in the entry succeeded while others failed.

Upload a field file

POST /upload Uploads a field boundary file for the specified Leaf user. The file is processed asynchronously. Use the Get an upload or Get upload entries endpoints to track progress.

Parameters

ParameterTypeDescription
leafUserIdquery (UUID)Required. The Leaf user who owns the fields.
farmIdquery (integer)Optional farm to associate with the uploaded fields.

Request

curl -X POST \
  -H 'Authorization: Bearer YOUR_TOKEN' \
  -F 'file=@/path/to/boundaries.zip' \
  'https://api.withleaf.io/services/uploadservice/api/upload?leafUserId=UUID'

Response

{
  "id": "f1e2d3c4-b5a6-7890-abcd-ef1234567890",
  "leafUserId": "7494c90e-28b8-4bb2-9ede-95c1cc894349",
  "originalFileUrl": "https://storage.withleaf.io/upload/f1e2d3c4-b5a6-7890-abcd-ef1234567890.zip",
  "fileName": "boundaries.zip",
  "status": "RECEIVED",
  "createdTime": "2024-01-15T19:48:51.017Z"
}
If the .zip does not contain the required shapefile components (.shp, .shx, .dbf), the upload fails with status FAILED.

Get all uploads

GET /upload Returns a paginated list of field boundary uploads.

Parameters

ParameterTypeDescription
leafUserIdstring (UUID)Filter by Leaf user.
statusstringRECEIVED, PROCESSED, or FAILED.
pageintegerPage number (default 0).
sizeintegerPage size (default 20).

Request

curl -X GET \
  -H 'Authorization: Bearer YOUR_TOKEN' \
  'https://api.withleaf.io/services/uploadservice/api/upload?leafUserId=UUID'

Response

[
  {
    "id": "f1e2d3c4-b5a6-7890-abcd-ef1234567890",
    "leafUserId": "7494c90e-28b8-4bb2-9ede-95c1cc894349",
    "originalFileUrl": "https://storage.withleaf.io/upload/f1e2d3c4-b5a6-7890-abcd-ef1234567890.zip",
    "fileName": "boundaries.zip",
    "status": "PROCESSED",
    "createdTime": "2024-01-15T19:48:51.017Z"
  }
]

Get an upload

GET /upload/{uploadId} Returns a single field boundary upload by its ID.

Parameters

ParameterTypeDescription
uploadIdpath (UUID)The upload ID.

Request

curl -X GET \
  -H 'Authorization: Bearer YOUR_TOKEN' \
  'https://api.withleaf.io/services/uploadservice/api/upload/{uploadId}'

Response

{
  "id": "f1e2d3c4-b5a6-7890-abcd-ef1234567890",
  "leafUserId": "7494c90e-28b8-4bb2-9ede-95c1cc894349",
  "originalFileUrl": "https://storage.withleaf.io/upload/f1e2d3c4-b5a6-7890-abcd-ef1234567890.zip",
  "fileName": "boundaries.zip",
  "status": "PROCESSED",
  "createdTime": "2024-01-15T19:48:51.017Z"
}

Get upload entries

GET /upload/{uploadId}/entries Returns the individual entries for each recognized file extracted from an upload. Each entry tracks its own processing status and lists the Leaf field IDs created from that recognized file.

Parameters

ParameterTypeDescription
uploadIdpath (UUID)The upload ID.
pageintegerPage number (default 0).
sizeintegerPage size (default 20).

Request

curl -X GET \
  -H 'Authorization: Bearer YOUR_TOKEN' \
  'https://api.withleaf.io/services/uploadservice/api/upload/{uploadId}/entries'

Response

[
  {
    "id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
    "uploadId": "f1e2d3c4-b5a6-7890-abcd-ef1234567890",
    "leafUserId": "7494c90e-28b8-4bb2-9ede-95c1cc894349",
    "fieldId": [
      "0071484f-4a75-4190-9fd0-f5995d241c2c",
      "9c2d4d24-9f31-4c0b-9b4b-7a5df4d0d5b6"
    ],
    "converterFormat": "GEOJSON",
    "originalFileUrl": "https://storage.withleaf.io/upload/entries/a1b2c3d4.geojson",
    "status": "FINISHED",
    "createFieldErrorDetails": [],
    "createdTime": "2024-01-15T19:48:51.017Z",
    "processedTime": "2024-01-15T19:49:20.104Z"
  }
]
Poll the entries endpoint to track each recognized file inside the upload. Use the fieldId array to fetch the created fields from the Fields API, and inspect createFieldErrorDetails when a file finishes with FAILED or PARTIALLY_FINISHED.
Last modified on March 19, 2026