<?php

class Wb_Api_Form
{

  public function register_routes()
  {
    register_rest_route('wb-onboard/v1', '/save-form', array(
      'methods' => 'POST',
      'callback' => [$this, 'save_form'],
      'permission_callback' => [$this, 'wb_register_form_permission_callback']
    ));

    register_rest_route('wb-onboard/v1', '/get-form', array(
      'methods' => 'GET',
      'callback' => [$this, 'get_form'],
      'permission_callback' => [$this, 'wb_register_form_permission_callback']
    ));

    register_rest_route('wb-onboard/v1', '/upload-image', array(
      'methods' => 'POST',
      'callback' => [$this, 'upload_image'],
      'permission_callback' => [$this, 'wb_register_form_permission_callback']
    ));
  }

  public function save_form($request)
  {
    $wb_onboard_form_data = $request->get_param('wb_onboard_form_data');
    $step_n = $request->get_param('step_n');
    $page_id = $request->get_param('page_id'); // Optionnel pour le leadership

    // For testing, do this to reset the form
    // $wb_onboard_form_data = "";

    // Vérifier le leadership avant de permettre la sauvegarde
    if (!empty($page_id) && !WB_Leader_Service::is_leader($page_id)) {
      return wp_send_json_error([
        'message' => 'Sauvegarde refusée - vous n\'êtes pas le leader actuel',
        'code' => 'NOT_LEADER'
      ], 403);
    }

    // Update the options
    update_option('options_wb_onboard_form_data', json_encode($wb_onboard_form_data));
    update_option('options_wb_onboard_form_step_n', $step_n);

    // Créer une sauvegarde JSON dans la table SEULEMENT si ça fait plus de 2 minutes
    $backup_id = null;
    if (!empty($wb_onboard_form_data)) {
      $time_since_last = WB_Backup_Service::time_from_last_entry();
      $min_interval = 120; // 2 minutes en secondes

      if ($time_since_last > $min_interval) {
        $backup_data = [
          'form_data' => $wb_onboard_form_data,
          'step_n' => $step_n,
          'page_id' => $page_id,
          'timestamp' => time()
        ];

        $backup_id = WB_Backup_Service::add_json($backup_data);

        if ($backup_id === false) {
          error_log('Erreur lors de la sauvegarde JSON dans save_form');
        }
      }
    }

    // Mettre à jour le timestamp du leader si page_id fourni
    if (!empty($page_id)) {
      // Simple ping d'activité si on est le leader
      WB_Leader_Service::update_leader_activity($page_id);
    }

    $response_data = [
      'message' => 'Data successfully added.',
      'backup_id' => $backup_id,
      'step_n' => $step_n
    ];

    return wp_send_json_success($response_data, 200);
  }

  public function get_form()
  {

    $wb_onboard_form_data = json_decode(get_option('options_wb_onboard_form_data'));
    $wb_onboard_form_step_n = json_decode(get_option('options_wb_onboard_form_step_n'));

    return wp_send_json_success(array(
      'wb_onboard_form_data' => $wb_onboard_form_data,
      'wb_onboard_form_step_n' => $wb_onboard_form_step_n ?? 0
    ), 200);
  }

  public function wb_register_form_permission_callback()
  {
    return true;
    if (is_user_logged_in()) {
      $user = wp_get_current_user();
      $role = (array) $user->roles;
      if (isset($role[0]) && ($role[0] == 'wb_onboarding_user' || $role[0] == 'administrator')) {
        return true;
      }
    }
    return new WP_Error('rest_forbidden', esc_html__('You do not have REST permissions.', 'wb-onboarding'), array('status' => 401));
  }

  /**
   * Recherche une image existante par son hash
   */
  private function get_attachment_by_hash($hash)
  {
    $args = array(
      'post_type' => 'attachment',
      'meta_key' => 'image_hash',
      'meta_value' => $hash,
      'posts_per_page' => 1
    );

    $attachments = get_posts($args);

    return !empty($attachments) ? $attachments[0] : null;
  }

