Spray Window
Agriculture Math & Calculations Credits / request: 1Finds hourly windows suitable for spraying from wind, rain, humidity and temperature. Not a pesticide prescription.
GET
https://api.apikodu.com/api/v1/agriculture/spraywindow
Documentation
Overview
Finds hourly windows suitable for spraying from wind, 6h rain, humidity and temperature. Not a prescription. Weather data © Copernicus ERA5 / ERA5-Land (contains modified Copernicus Climate Change Service information) / Open-Meteo / OpenWeather / MET Norway.
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
GET
https://api.apikodu.com/api/v1/agriculture/spraywindow?latitude=39.92&longitude=32.87&hours=48
GET query or POST JSON (with hourly).
Parameters
| Name | Type | Required | Default | Options | Description |
|---|---|---|---|---|---|
latitude |
number | Optional | — | — | Required without hourly. 0.1° cell. |
longitude |
number | Optional | — | — | Longitude. |
hours |
integer | Optional | 48 |
— | Hours ahead. Default 48. Range 1–168. |
includeHours |
boolean | Optional | true |
true false |
Hourly breakdown. |
windMin |
number | Optional | 3 |
— | Wind lower threshold km/h. Default 3. |
windMax |
number | Optional | 15 |
— | Wind upper threshold km/h. Default 15. |
rain6h |
number | Optional | 0.2 |
— | Max rain in previous 6 hours, mm. Default 0.2. |
humidityMax |
number | Optional | 90 |
— | Humidity upper threshold %. Default 90. |
tempMin |
number | Optional | 10 |
— | Temperature lower threshold °C. Default 10. |
tempMax |
number | Optional | 25 |
— | Temperature upper threshold °C. Default 25. |
hourly |
json | Optional | — | — | [{time,temp,humidity,windKmh,rainMm}]. Overrides lat/lon. |
Response
| Name | Type | Description |
|---|---|---|
suitableHours |
integer | Number of hours that meet the thresholds. |
hoursEvaluated |
integer | Number of hours evaluated. |
fromTime |
string | First evaluated hour (UTC ISO). |
toTime |
string | Last evaluated hour (UTC ISO). |
windMin |
number | Wind lower threshold km/h used. |
windMax |
number | Wind upper threshold km/h used. |
rain6h |
number | 6-hour rain threshold mm used. |
humidityMax |
number | Humidity upper threshold % used. |
tempMin |
number | Temperature lower threshold °C used. |
tempMax |
number | Temperature upper threshold °C used. |
gridLatitude |
number | 0.1° cell latitude. Null when hourly was used. |
gridLongitude |
number | 0.1° cell longitude. Null when hourly was used. |
windows |
array | Contiguous suitable hour ranges. |
windows[].fromTime |
string | Window start UTC ISO. |
windows[].toTime |
string | Window end UTC ISO. |
windows[].hours |
integer | Hours in the window. |
hours |
array | Hourly rows when includeHours=true. Empty array when false. |
hours[].time |
string | Hour UTC ISO. |
hours[].suitable |
boolean | true when all thresholds are met. |
hours[].temp |
number | Temperature °C. |
hours[].humidity |
number | Relative humidity %. |
hours[].windKmh |
number | Wind km/h. |
hours[].rainMm |
number | Rain in that hour, mm. |
hours[].rain6hMm |
number | Total rain in the previous 6 hours, mm. |
hours[].reasons |
array | Threshold violations when not suitable (wind-low, rain-6h ...). |
method |
string | Calculation method. hourly-threshold-window for this API. |
source |
string | user: dailyTemps or et0Mm. db: tarim_hava cell. |
disclaimer |
string | Decision-support disclaimer. Not agronomic advice or a prescription. |
Errors
| HTTP | code | Description |
|---|---|---|
400 |
-255 |
latitude/longitude are required without hourly. |
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 created; Worker is filling hourly data. Retry in a minute. |
400 |
-249 |
hours outside 1–168, invalid thresholds, or hourly > 168. |
400 |
-254 |
hourly.time is not a valid datetime. |
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": {
"suitableHours": 2,
"hoursEvaluated": 2,
"fromTime": "2026-08-28T10:00:00Z",
"toTime": "2026-08-28T11:00:00Z",
"windMin": 3.0,
"windMax": 15.0,
"rain6h": 0.2,
"humidityMax": 90.0,
"tempMin": 10.0,
"tempMax": 25.0,
"windows": [
{
"fromTime": "2026-08-28T10:00:00Z",
"toTime": "2026-08-28T11:00:00Z",
"hours": 2
}
],
"method": "hourly-threshold-window",
"source": "user",
"disclaimer": "Decision support only. Not agronomic advice. Not a pesticide prescription."
}
}
Code samples
const response = await fetch('https://api.apikodu.com/api/v1/agriculture/spraywindow', {
method: 'GET',
headers: {
'x-api-key': 'YOUR_API_KEY'
}
});
const data = await response.json();
console.log(data);
import requests
headers = {
'x-api-key': 'YOUR_API_KEY'
}
response = requests.get('https://api.apikodu.com/api/v1/agriculture/spraywindow', headers=headers)
print(response.json())
using var client = new HttpClient();
client.DefaultRequestHeaders.Add("x-api-key", "YOUR_API_KEY");
var response = await client.GetStringAsync("https://api.apikodu.com/api/v1/agriculture/spraywindow");
Console.WriteLine(response);
$response = file_get_contents('https://api.apikodu.com/api/v1/agriculture/spraywindow', false, stream_context_create([
'http' => [
'header' => "x-api-key: YOUR_API_KEY"
]
]));
print_r(json_decode($response, true));
curl -X GET 'https://api.apikodu.com/api/v1/agriculture/spraywindow' \
-H 'x-api-key: YOUR_API_KEY'
Start building in minutes
Create a free account, get your API key and send your first request in minutes.