// LocalGreenChain Database Schema
// Prisma ORM configuration for PostgreSQL

generator client {
  provider = "prisma-client-js"
}

datasource db {
  provider = "postgresql"
  url      = env("DATABASE_URL")
}

// ============================================
// USER & AUTHENTICATION
// ============================================

model User {
  id            String    @id @default(cuid())
  email         String    @unique
  name          String
  walletAddress String?   @unique
  passwordHash  String?

  // Profile
  avatarUrl     String?
  bio           String?

  // Location
  latitude      Float?
  longitude     Float?
  address       String?
  city          String?
  country       String?

  // User type
  userType      UserType  @default(CONSUMER)

  // Timestamps
  createdAt     DateTime  @default(now())
  updatedAt     DateTime  @updatedAt
  lastLoginAt   DateTime?

  // Relations
  ownedPlants           Plant[]
  verticalFarms         VerticalFarm[]
  consumerPreferences   ConsumerPreference[]
  supplyCommitments     SupplyCommitment[]
  sentTransportEvents   TransportEvent[]      @relation("Sender")
  receivedTransportEvents TransportEvent[]    @relation("Receiver")
  seasonalPlans         SeasonalPlan[]
  auditLogs             AuditLog[]

  @@index([email])
  @@index([userType])
}

enum UserType {
  CONSUMER
  GROWER
  DISTRIBUTOR
  PROCESSOR
  ADMIN
}

// ============================================
// PLANT & LINEAGE TRACKING
// ============================================

model Plant {
  id              String    @id @default(cuid())

  // Plant identification
  commonName      String
  scientificName  String?
  species         String?
  genus           String?
  family          String?

  // Lineage tracking
  parentPlantId   String?
  parentPlant     Plant?    @relation("PlantLineage", fields: [parentPlantId], references: [id])
  childPlants     Plant[]   @relation("PlantLineage")
  propagationType PropagationType @default(ORIGINAL)
  generation      Int       @default(0)

  // Lifecycle
  plantedDate     DateTime
  harvestedDate   DateTime?
  status          PlantStatus @default(SPROUTED)

  // Location
  latitude        Float
  longitude       Float
  address         String?
  city            String?
  country         String?

  // Owner
  ownerId         String
  owner           User      @relation(fields: [ownerId], references: [id])

  // Environmental data (JSON for flexibility)
  environment     Json?
  growthMetrics   Json?

  // Metadata
  notes           String?
  images          String[]
  plantsNetId     String?

  // Blockchain integration
  blockIndex      Int?
  blockHash       String?

  // Timestamps
  registeredAt    DateTime  @default(now())
  updatedAt       DateTime  @updatedAt

  // Relations
  transportEvents TransportEvent[]
  cropBatches     CropBatch[]

  @@index([ownerId])
  @@index([commonName])
  @@index([status])
  @@index([parentPlantId])
  @@index([latitude, longitude])
}

enum PropagationType {
  SEED
  CLONE
  CUTTING
  DIVISION
  GRAFTING
  ORIGINAL
}

enum PlantStatus {
  SPROUTED
  GROWING
  MATURE
  FLOWERING
  FRUITING
  DORMANT
  DECEASED
}

// ============================================
// TRANSPORT & SUPPLY CHAIN
// ============================================

