<?php

namespace BexioConnectorByHelvy;

/**
 * Custom Invoice Email
 * 
 * Sends invoice PDF to custom billing email or default email based on customer preference
 * 
 * @since 0.4.0
 */

defined('ABSPATH') || exit;

class CustomInvoiceEmail extends \WC_Email
{
    /**
     * Constructor
     */
    public function __construct()
    {
        $this->id = 'bexio_invoice_email';
        $this->title = __('Bexio Invoice Email', 'bexio-connector-by-helvy');
        $this->description = __('Custom invoice email sent to billing email when order is completed.', 'bexio-connector-by-helvy');
        $this->template_html = 'emails/customer-invoice.php';
        $this->template_plain = 'emails/plain/customer-invoice.php';
        $this->template_base = plugin_dir_path(__FILE__) . '../../templates/';
        $this->customer_email = true;
        $this->manual = false;
        
        // Initialize placeholders early
        $this->placeholders = array(
            '{order_number}' => '',
            '{order_date}' => '',
        );

        _bcbh_log("CustomInvoiceEmail: Constructor called - email class instantiated");

        // Triggers for this email
        add_action('woocommerce_order_status_completed', array($this, 'trigger'), 10, 2);
        _bcbh_log("CustomInvoiceEmail: Registered trigger hook for woocommerce_order_status_completed");

        // Call parent constructor - this will handle form fields and settings initialization
        parent::__construct();
        
        _bcbh_log("CustomInvoiceEmail: Constructor completed successfully");
    }

    /**
     * Get email subject.
     *
     * @since  0.4.0
     * @return string
     */
    public function get_default_subject()
    {
        return __('Invoice for your order {order_number}', 'bexio-connector-by-helvy');
    }

    /**
     * Get email heading.
     *
     * @since  0.4.0
     * @return string
     */
    public function get_default_heading()
    {
        return __('Invoice for your order {order_number}', 'bexio-connector-by-helvy');
    }

