feat: garden plants crud (task 72)
- perenual species lookup with 24h db cache (api key optional) - /api/garden/species-search route handler - createPlant / updatePlant / deletePlant server actions - addPlantImage / removePlantImage / setPrimaryImage actions (max 10) - listPlants query grouped by container with last-watered subquery - getPlant query with care log summary and active schedules - plant-form client component with species autofill and image upload - plant-list server component grouped by container with unassigned bucket - plant-detail client component with info/gallery/care tabs - species-search debounced combobox component - /garden/plants/new, /[id], /[id]/edit pages - garden.plant entity registered with search and share support - /garden page updated to containers/plants tabs (default: containers)
This commit is contained in:
@@ -11,6 +11,45 @@ export type ContainerShareData = {
|
||||
plants: { id: string; name: string; scientificName: string | null }[];
|
||||
};
|
||||
|
||||
export type PlantShareData = {
|
||||
id: string;
|
||||
name: string;
|
||||
scientificName: string | null;
|
||||
primaryImageUrl: string | null;
|
||||
images: string[];
|
||||
healthStatus: string;
|
||||
growthStage: string | null;
|
||||
category: string;
|
||||
wateringNotes: string | null;
|
||||
fertilizingNotes: string | null;
|
||||
notes: string | null;
|
||||
sunlight: string | null;
|
||||
};
|
||||
|
||||
export async function loadPlantForShare(id: string): Promise<PlantShareData | null> {
|
||||
const [plant] = await db
|
||||
.select({
|
||||
id: gardenPlants.id,
|
||||
name: gardenPlants.name,
|
||||
scientificName: gardenPlants.scientificName,
|
||||
primaryImageUrl: gardenPlants.primaryImageUrl,
|
||||
images: gardenPlants.images,
|
||||
healthStatus: gardenPlants.healthStatus,
|
||||
growthStage: gardenPlants.growthStage,
|
||||
category: gardenPlants.category,
|
||||
wateringNotes: gardenPlants.wateringNotes,
|
||||
fertilizingNotes: gardenPlants.fertilizingNotes,
|
||||
notes: gardenPlants.notes,
|
||||
sunlight: gardenPlants.sunlight,
|
||||
})
|
||||
.from(gardenPlants)
|
||||
.where(eq(gardenPlants.id, id))
|
||||
.limit(1);
|
||||
|
||||
if (!plant) return null;
|
||||
return plant;
|
||||
}
|
||||
|
||||
export async function loadContainerForShare(id: string): Promise<ContainerShareData | null> {
|
||||
const [container] = await db
|
||||
.select()
|
||||
|
||||
Reference in New Issue
Block a user