Merge branch 'master' of github.com:woothemes/woocommerce
This commit is contained in:
commit
4a6df7d7e1
|
@ -2,11 +2,11 @@
|
||||||
/**
|
/**
|
||||||
* Handles taxonomies in admin
|
* Handles taxonomies in admin
|
||||||
*
|
*
|
||||||
* @class WC_Admin_Taxonomies
|
* @class WC_Admin_Taxonomies
|
||||||
* @version 2.1.0
|
* @version 2.3.10
|
||||||
* @package WooCommerce/Admin
|
* @package WooCommerce/Admin
|
||||||
* @category Class
|
* @category Class
|
||||||
* @author WooThemes
|
* @author WooThemes
|
||||||
*/
|
*/
|
||||||
|
|
||||||
if ( ! defined( 'ABSPATH' ) ) {
|
if ( ! defined( 'ABSPATH' ) ) {
|
||||||
|
@ -58,7 +58,7 @@ class WC_Admin_Taxonomies {
|
||||||
* @param mixed $taxonomy
|
* @param mixed $taxonomy
|
||||||
*/
|
*/
|
||||||
public function create_term( $term_id, $tt_id = '', $taxonomy = '' ) {
|
public function create_term( $term_id, $tt_id = '', $taxonomy = '' ) {
|
||||||
if ( $taxonomy != 'product_cat' && ! taxonomy_is_product_attribute( $taxonomy ) ) {
|
if ( 'product_cat' != $taxonomy && ! taxonomy_is_product_attribute( $taxonomy ) ) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -98,8 +98,8 @@ class WC_Admin_Taxonomies {
|
||||||
</div>
|
</div>
|
||||||
<div class="form-field">
|
<div class="form-field">
|
||||||
<label><?php _e( 'Thumbnail', 'woocommerce' ); ?></label>
|
<label><?php _e( 'Thumbnail', 'woocommerce' ); ?></label>
|
||||||
<div id="product_cat_thumbnail" style="float:left;margin-right:10px;"><img src="<?php echo wc_placeholder_img_src(); ?>" width="60px" height="60px" /></div>
|
<div id="product_cat_thumbnail" style="float: left; margin-right: 10px;"><img src="<?php echo esc_url( wc_placeholder_img_src() ); ?>" width="60px" height="60px" /></div>
|
||||||
<div style="line-height:60px;">
|
<div style="line-height: 60px;">
|
||||||
<input type="hidden" id="product_cat_thumbnail_id" name="product_cat_thumbnail_id" />
|
<input type="hidden" id="product_cat_thumbnail_id" name="product_cat_thumbnail_id" />
|
||||||
<button type="button" class="upload_image_button button"><?php _e( 'Upload/Add image', 'woocommerce' ); ?></button>
|
<button type="button" class="upload_image_button button"><?php _e( 'Upload/Add image', 'woocommerce' ); ?></button>
|
||||||
<button type="button" class="remove_image_button button"><?php _e( 'Remove image', 'woocommerce' ); ?></button>
|
<button type="button" class="remove_image_button button"><?php _e( 'Remove image', 'woocommerce' ); ?></button>
|
||||||
|
@ -107,8 +107,8 @@ class WC_Admin_Taxonomies {
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
|
|
||||||
// Only show the "remove image" button when needed
|
// Only show the "remove image" button when needed
|
||||||
if ( ! jQuery('#product_cat_thumbnail_id').val() ) {
|
if ( ! jQuery( '#product_cat_thumbnail_id' ).val() ) {
|
||||||
jQuery('.remove_image_button').hide();
|
jQuery( '.remove_image_button' ).hide();
|
||||||
}
|
}
|
||||||
|
|
||||||
// Uploading files
|
// Uploading files
|
||||||
|
@ -126,30 +126,30 @@ class WC_Admin_Taxonomies {
|
||||||
|
|
||||||
// Create the media frame.
|
// Create the media frame.
|
||||||
file_frame = wp.media.frames.downloadable_file = wp.media({
|
file_frame = wp.media.frames.downloadable_file = wp.media({
|
||||||
title: '<?php _e( 'Choose an image', 'woocommerce' ); ?>',
|
title: '<?php _e( "Choose an image", "woocommerce" ); ?>',
|
||||||
button: {
|
button: {
|
||||||
text: '<?php _e( 'Use image', 'woocommerce' ); ?>',
|
text: '<?php _e( "Use image", "woocommerce" ); ?>'
|
||||||
},
|
},
|
||||||
multiple: false
|
multiple: false
|
||||||
});
|
});
|
||||||
|
|
||||||
// When an image is selected, run a callback.
|
// When an image is selected, run a callback.
|
||||||
file_frame.on( 'select', function() {
|
file_frame.on( 'select', function() {
|
||||||
attachment = file_frame.state().get('selection').first().toJSON();
|
var attachment = file_frame.state().get( 'selection' ).first().toJSON();
|
||||||
|
|
||||||
jQuery('#product_cat_thumbnail_id').val( attachment.id );
|
jQuery( '#product_cat_thumbnail_id' ).val( attachment.id );
|
||||||
jQuery('#product_cat_thumbnail img').attr('src', attachment.sizes.thumbnail.url );
|
jQuery( '#product_cat_thumbnail img' ).attr( 'src', attachment.sizes.thumbnail.url );
|
||||||
jQuery('.remove_image_button').show();
|
jQuery( '.remove_image_button' ).show();
|
||||||
});
|
});
|
||||||
|
|
||||||
// Finally, open the modal.
|
// Finally, open the modal.
|
||||||
file_frame.open();
|
file_frame.open();
|
||||||
});
|
});
|
||||||
|
|
||||||
jQuery( document ).on( 'click', '.remove_image_button', function( event ) {
|
jQuery( document ).on( 'click', '.remove_image_button', function() {
|
||||||
jQuery('#product_cat_thumbnail img').attr('src', '<?php echo wc_placeholder_img_src(); ?>');
|
jQuery( '#product_cat_thumbnail img' ).attr( 'src', '<?php echo esc_js( wc_placeholder_img_src() ); ?>' );
|
||||||
jQuery('#product_cat_thumbnail_id').val('');
|
jQuery( '#product_cat_thumbnail_id' ).val( '' );
|
||||||
jQuery('.remove_image_button').hide();
|
jQuery( '.remove_image_button' ).hide();
|
||||||
return false;
|
return false;
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -189,14 +189,19 @@ class WC_Admin_Taxonomies {
|
||||||
<tr class="form-field">
|
<tr class="form-field">
|
||||||
<th scope="row" valign="top"><label><?php _e( 'Thumbnail', 'woocommerce' ); ?></label></th>
|
<th scope="row" valign="top"><label><?php _e( 'Thumbnail', 'woocommerce' ); ?></label></th>
|
||||||
<td>
|
<td>
|
||||||
<div id="product_cat_thumbnail" style="float:left;margin-right:10px;"><img src="<?php echo $image; ?>" width="60px" height="60px" /></div>
|
<div id="product_cat_thumbnail" style="float: left; margin-right: 10px;"><img src="<?php echo esc_url( $image ); ?>" width="60px" height="60px" /></div>
|
||||||
<div style="line-height:60px;">
|
<div style="line-height: 60px;">
|
||||||
<input type="hidden" id="product_cat_thumbnail_id" name="product_cat_thumbnail_id" value="<?php echo $thumbnail_id; ?>" />
|
<input type="hidden" id="product_cat_thumbnail_id" name="product_cat_thumbnail_id" value="<?php echo $thumbnail_id; ?>" />
|
||||||
<button type="submit" class="upload_image_button button"><?php _e( 'Upload/Add image', 'woocommerce' ); ?></button>
|
<button type="button" class="upload_image_button button"><?php _e( 'Upload/Add image', 'woocommerce' ); ?></button>
|
||||||
<button type="submit" class="remove_image_button button"><?php _e( 'Remove image', 'woocommerce' ); ?></button>
|
<button type="button" class="remove_image_button button"><?php _e( 'Remove image', 'woocommerce' ); ?></button>
|
||||||
</div>
|
</div>
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
|
|
||||||
|
// Only show the "remove image" button when needed
|
||||||
|
if ( '0' === jQuery( '#product_cat_thumbnail_id' ).val() ) {
|
||||||
|
jQuery( '.remove_image_button' ).hide();
|
||||||
|
}
|
||||||
|
|
||||||
// Uploading files
|
// Uploading files
|
||||||
var file_frame;
|
var file_frame;
|
||||||
|
|
||||||
|
@ -212,30 +217,30 @@ class WC_Admin_Taxonomies {
|
||||||
|
|
||||||
// Create the media frame.
|
// Create the media frame.
|
||||||
file_frame = wp.media.frames.downloadable_file = wp.media({
|
file_frame = wp.media.frames.downloadable_file = wp.media({
|
||||||
title: '<?php _e( 'Choose an image', 'woocommerce' ); ?>',
|
title: '<?php _e( "Choose an image", "woocommerce" ); ?>',
|
||||||
button: {
|
button: {
|
||||||
text: '<?php _e( 'Use image', 'woocommerce' ); ?>',
|
text: '<?php _e( "Use image", "woocommerce" ); ?>'
|
||||||
},
|
},
|
||||||
multiple: false
|
multiple: false
|
||||||
});
|
});
|
||||||
|
|
||||||
// When an image is selected, run a callback.
|
// When an image is selected, run a callback.
|
||||||
file_frame.on( 'select', function() {
|
file_frame.on( 'select', function() {
|
||||||
attachment = file_frame.state().get('selection').first().toJSON();
|
var attachment = file_frame.state().get( 'selection' ).first().toJSON();
|
||||||
|
|
||||||
jQuery('#product_cat_thumbnail_id').val( attachment.id );
|
jQuery( '#product_cat_thumbnail_id' ).val( attachment.id );
|
||||||
jQuery('#product_cat_thumbnail img').attr('src', attachment.sizes.thumbnail.url );
|
jQuery( '#product_cat_thumbnail img' ).attr( 'src', attachment.sizes.thumbnail.url );
|
||||||
jQuery('.remove_image_button').show();
|
jQuery( '.remove_image_button' ).show();
|
||||||
});
|
});
|
||||||
|
|
||||||
// Finally, open the modal.
|
// Finally, open the modal.
|
||||||
file_frame.open();
|
file_frame.open();
|
||||||
});
|
});
|
||||||
|
|
||||||
jQuery( document ).on( 'click', '.remove_image_button', function( event ) {
|
jQuery( document ).on( 'click', '.remove_image_button', function() {
|
||||||
jQuery('#product_cat_thumbnail img').attr('src', '<?php echo wc_placeholder_img_src(); ?>');
|
jQuery( '#product_cat_thumbnail img' ).attr( 'src', '<?php echo esc_js( wc_placeholder_img_src() ); ?>' );
|
||||||
jQuery('#product_cat_thumbnail_id').val('');
|
jQuery( '#product_cat_thumbnail_id' ).val( '' );
|
||||||
jQuery('.remove_image_button').hide();
|
jQuery( '.remove_image_button' ).hide();
|
||||||
return false;
|
return false;
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
|
@ -29,12 +29,12 @@ if ( ! defined( 'ABSPATH' ) ) {
|
||||||
<tr>
|
<tr>
|
||||||
<td data-export-label="Home URL"><?php _e( 'Home URL', 'woocommerce' ); ?>:</td>
|
<td data-export-label="Home URL"><?php _e( 'Home URL', 'woocommerce' ); ?>:</td>
|
||||||
<td class="help"><?php echo '<a href="#" class="help_tip" data-tip="' . esc_attr__( 'The URL of your site\'s homepage.', 'woocommerce' ) . '">[?]</a>'; ?></td>
|
<td class="help"><?php echo '<a href="#" class="help_tip" data-tip="' . esc_attr__( 'The URL of your site\'s homepage.', 'woocommerce' ) . '">[?]</a>'; ?></td>
|
||||||
<td><?php echo home_url(); ?></td>
|
<td><?php form_option( 'home' ); ?></td>
|
||||||
</tr>
|
</tr>
|
||||||
<tr>
|
<tr>
|
||||||
<td data-export-label="Site URL"><?php _e( 'Site URL', 'woocommerce' ); ?>:</td>
|
<td data-export-label="Site URL"><?php _e( 'Site URL', 'woocommerce' ); ?>:</td>
|
||||||
<td class="help"><?php echo '<a href="#" class="help_tip" data-tip="' . esc_attr__( 'The root URL of your site.', 'woocommerce' ) . '">[?]</a>'; ?></td>
|
<td class="help"><?php echo '<a href="#" class="help_tip" data-tip="' . esc_attr__( 'The root URL of your site.', 'woocommerce' ) . '">[?]</a>'; ?></td>
|
||||||
<td><?php echo site_url(); ?></td>
|
<td><?php form_option( 'siteurl' ); ?></td>
|
||||||
</tr>
|
</tr>
|
||||||
<tr>
|
<tr>
|
||||||
<td data-export-label="WC Version"><?php _e( 'WC Version', 'woocommerce' ); ?>:</td>
|
<td data-export-label="WC Version"><?php _e( 'WC Version', 'woocommerce' ); ?>:</td>
|
||||||
|
|
|
@ -2045,6 +2045,8 @@ class WC_AJAX {
|
||||||
if ( $refund_id && 'shop_order_refund' === get_post_type( $refund_id ) ) {
|
if ( $refund_id && 'shop_order_refund' === get_post_type( $refund_id ) ) {
|
||||||
wc_delete_shop_order_transients( wp_get_post_parent_id( $refund_id ) );
|
wc_delete_shop_order_transients( wp_get_post_parent_id( $refund_id ) );
|
||||||
wp_delete_post( $refund_id );
|
wp_delete_post( $refund_id );
|
||||||
|
|
||||||
|
do_action( 'woocommerce_refund_deleted', $refund_id );
|
||||||
}
|
}
|
||||||
|
|
||||||
die();
|
die();
|
||||||
|
|
|
@ -64,33 +64,7 @@ class WC_Cache_Helper {
|
||||||
private static function delete_version_transients( $version ) {
|
private static function delete_version_transients( $version ) {
|
||||||
if ( ! wp_using_ext_object_cache() ) {
|
if ( ! wp_using_ext_object_cache() ) {
|
||||||
global $wpdb;
|
global $wpdb;
|
||||||
$wpdb->query( $wpdb->prepare( "
|
$wpdb->query( $wpdb->prepare( "DELETE FROM {$wpdb->options} WHERE option_name LIKE %s;", "\_transient\_%" . $version ) );
|
||||||
DELETE a, b
|
|
||||||
FROM {$wpdb->options} a, {$wpdb->options} b
|
|
||||||
WHERE
|
|
||||||
( a.option_name LIKE %s OR a.option_name LIKE %s ) AND
|
|
||||||
a.option_name NOT LIKE '\_transient\_timeout\_%%' AND
|
|
||||||
a.option_name NOT LIKE '\_site\_transient\_timeout\_%%' AND
|
|
||||||
(
|
|
||||||
b.option_name = CONCAT(
|
|
||||||
'_transient_timeout_',
|
|
||||||
SUBSTRING(
|
|
||||||
a.option_name,
|
|
||||||
CHAR_LENGTH('_transient_') + 1
|
|
||||||
)
|
|
||||||
) OR
|
|
||||||
b.option_name = CONCAT(
|
|
||||||
'_site_transient_timeout_',
|
|
||||||
SUBSTRING(
|
|
||||||
a.option_name,
|
|
||||||
CHAR_LENGTH('_site_transient_') + 1
|
|
||||||
)
|
|
||||||
)
|
|
||||||
)
|
|
||||||
",
|
|
||||||
"\_transient\_%" . $version,
|
|
||||||
"\_site\_transient\_%" . $version
|
|
||||||
) );
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -350,7 +350,7 @@ class WC_Coupon {
|
||||||
* Ensure coupon amount is valid or throw exception
|
* Ensure coupon amount is valid or throw exception
|
||||||
*/
|
*/
|
||||||
private function validate_maximum_amount() {
|
private function validate_maximum_amount() {
|
||||||
if ( $this->maximum_amount > 0 && wc_format_decimal( $this->minimum_amount ) < wc_format_decimal( WC()->cart->subtotal ) ) {
|
if ( $this->maximum_amount > 0 && wc_format_decimal( $this->maximum_amount ) < wc_format_decimal( WC()->cart->subtotal ) ) {
|
||||||
throw new Exception( self::E_WC_COUPON_MAX_SPEND_LIMIT_MET );
|
throw new Exception( self::E_WC_COUPON_MAX_SPEND_LIMIT_MET );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1395,6 +1395,60 @@ class WC_Geo_IP {
|
||||||
return $this->_common_get_record( $seek_country );
|
return $this->_common_get_record( $seek_country );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function _geoip_seek_country_v6( $ipnum ) {
|
||||||
|
// arrays from unpack start with offset 1
|
||||||
|
// yet another php mystery. array_merge work around
|
||||||
|
// this broken behaviour
|
||||||
|
$v6vec = array_merge( unpack( 'C16', $ipnum ) );
|
||||||
|
|
||||||
|
$offset = 0;
|
||||||
|
for ( $depth = 127; $depth >= 0; --$depth ) {
|
||||||
|
if ( $this->flags & self::GEOIP_MEMORY_CACHE ) {
|
||||||
|
$buf = $this->_safe_substr(
|
||||||
|
$this->memory_buffer,
|
||||||
|
2 * $this->record_length * $offset,
|
||||||
|
2 * $this->record_length
|
||||||
|
);
|
||||||
|
} elseif ( $this->flags & self::GEOIP_SHARED_MEMORY ) {
|
||||||
|
$buf = @shmop_read(
|
||||||
|
$this->shmid,
|
||||||
|
2 * $this->record_length * $offset,
|
||||||
|
2 * $this->record_length
|
||||||
|
);
|
||||||
|
} else {
|
||||||
|
fseek( $this->filehandle, 2 * $this->record_length * $offset, SEEK_SET ) == 0
|
||||||
|
or trigger_error( 'GeoIP API: fseek failed', E_USER_ERROR );
|
||||||
|
|
||||||
|
$buf = fread( $this->filehandle, 2 * $this->record_length );
|
||||||
|
}
|
||||||
|
$x = array( 0, 0 );
|
||||||
|
for ( $i = 0; $i < 2; ++$i ) {
|
||||||
|
for ( $j = 0; $j < $this->record_length; ++$j ) {
|
||||||
|
$x[ $i ] += ord( $buf[ $this->record_length * $i + $j ] ) << ( $j * 8 );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
$bnum = 127 - $depth;
|
||||||
|
$idx = $bnum >> 3;
|
||||||
|
$b_mask = 1 << ( $bnum & 7 ^ 7 );
|
||||||
|
if ( ( $v6vec[ $idx ] & $b_mask ) > 0 ) {
|
||||||
|
if ( $x[1] >= $this->databaseSegments ) {
|
||||||
|
return $x[1];
|
||||||
|
}
|
||||||
|
$offset = $x[1];
|
||||||
|
} else {
|
||||||
|
if ( $x[0] >= $this->databaseSegments ) {
|
||||||
|
return $x[0];
|
||||||
|
}
|
||||||
|
$offset = $x[0];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
trigger_error( 'GeoIP API: Error traversing database - perhaps it is corrupt?', E_USER_ERROR );
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
private function _geoip_seek_country( $ipnum ) {
|
private function _geoip_seek_country( $ipnum ) {
|
||||||
$offset = 0;
|
$offset = 0;
|
||||||
for ( $depth = 31; $depth >= 0; --$depth ) {
|
for ( $depth = 31; $depth >= 0; --$depth ) {
|
||||||
|
@ -1412,7 +1466,7 @@ class WC_Geo_IP {
|
||||||
);
|
);
|
||||||
} else {
|
} else {
|
||||||
fseek( $this->filehandle, 2 * $this->record_length * $offset, SEEK_SET ) == 0
|
fseek( $this->filehandle, 2 * $this->record_length * $offset, SEEK_SET ) == 0
|
||||||
or trigger_error( "GeoIP API: fseek failed", E_USER_ERROR );
|
or trigger_error( 'GeoIP API: fseek failed', E_USER_ERROR );
|
||||||
|
|
||||||
$buf = fread( $this->filehandle, 2 * $this->record_length );
|
$buf = fread( $this->filehandle, 2 * $this->record_length );
|
||||||
}
|
}
|
||||||
|
@ -1438,12 +1492,12 @@ class WC_Geo_IP {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
trigger_error( "GeoIP API: Error traversing database - perhaps it is corrupt?", E_USER_ERROR );
|
trigger_error( 'GeoIP API: Error traversing database - perhaps it is corrupt?', E_USER_ERROR );
|
||||||
|
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
function geoip_record_by_addr( $addr ) {
|
public function geoip_record_by_addr( $addr ) {
|
||||||
if ( $addr == null ) {
|
if ( $addr == null ) {
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
@ -1452,11 +1506,25 @@ class WC_Geo_IP {
|
||||||
return $this->_get_record( $ipnum );
|
return $this->_get_record( $ipnum );
|
||||||
}
|
}
|
||||||
|
|
||||||
function geoip_country_id_by_addr( $addr ) {
|
public function geoip_country_id_by_addr_v6( $addr ) {
|
||||||
|
$ipnum = inet_pton( $addr );
|
||||||
|
return $this->_geoip_seek_country_v6( $ipnum ) - self::GEOIP_COUNTRY_BEGIN;
|
||||||
|
}
|
||||||
|
|
||||||
|
public function geoip_country_id_by_addr( $addr ) {
|
||||||
$ipnum = ip2long( $addr );
|
$ipnum = ip2long( $addr );
|
||||||
return $this->_geoip_seek_country( $ipnum ) - self::GEOIP_COUNTRY_BEGIN;
|
return $this->_geoip_seek_country( $ipnum ) - self::GEOIP_COUNTRY_BEGIN;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public function geoip_country_code_by_addr_v6( $addr ) {
|
||||||
|
$country_id = $this->geoip_country_id_by_addr_v6( $addr );
|
||||||
|
if ( $country_id !== false ) {
|
||||||
|
return $this->GEOIP_COUNTRY_CODES[ $country_id ];
|
||||||
|
}
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
public function geoip_country_code_by_addr( $addr ) {
|
public function geoip_country_code_by_addr( $addr ) {
|
||||||
if ( $this->databaseType == self::GEOIP_CITY_EDITION_REV1 ) {
|
if ( $this->databaseType == self::GEOIP_CITY_EDITION_REV1 ) {
|
||||||
$record = $this->geoip_record_by_addr( $addr);
|
$record = $this->geoip_record_by_addr( $addr);
|
||||||
|
|
|
@ -9,7 +9,7 @@
|
||||||
* @author WooThemes
|
* @author WooThemes
|
||||||
* @category Admin
|
* @category Admin
|
||||||
* @package WooCommerce/Classes
|
* @package WooCommerce/Classes
|
||||||
* @version 2.3.0
|
* @version 2.4.0
|
||||||
*/
|
*/
|
||||||
|
|
||||||
if ( ! defined( 'ABSPATH' ) ) {
|
if ( ! defined( 'ABSPATH' ) ) {
|
||||||
|
@ -22,14 +22,15 @@ if ( ! defined( 'ABSPATH' ) ) {
|
||||||
class WC_Geolocation {
|
class WC_Geolocation {
|
||||||
|
|
||||||
/** URL to the geolocation database we're using */
|
/** URL to the geolocation database we're using */
|
||||||
const GEOLITE_DB = 'http://geolite.maxmind.com/download/geoip/database/GeoLiteCountry/GeoIP.dat.gz';
|
const GEOLITE_DB = 'http://geolite.maxmind.com/download/geoip/database/GeoLiteCountry/GeoIP.dat.gz';
|
||||||
|
const GEOLITE_IPV6_DB = 'http://geolite.maxmind.com/download/geoip/database/GeoIPv6.dat.gz';
|
||||||
|
|
||||||
/** @var array API endpoints for looking up user IP address */
|
/** @var array API endpoints for looking up user IP address */
|
||||||
private static $ip_lookup_apis = array(
|
private static $ip_lookup_apis = array(
|
||||||
'icanhazip' => 'http://ipv4.icanhazip.com',
|
'icanhazip' => 'http://icanhazip.com',
|
||||||
'ipify' => 'http://api.ipify.org/',
|
'ipify' => 'http://api.ipify.org/',
|
||||||
'ipecho' => 'http://ipecho.net/plain',
|
'ipecho' => 'http://ipecho.net/plain',
|
||||||
'ident' => 'http://v4.ident.me',
|
'ident' => 'http://ident.me',
|
||||||
'whatismyipaddress' => 'http://bot.whatismyipaddress.com',
|
'whatismyipaddress' => 'http://bot.whatismyipaddress.com',
|
||||||
'ip.appspot' => 'http://ip.appspot.com'
|
'ip.appspot' => 'http://ip.appspot.com'
|
||||||
);
|
);
|
||||||
|
@ -119,12 +120,18 @@ class WC_Geolocation {
|
||||||
*/
|
*/
|
||||||
public static function geolocate_ip( $ip_address = '', $fallback = true ) {
|
public static function geolocate_ip( $ip_address = '', $fallback = true ) {
|
||||||
// If GEOIP is enabled in CloudFlare, we can use that (Settings -> CloudFlare Settings -> Settings Overview)
|
// If GEOIP is enabled in CloudFlare, we can use that (Settings -> CloudFlare Settings -> Settings Overview)
|
||||||
if ( ! empty( $_SERVER[ "HTTP_CF_IPCOUNTRY" ] ) ) {
|
if ( ! empty( $_SERVER['HTTP_CF_IPCOUNTRY'] ) ) {
|
||||||
$country_code = sanitize_text_field( strtoupper( $_SERVER["HTTP_CF_IPCOUNTRY"] ) );
|
$country_code = sanitize_text_field( strtoupper( $_SERVER['HTTP_CF_IPCOUNTRY'] ) );
|
||||||
} else {
|
} else {
|
||||||
$ip_address = $ip_address ? $ip_address : self::get_ip_address();
|
$ip_address = $ip_address ? $ip_address : self::get_ip_address();
|
||||||
|
|
||||||
if ( file_exists( self::get_local_database_path() ) ) {
|
if ( self::is_IPv6( $ip_address ) ) {
|
||||||
|
$database = self::get_local_database_path( 'v6' );
|
||||||
|
} else {
|
||||||
|
$database = self::get_local_database_path();
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( file_exists( $database ) ) {
|
||||||
$country_code = self::geolocate_via_db( $ip_address );
|
$country_code = self::geolocate_via_db( $ip_address );
|
||||||
} else {
|
} else {
|
||||||
$country_code = self::geolocate_via_api( $ip_address );
|
$country_code = self::geolocate_via_api( $ip_address );
|
||||||
|
@ -144,11 +151,14 @@ class WC_Geolocation {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Path to our local db
|
* Path to our local db
|
||||||
|
* @param string $version
|
||||||
* @return string
|
* @return string
|
||||||
*/
|
*/
|
||||||
private static function get_local_database_path() {
|
private static function get_local_database_path( $version = 'v4' ) {
|
||||||
|
$version = ( 'v4' == $version ) ? '' : 'v6';
|
||||||
$upload_dir = wp_upload_dir();
|
$upload_dir = wp_upload_dir();
|
||||||
return $upload_dir['basedir'] . '/GeoIP.dat';
|
|
||||||
|
return $upload_dir['basedir'] . '/GeoIP' . $version . '.dat';
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -164,24 +174,29 @@ class WC_Geolocation {
|
||||||
|
|
||||||
require_once( ABSPATH . 'wp-admin/includes/file.php' );
|
require_once( ABSPATH . 'wp-admin/includes/file.php' );
|
||||||
|
|
||||||
$tmp_database = download_url( self::GEOLITE_DB );
|
$tmp_databases = array(
|
||||||
|
'v4' => download_url( self::GEOLITE_DB ),
|
||||||
|
'v6' => download_url( self::GEOLITE_IPV6_DB )
|
||||||
|
);
|
||||||
|
|
||||||
if ( ! is_wp_error( $tmp_database ) ) {
|
foreach ( $tmp_databases as $tmp_database_version => $tmp_database_path ) {
|
||||||
$gzhandle = @gzopen( $tmp_database, 'r' );
|
if ( ! is_wp_error( $tmp_database_path ) ) {
|
||||||
$handle = @fopen( self::get_local_database_path(), 'w' );
|
$gzhandle = @gzopen( $tmp_database_path, 'r' );
|
||||||
|
$handle = @fopen( self::get_local_database_path( $tmp_database_version ), 'w' );
|
||||||
|
|
||||||
if ( $gzhandle && $handle ) {
|
if ( $gzhandle && $handle ) {
|
||||||
while ( ( $string = gzread( $gzhandle, 4096 ) ) != false ) {
|
while ( ( $string = gzread( $gzhandle, 4096 ) ) != false ) {
|
||||||
fwrite( $handle, $string, strlen( $string ) );
|
fwrite( $handle, $string, strlen( $string ) );
|
||||||
|
}
|
||||||
|
gzclose( $gzhandle );
|
||||||
|
fclose( $handle );
|
||||||
|
} else {
|
||||||
|
$logger->add( 'geolocation', 'Unable to open database file' );
|
||||||
}
|
}
|
||||||
gzclose( $gzhandle );
|
@unlink( $tmp_database_path );
|
||||||
fclose( $handle );
|
|
||||||
} else {
|
} else {
|
||||||
$logger->add( 'geolocation', 'Unable to open database file' );
|
$logger->add( 'geolocation', 'Unable to download GeoIP Database: ' . $tmp_database_path->get_error_message() );
|
||||||
}
|
}
|
||||||
@unlink( $tmp_database );
|
|
||||||
} else {
|
|
||||||
$logger->add( 'geolocation', 'Unable to download GeoIP Database: ' . $tmp_database->get_error_message() );
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -194,11 +209,19 @@ class WC_Geolocation {
|
||||||
if ( ! class_exists( 'WC_Geo_IP' ) ) {
|
if ( ! class_exists( 'WC_Geo_IP' ) ) {
|
||||||
include_once( 'class-wc-geo-ip.php' );
|
include_once( 'class-wc-geo-ip.php' );
|
||||||
}
|
}
|
||||||
$database = self::get_local_database_path();
|
|
||||||
$gi = new WC_Geo_IP();
|
|
||||||
|
|
||||||
$gi->geoip_open( $database, 0 );
|
$gi = new WC_Geo_IP();
|
||||||
$country_code = $gi->geoip_country_code_by_addr( $ip_address );
|
|
||||||
|
if ( self::is_IPv6( $ip_address ) ) {
|
||||||
|
$database = self::get_local_database_path( 'v6' );
|
||||||
|
$gi->geoip_open( $database, 0 );
|
||||||
|
$country_code = $gi->geoip_country_code_by_addr_v6( $ip_address );
|
||||||
|
} else {
|
||||||
|
$database = self::get_local_database_path();
|
||||||
|
$gi->geoip_open( $database, 0 );
|
||||||
|
$country_code = $gi->geoip_country_code_by_addr( $ip_address );
|
||||||
|
}
|
||||||
|
|
||||||
$gi->geoip_close();
|
$gi->geoip_close();
|
||||||
|
|
||||||
return sanitize_text_field( strtoupper( $country_code ) );
|
return sanitize_text_field( strtoupper( $country_code ) );
|
||||||
|
@ -250,6 +273,18 @@ class WC_Geolocation {
|
||||||
|
|
||||||
return $country_code;
|
return $country_code;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Test if is IPv6
|
||||||
|
*
|
||||||
|
* @since 2.4.0
|
||||||
|
*
|
||||||
|
* @param string $ip_address
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
|
private static function is_IPv6( $ip_address ) {
|
||||||
|
return false !== filter_var( $ip_address, FILTER_VALIDATE_IP, FILTER_FLAG_IPV6 );
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
WC_Geolocation::init();
|
WC_Geolocation::init();
|
||||||
|
|
|
@ -72,6 +72,10 @@ if ( ! comments_open() ) {
|
||||||
'comment_field' => ''
|
'comment_field' => ''
|
||||||
);
|
);
|
||||||
|
|
||||||
|
if ( $account_page_url = wc_get_page_permalink( 'myaccount' ) ) {
|
||||||
|
$comment_form['must_log_in'] = '<p class="must-log-in">' . sprintf( __( 'You must be <a href="%s">logged in</a> to post a review.' ), esc_url( $account_page_url ) ) . '</p>';
|
||||||
|
}
|
||||||
|
|
||||||
if ( get_option( 'woocommerce_enable_review_rating' ) === 'yes' ) {
|
if ( get_option( 'woocommerce_enable_review_rating' ) === 'yes' ) {
|
||||||
$comment_form['comment_field'] = '<p class="comment-form-rating"><label for="rating">' . __( 'Your Rating', 'woocommerce' ) .'</label><select name="rating" id="rating">
|
$comment_form['comment_field'] = '<p class="comment-form-rating"><label for="rating">' . __( 'Your Rating', 'woocommerce' ) .'</label><select name="rating" id="rating">
|
||||||
<option value="">' . __( 'Rate…', 'woocommerce' ) . '</option>
|
<option value="">' . __( 'Rate…', 'woocommerce' ) . '</option>
|
||||||
|
|
|
@ -62,7 +62,7 @@ global $product, $post;
|
||||||
?>
|
?>
|
||||||
</select> <?php
|
</select> <?php
|
||||||
if ( sizeof( $attributes ) === $loop ) {
|
if ( sizeof( $attributes ) === $loop ) {
|
||||||
echo '<a class="reset_variations" href="#reset">' . __( 'Clear selection', 'woocommerce' ) . '</a>';
|
echo '<a class="reset_variations" href="#">' . __( 'Clear selection', 'woocommerce' ) . '</a>';
|
||||||
}
|
}
|
||||||
?></td>
|
?></td>
|
||||||
</tr>
|
</tr>
|
||||||
|
|
Loading…
Reference in New Issue