    /**
     * Trigger the sending of this email.
     *
     * @param int            $order_id The order ID.
     * @param \WC_Order|false $order Order object.
     */
    public function trigger($order_id, $order = false)
    {
        _bcbh_log("CustomInvoiceEmail: Trigger called for order {$order_id}");
        
        // Check if custom invoice email is enabled in settings
        $email_enabled = get_option(AdminAPISettings::$prefix . 'custom_invoice_email_enabled', false);
        _bcbh_log("CustomInvoiceEmail: Email enabled setting value: " . ($email_enabled ? 'true' : 'false'));
        _bcbh_log("CustomInvoiceEmail: Settings prefix being used: " . AdminAPISettings::$prefix);
        _bcbh_log("CustomInvoiceEmail: Full setting key: " . AdminAPISettings::$prefix . 'custom_invoice_email_enabled');
        
        if (!$email_enabled) {
            _bcbh_log("CustomInvoiceEmail: Custom invoice email is disabled in settings");
            return;
        }

        // Optional: Prevent rapid-fire duplicates (within 1 hour) but allow legitimate re-sends
        $last_sent = get_post_meta($order_id, AdminAPISettings::$prefix . 'custom_invoice_email_last_sent', true);
        if ($last_sent) {
            $time_diff = time() - strtotime($last_sent);
            if ($time_diff < 3600) { // Less than 1 hour
                _bcbh_log("CustomInvoiceEmail: Custom invoice email sent recently for order {$order_id} (less than 1 hour ago), skipping duplicate");
                return;
            }
            _bcbh_log("CustomInvoiceEmail: Custom invoice email was sent before for order {$order_id}, but allowing re-send after " . round($time_diff / 60) . " minutes");
        }

        $this->setup_locale();

        if ($order_id && !is_a($order, 'WC_Order')) {
            $order = \wc_get_order($order_id);
            _bcbh_log("CustomInvoiceEmail: Fetched order object from order ID");
        }

        if (!is_a($order, 'WC_Order')) {
            _bcbh_log("CustomInvoiceEmail: Invalid order object for order {$order_id}");
            $this->restore_locale();
            return;
        }

        _bcbh_log("CustomInvoiceEmail: Processing order {$order_id}, status: " . $order->get_status());

        $this->object = $order;
        $this->placeholders['{order_number}'] = $order->get_order_number();
        $this->placeholders['{order_date}'] = \wc_format_datetime($order->get_date_created());

        // Check if there's a Bexio invoice for this order
        $bexio_invoice_id = get_post_meta($order->get_id(), AdminAPISettings::$prefix . 'bexio_invoice_id', true);
        _bcbh_log("CustomInvoiceEmail: Bexio invoice ID for order {$order_id}: " . ($bexio_invoice_id ?: 'none'));
        
        if (!$bexio_invoice_id) {
            _bcbh_log("CustomInvoiceEmail: No Bexio invoice found for order {$order_id}, skipping custom invoice email");
            $this->restore_locale();
            return;
        }

        // Determine recipient email based on custom logic
        $recipient_email = $this->determine_recipient_email($order);
        _bcbh_log("CustomInvoiceEmail: Determined recipient email: " . ($recipient_email ?: 'none'));
        
        if (!$recipient_email) {
            _bcbh_log("CustomInvoiceEmail: No valid recipient email found for order {$order_id}");
            $this->restore_locale();
            return;
        }

        $this->recipient = $recipient_email;
        
        _bcbh_log("CustomInvoiceEmail: About to send invoice email for order {$order_id} to {$recipient_email}");
        
        // Check if email is enabled and has valid recipient
        $is_enabled = $this->is_enabled();
        $has_recipient = !empty($this->get_recipient());
        
        _bcbh_log("CustomInvoiceEmail: Email enabled check: " . ($is_enabled ? 'true' : 'false'));
        _bcbh_log("CustomInvoiceEmail: Has recipient check: " . ($has_recipient ? 'true' : 'false'));
        _bcbh_log("CustomInvoiceEmail: Final recipient: " . $this->get_recipient());
        
        // Additional debugging for WooCommerce email system
        if (function_exists('wc_mail')) {
            _bcbh_log("CustomInvoiceEmail: wc_mail function is available");
        } else {
            _bcbh_log("CustomInvoiceEmail: wc_mail function is NOT available");
        }
        
        // Check WordPress mail configuration
        $wp_mail_from = get_option('admin_email');
        _bcbh_log("CustomInvoiceEmail: WordPress admin email (wp_mail from): " . $wp_mail_from);
        
        // Check if any mail plugins or SMTP are configured
        if (defined('WPMS_ON') || defined('WPMS_PLUGIN_VER')) {
            _bcbh_log("CustomInvoiceEmail: WP Mail SMTP plugin detected");
        } else {
            _bcbh_log("CustomInvoiceEmail: No WP Mail SMTP plugin detected - using default PHP mail");
        }

        if ($is_enabled && $has_recipient) {
            _bcbh_log("CustomInvoiceEmail: Calling send method...");
            
            try {
                // Get all necessary components
                $recipient = $this->get_recipient();
                $subject = $this->get_subject();
                $content = $this->get_content();
                $headers = $this->get_headers();
                $attachments = $this->get_attachments();
                
                // Validate all components
                if (empty($recipient) || !is_email($recipient)) {
                    _bcbh_log("CustomInvoiceEmail: Invalid recipient email: " . $recipient);
                    $this->restore_locale();
                    return;
                }
                
                if (empty($subject)) {
                    _bcbh_log("CustomInvoiceEmail: Empty subject, using default");
                    $subject = "Invoice for your order";
                }
                
                if (empty($content)) {
                    _bcbh_log("CustomInvoiceEmail: Empty content, using minimal template");
                    $content = "<p>Thank you for your order. Please find your invoice attached.</p>";
                }
                
                _bcbh_log("CustomInvoiceEmail: Email components prepared:");
                _bcbh_log("CustomInvoiceEmail: - Recipient: " . $recipient);
                _bcbh_log("CustomInvoiceEmail: - Subject: " . $subject);
                _bcbh_log("CustomInvoiceEmail: - Headers: " . str_replace("\r\n", " | ", $headers));
                _bcbh_log("CustomInvoiceEmail: - Attachments count: " . count($attachments));
                _bcbh_log("CustomInvoiceEmail: - Content length: " . strlen($content) . " characters");
                
                // Try sending the email using WooCommerce send method
                $sent = $this->send($recipient, $subject, $content, $headers, $attachments);
                
                _bcbh_log("CustomInvoiceEmail: WooCommerce send method returned: " . ($sent ? 'true' : 'false'));
                
                if ($sent) {
                    _bcbh_log("CustomInvoiceEmail: Email sent successfully for order {$order_id}");
                    
                    // Update timestamp for time-based duplicate prevention
                    update_post_meta($order_id, AdminAPISettings::$prefix . 'custom_invoice_email_last_sent', current_time('mysql'));
                    
                } else {
                    _bcbh_log("CustomInvoiceEmail: WooCommerce send method failed, trying direct wp_mail...");
                    
                    // Convert headers array to string if needed
                    $headers_string = is_array($headers) ? implode("\r\n", $headers) : $headers;
                    
                    // Try direct wp_mail as fallback (this is what standard WooCommerce emails ultimately use)
                    $wp_mail_sent = wp_mail($recipient, $subject, $content, $headers_string, $attachments);
                    
                    if ($wp_mail_sent) {
                        _bcbh_log("CustomInvoiceEmail: Direct wp_mail succeeded for order {$order_id}");
                        
                        // Update timestamp for time-based duplicate prevention
                        update_post_meta($order_id, AdminAPISettings::$prefix . 'custom_invoice_email_last_sent', current_time('mysql'));
                        
                    } else {
                        _bcbh_log("CustomInvoiceEmail: Direct wp_mail also failed for order {$order_id}");
                        
                        // If wp_mail failed with attachments, try without attachments
                        if (!empty($attachments)) {
                            _bcbh_log("CustomInvoiceEmail: Attempting wp_mail without attachments...");
                            
                            $wp_mail_no_attachments = wp_mail($recipient, $subject, $content, $headers_string, array());
                            
                            if ($wp_mail_no_attachments) {
                                _bcbh_log("CustomInvoiceEmail: wp_mail without attachments succeeded for order {$order_id}");
                                
                                // Update timestamp for time-based duplicate prevention
                                update_post_meta($order_id, AdminAPISettings::$prefix . 'custom_invoice_email_last_sent', current_time('mysql'));
                                
                            } else {
                                _bcbh_log("CustomInvoiceEmail: wp_mail without attachments also failed for order {$order_id}");
                            }
                        }
                    }
                    
                    // Try to get more error details
                    $errors = [];
                    if (function_exists('error_get_last')) {
                        $last_error = error_get_last();
                        if ($last_error) {
                            $errors[] = "Last PHP error: " . $last_error['message'];
                        }
                    }
                    
                    _bcbh_log("CustomInvoiceEmail: Email failure details: " . print_r($errors, true));
                }
            } catch (\Exception $e) {
                _bcbh_log("CustomInvoiceEmail: Exception while sending email for order {$order_id}: " . $e->getMessage());
                _bcbh_log("CustomInvoiceEmail: Exception stack trace: " . $e->getTraceAsString());
            }
        } else {
            _bcbh_log("CustomInvoiceEmail: Email not sent - either not enabled or no recipient");
        }

        $this->restore_locale();
    }

