<?php
/**
 * REST controller for handling SpectatorViews ping updates.
 *
 * @package Ilabs\Firevert\Modules\SpectatorViews\Api\Controller
 */

declare( strict_types=1 );

namespace Ilabs\Firevert\Modules\SpectatorViews\Api\Controller;

use Ilabs\Firevert\Core\Api\Controller\AbstractController;
use Ilabs\Firevert\Modules\SpectatorViews\Services\Helper\SpectatorTextPreparer;
use Ilabs\Firevert\Modules\SpectatorViews\Services\SpectatorTrackingService;
use WP_REST_Request;
use WP_REST_Response;

/**
 * Class PingController
 */
final class PingController extends AbstractController {

	/**
	 * SpectatorTrackingService instance.
	 *
	 * @var SpectatorTrackingService
	 */
	private SpectatorTrackingService $tracking_service;

	/**
	 * Constructor.
	 *
	 * @param SpectatorTrackingService $tracking_service The tracking service instance.
	 */
	public function __construct( SpectatorTrackingService $tracking_service ) {
		$this->tracking_service = $tracking_service;

		parent::__construct();
	}

	/**
	 * Registers REST API routes.
	 *
	 * @return void
	 */
	public function register_routes(): void {
		add_action( 'rest_api_init', array( $this, 'on_rest_api_init' ) );
	}

	/**
	 * Registers the ping endpoint for refreshing active viewer status.
	 *
	 * @return void
	 */
	public function on_rest_api_init(): void {
		register_rest_route(
			'firevert/v1',
			'/spectator-views/ping',
			array(
				'methods'             => 'GET',
				'callback'            => array( $this, 'refresh_ping' ),
				'permission_callback' => $this->get_permission_callback(),
				'args'                => array(
					'product_id' => array(
						'required'          => true,
						'validate_callback' => function ( $param ) {
							return is_numeric( $param ) && intval( $param ) > 0;
						},
						'sanitize_callback' => 'absint',
					),
				),
			)
		);
	}

	/**
	 * Refreshes the active status of a viewer for a specific product.
	 *
	 * @param WP_REST_Request $request REST request object.
	 *
	 * @return WP_REST_Response REST response with updated viewer count.
	 */
	public function refresh_ping( WP_REST_Request $request ): WP_REST_Response {
		$product_id   = (int) $request->get_param( 'product_id' );
		$visitor_hash = SpectatorTrackingService::hash_visitor();

		$active_count = $this->tracking_service->ping( $product_id, $visitor_hash );

		return new WP_REST_Response(
			array(
				'success'      => true,
				'viewersCount' => $active_count,
				'productId'    => $product_id,
				'text'         => SpectatorTextPreparer::get_spectator_text( $active_count ),
			)
		);
	}
}
