Harvest Window
Agriculture Math & Calculations Credits / request: 1Accumulates crop GDD against the harvest threshold and estimates the harvest date. Not a prescription.
POST
https://api.apikodu.com/api/v1/agriculture/harvestwindow
Documentation
Overview
Accumulates crop GDD to the harvest (or stageCode) threshold. Not a prescription.
Authentication
Every request requires the x-api-key header. Credits used and remaining quota are returned in response headers (x-api-credits-used, x-api-remaining-credits, x-rate-limit-*).
Request
POST
https://api.apikodu.com/api/v1/agriculture/harvestwindow
JSON body. GET query also exists. dailyTemps or lat/lon.
Parameters
| Name | Type | Required | Default | Options | Description |
|---|---|---|---|---|---|
crop |
string | * Required | wheat |
wheat barley maize sunflower cotton potato tomato rapeseed oats rye sugarbeet grape apple chickpea lentil |
Crop code. |
fromDate |
string | * Required | — | — | YYYY-MM-DD |
toDate |
string | Optional | — | — | YYYY-MM-DD. Empty uses fromDate+365. |
latitude |
number | Optional | — | — | Required without dailyTemps. |
longitude |
number | Optional | — | — | Longitude. |
stageCode |
string | Optional | harvest |
emergence flowering harvest |
GDD threshold code. Default harvest. |
includeDaily |
boolean | Optional | true |
true false |
Daily GDD. Default true. |
dailyTemps |
json | Optional | — | — | [{date,tmin,tmax}]. Overrides lat/lon. |
Response
| Name | Type | Description |
|---|---|---|
crop |
string | Normalized crop. |
stageCode |
string | Threshold code used. |
threshold |
number | Required cumulative GDD. |
gddCumulative |
number | Accumulated GDD. |
reached |
boolean | true when the threshold is reached. |
reachedDate |
string | Day the threshold was crossed. Null if not. |
remainingGdd |
number | Remaining GDD. 0 when reached. |
estimatedDate |
string | Estimate from mean daily GDD. Null without data. |
fromDate |
string | YYYY-MM-DD. |
toDate |
string | YYYY-MM-DD. |
daysTotal |
integer | Calendar days in the window. |
daysWithData |
integer | Days used for GDD. |
missingCount |
integer | Missing day count. |
missingDates |
array | First 10 missing dates. |
gridLatitude |
number | 0.1° cell. |
gridLongitude |
number | 0.1° cell. |
stages |
array | Crop GDD thresholds. |
stages[].code |
string | emergence, flowering, harvest ... |
stages[].threshold |
number | Threshold GDD. |
stages[].reached |
boolean | Whether reached. |
daily |
array | When includeDaily=true. |
daily[].date |
string | YYYY-MM-DD. |
daily[].tmin |
number | Min °C. |
daily[].tmax |
number | Max °C. |
daily[].gdd |
number | Daily GDD. |
daily[].gddCumulative |
number | Cumulative. |
method |
string | gdd-harvest. |
source |
string | database or user. |
disclaimer |
string | Decision-support disclaimer. |
Errors
| HTTP | code | Description |
|---|---|---|
400 |
-250 |
crop missing or unknown. |
400 |
-249 |
stageCode not on this crop or body empty. |
400 |
-254 |
Invalid date range. |
400 |
-255 |
dailyTemps or lat/lon required. |
429 |
-316 |
Daily new location (cell) limit (50) reached. Previously requested locations keep working; new locations next day (UTC). Retry-After header gives seconds until end of day. |
503 |
-256 |
Cell is filling. |
400 |
-251 |
No weather. |
401 |
-100 |
x-api-key is missing, empty, malformed, inactive, banned, expired, IP-restricted, or not allowed for this API. |
429 |
-221 |
Per-minute request limit exceeded. Response headers: x-rate-limit-limit, x-rate-limit-remaining, x-rate-limit-reset. |
429 |
— | Package credit quota cannot cover this request. Body may be { error, limit, currentUsage, requestCost } (no code field). |
500 |
-1 |
Unexpected server error. message is a generic error text without technical details. |
Notes
- Success body is { data: { ... } }. Error body is { code, message }. code is an ApiResponseCode enum value (negative integer).
Sample response
{
"data": {
"crop": "wheat",
"stageCode": "harvest",
"threshold": 1600.0,
"gddCumulative": 1624.5,
"reached": true,
"reachedDate": "2026-07-18",
"remainingGdd": 0.0,
"estimatedDate": "2026-07-18",
"fromDate": "2026-03-01",
"toDate": "2026-08-31",
"daysTotal": 184,
"daysWithData": 180,
"missingCount": 4,
"missingDates": [
"2026-03-12"
],
"gridLatitude": 39.90,
"gridLongitude": 32.90,
"stages": [
{
"code": "emergence",
"threshold": 120.0,
"reached": true
},
{
"code": "flowering",
"threshold": 800.0,
"reached": true
},
{
"code": "harvest",
"threshold": 1600.0,
"reached": true
}
],
"daily": [
{
"date": "2026-03-01",
"tmin": 2.0,
"tmax": 12.0,
"gdd": 3.0,
"gddCumulative": 3.0
}
],
"method": "gdd-harvest",
"source": "database",
"disclaimer": "Decision support only. Not agronomic advice. Weather data: Copernicus ERA5 / ERA5-Land, Open-Meteo, OpenWeather, MET Norway. Contains modified Copernicus Climate Change Service information."
}
}
Code samples
const response = await fetch('https://api.apikodu.com/api/v1/agriculture/harvestwindow', {
method: 'POST',
headers: {
'Content-Type': 'application/json',
'x-api-key': 'YOUR_API_KEY'
},
body: JSON.stringify({
name: 'example',
value: 123
})
});
const data = await response.json();
console.log(data);
import requests
headers = {
'Content-Type': 'application/json',
'x-api-key': 'YOUR_API_KEY'
}
payload = {
'name': 'example',
'value': 123
}
response = requests.post('https://api.apikodu.com/api/v1/agriculture/harvestwindow', headers=headers, json=payload)
data = response.json()
print(data)
using var client = new HttpClient();
client.DefaultRequestHeaders.Add("x-api-key", "YOUR_API_KEY");
var payload = new { name = "example", value = 123 };
var json = JsonSerializer.Serialize(payload);
var content = new StringContent(json, Encoding.UTF8, "application/json");
var response = await client.PostAsync("https://api.apikodu.com/api/v1/agriculture/harvestwindow", content);
response.EnsureSuccessStatusCode();
var data = await response.Content.ReadAsStringAsync();
Console.WriteLine(data);
$data = [
'name' => 'example',
'value' => 123
];
$response = file_get_contents('https://api.apikodu.com/api/v1/agriculture/harvestwindow', false, stream_context_create([
'http' => [
'header' => "x-api-key: YOUR_API_KEY"
],
'method' => 'POST',"
'content' => json_encode($data)
]));
print_r(json_decode($response, true));
curl -X POST 'https://api.apikodu.com/api/v1/agriculture/harvestwindow' \
-H 'Content-Type: application/json' \
-H 'x-api-key: YOUR_API_KEY' \
-d '{
"name": "example",
"value": 123
}'
Start building in minutes
Create a free account, get your API key and send your first request in minutes.