<?php

namespace PloverCRM\Core\Api\V1;

use PloverCRM\Core\Api\AbstractEndpoint;
use PloverCRM\Modules\PushNotifications\Services\HubPushGateway;
use WP_REST_Request;

/**
 * Mobile notification installation registration for the current workspace.
 *
 * PUT    /wp-json/plover-crm/v1/mobile-notifications/installation
 * DELETE /wp-json/plover-crm/v1/mobile-notifications/installation
 */
class MobileNotificationsEndpoint extends AbstractEndpoint
{
    private function getErrorStatus(\WP_Error $error, int $default = 503): int
    {
        $data = $error->get_error_data();

        return is_array($data) ? (int) ($data['status'] ?? $default) : $default;
    }

    public function getRoute(): string
    {
        return '/mobile-notifications/installation';
    }

    public function getMethod()
    {
        return ['PUT', 'DELETE'];
    }

    public function handle(WP_REST_Request $request)
    {
        if ($request->get_method() === 'DELETE') {
            return $this->unlinkInstallation($request);
        }

        return $this->upsertInstallation($request);
    }

    private function upsertInstallation(WP_REST_Request $request)
    {
        $data = $request->get_json_params();
        $installationId = sanitize_text_field((string) ($data['installation_id'] ?? ''));
        $expoToken = sanitize_text_field((string) ($data['expo_token'] ?? ''));
        $platform = sanitize_text_field((string) ($data['platform'] ?? ''));
        $appVariant = sanitize_text_field((string) ($data['app_variant'] ?? 'plovercrm-mobile-app'));
        $appVersion = sanitize_text_field((string) ($data['app_version'] ?? ''));
        $timezone = sanitize_text_field((string) ($data['timezone'] ?? ''));
        $preferences = is_array($data['preferences'] ?? null) ? $data['preferences'] : [];
        $activityEnabled = !empty($preferences['activity_enabled']);

        if ($installationId === '' || $expoToken === '' || $platform === '') {
            return $this->error('installation_id, expo_token, and platform are required.', 400, 'missing_required_fields');
        }

        $result = HubPushGateway::syncInstallation([
            'installation_id' => $installationId,
            'expo_token' => $expoToken,
            'platform' => $platform,
            'app_variant' => $appVariant,
            'app_version' => $appVersion,
            'timezone' => $timezone,
            'preferences' => [
                'marketing_enabled' => !array_key_exists('marketing_enabled', $preferences) || !empty($preferences['marketing_enabled']),
                'daily_summary_enabled' => !array_key_exists('daily_summary_enabled', $preferences) || !empty($preferences['daily_summary_enabled']),
            ],
            'binding' => [
                'activity_enabled' => $activityEnabled,
            ],
        ]);

        if (is_wp_error($result)) {
            return $this->error(
                $result->get_error_message(),
                $this->getErrorStatus($result),
                $result->get_error_code()
            );
        }

        return $this->success([
            'registered' => true,
            'installation_id' => $installationId,
            'activity_enabled' => $activityEnabled,
            'hub' => $result['data'] ?? [],
        ]);
    }

    private function unlinkInstallation(WP_REST_Request $request)
    {
        $data = $request->get_json_params();
        $installationId = sanitize_text_field((string) ($data['installation_id'] ?? ''));

        if ($installationId === '') {
            return $this->error('installation_id is required.', 400, 'missing_installation_id');
        }

        $result = HubPushGateway::unlinkInstallation($installationId);

        if (is_wp_error($result)) {
            return $this->error(
                $result->get_error_message(),
                $this->getErrorStatus($result),
                $result->get_error_code()
            );
        }

        return $this->success([
            'unlinked' => true,
            'installation_id' => $installationId,
            'hub' => $result['data'] ?? [],
        ]);
    }
}
