'DE' | '', 'ip' => '1.2.3.4' | '' ]. */ public static function for_request() { // phpcs:disable WordPress.Security.ValidatedSanitizedInput $cf = isset( $_SERVER['HTTP_CF_IPCOUNTRY'] ) ? self::valid_country( wp_unslash( $_SERVER['HTTP_CF_IPCOUNTRY'] ) ) : ''; if ( $cf ) { return array( 'country' => $cf, 'ip' => '', ); } $ip = isset( $_SERVER['REMOTE_ADDR'] ) ? trim( wp_unslash( $_SERVER['REMOTE_ADDR'] ) ) : ''; // phpcs:enable $ip = apply_filters( 'postaramail_client_ip', $ip ); // behind a proxy? return the real visitor address here. if ( ! $ip || ! filter_var( $ip, FILTER_VALIDATE_IP, FILTER_FLAG_NO_PRIV_RANGE | FILTER_FLAG_NO_RES_RANGE ) ) { return array( 'country' => '', 'ip' => '', ); } return array( 'country' => '', 'ip' => $ip, ); } /** * A saved user's country, from what the site already knows: WooCommerce billing / shipping country, * a few common profile fields, or WooCommerce's customer table. Empty when unknown. */ public static function for_user( $user_id ) { $keys = apply_filters( 'postaramail_country_meta_keys', array( 'billing_country', 'shipping_country', 'country', 'user_country', 'um_country', 'wc_country' ) ); foreach ( (array) $keys as $key ) { $c = self::valid_country( get_user_meta( $user_id, $key, true ) ); if ( $c ) { return $c; } } // WooCommerce Analytics keeps one row per customer, including their country. global $wpdb; $table = $wpdb->prefix . 'wc_customer_lookup'; if ( self::table_exists( $table ) ) { $c = self::valid_country( $wpdb->get_var( $wpdb->prepare( "SELECT country FROM {$table} WHERE user_id = %d AND country <> '' LIMIT 1", $user_id ) ) ); // phpcs:ignore WordPress.DB if ( $c ) { return $c; } } return ''; } /** * The last IP address the site saw for this user (login sessions, or fields some plugins keep), when there is * no country. It is sent once; PostaraMail turns it into a country and throws it away. */ public static function ip_for_user( $user_id ) { $candidates = array(); if ( class_exists( 'WP_Session_Tokens' ) ) { $sessions = WP_Session_Tokens::get_instance( $user_id )->get_all(); usort( $sessions, function ( $a, $b ) { return ( isset( $b['login'] ) ? (int) $b['login'] : 0 ) - ( isset( $a['login'] ) ? (int) $a['login'] : 0 ); } ); foreach ( $sessions as $s ) { if ( ! empty( $s['ip'] ) ) { $candidates[] = $s['ip']; } } } $keys = apply_filters( 'postaramail_ip_meta_keys', array( 'last_login_ip', 'registration_ip', 'user_registration_ip', 'ip_address', 'user_ip', '_user_ip', 'wc_last_ip' ) ); foreach ( (array) $keys as $key ) { $v = get_user_meta( $user_id, $key, true ); if ( is_string( $v ) && $v ) { $candidates[] = $v; } } foreach ( $candidates as $ip ) { $ip = trim( (string) $ip ); if ( filter_var( $ip, FILTER_VALIDATE_IP, FILTER_FLAG_NO_PRIV_RANGE | FILTER_FLAG_NO_RES_RANGE ) ) { return $ip; } } return ''; } private static function table_exists( $table ) { static $cache = array(); if ( ! isset( $cache[ $table ] ) ) { global $wpdb; $cache[ $table ] = ( $table === $wpdb->get_var( $wpdb->prepare( 'SHOW TABLES LIKE %s', $table ) ) ); // phpcs:ignore WordPress.DB } return $cache[ $table ]; } }