    /**
     * Determine recipient email based on custom billing email or default email
     *
     * @param \WC_Order $order
     * @return string|false
     */
    private function determine_recipient_email($order)
    {
        _bcbh_log("CustomInvoiceEmail: Starting recipient email determination for order {$order->get_id()}");
        
        // Method 1: Check for custom billing email field (the main feature request)
        $custom_billing_email = get_post_meta($order->get_id(), '_billing_email', true);
        _bcbh_log("CustomInvoiceEmail: Checking _billing_email meta: " . ($custom_billing_email ?: 'empty'));
        
        if (!empty($custom_billing_email) && is_email($custom_billing_email)) {
            _bcbh_log("CustomInvoiceEmail: Using custom billing email from _billing_email meta: {$custom_billing_email}");
            return $custom_billing_email;
        }

        // Method 2: Check for custom billing email field with different key
        $custom_billing_email_alt = get_post_meta($order->get_id(), '_billing_invoice_email', true);
        _bcbh_log("CustomInvoiceEmail: Checking _billing_invoice_email meta: " . ($custom_billing_email_alt ?: 'empty'));
        
        if (!empty($custom_billing_email_alt) && is_email($custom_billing_email_alt)) {
            _bcbh_log("CustomInvoiceEmail: Using custom billing email from _billing_invoice_email meta: {$custom_billing_email_alt}");
            return $custom_billing_email_alt;
        }

        // Method 3: Check if there's a custom field for invoice email in billing data
        $billing_data = $order->get_data()['billing'];
        _bcbh_log("CustomInvoiceEmail: Checking billing data for invoice_email: " . (isset($billing_data['invoice_email']) ? $billing_data['invoice_email'] : 'not set'));
        
        if (isset($billing_data['invoice_email']) && !empty($billing_data['invoice_email']) && is_email($billing_data['invoice_email'])) {
            _bcbh_log("CustomInvoiceEmail: Using custom billing email from billing data: {$billing_data['invoice_email']}");
            return $billing_data['invoice_email'];
        }

        // Fallback to default billing email
        $default_email = $order->get_billing_email();
        _bcbh_log("CustomInvoiceEmail: Checking default billing email: " . ($default_email ?: 'empty'));
        
        if (!empty($default_email) && is_email($default_email)) {
            _bcbh_log("CustomInvoiceEmail: Using default billing email: {$default_email}");
            return $default_email;
        }

        _bcbh_log("CustomInvoiceEmail: No valid email found for order {$order->get_id()}");
        return false;
    }