model TransportEvent {
  id              String    @id @default(cuid())

  // Event type
  eventType       TransportEventType

  // Locations
  fromLatitude    Float
  fromLongitude   Float
  fromAddress     String?
  fromCity        String?
  fromCountry     String?
  fromLocationType LocationType
  fromFacilityId  String?
  fromFacilityName String?

  toLatitude      Float
  toLongitude     Float
  toAddress       String?
  toCity          String?
  toCountry       String?
  toLocationType  LocationType
  toFacilityId    String?
  toFacilityName  String?

  // Distance and duration
  distanceKm      Float
  durationMinutes Int

  // Environmental impact
  transportMethod TransportMethod
  carbonFootprintKg Float

  // Parties
  senderId        String
  sender          User      @relation("Sender", fields: [senderId], references: [id])
  receiverId      String
  receiver        User      @relation("Receiver", fields: [receiverId], references: [id])

  // Verification signatures
  senderSignature   String?
  receiverSignature String?
  verifierSignature String?

  // Status
  status          TransportStatus @default(PENDING)

  // Metadata
  notes           String?
  photos          String[]
  documents       String[]

  // Extended event data (JSON for type-specific fields)
  eventData       Json?

  // Blockchain integration
  blockIndex      Int?
  blockHash       String?
  cumulativeCarbonKg Float?
  cumulativeFoodMiles Float?

  // Timestamps
  timestamp       DateTime  @default(now())
  createdAt       DateTime  @default(now())
  updatedAt       DateTime  @updatedAt

  // Relations
  plants          Plant[]
  seedBatch       SeedBatch? @relation(fields: [seedBatchId], references: [id])
  seedBatchId     String?
  harvestBatch    HarvestBatch? @relation(fields: [harvestBatchId], references: [id])
  harvestBatchId  String?

  @@index([eventType])
  @@index([senderId])
  @@index([receiverId])
  @@index([status])
  @@index([timestamp])
}

enum TransportEventType {
  SEED_ACQUISITION
  PLANTING
  GROWING_TRANSPORT
  HARVEST
  PROCESSING
  DISTRIBUTION
  CONSUMER_DELIVERY
  SEED_SAVING
  SEED_SHARING
}

enum LocationType {
  FARM
  GREENHOUSE
  VERTICAL_FARM
  WAREHOUSE
  HUB
  MARKET
  CONSUMER
  SEED_BANK
  OTHER
}

enum TransportMethod {
  WALKING
  BICYCLE
  ELECTRIC_VEHICLE
  HYBRID_VEHICLE
  GASOLINE_VEHICLE
  DIESEL_TRUCK
  ELECTRIC_TRUCK
  REFRIGERATED_TRUCK
  RAIL
  SHIP
  AIR
  DRONE
  LOCAL_DELIVERY
  CUSTOMER_PICKUP
}

enum TransportStatus {
  PENDING
  IN_TRANSIT
  DELIVERED
  VERIFIED
  DISPUTED
}

// Seed Batch for tracking seeds through the system
model SeedBatch {
  id              String    @id @default(cuid())

  // Seed info
  species         String
  variety         String?
  quantity        Float
  quantityUnit    String    @default("seeds")

  // Lineage
  geneticLineageId String?
  parentPlantIds  String[]
  generation      Int       @default(0)

  // Quality
  germinationRate Float?
  purityPercentage Float?
  harvestDate     DateTime?
  expirationDate  DateTime?

  // Certifications
  certifications  String[]
  certificationDocs String[]

  // Storage
  storageTemperature Float?
  storageHumidity    Float?
  containerType      String?

  // Status
  status          SeedBatchStatus @default(AVAILABLE)

  // Timestamps
  createdAt       DateTime  @default(now())
  updatedAt       DateTime  @updatedAt

  // Relations
  transportEvents TransportEvent[]
  cropBatches     CropBatch[]

  @@index([species])
  @@index([status])
}

enum SeedBatchStatus {
  AVAILABLE
  PARTIALLY_USED
  DEPLETED
  EXPIRED
}

// Harvest Batch for tracking harvested produce
model HarvestBatch {
  id              String    @id @default(cuid())

  // Harvest info
  produceType     String
  harvestType     String    @default("full")

  // Quantities
  grossWeight     Float
  netWeight       Float
  weightUnit      String    @default("kg")
  itemCount       Int?

  // Quality
  qualityGrade    String?
  qualityNotes    String?

  // Storage
  packagingType   String?
  shelfLifeHours  Int?
  temperatureMin  Float?
  temperatureMax  Float?

  // Timestamps
  harvestedAt     DateTime  @default(now())
  createdAt       DateTime  @default(now())
  updatedAt       DateTime  @updatedAt

  // Relations
  transportEvents TransportEvent[]
  cropBatch       CropBatch? @relation(fields: [cropBatchId], references: [id])
  cropBatchId     String?

  @@index([produceType])
  @@index([harvestedAt])
}

