为Woocommerce cookie添加安全属性

我试图让我们的服务器PCI兼容,并设置Woocommerce cookie的最后一个问题,以确保安全。 我正在运行Wordpress / Woocommerce的所有当前版本,并且服务器在整个站点上运行100%SSL / HTTPS。

我想要保护的cookies: woocommerce_recently_viewed

我已经尝试了以下没有运气:

添加到我的函数文件中:

 add_filter( 'wc_session_use_secure_cookie', '__return_true' ); 

添加到index.php中:

 @ini_set('session.cookie_httponly', 'On'); @ini_set('session.cookie_secure', 'On'); @ini_set('session.use_only_cookies', 'On'); 

添加到php.ini中:

 session.cookie_httponly = 1 session.cookie_secure = 1 session.use_only_cookies = 1 

我最后的手段是调整服务器configuration(我正在运行的Nginx),但宁愿处理这个问题的应用程序级别。 任何有关这个问题的帮助将不胜感激。

首先要做的是: woocommerce_recently_viewed不是PHP意义上的“会话cookie”。 这是使用setcookie PHP函数创建的普通cookie。

这意味着ini_setwc_session_use_secure_cookie都不会改变这种行为。

我已经下载了WooCommerce源代码,发现woocommerce\includes\wc-product-functions.php

 /** * Track product views. */ function wc_track_product_view() { if ( ! is_singular( 'product' ) || ! is_active_widget( false, false, 'woocommerce_recently_viewed_products', true ) ) { return; } global $post; if ( empty( $_COOKIE['woocommerce_recently_viewed'] ) ) $viewed_products = array(); else $viewed_products = (array) explode( '|', $_COOKIE['woocommerce_recently_viewed'] ); if ( ! in_array( $post->ID, $viewed_products ) ) { $viewed_products[] = $post->ID; } if ( sizeof( $viewed_products ) > 15 ) { array_shift( $viewed_products ); } // Store for session only wc_setcookie( 'woocommerce_recently_viewed', implode( '|', $viewed_products ) ); } add_action( 'template_redirect', 'wc_track_product_view', 20 ); 

wc_setcookie定义如下( woocommerce\includes\wc-core-functions.php ):

 /** * Set a cookie - wrapper for setcookie using WP constants. * * @param string $name Name of the cookie being set. * @param string $value Value of the cookie. * @param integer $expire Expiry of the cookie. * @param string $secure Whether the cookie should be served only over https. */ function wc_setcookie( $name, $value, $expire = 0, $secure = false ) { if ( ! headers_sent() ) { setcookie( $name, $value, $expire, COOKIEPATH ? COOKIEPATH : '/', COOKIE_DOMAIN, $secure ); } elseif ( defined( 'WP_DEBUG' ) && WP_DEBUG ) { headers_sent( $file, $line ); trigger_error( "{$name} cookie cannot be set - headers already sent by {$file} on line {$line}", E_USER_NOTICE ); } } 

正如你所看到的,没有任何WordPress的过滤器(真的应该是一个设置,请求一个功能请求!),所以你需要添加$secure参数到woocommerce来源…

…但还有另外一种方式(有点像猴子补丁,但是嘿,至少我们不会在更新的时候破坏东西):

 function custom_wc_track_product_view() { if ( ! is_singular( 'product' ) || ! is_active_widget( false, false, 'woocommerce_recently_viewed_products', true ) ) { return; } global $post; if ( empty( $_COOKIE['woocommerce_recently_viewed'] ) ) $viewed_products = array(); else $viewed_products = (array) explode( '|', $_COOKIE['woocommerce_recently_viewed'] ); if ( ! in_array( $post->ID, $viewed_products ) ) { $viewed_products[] = $post->ID; } if ( sizeof( $viewed_products ) > 15 ) { array_shift( $viewed_products ); } // Store for session only wc_setcookie( 'woocommerce_recently_viewed', implode( '|', $viewed_products ), 0, true ); } remove_action( 'template_redirect', 'wc_track_product_view', 20 ); add_action( 'template_redirect', 'custom_wc_track_product_view', 20 ); 

我已经复制了另一个名字的功能,做了我需要的改变,然后我用我的原来的钩子代替。 把这个代码放在一个新的插件或主题functions.php

可惜的是,没有WooCommerce协作,没有更好的办法。