【问题标题】:If cookie exists read and set it's value to a variable in Woocommerce如果 cookie 存在,则读取并将其值设置为 Woocommerce 中的变量
【发布时间】:2021-05-31 08:14:15
【问题描述】:

我在 Woocommerce 商店中创建了两个自定义函数。这个想法是将某种类型的产品限制为最多 3 个。我想设置一个 cookie 一周,以防止同一客户购买更多相同类型的产品。因此,如果客户今天购买了 1 个,那么在接下来的 6 天内,他们仍然可以再购买 2 个,直到 cookie 过期。但 3 永远是最大值。

该功能的工作原理是,如果在一个会话中将超过 3 个项目添加到购物篮中,它将设置一个限制,并且结帐后 cookie 仍然存在。我的预感是它没有在正确的时间被读取,或者被传递给检查它是否存在的函数。

    function filter_woocommerce_add_to_cart_validation( $true, $product_id, $request_quantity, $variation_id = '', $request_variation = '' ) {
        // holds checks for all products in cart to see if they're in our category
        $lpc_cookie = $_COOKIE['lpc'];

        if ( isset( $lpc_cookie ) ) {
            $category_checks = $lpc_cookie;
        } else {
            $category_checks = 0;
        }

        $limited_product_count = 4;
        $limited_slug = 'instant-print'; //replace 'instant-print' with your category's slug

        // check each cart item for our category
        if( ! is_admin() ) {
            foreach ( WC()->cart->get_cart() as $cart_item_key => $cart_item ) {
                $product = $cart_item['data'];

                if ( has_term( $limited_slug, 'product_cat', $product->id ) ) {
                    $category_checks += $cart_item['quantity'];
                }
            }
        }

        // We also check the item that the user is trying to add to cart
        if ( has_term( $limited_slug, 'product_cat', $product_id ) ) {
            $category_checks += $request_quantity;
        }

        if ($category_checks >= $limited_product_count) {
            $notice = 'Sorry, you have reached the maximum amount for this type of product that you can purchase during this period.';
            wc_add_notice( __( $notice, 'textdomain' ), 'error' );
            return false;
        }

        return $true;
    };

    add_filter( 'woocommerce_add_to_cart_validation', 'filter_woocommerce_add_to_cart_validation', 10, 3 );

    function set_cookie_for_limited_products () {
        $limited_slug = 'instant-print'; //replace 'instant-print' with your category's slug
        // check each cart item for our category
        if( ! is_admin() ) {
            foreach ( WC()->cart->get_cart() as $cart_item_key => $cart_item ) {
                $product = $cart_item['data'];

                if ( has_term( $limited_slug, 'product_cat', $product->id ) ) {
                    $category_checks += $cart_item['quantity'];
                }
            }
        }

        // $expire = time() + 60 * 60 * 24 * 7; // expires in one week
        $expire = time() + 60 * 60; // expires in one hour
        setcookie('lpc', $category_checks, $expire);
    }

    add_filter( 'woocommerce_before_checkout_form', 'set_cookie_for_limited_products' );

我希望这是显而易见的。最初我试图 echo 和 var_dump 变量,但我发现这会导致其他东西中断。

【问题讨论】:

  • 为什么要把这个放在cookies里???如果用户决定只打开其他浏览器或使用“新私人窗口”怎么办?为什么不在数据库中插入与用户相关的购买,并检查用户是否通过数据库查询购买......
  • @lharby 客户必须在商店注册?如果是这样,您应该实现与用户一起存储,如果您强制客户端注册,我可以帮助您,使用 cookie 不是一个好主意
  • @DanielRiera 这是我目前的设置,imgur.com/m5DAs0G 所以你是说我应该禁用访客结帐?我不想让人们停止订购。我知道 cookie 有缺陷,但我也不知道如何读取或写入任何数据库查询。
  • @lharby 检查我的答案 :)
  • 哦,我更喜欢同时使用这两个选项的想法。我稍后会尝试检查并回复您。谢谢。

标签: php wordpress cookies woocommerce


【解决方案1】:

这很简单,我可以举个例子,但是如果客人可以购买,你将无法保存该信息,这是一个考虑了两种可能情况的例子。

