#!/usr/bin/env bash
# Copyright 2025 Google LLC
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
#     http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
#
# SPDX-License-Identifier: Apache-2.0

# Version bump script for Genkit Python packages.
# Bumps version in core package and all plugins simultaneously.

set -euo pipefail

# Colors for output
RED='\033[0;31m'
GREEN='\033[0;32m'
YELLOW='\033[1;33m'
BLUE='\033[0;34m'
CYAN='\033[0;36m'
NC='\033[0m' # No Color

# Get the directory of this script and the py directory
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
PY_DIR="$(cd "${SCRIPT_DIR}/.." && pwd)"

cd "$PY_DIR"

# Get current version
CURRENT_VERSION=$(grep '^version' packages/genkit/pyproject.toml | head -1 | sed 's/.*= *"//' | sed 's/".*//')

usage() {
  echo "Usage: $0 [OPTIONS] <new_version>"
  echo ""
  echo "Bump version for all Genkit Python packages."
  echo ""
  echo "Arguments:"
  echo "  new_version    New version number (e.g., 0.5.0, 1.0.0)"
  echo ""
  echo "Options:"
  echo "  --major        Bump major version (X.0.0)"
  echo "  --minor        Bump minor version (x.Y.0)"
  echo "  --patch        Bump patch version (x.y.Z)"
  echo "  --dry-run      Show what would be changed without making changes"
  echo "  -h, --help     Show this help message"
  echo ""
  echo "Current version: $CURRENT_VERSION"
  echo ""
  echo "Examples:"
  echo "  $0 0.5.0           # Set specific version"
  echo "  $0 --minor         # Bump minor version (0.4.0 -> 0.5.0)"
  echo "  $0 --patch         # Bump patch version (0.4.0 -> 0.4.1)"
  echo "  $0 --major         # Bump major version (0.4.0 -> 1.0.0)"
}

# Parse current version
IFS='.' read -r MAJOR MINOR PATCH <<< "$CURRENT_VERSION"

# Parse arguments
DRY_RUN=false
NEW_VERSION=""

while [[ $# -gt 0 ]]; do
  case "$1" in
    --major)
      MAJOR=$((MAJOR + 1))
      MINOR=0
      PATCH=0
      NEW_VERSION="$MAJOR.$MINOR.$PATCH"
      shift
      ;;
    --minor)
      MINOR=$((MINOR + 1))
      PATCH=0
      NEW_VERSION="$MAJOR.$MINOR.$PATCH"
      shift
      ;;
    --patch)
      PATCH=$((PATCH + 1))
      NEW_VERSION="$MAJOR.$MINOR.$PATCH"
      shift
      ;;
    --dry-run)
      DRY_RUN=true
      shift
      ;;
    -h|--help)
      usage
      exit 0
      ;;
    -*)
      echo "Unknown option: $1"
      usage
      exit 1
      ;;
    *)
      if [ -z "$NEW_VERSION" ]; then
        NEW_VERSION="$1"
      else
        echo "Error: Multiple versions specified"
        usage
        exit 1
      fi
      shift
      ;;
  esac
done

if [ -z "$NEW_VERSION" ]; then
  echo "Error: No version specified"
  usage
  exit 1
fi

# Validate version format
if ! [[ "$NEW_VERSION" =~ ^[0-9]+\.[0-9]+\.[0-9]+$ ]]; then
  echo -e "${RED}Error${NC}: Invalid version format '$NEW_VERSION'. Expected format: X.Y.Z"
  exit 1
fi

echo -e "${BLUE}╔════════════════════════════════════════════════════════════════╗${NC}"
echo -e "${BLUE}║              Genkit Python Version Bump                        ║${NC}"
echo -e "${BLUE}╚════════════════════════════════════════════════════════════════╝${NC}"
echo ""
echo -e "Current version: ${YELLOW}$CURRENT_VERSION${NC}"
echo -e "New version:     ${GREEN}$NEW_VERSION${NC}"
echo ""

if $DRY_RUN; then
  echo -e "${CYAN}[DRY RUN] The following files would be updated:${NC}"
  echo ""
fi

# Function to update version in a file
update_version() {
  local file="$1"
  local pkg_name
  pkg_name=$(grep '^name' "$file" | head -1 | sed 's/.*= *"//' | sed 's/".*//')
  
  if $DRY_RUN; then
    echo -e "  Would update: $file ($pkg_name)"
  else
    # Use sed to replace version line
    if [[ "$OSTYPE" == "darwin"* ]]; then
      # macOS sed
      sed -i '' "s/^version *= *\"$CURRENT_VERSION\"/version = \"$NEW_VERSION\"/" "$file"
    else
      # GNU sed
      sed -i "s/^version *= *\"$CURRENT_VERSION\"/version = \"$NEW_VERSION\"/" "$file"
    fi
    echo -e "  ${GREEN}✓${NC} Updated: $file ($pkg_name)"
  fi
}

# Update core package
echo -e "${CYAN}Updating core package...${NC}"
update_version "packages/genkit/pyproject.toml"

# Update all plugins
echo -e "\n${CYAN}Updating plugins...${NC}"
for f in plugins/*/pyproject.toml; do
  if [ -f "$f" ]; then
    update_version "$f"
  fi
done

# Update all samples
echo -e "\n${CYAN}Updating samples...${NC}"
for f in samples/*/pyproject.toml; do
  if [ -f "$f" ]; then
    update_version "$f"
  fi
done

echo ""

if $DRY_RUN; then
  echo -e "${YELLOW}[DRY RUN] No changes were made.${NC}"
  echo -e "Run without --dry-run to apply changes."
else
  # Update lock file
  echo -e "${CYAN}Updating lock file...${NC}"
  uv lock > /dev/null 2>&1
  echo -e "  ${GREEN}✓${NC} uv.lock updated"
  
  echo ""
  echo -e "${GREEN}╔════════════════════════════════════════════════════════════════╗${NC}"
  echo -e "${GREEN}║  ✓ Version bumped to $NEW_VERSION                               ║${NC}"
  echo -e "${GREEN}╚════════════════════════════════════════════════════════════════╝${NC}"
  echo ""
  echo -e "Next steps:"
  echo -e "  1. Update CHANGELOG.md with release notes"
  echo -e "  2. Run ${CYAN}py/bin/release_check${NC} to verify release readiness"
  echo -e "  3. Commit changes: ${CYAN}git commit -am 'chore: bump version to $NEW_VERSION'${NC}"
  echo -e "  4. Create release tag: ${CYAN}git tag -a py-v$NEW_VERSION -m 'Python SDK v$NEW_VERSION'${NC}"
fi