  private function handle_image_upload($image_data, $field_name)
  {
    // If it's an array, just return it
    if (is_array($image_data)) {
      return $image_data;
    }

    // If it's a simple URL (not data:image)
    if (strpos($image_data, 'data:image') !== 0) {
      return [
        'url' => $image_data,
        'attachment_id' => null
      ];
    }

    // Generate a unique hash for the image
    $image_hash = md5($image_data);

    // Check if an image with this hash already exists
    $existing_attachment = $this->get_attachment_by_hash($image_hash);

    if ($existing_attachment) {
      return [
        'url' => wp_get_attachment_url($existing_attachment->ID),
        'attachment_id' => $existing_attachment->ID
      ];
    }

    $upload_dir = wp_upload_dir();
    $decoded_img = base64_decode(explode(',', $image_data)[1]);

    // Determine image type from the data URL
    $mime_type = $this->get_mime_from_data($image_data);
    $extension = $this->get_extension_from_mime($mime_type);
    $filename = $field_name . '-' . time() . '.' . $extension;
    $file_path = $upload_dir['path'] . '/' . $filename;

    // Save the original image temporarily
    file_put_contents($file_path, $decoded_img);

    // Maximum file size (1MB)
    $max_size = 1 * 1024 * 1024;

    // Get current size
    $current_size = filesize($file_path);

    if ($current_size > $max_size) {
      // Load required WordPress image handling functions
      require_once(ABSPATH . 'wp-admin/includes/image.php');
      require_once(ABSPATH . 'wp-admin/includes/file.php');
      require_once(ABSPATH . 'wp-admin/includes/media.php');

      // Create image resource from file
      $image = wp_get_image_editor($file_path);

      if (!is_wp_error($image)) {
        // Start with dimensions reduction if image is very large
        $image_info = getimagesize($file_path);
        $width = $image_info[0];
        $height = $image_info[1];

        // If the image is very large dimensionally, resize it first
        if ($width > 2000 || $height > 2000) {
          $max_dimension = 2000;
          if ($width > $height) {
            $new_width = $max_dimension;
            $new_height = round($height * ($max_dimension / $width));
          } else {
            $new_height = $max_dimension;
            $new_width = round($width * ($max_dimension / $height));
          }
          $image->resize($new_width, $new_height, false);
          $image->save($file_path);

          // Reload the image after resizing
          $image = wp_get_image_editor($file_path);
        }

        // Try different quality settings to get under 1MB
        $quality = 90;
        $min_quality = 50;
        $temp_file = $file_path . '.tmp';

        while ($quality >= $min_quality) {
          // Set quality and save to temp file
          $image->set_quality($quality);
          $result = $image->save($temp_file);

          // Check if save was successful and file exists
          if (!is_wp_error($result) && file_exists($temp_file)) {
            // Check size
            $new_size = filesize($temp_file);

            if ($new_size <= $max_size) {
              // Success - replace original with compressed version
              unlink($file_path);
              rename($temp_file, $file_path);
              break;
            } else {
              // Remove temp file and try with lower quality
              unlink($temp_file);
            }
          }

          $quality -= 10;
        }

        // If we couldn't compress enough with quality alone, resize dimensions
        if ($quality < $min_quality && file_exists($file_path)) {
          // Reload the image object with the current state
          $image = wp_get_image_editor($file_path);

          if (!is_wp_error($image)) {
            // Get current dimensions
            $image_size = $image->get_size();
            $width = $image_size['width'];
            $height = $image_size['height'];

            // Start with 80% of current size and keep reducing until under limit
            $scale = 0.8;

            while ($scale > 0.3) { // Don't go below 30% of original size
              $new_width = round($width * $scale);
              $new_height = round($height * $scale);

              $image->resize($new_width, $new_height, false);
              $image->set_quality(70); // Use a moderate quality
              $result = $image->save($file_path);

              if (!is_wp_error($result) && file_exists($file_path) && filesize($file_path) <= $max_size) {
                break;
              }

              // Reload the image for next attempt
              $image = wp_get_image_editor($file_path);
              if (is_wp_error($image)) {
                break;
              }

              $scale -= 0.1;
            }
          }
        }
      }
    }

    $attachment = array(
      'post_mime_type' => $mime_type,
      'post_title' => sanitize_file_name($filename),
      'post_content' => '',
      'post_status' => 'inherit',
      'meta_input' => array(
        'image_hash' => $image_hash
      )
    );

    $attach_id = wp_insert_attachment($attachment, $file_path);
    require_once(ABSPATH . 'wp-admin/includes/image.php');
    $attach_data = wp_generate_attachment_metadata($attach_id, $file_path);
    wp_update_attachment_metadata($attach_id, $attach_data);

    return [
      'url' => wp_get_attachment_url($attach_id),
      'attachment_id' => $attach_id
    ];
  }

  // Helper function to get mime type from data URL
  private function get_mime_from_data($data)
  {
    preg_match('/data:(image\/[^;]+)/', $data, $matches);
    return isset($matches[1]) ? $matches[1] : 'image/png';
  }

  // Helper function to get file extension from mime type
  private function get_extension_from_mime($mime)
  {
    $mime_map = [
      'image/jpeg' => 'jpg',
      'image/png' => 'png',
      'image/gif' => 'gif',
      'image/webp' => 'webp',
    ];

    return isset($mime_map[$mime]) ? $mime_map[$mime] : 'png';
  }

  public function upload_image($request)
  {
    $image_data = $request->get_param('image');
    $field_name = $request->get_param('fieldName');

    $upload_result = $this->handle_image_upload($image_data, $field_name);

    return wp_send_json_success([
      'url' => $upload_result['url'],
      'attachment_id' => $upload_result['attachment_id']
    ], 200);
  }
}