// ============================================
// VERTICAL FARMING
// ============================================

model VerticalFarm {
  id              String    @id @default(cuid())
  name            String

  // Owner
  ownerId         String
  owner           User      @relation(fields: [ownerId], references: [id])

  // Location
  latitude        Float
  longitude       Float
  address         String
  city            String
  country         String
  timezone        String    @default("UTC")

  // Facility specs (JSON for complex nested structure)
  specs           Json

  // Systems configuration (JSON for flexibility)
  environmentalControl Json?
  irrigationSystem     Json?
  lightingSystem       Json?
  nutrientSystem       Json?

  // Automation
  automationLevel AutomationLevel @default(MANUAL)
  automationSystems Json?

  // Status
  status          FarmStatus @default(OFFLINE)
  operationalSince DateTime?
  lastMaintenanceDate DateTime?

  // Performance metrics
  capacityUtilization Float?
  yieldEfficiency     Float?
  energyEfficiencyScore Float?

  // Timestamps
  createdAt       DateTime  @default(now())
  updatedAt       DateTime  @updatedAt

  // Relations
  zones           GrowingZone[]
  cropBatches     CropBatch[]
  resourceUsage   ResourceUsage[]
  farmAnalytics   FarmAnalytics[]

  @@index([ownerId])
  @@index([status])
  @@index([city, country])
}

enum AutomationLevel {
  MANUAL
  SEMI_AUTOMATED
  FULLY_AUTOMATED
}

enum FarmStatus {
  OFFLINE
  STARTING
  OPERATIONAL
  MAINTENANCE
  EMERGENCY
}

model GrowingZone {
  id              String    @id @default(cuid())
  name            String
  level           Int

  // Dimensions
  areaSqm         Float
  lengthM         Float?
  widthM          Float?

  // Growing system
  growingMethod   GrowingMethod
  plantPositions  Int

  // Current status
  currentCrop     String?
  plantingDate    DateTime?
  expectedHarvestDate DateTime?

  // Environment targets (JSON)
  environmentTargets Json?

  // Current readings (JSON)
  currentEnvironment Json?

  // Status
  status          ZoneStatus @default(EMPTY)

  // Timestamps
  createdAt       DateTime  @default(now())
  updatedAt       DateTime  @updatedAt

  // Relations
  farm            VerticalFarm @relation(fields: [farmId], references: [id], onDelete: Cascade)
  farmId          String
  cropBatches     CropBatch[]

  @@index([farmId])
  @@index([status])
}

enum GrowingMethod {
  NFT
  DWC
  EBB_FLOW
  AEROPONICS
  VERTICAL_TOWERS
  RACK_SYSTEM
}

enum ZoneStatus {
  EMPTY
  PREPARING
  PLANTED
  GROWING
  HARVESTING
  CLEANING
}

model CropBatch {
  id              String    @id @default(cuid())

  // Crop info
  cropType        String
  variety         String?

  // Growing
  plantCount      Int
  plantingDate    DateTime
  transplantDate  DateTime?

  // Progress
  currentStage    String    @default("germinating")
  currentDay      Int       @default(0)
  healthScore     Float?

  // Expected
  expectedHarvestDate DateTime
  expectedYieldKg Float

  // Actual (after harvest)
  actualHarvestDate DateTime?
  actualYieldKg   Float?
  qualityGrade    String?

  // Status
  status          CropBatchStatus @default(GERMINATING)

  // Issues (JSON array)
  issues          Json?

  // Environmental log (JSON array)
  environmentLog  Json?

  // Timestamps
  createdAt       DateTime  @default(now())
  updatedAt       DateTime  @updatedAt

  // Relations
  farm            VerticalFarm @relation(fields: [farmId], references: [id])
  farmId          String
  zone            GrowingZone @relation(fields: [zoneId], references: [id])
  zoneId          String
  recipe          GrowingRecipe? @relation(fields: [recipeId], references: [id])
  recipeId        String?
  seedBatch       SeedBatch? @relation(fields: [seedBatchId], references: [id])
  seedBatchId     String?
  plants          Plant[]
  harvestBatches  HarvestBatch[]

  @@index([farmId])
  @@index([zoneId])
  @@index([status])
  @@index([cropType])
}

