<?php
/**
 * This file is part of the Wisewand WordPress plugin.
 *
 * @package Wisewand
 * @since 1.0.0
 * @license GPL-2.0-or-later
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation; either version 2 of the License, or
 * (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program. If not, see <https://www.gnu.org/licenses/>.
 */
namespace Wisewand\RSS;

// Exit if accessed directly
if ( ! defined( 'ABSPATH' ) ) {
	exit;
}

use Wisewand\Logging\Logger;
use Wisewand\Utils\Options;
use Wisewand\Utils\Wisewand_API_Client;
use Wisewand\Content\Content_Manager;
use Wisewand\Calendar\Calendar_Entry_Manager;

// phpcs:disable WordPress.PHP.DevelopmentFunctions.error_log_error_log -- error_log() used within WP_DEBUG conditionals

class RSS_CRON {

	private $feed_manager;
	private $article_manager;
	private $sync_engine;
	private $logger;
	private $options;

	public function __construct(
		Options $options,
		Logger $logger,
		Content_Manager $content_manager,
		Calendar_Entry_Manager $calendar_manager
	) {
		$this->options = $options;
		$this->logger  = $logger;

		// Initialize API client
		$api_client = new Wisewand_API_Client( $this->options->get( 'wisewand_api_key' ), $logger );

		// Initialize managers
		$this->feed_manager    = new RSS_Feed_Manager( $logger );
		$this->article_manager = new RSS_Article_Manager( $logger );

		// Initialize RSS Calendar Bridge for calendar integration
		$calendar_bridge = new RSS_Calendar_Bridge(
			$calendar_manager,
			$this->article_manager,
			$this->feed_manager,
			$logger
		);

		// Initialize sync engine with calendar integration
		$this->sync_engine = new RSS_Sync_Engine(
			$api_client,
			$this->feed_manager,
			$this->article_manager,
			$content_manager,
			$calendar_manager,
			$calendar_bridge,
			$logger,
			$options
		);
	}

	/**
	 * Main CRON job: Sync all feeds that are due
	 * Runs hourly via WordPress CRON
	 */
	public function run() {
		if ( WP_DEBUG ) {
			error_log( '=== RSS_CRON: Starting RSS feeds sync ===' );
		}

		$this->logger->info( 'RSS CRON job started' );

		$summary = array(
			'feeds_checked'       => 0,
			'feeds_synced'        => 0,
			'articles_discovered' => 0,
			'articles_imported'   => 0,
			'articles_failed'     => 0,
			'start_time'          => current_time( 'mysql' ),
			'errors'              => array(),
		);

		try {
			// Get feeds that are due for synchronization
			$feeds_due = $this->feed_manager->get_feeds_due_for_sync();

			$summary['feeds_checked'] = count( $feeds_due );

			if ( WP_DEBUG ) {
				error_log( "RSS_CRON: Found {$summary['feeds_checked']} feeds due for sync" );
			}

			if ( empty( $feeds_due ) ) {
				$this->logger->info( 'No feeds due for sync' );
				if ( WP_DEBUG ) {
					error_log( 'RSS_CRON: No feeds due for sync, exiting' );
				}
				return $summary;
			}

			// Process each feed
			foreach ( $feeds_due as $feed ) {
				if ( WP_DEBUG ) {
					error_log( "RSS_CRON: Processing feed '{$feed['feed_name']}' (ID: {$feed['id']})" );
				}

				// Check if it's the right time for this feed
				if ( ! $this->is_sync_time_for_feed( $feed ) ) {
					if ( WP_DEBUG ) {
						error_log( "RSS_CRON: Not the right time for feed {$feed['id']}, skipping" );
					}
					continue;
				}

				// Sync the feed
				$result = $this->sync_engine->sync_feed( $feed['id'], false );

				if ( is_wp_error( $result ) ) {
					$summary['errors'][] = sprintf(
						/* translators: 1: Feed name, 2: Error message */
						__( 'Feed "%1$s": %2$s', 'wisewand-ai-content-writer-seo-content-generator' ),
						$feed['feed_name'],
						$result->get_error_message()
					);
					continue;
				}

				++$summary['feeds_synced'];
				$summary['articles_discovered'] += $result['articles_discovered'] ?? 0;
				$summary['articles_imported']   += $result['articles_imported'] ?? 0;
				$summary['articles_failed']     += $result['articles_failed'] ?? 0;
			}

			$summary['end_time'] = current_time( 'mysql' );

			$this->logger->info( 'RSS CRON job completed', $summary );

			if ( WP_DEBUG ) {
				error_log( "RSS_CRON: Completed - {$summary['feeds_synced']} feeds synced, {$summary['articles_imported']} articles imported" );
			}
		} catch ( \Exception $e ) {
			$this->logger->error(
				'RSS CRON job failed',
				array(
					'error' => $e->getMessage(),
					'trace' => $e->getTraceAsString(),
				)
			);

			$summary['errors'][] = $e->getMessage();

			if ( WP_DEBUG ) {
				error_log( 'RSS_CRON: Exception - ' . $e->getMessage() );
			}
		}

		// Store summary in option for dashboard display
		update_option( 'wisewand_rss_last_cron_summary', wp_json_encode( $summary ) );

		return $summary;
	}

