HEX
Server: LiteSpeed
System: Linux emerald.serverdnsnetwork.com 5.14.0-611.5.1.el9_7.x86_64 #1 SMP PREEMPT_DYNAMIC Tue Nov 11 08:09:09 EST 2025 x86_64
User: mahdetej (1135)
PHP: 8.1.34
Disabled: show_source, system, shell_exec, passthru, exec, popen, proc_open
Upload Files
File: /home/mahdetej/public_html/wp-content/plugins/Melli-shild/includes/class-darkshield-utils.php
<?php
if ( ! defined( 'ABSPATH' ) ) {
    exit;
}

class DarkShield_Utils {

    // ========================================
    // Mode
    // ========================================

    public static function get_mode() {
        static $mode = null;
        if ( null !== $mode ) {
            return $mode;
        }
        $mode = get_option( Melli_Shield_Config::OPTION_MODE, 'normal' );
        if ( ! in_array( $mode, array( 'normal', 'national', 'offline' ), true ) ) {
            $mode = 'normal';
        }
        return $mode;
    }

    public static function set_mode( $new_mode ) {
        if ( ! in_array( $new_mode, array( 'normal', 'national', 'offline' ), true ) ) {
            return false;
        }
        $old = self::get_mode();
        update_option( Melli_Shield_Config::OPTION_MODE, $new_mode );

        if ( $old !== $new_mode && class_exists( 'DarkShield_Compatibility' ) ) {
            DarkShield_Compatibility::purge_caches();
        }

        Melli_Shield_Migrator::fire_mode_changed( $new_mode, $old );
        return true;
    }

    public static function get_mode_label( $mode = null ) {
        if ( null === $mode ) {
            $mode = self::get_mode();
        }
        $labels = array(
            'normal'   => __( 'عادی', 'melli-shield' ),
            'national' => __( 'ملی', 'melli-shield' ),
            'offline'  => __( 'آفلاین', 'melli-shield' ),
        );
        return isset( $labels[ $mode ] ) ? $labels[ $mode ] : $labels['normal'];
    }

    public static function is_blocking_active() {
        return 'normal' !== self::get_mode();
    }

    // ========================================
    // Settings
    // ========================================

    public static function get_settings() {
        static $settings = null;
        if ( null !== $settings ) {
            return $settings;
        }
        $defaults = array(
            'block_fonts' => 1, 'block_cdn' => 1, 'block_analytics' => 1,
            'block_updates' => 1, 'block_gravatar' => 1, 'block_embeds' => 1,
            'block_recaptcha' => 1, 'block_heartbeat' => 0, 'block_email' => 0,
            'allow_messenger' => 1, 'log_enabled' => 1, 'log_retention' => 30,
        );
        $settings = wp_parse_args( get_option( Melli_Shield_Config::OPTION_SETTINGS, array() ), $defaults );
        return $settings;
    }

    public static function get_setting( $key, $default = null ) {
        $s = self::get_settings();
        return isset( $s[ $key ] ) ? $s[ $key ] : $default;
    }

    // ========================================
    // Domain Helpers
    // ========================================

    public static function extract_domain( $url ) {
        if ( empty( $url ) ) {
            return '';
        }
        if ( strpos( $url, '//' ) === 0 ) {
            $url = 'https:' . $url;
        }
        if ( strpos( $url, '://' ) === false ) {
            $url = 'https://' . $url;
        }
        $parsed = wp_parse_url( $url );
        return isset( $parsed['host'] ) ? strtolower( $parsed['host'] ) : '';
    }

    public static function get_site_domain() {
        static $domain = null;
        if ( null === $domain ) {
            $domain = self::extract_domain( home_url() );
        }
        return $domain;
    }

    public static function is_local_domain( $domain ) {
        if ( empty( $domain ) ) {
            return true;
        }
        $domain = strtolower( $domain );

        if ( in_array( $domain, array( 'localhost', '127.0.0.1', '0.0.0.0', '::1' ), true ) ) {
            return true;
        }

        $local_tlds = array( '.local', '.localhost', '.test', '.example', '.invalid', '.dev' );
        foreach ( $local_tlds as $tld ) {
            if ( substr( $domain, -strlen( $tld ) ) === $tld ) {
                return true;
            }
        }

        if ( filter_var( $domain, FILTER_VALIDATE_IP ) ) {
            if ( ! filter_var( $domain, FILTER_VALIDATE_IP, FILTER_FLAG_NO_PRIV_RANGE | FILTER_FLAG_NO_RES_RANGE ) ) {
                return true;
            }
        }

        return false;
    }