function filter_woocommerce_add_to_cart_validation( $true, $product_id, $request_quantity, $variation_id = '', $request_variation = '' ) {
        // holds checks for all products in cart to see if they're in our category

        $limited_product_count = 4;
        $limited_slug = 'instant-print'; //replace 'instant-print' with your category's slug

        if(is_user_logged_in()) {
            //Using database
            $user_id = get_current_user_id();
            $lpc_cookie = get_user_meta( $user_id, $limited_slug, true );
            $expire = get_user_meta( $user_id, $limited_slug . '_expire', true );
        }else{
            //Using cookie
            $lpc_cookie = $_COOKIE['lpc'];
        }

        //Check lpc_cookie and expire value
        if ( isset( $lpc_cookie ) && $expire > time() ) {
            $category_checks = $lpc_cookie;
        } else {
            $category_checks = 0;
        }

        

        // check each cart item for our category
        if( ! is_admin() ) {
            foreach ( WC()->cart->get_cart() as $cart_item_key => $cart_item ) {
                $product = $cart_item['data'];

                if ( has_term( $limited_slug, 'product_cat', $product->id ) ) {
                    $category_checks += $cart_item['quantity'];
                }
            }
        }

        // We also check the item that the user is trying to add to cart
        if ( has_term( $limited_slug, 'product_cat', $product_id ) ) {
            $category_checks += $request_quantity;
        }

        if ($category_checks >= $limited_product_count) {
            $notice = 'Sorry, you have reached the maximum amount for this type of product that you can purchase during this period.';
            wc_add_notice( __( $notice, 'textdomain' ), 'error' );
            return false;
        }

        return $true;
    };

    add_filter( 'woocommerce_add_to_cart_validation', 'filter_woocommerce_add_to_cart_validation', 10, 3 );

    function set_cookie_for_limited_products () {
        $limited_slug = 'instant-print'; //replace 'instant-print' with your category's slug
        // check each cart item for our category
        if( ! is_admin() ) {
            foreach ( WC()->cart->get_cart() as $cart_item_key => $cart_item ) {
                $product = $cart_item['data'];

                if ( has_term( $limited_slug, 'product_cat', $product->id ) ) {
                    $category_checks += $cart_item['quantity'];
                }
            }
        }

        // $expire = time() + 60 * 60 * 24 * 7; // expires in one week
        $expire = time() + 60 * 60; // expires in one hour

        if(is_user_logged_in()) {
            //Using database
            $user_id = get_current_user_id();
            update_user_meta( $user_id, $limited_slug, $category_checks );
            update_user_meta( $user_id, $limited_slug . '_expire', $expire );
        }else{
            //Using cookie
            setcookie('lpc', $category_checks, $expire);
        }
    }

    add_filter( 'woocommerce_before_checkout_form', 'set_cookie_for_limited_products' );

【讨论】:

  • 嗯,这就是我要走的方向。我的问题和上面一样。为了复制它,我退出了 WP。买了两件,退房了。然后回到新的会话。在我看来,这意味着现在我只能将有限类别中的 1 件商品添加到我的购物车中,因为 cookie(或 get_user_meta)应该设置为 2,但商店页面上没有读取它。所以这永远不会被设置$category_checks = $lpc_cookie;,我不知道如何解决这个问题,测试这似乎也很困难。
  • 也许我需要一个不同于 filter_woocommerce_add_to_cart_validation 的函数来检查 cookie/db 值是否存在于所有商店页面中(尽管在我看来这应该足够了)
  • 检查您的数据库,如果您的用户 ID 上存在 prefix_usermeta 即时打印 meta_key
  • 是的,它确实存在,请参阅imgur.com/0SOXvwU,但无论哪种方式,它都不会通过 db 值或 cookie 值传递给 $category_checks
  • 嗯,我可能此时已经注销,然后使用 cookie 方法进行了结帐,但我希望这是通过一种方法或另一种方法设置的。在一个新的会话中,尽管设置了 db 和/或 cookie,它仍然可以让我将另外 3 个产品添加到购物篮中。我打算建议继续聊天,但我似乎没有这个选项。 chat.stackoverflow.com/?tab=site&host=stackoverflow.com
猜你喜欢
  • 1970-01-01
  • 2018-10-05
  • 2019-08-27
  • 1970-01-01
  • 2014-05-17
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多