    /**
     * Get content html.
     *
     * @return string
     */
    public function get_content_html()
    {
        _bcbh_log("CustomInvoiceEmail: get_content_html() called");
        _bcbh_log("CustomInvoiceEmail: Template HTML path: " . $this->template_html);
        _bcbh_log("CustomInvoiceEmail: Template base path: " . $this->template_base);
        _bcbh_log("CustomInvoiceEmail: Full template path: " . $this->template_base . $this->template_html);
        _bcbh_log("CustomInvoiceEmail: Template file exists: " . (file_exists($this->template_base . $this->template_html) ? 'yes' : 'no'));
        
        $content = \wc_get_template_html(
            $this->template_html,
            array(
                'order'              => $this->object,
                'email_heading'      => $this->get_heading(),
                'additional_content' => $this->get_additional_content(),
                'sent_to_admin'      => false,
                'plain_text'         => false,
                'email'              => $this,
            ),
            '',
            $this->template_base
        );
        
        _bcbh_log("CustomInvoiceEmail: Generated content length: " . strlen($content) . " characters");
        if (strlen($content) < 100) {
            _bcbh_log("CustomInvoiceEmail: Short content: " . $content);
        }
        
        // If template loading failed, provide a fallback with proper WooCommerce styling
        if (empty($content) || strlen($content) < 50) {
            _bcbh_log("CustomInvoiceEmail: Template loading failed, using fallback content");
            
            ob_start();
            
            // Start with WooCommerce email header
            do_action('woocommerce_email_header', $this->get_heading(), $this);
            
            // Add our content
            if ($this->object && is_a($this->object, 'WC_Order')) {
                echo '<p>' . sprintf(esc_html__('Hi %s,', 'woocommerce'), esc_html($this->object->get_billing_first_name())) . '</p>';
            } else {
                echo '<p>' . esc_html__('Hi,', 'woocommerce') . '</p>';
            }
            
            echo '<p>' . esc_html__('Thank you for your order. Please find your invoice attached to this email.', 'bexio-connector-by-helvy') . '</p>';
            
            // Add additional content if set
            if ($this->get_additional_content()) {
                echo wp_kses_post(wpautop(wptexturize($this->get_additional_content())));
            }
            
            // End with WooCommerce email footer
            do_action('woocommerce_email_footer', $this);
            
            $content = ob_get_clean();
            _bcbh_log("CustomInvoiceEmail: Fallback content generated, length: " . strlen($content));
        }
        
        return $content;
    }

    /**
     * Get content (override to handle HTML vs plain text)
     *
     * @return string
     */
    public function get_content()
    {
        _bcbh_log("CustomInvoiceEmail: get_content() called with email_type: " . $this->get_email_type());
        
        if ('html' === $this->get_email_type() || 'multipart' === $this->get_email_type()) {
            $content = $this->get_content_html();
            _bcbh_log("CustomInvoiceEmail: Using HTML content, length: " . strlen($content));
            return $content;
        } else {
            $content = $this->get_content_plain();
            _bcbh_log("CustomInvoiceEmail: Using plain content, length: " . strlen($content));
            return $content;
        }
    }

    /**
     * Get content plain.
     *
     * @return string
     */
    public function get_content_plain()
    {
        return \wc_get_template_html(
            $this->template_plain,
            array(
                'order'              => $this->object,
                'email_heading'      => $this->get_heading(),
                'additional_content' => $this->get_additional_content(),
                'sent_to_admin'      => false,
                'plain_text'         => true,
                'email'              => $this,
            ),
            '',
            $this->template_base
        );
    }

    /**
     * Default content to show below main email content.
     *
     * @since 0.4.0
     * @return string
     */
    public function get_default_additional_content()
    {
        return __('Thank you for your order. Please find your invoice attached.', 'bexio-connector-by-helvy');
    }

    /**
     * Return true if the email is enabled.
     *
     * @return bool
     */
    public function is_enabled()
    {
        return apply_filters('woocommerce_email_enabled_' . $this->id, 'yes' === $this->enabled, $this->object, $this);
    }

    /**
     * Admin Panel Options Processing.
     */
    public function process_admin_options()
    {
        // Save regular options
        parent::process_admin_options();
    }