enum CropBatchStatus {
  GERMINATING
  GROWING
  READY
  HARVESTING
  COMPLETED
  FAILED
}

model GrowingRecipe {
  id              String    @id @default(cuid())
  name            String
  cropType        String
  variety         String?
  version         String    @default("1.0")

  // Stages (JSON array of GrowthStage)
  stages          Json

  // Expected outcomes
  expectedDays    Int
  expectedYieldGrams Float
  expectedYieldPerSqm Float?

  // Requirements (JSON)
  requirements    Json?

  // Source
  source          RecipeSource @default(INTERNAL)
  author          String?
  rating          Float?
  timesUsed       Int       @default(0)

  // Timestamps
  createdAt       DateTime  @default(now())
  updatedAt       DateTime  @updatedAt

  // Relations
  cropBatches     CropBatch[]

  @@index([cropType])
  @@index([source])
}

enum RecipeSource {
  INTERNAL
  COMMUNITY
  COMMERCIAL
}

model ResourceUsage {
  id              String    @id @default(cuid())

  // Period
  periodStart     DateTime
  periodEnd       DateTime

  // Energy
  electricityKwh  Float
  electricityCostUsd Float?
  renewablePercent Float?
  peakDemandKw    Float?

  // Water
  waterUsageL     Float
  waterCostUsd    Float?
  waterRecycledPercent Float?

  // CO2
  co2UsedKg       Float?
  co2CostUsd      Float?

  // Nutrients
  nutrientsUsedL  Float?
  nutrientCostUsd Float?

  // Efficiency metrics
  kwhPerKgProduce Float?
  litersPerKgProduce Float?
  costPerKgProduce Float?

  // Timestamps
  createdAt       DateTime  @default(now())

  // Relations
  farm            VerticalFarm @relation(fields: [farmId], references: [id])
  farmId          String

  @@index([farmId])
  @@index([periodStart, periodEnd])
}

model FarmAnalytics {
  id              String    @id @default(cuid())

  // Period
  period          String
  generatedAt     DateTime  @default(now())

  // Production
  totalYieldKg    Float
  yieldPerSqmPerYear Float?
  cropCyclesCompleted Int
  averageCyclesDays Float?

  // Quality
  averageQualityScore Float?
  gradeAPercent   Float?
  wastagePercent  Float?

  // Efficiency
  cropSuccessRate Float?
  spaceUtilization Float?
  laborHoursPerKg Float?

  // Financial
  revenueUsd      Float?
  costUsd         Float?
  profitMarginPercent Float?
  revenuePerSqm   Float?

  // Environmental
  carbonFootprintKgPerKg Float?
  waterUseLPerKg  Float?
  energyUseKwhPerKg Float?

  // Top crops (JSON arrays)
  topCropsByYield Json?
  topCropsByRevenue Json?
  topCropsByEfficiency Json?

  // Timestamps
  createdAt       DateTime  @default(now())

  // Relations
  farm            VerticalFarm @relation(fields: [farmId], references: [id])
  farmId          String

  @@index([farmId])
  @@index([period])
}

// ============================================
// DEMAND & MARKET MATCHING
// ============================================