    public static function is_iranian_domain( $domain ) {
        $domain = strtolower( $domain );

        if ( substr( $domain, -3 ) === '.ir' ) {
            return true;
        }

        static $iranian = null;
        if ( null === $iranian ) {
            $file = DARKSHIELD_PLUGIN_DIR . 'data/iranian-domains.php';
            $iranian = file_exists( $file ) ? include $file : array();
            if ( ! is_array( $iranian ) ) {
                $iranian = array();
            }
        }

        if ( in_array( $domain, $iranian, true ) ) {
            return true;
        }

        foreach ( $iranian as $ir ) {
            if ( substr( $domain, -( strlen( $ir ) + 1 ) ) === '.' . $ir ) {
                return true;
            }
        }

        return false;
    }

    // ========================================
    // Known Domains
    // ========================================

    public static function get_known_domains() {
        static $domains = null;
        if ( null !== $domains ) {
            return $domains;
        }
        $file = DARKSHIELD_PLUGIN_DIR . 'data/known-domains.php';
        $domains = file_exists( $file ) ? include $file : array();
        if ( ! is_array( $domains ) ) {
            $domains = array();
        }
        return $domains;
    }

    // ========================================
    // Whitelist
    // ========================================

    public static function is_whitelisted( $domain ) {
        static $wl = null;
        if ( null === $wl ) {
            $wl = get_option( Melli_Shield_Config::OPTION_WHITELIST, array() );
            if ( ! is_array( $wl ) ) {
                $wl = array();
            }
        }
        $domain = strtolower( $domain );
        if ( in_array( $domain, $wl, true ) ) {
            return true;
        }
        foreach ( $wl as $w ) {
            if ( substr( $domain, -( strlen( $w ) + 1 ) ) === '.' . $w ) {
                return true;
            }
        }
        return false;
    }

    // ========================================
    // Messenger Domains
    // ========================================

    public static function is_messenger_domain( $domain ) {
        $known = self::get_known_domains();
        if ( ! isset( $known['messenger'] ) || ! is_array( $known['messenger'] ) ) {
            return false;
        }
        $domain = strtolower( $domain );
        if ( in_array( $domain, $known['messenger'], true ) ) {
            return true;
        }
        foreach ( $known['messenger'] as $m ) {
            if ( substr( $domain, -( strlen( $m ) + 1 ) ) === '.' . $m ) {
                return true;
            }
        }
        return false;
    }

    // ========================================
    // Allowed Services (SMS, Payment, etc.)
    // ========================================

    public static function get_allowed_services() {
        static $services = null;
        if ( null !== $services ) {
            return $services;
        }
        $raw = get_option( Melli_Shield_Config::OPTION_ALLOWED_SERVICES, '' );
        if ( empty( $raw ) ) {
            $services = array();
            return $services;
        }
        $services = array();
        foreach ( explode( "\n", $raw ) as $line ) {
            $d = strtolower( trim( $line ) );
            if ( ! empty( $d ) && strpos( $d, '.' ) !== false ) {
                $services[] = $d;
            }
        }
        return $services;
    }

    public static function is_allowed_service( $domain ) {
        $services = self::get_allowed_services();
        if ( empty( $services ) ) {
            return false;
        }
        $domain = strtolower( $domain );
        if ( in_array( $domain, $services, true ) ) {
            return true;
        }
        foreach ( $services as $s ) {
            if ( substr( $domain, -( strlen( $s ) + 1 ) ) === '.' . $s ) {
                return true;
            }
        }
        return false;
    }

    // ========================================
    // Protected Handles
    // ========================================

    public static function is_protected_handle( $handle ) {
        global $melli_shield_protected_handles, $darkshield_protected_handles;
        $handles = is_array( $melli_shield_protected_handles ) ? $melli_shield_protected_handles : $darkshield_protected_handles;
        if ( ! is_array( $handles ) ) {
            return false;
        }
        return in_array( $handle, $handles, true );
    }

    // ========================================
    // Internal URL Detection
    // ========================================

    public static function is_internal_url( $url ) {
        if ( empty( $url ) ) {
            return true;
        }
        if ( strpos( $url, '//' ) === false ) {
            return true;
        }

        $check = $url;
        if ( strpos( $check, '//' ) === 0 ) {
            $check = 'https:' . $check;
        }

        $domain = self::extract_domain( $check );

        if ( empty( $domain ) ) {
            return true;
        }
        if ( $domain === self::get_site_domain() ) {
            return true;
        }
        if ( self::is_local_domain( $domain ) ) {
            return true;
        }

        return false;
    }