	/**
	 * Check if it's the right time to sync this feed based on schedule settings
	 *
	 * @param array $feed Feed data
	 * @return bool True if should sync now
	 */
	private function is_sync_time_for_feed( $feed ) {
		$schedule_type = $feed['import_schedule_type'] ?? 'every_6_hours';

		// Hourly and every_6_hours always sync when due (next_sync_at check already done)
		if ( in_array( $schedule_type, array( 'hourly', 'every_6_hours' ), true ) ) {
			return true;
		}

		// Daily: Check time and day of week
		if ( $schedule_type === 'daily' ) {
			return $this->check_daily_schedule( $feed );
		}

		// Custom: Always sync when due
		return true;
	}

	/**
	 * Check if current time matches daily schedule settings
	 *
	 * @param array $feed Feed data
	 * @return bool True if should sync now
	 */
	private function check_daily_schedule( $feed ) {
		$schedule_time = $feed['import_schedule_time'];
		$schedule_days = $feed['import_schedule_days'];

		$current_hour = (int) current_time( 'H' );
		$current_day  = (int) current_time( 'N' ); // 1=Monday, 7=Sunday

		// Check day of week
		if ( ! empty( $schedule_days ) ) {
			$allowed_days = array_map( 'intval', explode( ',', $schedule_days ) );
			if ( ! in_array( $current_day, $allowed_days, true ) ) {
				return false; // Wrong day
			}
		}

		// Check hour (allow 1-hour window for CRON flexibility)
		if ( $schedule_time ) {
			$target_hour = (int) gmdate( 'H', strtotime( $schedule_time ) );

			// Allow sync if within 1 hour of target time
			if ( abs( $current_hour - $target_hour ) > 1 ) {
				return false; // Wrong time
			}
		}

		return true;
	}

	/**
	 * Manual sync trigger (for "Sync Now" button)
	 *
	 * @param int $feed_id Feed ID
	 * @return array|WP_Error Sync results
	 */
	public function manual_sync_feed( $feed_id ) {
		if ( WP_DEBUG ) {
			error_log( "RSS_CRON: Manual sync triggered for feed {$feed_id}" );
		}

		return $this->sync_engine->sync_feed( $feed_id, true );
	}

	/**
	 * Cleanup old failed articles (maintenance task)
	 * Should be called weekly
	 */
	public function cleanup_old_articles() {
		$this->logger->info( 'Starting RSS articles cleanup' );

		$cleanup_stats = $this->article_manager->cleanup_old_articles();

		// Log cleanup results for monitoring.
		if ( WP_DEBUG ) {
			error_log(
				sprintf(
					'RSS_CLEANUP: Daily cleanup completed - Failed: %d, Deleted: %d, Ungenerated: %d',
					$cleanup_stats['failed_deleted'],
					$cleanup_stats['deleted_removed'],
					$cleanup_stats['ungenerated_removed']
				)
			);
		}

		$this->logger->info(
			'RSS articles cleanup completed',
			array(
				'failed_deleted'      => $cleanup_stats['failed_deleted'],
				'deleted_removed'     => $cleanup_stats['deleted_removed'],
				'ungenerated_removed' => $cleanup_stats['ungenerated_removed'],
			)
		);

		return $cleanup_stats;
	}
}