model ConsumerPreference {
  id              String    @id @default(cuid())

  // Consumer
  consumerId      String
  consumer        User      @relation(fields: [consumerId], references: [id])

  // Location
  latitude        Float
  longitude       Float
  maxDeliveryRadiusKm Float @default(50)
  city            String?
  region          String?

  // Dietary preferences
  dietaryType     String[]
  allergies       String[]
  dislikes        String[]

  // Produce preferences (JSON)
  preferredCategories String[]
  preferredItems  Json?

  // Quality preferences
  certificationPreferences String[]
  freshnessImportance Int @default(3)
  priceImportance Int @default(3)
  sustainabilityImportance Int @default(3)

  // Delivery preferences (JSON)
  deliveryPreferences Json?

  // Household
  householdSize   Int       @default(1)
  weeklyBudget    Float?
  currency        String?   @default("USD")

  // Timestamps
  createdAt       DateTime  @default(now())
  updatedAt       DateTime  @updatedAt

  @@unique([consumerId])
  @@index([latitude, longitude])
}

model DemandSignal {
  id              String    @id @default(cuid())

  // Region scope
  centerLat       Float
  centerLon       Float
  radiusKm        Float
  regionName      String

  // Time scope
  periodStart     DateTime
  periodEnd       DateTime
  seasonalPeriod  String    // spring, summer, fall, winter

  // Aggregated demand (JSON array of DemandItem)
  demandItems     Json

  // Statistics
  totalConsumers  Int
  totalWeeklyDemandKg Float
  confidenceLevel Float

  // Supply status
  currentSupplyKg Float?
  supplyGapKg     Float?
  supplyStatus    SupplyStatus @default(BALANCED)

  // Timestamps
  timestamp       DateTime  @default(now())
  createdAt       DateTime  @default(now())

  // Relations
  marketMatches   MarketMatch[]

  @@index([regionName])
  @@index([periodStart, periodEnd])
  @@index([supplyStatus])
}

enum SupplyStatus {
  SURPLUS
  BALANCED
  SHORTAGE
  CRITICAL
}

model SupplyCommitment {
  id              String    @id @default(cuid())

  // Grower
  growerId        String
  grower          User      @relation(fields: [growerId], references: [id])

  // Produce
  produceType     String
  variety         String?

  // Commitment
  committedQuantityKg Float
  availableFrom   DateTime
  availableUntil  DateTime

  // Pricing
  pricePerKg      Float
  currency        String    @default("USD")
  minimumOrderKg  Float     @default(0)
  bulkDiscountThreshold Float?
  bulkDiscountPercent Float?

  // Quality
  certifications  String[]
  freshnessGuaranteeHours Int?

  // Delivery
  deliveryRadiusKm Float
  deliveryMethods String[]

  // Status
  status          CommitmentStatus @default(AVAILABLE)
  remainingKg     Float

  // Timestamps
  timestamp       DateTime  @default(now())
  createdAt       DateTime  @default(now())
  updatedAt       DateTime  @updatedAt

  // Relations
  marketMatches   MarketMatch[]

  @@index([growerId])
  @@index([produceType])
  @@index([status])
  @@index([availableFrom, availableUntil])
}

enum CommitmentStatus {
  AVAILABLE
  PARTIALLY_COMMITTED
  FULLY_COMMITTED
  EXPIRED
}

model MarketMatch {
  id              String    @id @default(cuid())

  // Parties
  consumerId      String
  growerId        String

  // Links
  demandSignalId  String
  demandSignal    DemandSignal @relation(fields: [demandSignalId], references: [id])
  supplyCommitmentId String
  supplyCommitment SupplyCommitment @relation(fields: [supplyCommitmentId], references: [id])

  // Match details
  produceType     String
  matchedQuantityKg Float

  // Transaction
  agreedPricePerKg Float
  totalPrice      Float
  currency        String    @default("USD")

  // Delivery
  deliveryDate    DateTime
  deliveryMethod  String
  deliveryLatitude Float?
  deliveryLongitude Float?
  deliveryAddress String?

  // Status
  status          MatchStatus @default(PENDING)

  // Ratings
  consumerRating  Float?
  growerRating    Float?
  feedback        String?

  // Timestamps
  timestamp       DateTime  @default(now())
  createdAt       DateTime  @default(now())
  updatedAt       DateTime  @updatedAt

  @@index([consumerId])
  @@index([growerId])
  @@index([status])
  @@index([deliveryDate])
}