    /**
     * Setup email settings screen.
     * Override this in your email.
     */
    public function init_form_fields()
    {
        _bcbh_log("CustomInvoiceEmail: init_form_fields() called");
        
        // Ensure placeholders are set
        if (empty($this->placeholders)) {
            $this->placeholders = array(
                '{order_number}' => '',
                '{order_date}' => '',
            );
        }
        
        try {
            /* translators: %s: list of placeholders */
            $placeholder_text = sprintf(__('Available placeholders: %s', 'woocommerce'), '<code>' . esc_html(implode('</code>, <code>', array_keys($this->placeholders))) . '</code>');
            $this->form_fields = array(
                'enabled' => array(
                    'title'   => __('Enable/Disable', 'woocommerce'),
                    'type'    => 'checkbox',
                    'label'   => __('Enable this email notification', 'woocommerce'),
                    'default' => 'yes',
                ),
                'subject' => array(
                    'title'       => __('Subject', 'woocommerce'),
                    'type'        => 'text',
                    'desc_tip'    => true,
                    'description' => $placeholder_text,
                    'placeholder' => $this->get_default_subject(),
                    'default'     => '',
                ),
                'heading' => array(
                    'title'       => __('Email heading', 'woocommerce'),
                    'type'        => 'text',
                    'desc_tip'    => true,
                    'description' => $placeholder_text,
                    'placeholder' => $this->get_default_heading(),
                    'default'     => '',
                ),
                'additional_content' => array(
                    'title'       => __('Additional content', 'woocommerce'),
                    'description' => __('Text to appear below the main email content.', 'woocommerce') . ' ' . $placeholder_text,
                    'css'         => 'width:400px; height: 75px;',
                    'placeholder' => __('N/A', 'woocommerce'),
                    'type'        => 'textarea',
                    'default'     => $this->get_default_additional_content(),
                    'desc_tip'    => true,
                ),
                'email_type' => array(
                    'title'       => __('Email type', 'woocommerce'),
                    'type'        => 'select',
                    'description' => __('Choose which format of email to send.', 'woocommerce'),
                    'default'     => 'html',
                    'class'       => 'email_type wc-enhanced-select',
                    'options'     => $this->get_email_type_options(),
                    'desc_tip'    => true,
                ),
            );
            
            _bcbh_log("CustomInvoiceEmail: Form fields initialized successfully");
            
        } catch (Exception $e) {
            _bcbh_log("CustomInvoiceEmail: Error in init_form_fields: " . $e->getMessage());
        }
    }

    /**
     * Get email type options for the form field
     *
     * @return array
     */
    public function get_email_type_options()
    {
        $types = array( 'plain' => __( 'Plain text', 'woocommerce' ) );

        if ( class_exists( 'DOMDocument' ) ) {
            $types['html']      = __( 'HTML', 'woocommerce' );
            $types['multipart'] = __( 'Multipart', 'woocommerce' );
        }

        return $types;
    }

    /**
     * Get email type (HTML, plain, or multipart)
     *
     * @return string
     */
    public function get_email_type()
    {
        return $this->email_type && class_exists('DOMDocument') ? $this->email_type : 'plain';
    }

    /**
     * Get email headers.
     *
     * @return string
     */
    public function get_headers()
    {
        $headers = parent::get_headers();
        
        // Ensure we have a proper FROM header if it's missing
        if (strpos($headers, 'From:') === false) {
            $from_name = get_option('woocommerce_email_from_name');
            $from_email = get_option('woocommerce_email_from_address');
            
            if (empty($from_name)) {
                $from_name = get_bloginfo('name');
            }
            
            if (empty($from_email)) {
                $from_email = get_option('admin_email');
            }
            
            // Ensure proper line ending format for email headers
            $from_header = "From: {$from_name} <{$from_email}>" . "\r\n";
            
            // Add the FROM header at the beginning with proper line breaks
            $headers = $from_header . $headers;
            
            _bcbh_log("CustomInvoiceEmail: Added missing FROM header: {$from_header}");
        }
        
        // Clean up headers to ensure proper formatting
        $headers = str_replace("\n", "\r\n", $headers); // Normalize line endings
        $headers = preg_replace("/\r\n+/", "\r\n", $headers); // Remove duplicate line breaks
        
        _bcbh_log("CustomInvoiceEmail: Final headers (cleaned): " . str_replace("\r\n", " | ", $headers));
        
        return $headers;
    }

    /**
     * Get email recipient.
     *
     * @return string
     */
    public function get_recipient()
    {
        $recipient = isset($this->recipient) ? $this->recipient : '';
        _bcbh_log("CustomInvoiceEmail: get_recipient() returning: " . $recipient);
        return $recipient;
    }
} 