    // ========================================
    // Should Block — Main Decision
    // ========================================

    public static function should_block( $url ) {
        $mode = self::get_mode();

        if ( 'normal' === $mode ) {
            return false;
        }

        if ( self::is_internal_url( $url ) ) {
            return false;
        }

        $domain = self::extract_domain( $url );

        if ( empty( $domain ) ) {
            return false;
        }

        if ( self::is_whitelisted( $domain ) ) {
            return false;
        }

        if ( self::is_allowed_service( $domain ) ) {
            return false;
        }

        if ( self::get_setting( 'allow_messenger', 1 ) && self::is_messenger_domain( $domain ) ) {
            return false;
        }

        if ( 'national' === $mode ) {
            return ! self::is_iranian_domain( $domain );
        }

        if ( 'offline' === $mode ) {
            return true;
        }

        return false;
    }

    // ========================================
    // Database Helpers
    // ========================================

    public static function table_exists( $table_name ) {
        static $cache = array();
        if ( isset( $cache[ $table_name ] ) ) {
            return $cache[ $table_name ];
        }
        global $wpdb;
        $result = $wpdb->get_var( $wpdb->prepare( "SHOW TABLES LIKE %s", $table_name ) );
        $cache[ $table_name ] = ( $result === $table_name );
        return $cache[ $table_name ];
    }

    public static function ensure_tables() {
        global $wpdb;
        $log  = Melli_Shield_Config::log_table();
        $scan = Melli_Shield_Config::scan_table();

        if ( ! self::table_exists( $log ) || ! self::table_exists( $scan ) ) {
            if ( class_exists( 'DarkShield_Activator' ) ) {
                DarkShield_Activator::create_tables();
            }
        }
    }

    // ========================================
    // Misc Helpers
    // ========================================

    public static function truncate( $string, $max = 100, $suffix = '...' ) {
        if ( mb_strlen( $string ) <= $max ) {
            return $string;
        }
        return mb_substr( $string, 0, $max - mb_strlen( $suffix ) ) . $suffix;
    }

    public static function format_bytes( $bytes, $decimals = 1 ) {
        if ( $bytes <= 0 ) {
            return '0 B';
        }
        $units  = array( 'B', 'KB', 'MB', 'GB' );
        $factor = floor( ( strlen( $bytes ) - 1 ) / 3 );
        return sprintf( "%.{$decimals}f %s", $bytes / pow( 1024, $factor ), $units[ $factor ] );
    }

    public static function is_rest_request() {
        return ( defined( 'REST_REQUEST' ) && REST_REQUEST );
    }

    public static function is_ajax_request() {
        return ( defined( 'DOING_AJAX' ) && DOING_AJAX );
    }

    public static function is_cron_request() {
        return ( defined( 'DOING_CRON' ) && DOING_CRON );
    }

    /**
     * Recent blocked log rows for dashboard.
     *
     * @param int $limit Max rows.
     * @return array<object>
     */
    public static function get_recent_log( $limit = 10 ) {
        global $wpdb;
        $table = Melli_Shield_Config::log_table();
        if ( ! self::table_exists( $table ) ) {
            return array();
        }
        $limit = max( 1, min( 50, (int) $limit ) );
        // phpcs:ignore WordPress.DB.PreparedSQL.InterpolatedNotPrepared
        return $wpdb->get_results( "SELECT * FROM {$table} WHERE blocked = 1 ORDER BY id DESC LIMIT {$limit}" );
    }

    /**
     * Top blocked domains for dashboard.
     *
     * @param int $limit Max rows.
     * @return array<object>
     */
    public static function get_top_blocked_domains( $limit = 8 ) {
        global $wpdb;
        $table = Melli_Shield_Config::log_table();
        if ( ! self::table_exists( $table ) ) {
            return array();
        }
        $limit = max( 1, min( 20, (int) $limit ) );
        // phpcs:ignore WordPress.DB.PreparedSQL.InterpolatedNotPrepared
        return $wpdb->get_results(
            "SELECT domain, COUNT(*) AS hits FROM {$table} WHERE blocked = 1 GROUP BY domain ORDER BY hits DESC LIMIT {$limit}"
        );
    }

}