enum MatchStatus {
  PENDING
  CONFIRMED
  IN_TRANSIT
  DELIVERED
  COMPLETED
  CANCELLED
}

model SeasonalPlan {
  id              String    @id @default(cuid())

  // Grower
  growerId        String
  grower          User      @relation(fields: [growerId], references: [id])

  // Season
  year            Int
  season          String    // spring, summer, fall, winter

  // Location context (JSON)
  location        Json

  // Growing capacity (JSON)
  growingCapacity Json

  // Planned crops (JSON array)
  plannedCrops    Json

  // Expected outcomes
  expectedTotalYieldKg Float?
  expectedRevenue Float?
  expectedCarbonFootprintKg Float?

  // Status
  status          PlanStatus @default(DRAFT)
  completionPercentage Float?

  // Timestamps
  createdAt       DateTime  @default(now())
  updatedAt       DateTime  @updatedAt

  @@index([growerId])
  @@index([year, season])
  @@index([status])
}

enum PlanStatus {
  DRAFT
  CONFIRMED
  IN_PROGRESS
  COMPLETED
}

model DemandForecast {
  id              String    @id @default(cuid())

  // Scope
  region          String
  forecastPeriodStart DateTime
  forecastPeriodEnd DateTime

  // Forecasts (JSON array of ProduceForecast)
  forecasts       Json

  // Model info
  modelVersion    String
  dataPointsUsed  Int
  lastTrainingDate DateTime?

  // Timestamps
  generatedAt     DateTime  @default(now())
  createdAt       DateTime  @default(now())

  @@index([region])
  @@index([forecastPeriodStart, forecastPeriodEnd])
}

model PlantingRecommendation {
  id              String    @id @default(cuid())

  // Grower
  growerId        String

  // Recommendation
  produceType     String
  variety         String?
  category        String

  // Quantities
  recommendedQuantity Float
  quantityUnit    String
  expectedYieldKg Float
  yieldConfidence Float

  // Timing
  plantByDate     DateTime
  expectedHarvestStart DateTime
  expectedHarvestEnd DateTime
  growingDays     Int

  // Market opportunity
  projectedDemandKg Float?
  projectedPricePerKg Float?
  projectedRevenue Float?
  marketConfidence Float?

  // Risk assessment (JSON)
  riskFactors     Json?
  overallRisk     String    @default("medium")

  // Reasoning
  demandSignalIds String[]
  explanation     String?

  // Timestamps
  timestamp       DateTime  @default(now())
  createdAt       DateTime  @default(now())

  @@index([growerId])
  @@index([produceType])
  @@index([plantByDate])
}

// ============================================
// AUDIT & TRANSPARENCY
// ============================================

model AuditLog {
  id              String    @id @default(cuid())

  // Actor
  userId          String?
  user            User?     @relation(fields: [userId], references: [id])

  // Action
  action          String
  entityType      String
  entityId        String?

  // Details
  previousValue   Json?
  newValue        Json?
  metadata        Json?

  // Source
  ipAddress       String?
  userAgent       String?

  // Timestamps
  timestamp       DateTime  @default(now())

  @@index([userId])
  @@index([entityType, entityId])
  @@index([action])
  @@index([timestamp])
}

model BlockchainBlock {
  id              String    @id @default(cuid())

  // Block data
  index           Int       @unique
  timestamp       DateTime
  previousHash    String
  hash            String    @unique
  nonce           Int

  // Block content type
  blockType       String    // "plant" or "transport"

  // Content reference
  plantId         String?
  transportEventId String?

  // Content snapshot (JSON)
  content         Json

  // Timestamps
  createdAt       DateTime  @default(now())

  @@index([blockType])
  @@index([hash])
}
