Overview
The Plants API provides access to the Garden.gg plant database and lets you manage plants within your plots. Browse thousands of plants by name, type, family, or growing zone, then add them to your garden plots to track their growth.
Endpoints
| Method | Path | Description | Auth Required |
|---|---|---|---|
GET | /plants | Browse plant database | Yes |
GET | /plants/:id | Get plant details | Yes |
POST | /plots/:id/plants | Add a plant to a plot | Yes |
PUT | /plots/:plotId/plants/:id | Update a plant in a plot | Yes |
DELETE | /plots/:plotId/plants/:id | Remove a plant from a plot | Yes |
Browse Plant Database
Search and filter the plant database.
GET /plants
Query Parameters
| Parameter | Type | Default | Description |
|---|---|---|---|
page | integer | 1 | Page number |
per_page | integer | 20 | Items per page (max 100) |
search | string | — | Search by common or botanical name |
type | string | — | Filter by type: vegetable, fruit, herb, flower, tree, shrub |
family | string | — | Filter by botanical family (e.g., Solanaceae) |
zone | string | — | Filter by compatible hardiness zone |
Response 200 OK
{
"data": [
{
"id": "plant_t0m4t0",
"common_name": "Tomato",
"botanical_name": "Solanum lycopersicum",
"type": "vegetable",
"family": "Solanaceae",
"zones": ["3", "4", "5", "6", "7", "8", "9", "10", "11"],
"days_to_germination": "5-10",
"days_to_harvest": "60-85",
"sun_requirement": "full_sun",
"water_requirement": "regular",
"spacing_cm": 60,
"image_url": "https://cdn.garden.gg/plants/tomato.jpg"
},
{
"id": "plant_b4s1l",
"common_name": "Basil",
"botanical_name": "Ocimum basilicum",
"type": "herb",
"family": "Lamiaceae",
"zones": ["4", "5", "6", "7", "8", "9", "10"],
"days_to_germination": "5-7",
"days_to_harvest": "50-75",
"sun_requirement": "full_sun",
"water_requirement": "regular",
"spacing_cm": 30,
"image_url": "https://cdn.garden.gg/plants/basil.jpg"
}
],
"total": 1247,
"page": 1,
"per_page": 20
}
Examples
cURL
# Search for tomato varieties
curl -X GET "https://garden.gg/api/v1/plants?search=tomato&type=vegetable" \
-H "Authorization: Bearer gg_live_your_api_key_here"
Python
import requests
headers = {"Authorization": "Bearer gg_live_your_api_key_here"}
# Search for herbs compatible with zone 6
response = requests.get(
"https://garden.gg/api/v1/plants",
headers=headers,
params={"type": "herb", "zone": "6"},
)
plants = response.json()
for plant in plants["data"]:
print(f"{plant['common_name']} ({plant['botanical_name']})")
Node.js
const params = new URLSearchParams({ search: "pepper", type: "vegetable" });
const response = await fetch(
`https://garden.gg/api/v1/plants?${params.toString()}`,
{ headers: { Authorization: "Bearer gg_live_your_api_key_here" } }
);
const { data: plants } = await response.json();
plants.forEach((p) => console.log(`${p.common_name} — ${p.days_to_harvest} days`));
Get Plant Details
Retrieve detailed information about a specific plant from the database.
GET /plants/:id
Response 200 OK
{
"id": "plant_t0m4t0",
"common_name": "Tomato",
"botanical_name": "Solanum lycopersicum",
"type": "vegetable",
"family": "Solanaceae",
"zones": ["3", "4", "5", "6", "7", "8", "9", "10", "11"],
"days_to_germination": "5-10",
"days_to_harvest": "60-85",
"sun_requirement": "full_sun",
"water_requirement": "regular",
"spacing_cm": 60,
"planting_depth_cm": 1,
"companion_plants": ["basil", "carrot", "marigold"],
"avoid_planting_near": ["fennel", "brassicas"],
"growing_tips": "Stake or cage indeterminate varieties. Prune suckers for larger fruit.",
"image_url": "https://cdn.garden.gg/plants/tomato.jpg"
}
Add Plant to Plot
Add a plant from the database to one of your plots.
POST /plots/:plotId/plants
Path Parameters
| Parameter | Type | Description |
|---|---|---|
plotId | string | The plot’s ID |
Request Body
| Field | Type | Required | Description |
|---|---|---|---|
plant_id | string | Yes | ID from the plant database |
variety | string | No | Specific variety name (e.g., “Cherokee Purple”) |
planted_date | string | No | Date planted in RFC 3339 format |
quantity | integer | No | Number of plants (default: 1) |
notes | string | No | Additional notes about this planting |
Request
{
"plant_id": "plant_t0m4t0",
"variety": "Cherokee Purple",
"planted_date": "2026-04-15T00:00:00Z",
"quantity": 3,
"notes": "Started from seed indoors on March 1"
}
Response 201 Created
{
"id": "ppl_c3d4e5f6",
"plot_id": "plt_m3n4o5p6",
"plant_id": "plant_t0m4t0",
"plant_name": "Tomato",
"variety": "Cherokee Purple",
"planted_date": "2026-04-15T00:00:00Z",
"quantity": 3,
"status": "planted",
"notes": "Started from seed indoors on March 1",
"created_at": "2026-03-15T10:00:00Z",
"updated_at": "2026-03-15T10:00:00Z"
}
Examples
cURL
curl -X POST "https://garden.gg/api/v1/plots/plt_m3n4o5p6/plants" \
-H "Authorization: Bearer gg_live_your_api_key_here" \
-H "Content-Type: application/json" \
-d '{
"plant_id": "plant_t0m4t0",
"variety": "Cherokee Purple",
"planted_date": "2026-04-15T00:00:00Z",
"quantity": 3
}'
Python
import requests
response = requests.post(
"https://garden.gg/api/v1/plots/plt_m3n4o5p6/plants",
headers={
"Authorization": "Bearer gg_live_your_api_key_here",
"Content-Type": "application/json",
},
json={
"plant_id": "plant_t0m4t0",
"variety": "Cherokee Purple",
"planted_date": "2026-04-15T00:00:00Z",
"quantity": 3,
},
)
plant = response.json()
print(f"Added {plant['variety']} to plot: {plant['id']}")
Node.js
const response = await fetch(
"https://garden.gg/api/v1/plots/plt_m3n4o5p6/plants",
{
method: "POST",
headers: {
Authorization: "Bearer gg_live_your_api_key_here",
"Content-Type": "application/json",
},
body: JSON.stringify({
plant_id: "plant_t0m4t0",
variety: "Cherokee Purple",
planted_date: "2026-04-15T00:00:00Z",
quantity: 3,
}),
}
);
const plant = await response.json();
console.log(`Added ${plant.variety} to plot: ${plant.id}`);
Update Plant in Plot
Update details of a plant that has been added to a plot.
PUT /plots/:plotId/plants/:id
Request Body
| Field | Type | Required | Description |
|---|---|---|---|
variety | string | No | Variety name |
planted_date | string | No | Date planted (RFC 3339) |
quantity | integer | No | Number of plants |
status | string | No | One of: planted, growing, flowering, fruiting, harvesting, dormant, removed |
notes | string | No | Additional notes |
Response 200 OK
Returns the full updated plant object.
Remove Plant from Plot
Remove a plant record from a plot.
DELETE /plots/:plotId/plants/:id
Response 204 No Content
No response body.
Error Responses
| Scenario | HTTP Status | Error Code |
|---|---|---|
| Plant not found in database | 404 | NOT_FOUND |
| Plot not found | 404 | NOT_FOUND |
| Plant not in this plot | 404 | NOT_FOUND |
| Invalid plant_id | 400 | VALIDATION_ERROR |
| Not your plot | 403 | FORBIDDEN |
| Not authenticated | 401 | UNAUTHORIZED |