require_relative "../helpers/app"
require "spaceship"

module Fastlane
  module Actions
    class BuildVersionAction < Action
      def self.run(params)
        sha = params[:sha]
        pr_number = params[:pr_number]
        branch = params[:branch]
        build_flavor = params[:build_flavor]
        version_name = params[:version_name]
        version_code = params[:version_code] || (other_action.max_version_code(build_flavor: build_flavor) + 1)

        if !pr_number && branch
          # check if there are any PRs with the same branch
          matching_prs = Github.list_prs(state: "open", head_ref: branch)
          if matching_prs.count > 1
            UI.important("Multiple PRs were matched for branch #{branch}: #{matching_prs.map { |pr| pr[:number] }.join(", ")}. Using the first one...")
          end
          if matching_prs.any?
            pr_number = matching_prs.first[:number]
          end
        end

        if !version_name.nil?
          # Check if it's a simple release version (x.y.z)
          match = version_name.match(/^(?<version>\d+\.\d+\.\d+)(?:[\+-](?<sha>[a-zA-Z0-9]+))?(?:[\+-\.](?:pr(?<pr>\d+))|[\+-\.](?<branch>[a-zA-Z0-9\-_]+))?$/)
          unless match
            UI.user_error!("Unable to parse version name: #{version_name}")
          end
          {
            version: match[:version],
            version_name: version_name,
            version_code: version_code,
            sha: match[:sha],
            branch: match[:branch],
            pr: match[:pr]
          }
        elsif (release_version = branch.match(/^releases?\/v?(?<version>\d+\.\d+\.\d+)?$/)&.[](:version))
          UI.message("Detected release branch: #{branch}")
          {
            version: release_version,
            version_code: version_code,
            version_name: release_version,
            sha: sha,
            branch: branch,
            pr: nil
          }
        else
          version = other_action.android_get_version_name(gradle_file: App::GRADLE_FILE)

          version_name = if pr_number
            UI.message("Detected PR number: #{pr_number}")
            "#{version}+#{sha}.pr#{pr_number}"
          elsif !branch.empty? && branch != Git.default_branch
            UI.message("Detected custom branch: #{branch}")
            "#{version}+#{sha}.#{branch.downcase.gsub(/[^a-zA-Z0-9\-_]/, "")}"
          else
            UI.message("Detected default branch: #{branch}")
            "#{version}+#{sha}"
          end

          {
            version: version,
            version_name: version_name,
            version_code: version_code,
            sha: sha,
            branch: branch,
            pr: pr_number
          }
        end
      end

      def self.description
        "Returns build version metadata"
      end

      def self.available_options
        [
          FastlaneCore::ConfigItem.new(key: :build_flavor,
            description: "Build flavor to use (#{BuildFlavor::ALL.join(", ")})",
            type: String,
            verify_block: proc do |value|
              UI.user_error!("Invalid flavor (must be #{BuildFlavor::ALL.join(", ")})") unless BuildFlavor::ALL.include?(value)
            end),
          FastlaneCore::ConfigItem.new(key: :version_name,
            description: "Version name to use",
            type: String,
            optional: true,
            verify_block: proc do |value|
              UI.user_error!("Invalid version name (must be a valid version name)") if value.empty?
            end),
          FastlaneCore::ConfigItem.new(key: :version_code,
            description: "Version code to use",
            type: Integer,
            optional: true,
            verify_block: proc do |value|
              UI.user_error!("Invalid version code (must be a valid version code)") unless value > 0
            end),
          FastlaneCore::ConfigItem.new(key: :sha,
            description: "SHA to use",
            type: String,
            optional: true,
            default_value: Git.current_sha(short: true)),
          FastlaneCore::ConfigItem.new(key: :pr_number,
            description: "Pull request number that triggered the distribution",
            optional: true,
            type: Integer,
            default_value: Github.pr_number,
            verify_block: proc do |value|
              UI.user_error!("Pull request number must be a positive integer") unless value.nil? || value > 0
            end),
          FastlaneCore::ConfigItem.new(key: :branch,
            description: "Branch to use",
            type: String,
            optional: true,
            default_value: Github.branch || Git.current_branch)

        ]
      end

      def self.authors
        ["Suno"]
      end

      def self.is_supported?(platform)
        platform == :android
      end
    end
  end
end
