/** * AJAX apply coupon on checkout page */ public function apply_coupon() { check_ajax_referer('apply-coupon', 'security'); if (!empty($_POST['coupon_code'])) { WC()->cart->add_discount(sanitize_text_field($_POST['coupon_code'])); } else { wc_add_notice(WC_Coupon::get_generic_coupon_error(WC_Coupon::E_WC_COUPON_PLEASE_ENTER), 'error'); } wc_print_notices(); die; }
/** * Apply sign up fee or recurring fee discount before tax is calculated * * * @since 1.2 */ public static function apply_subscription_discount_before_tax($original_price, $product, $cart) { global $woocommerce; if (!WC_Subscriptions_Product::is_subscription($product['product_id'])) { return $original_price; } $price = $original_price; if (!empty($cart->applied_coupons)) { foreach ($cart->applied_coupons as $code) { $coupon = new WC_Coupon($code); if ($coupon->apply_before_tax() && $coupon->is_valid()) { // Sign up fee discount if ('sign_up_fee' == WC_Subscriptions_Cart::get_recalculation_type() && 'sign_up_fee' == $coupon->type || 'base_recurring_fee' == WC_Subscriptions_Cart::get_recalculation_type() && 'recurring_fee' == $coupon->type || 0 == WC_Subscriptions_Cart::get_cart_subscription_sign_up_fee() && 'recurring_fee' == $coupon->type) { if ($original_price < $coupon->amount) { $discount_amount = $original_price; } else { $discount_amount = $coupon->amount; } $price = $original_price - $coupon->amount; if ($price < 0) { $price = 0; } // add to discount totals $woocommerce->cart->discount_cart = $woocommerce->cart->discount_cart + $discount_amount * $product['quantity']; } } } } return $price; }
/** * Prepare a single coupon output for response. * * @param WP_Post $post Post object. * @param WP_REST_Request $request Request object. * @return WP_REST_Response $data */ public function prepare_item_for_response($post, $request) { global $wpdb; // Get the coupon code. $code = $wpdb->get_var($wpdb->prepare("SELECT post_title FROM {$wpdb->posts} WHERE id = %s AND post_type = 'shop_coupon' AND post_status = 'publish'", $post->ID)); $coupon = new WC_Coupon($code); $data = array('id' => $coupon->id, 'code' => $coupon->code, 'date_created' => wc_rest_prepare_date_response($post->post_date_gmt), 'date_modified' => wc_rest_prepare_date_response($post->post_modified_gmt), 'discount_type' => $coupon->type, 'description' => $post->post_excerpt, 'amount' => wc_format_decimal($coupon->coupon_amount, 2), 'expiry_date' => !empty($coupon->expiry_date) ? wc_rest_prepare_date_response($coupon->expiry_date) : null, 'usage_count' => (int) $coupon->usage_count, 'individual_use' => 'yes' === $coupon->individual_use, 'product_ids' => array_map('absint', (array) $coupon->product_ids), 'exclude_product_ids' => array_map('absint', (array) $coupon->exclude_product_ids), 'usage_limit' => !empty($coupon->usage_limit) ? $coupon->usage_limit : null, 'usage_limit_per_user' => !empty($coupon->usage_limit_per_user) ? $coupon->usage_limit_per_user : null, 'limit_usage_to_x_items' => (int) $coupon->limit_usage_to_x_items, 'free_shipping' => $coupon->enable_free_shipping(), 'product_categories' => array_map('absint', (array) $coupon->product_categories), 'excluded_product_categories' => array_map('absint', (array) $coupon->exclude_product_categories), 'exclude_sale_items' => $coupon->exclude_sale_items(), 'minimum_amount' => wc_format_decimal($coupon->minimum_amount, 2), 'maximum_amount' => wc_format_decimal($coupon->maximum_amount, 2), 'email_restrictions' => $coupon->customer_email, 'used_by' => $coupon->get_used_by()); $context = !empty($request['context']) ? $request['context'] : 'view'; $data = $this->add_additional_fields_to_object($data, $request); $data = $this->filter_response_by_context($data, $context); // Wrap the data in a response object. $response = rest_ensure_response($data); $response->add_links($this->prepare_links($post)); /** * Filter the data for a response. * * The dynamic portion of the hook name, $this->post_type, refers to post_type of the post being * prepared for the response. * * @param WP_REST_Response $response The response object. * @param WP_Post $post Post object. * @param WP_REST_Request $request Request object. */ return apply_filters("woocommerce_rest_prepare_{$this->post_type}", $response, $post, $request); }
/** * Automatically apply coupons. * * Also removes auto-apply coupons (although that should happen * automatically, it seems we're on the safer side doing that as well * here). */ public static function wp_init() { global $wpdb, $woocommerce; if (isset($woocommerce) && isset($woocommerce->cart) && $woocommerce->cart->coupons_enabled()) { $coupons = $wpdb->get_results("SELECT DISTINCT ID, post_title FROM {$wpdb->posts} LEFT JOIN {$wpdb->postmeta} ON {$wpdb->posts}.ID = {$wpdb->postmeta}.post_id WHERE {$wpdb->posts}.post_status = 'publish' AND {$wpdb->postmeta}.meta_key = '_vd_auto'"); if ($coupons && count($coupons) > 0) { foreach ($coupons as $coupon) { $coupon_code = $coupon->post_title; $coupon = new WC_Coupon($coupon_code); if ($coupon->id) { if ($coupon->is_valid()) { if (!$woocommerce->cart->has_discount($coupon_code)) { $woocommerce->cart->add_discount($coupon_code); $msg = ''; $message = get_post_meta($coupon->id, '_vd_auto_message_display', true); $show_description = get_post_meta($coupon->id, '_vd_auto_description_display', true) == 'yes'; $show_info = get_post_meta($coupon->id, '_vd_auto_info_display', true) == 'yes'; if (!empty($message)) { $msg .= sprintf('<div class="coupon display message %s">', wp_strip_all_tags($coupon->code)); $msg .= stripslashes(wp_filter_kses($message)); $msg .= '</div>'; } if ($show_description) { if ($post = get_post($coupon->id)) { if (!empty($post->post_excerpt)) { $msg .= sprintf('<div class="coupon display description %s">', wp_strip_all_tags($coupon->code)); $msg .= stripslashes(wp_filter_kses($post->post_excerpt)); $msg .= '</div>'; } } } if ($show_info) { $msg .= sprintf('<div class="coupon display volume-discount %s">', wp_strip_all_tags($coupon->code)); $msg .= WooCommerce_Volume_Discount_Coupons_Shortcodes::get_volume_discount_info($coupon); $msg .= '</div>'; } if (!empty($msg)) { $woocommerce->add_message($msg); } } } else { if ($woocommerce->cart->has_discount($coupon_code)) { if (!empty($woocommerce->cart->applied_coupons)) { foreach ($woocommerce->cart->applied_coupons as $index => $code) { if ($coupon_code == $code) { unset($woocommerce->cart->applied_coupons[$index]); } } } } } } } } } }
/** * Get the coupon for the given ID * * @since 2.1 * @param int $id the coupon ID * @param string $fields fields to include in response * @return array|WP_Error */ public function get_coupon($id, $fields = null) { try { $id = $this->validate_request($id, 'shop_coupon', 'read'); if (is_wp_error($id)) { return $id; } $coupon = new WC_Coupon($id); if (0 === $coupon->get_id()) { throw new WC_API_Exception('woocommerce_api_invalid_coupon_id', __('Invalid coupon ID', 'woocommerce'), 404); } $coupon_data = array('id' => $coupon->get_id(), 'code' => $coupon->get_code(), 'type' => $coupon->get_discount_type(), 'created_at' => $this->server->format_datetime($coupon->get_date_created(), false, true), 'updated_at' => $this->server->format_datetime($coupon->get_date_modified(), false, true), 'amount' => wc_format_decimal($coupon->get_amount(), 2), 'individual_use' => $coupon->get_individual_use(), 'product_ids' => array_map('absint', (array) $coupon->get_product_ids()), 'exclude_product_ids' => array_map('absint', (array) $coupon->get_excluded_product_ids()), 'usage_limit' => $coupon->get_usage_limit() ? $coupon->get_usage_limit() : null, 'usage_limit_per_user' => $coupon->get_usage_limit_per_user() ? $coupon->get_usage_limit_per_user() : null, 'limit_usage_to_x_items' => (int) $coupon->get_limit_usage_to_x_items(), 'usage_count' => (int) $coupon->get_usage_count(), 'expiry_date' => $coupon->get_date_expires() ? $this->server->format_datetime($coupon->get_date_expires()) : null, 'enable_free_shipping' => $coupon->get_free_shipping(), 'product_category_ids' => array_map('absint', (array) $coupon->get_product_categories()), 'exclude_product_category_ids' => array_map('absint', (array) $coupon->get_excluded_product_categories()), 'exclude_sale_items' => $coupon->get_exclude_sale_items(), 'minimum_amount' => wc_format_decimal($coupon->get_minimum_amount(), 2), 'maximum_amount' => wc_format_decimal($coupon->get_maximum_amount(), 2), 'customer_emails' => $coupon->get_email_restrictions(), 'description' => $coupon->get_description()); return array('coupon' => apply_filters('woocommerce_api_coupon_response', $coupon_data, $coupon, $fields, $this->server)); } catch (WC_API_Exception $e) { return new WP_Error($e->getErrorCode(), $e->getMessage(), array('status' => $e->getCode())); } }
/** * Output the cart shortcode. * * @access public * @param array $atts * @return void */ public static function output($atts) { global $woocommerce; if (!defined('WOOCOMMERCE_CART')) { define('WOOCOMMERCE_CART', true); } // Add Discount if (!empty($_POST['apply_coupon'])) { if (!empty($_POST['coupon_code'])) { $woocommerce->cart->add_discount(sanitize_text_field($_POST['coupon_code'])); } else { $woocommerce->add_error(WC_Coupon::get_generic_coupon_error(WC_Coupon::E_WC_COUPON_PLEASE_ENTER)); } // Remove Coupon Codes } elseif (isset($_GET['remove_discounts'])) { $woocommerce->cart->remove_coupons($_GET['remove_discounts']); // Update Shipping } elseif (!empty($_POST['calc_shipping']) && $woocommerce->verify_nonce('cart')) { $validation = $woocommerce->validation(); $woocommerce->shipping->reset_shipping(); $woocommerce->customer->calculated_shipping(true); $country = woocommerce_clean($_POST['calc_shipping_country']); $state = woocommerce_clean($_POST['calc_shipping_state']); $postcode = apply_filters('woocommerce_shipping_calculator_enable_postcode', true) ? woocommerce_clean($_POST['calc_shipping_postcode']) : ''; $city = apply_filters('woocommerce_shipping_calculator_enable_city', false) ? woocommerce_clean($_POST['calc_shipping_city']) : ''; if ($postcode && !$validation->is_postcode($postcode, $country)) { $woocommerce->add_error(__('Please enter a valid postcode/ZIP.', 'woocommerce')); $postcode = ''; } elseif ($postcode) { $postcode = $validation->format_postcode($postcode, $country); } if ($country) { // Update customer location $woocommerce->customer->set_location($country, $state, $postcode, $city); $woocommerce->customer->set_shipping_location($country, $state, $postcode, $city); $woocommerce->add_message(__('Shipping costs updated.', 'woocommerce')); } else { $woocommerce->customer->set_to_base(); $woocommerce->customer->set_shipping_to_base(); $woocommerce->add_message(__('Shipping costs updated.', 'woocommerce')); } do_action('woocommerce_calculated_shipping'); } // Check cart items are valid do_action('woocommerce_check_cart_items'); // Calc totals $woocommerce->cart->calculate_totals(); if (sizeof($woocommerce->cart->get_cart()) == 0) { //woocommerce_get_template( 'cart/cart-empty.php' ); woocommerce_get_template('checkout/form-checkout.php'); } else { //woocommerce_get_template( 'cart/cart.php' ); woocommerce_get_template('checkout/form-checkout.php'); } }
/** * Evaluate common validity based on op and coupon codes. * * @param array $atts * @return boolean */ private static function _is_valid($atts) { $options = shortcode_atts(array('coupon' => null, 'code' => null, 'op' => 'and'), $atts); $code = null; if (!empty($options['code'])) { $code = $options['code']; } else { if (!empty($options['coupon'])) { $code = $options['coupon']; } } if ($code === null) { return ''; } $codes = array_map('trim', explode(',', $code)); $validities = array(); foreach ($codes as $code) { $coupon = new WC_Coupon($code); if ($coupon->id) { $validities[] = $coupon->is_valid(); } } if (count($validities) > 0) { $valid = $options['op'] != 'or'; foreach ($validities as $validity) { if ($options['op'] == 'or') { $valid = $valid || $validity; if ($valid) { break; } } else { $valid = $valid && $validity; if (!$valid) { break; } } } } else { $valid = false; } }
/** * AJAX apply coupon on checkout page * * @access public * @return void */ function woocommerce_ajax_apply_coupon() { global $woocommerce; check_ajax_referer('apply-coupon', 'security'); if (!empty($_POST['coupon_code'])) { $woocommerce->cart->add_discount(sanitize_text_field($_POST['coupon_code'])); } else { $woocommerce->add_error(WC_Coupon::get_generic_coupon_error(WC_Coupon::E_WC_COUPON_PLEASE_ENTER)); } $woocommerce->show_messages(); die; }
/** * Get the coupon for the given ID * * @since 2.1 * @param int $id the coupon ID * @param string $fields fields to include in response * @return array|WP_Error */ public function get_coupon($id, $fields = null) { global $wpdb; $id = $this->validate_request($id, 'shop_coupon', 'read'); if (is_wp_error($id)) { return $id; } // get the coupon code $code = $wpdb->get_var($wpdb->prepare("SELECT post_title FROM {$wpdb->posts} WHERE id = %s AND post_type = 'shop_coupon' AND post_status = 'publish'", $id)); if (is_null($code)) { return new WP_Error('woocommerce_api_invalid_coupon_id', __('Invalid coupon ID', 'woocommerce'), array('status' => 404)); } $coupon = new WC_Coupon($code); $coupon_post = get_post($coupon->id); $coupon_data = array('id' => $coupon->id, 'code' => $coupon->code, 'type' => $coupon->type, 'created_at' => $this->server->format_datetime($coupon_post->post_date_gmt), 'updated_at' => $this->server->format_datetime($coupon_post->post_modified_gmt), 'amount' => wc_format_decimal($coupon->amount, 2), 'individual_use' => 'yes' === $coupon->individual_use, 'product_ids' => array_map('absint', (array) $coupon->product_ids), 'exclude_product_ids' => array_map('absint', (array) $coupon->exclude_product_ids), 'usage_limit' => !empty($coupon->usage_limit) ? $coupon->usage_limit : null, 'usage_limit_per_user' => !empty($coupon->usage_limit_per_user) ? $coupon->usage_limit_per_user : null, 'limit_usage_to_x_items' => (int) $coupon->limit_usage_to_x_items, 'usage_count' => (int) $coupon->usage_count, 'expiry_date' => $this->server->format_datetime($coupon->expiry_date), 'apply_before_tax' => $coupon->apply_before_tax(), 'enable_free_shipping' => $coupon->enable_free_shipping(), 'product_category_ids' => array_map('absint', (array) $coupon->product_categories), 'exclude_product_category_ids' => array_map('absint', (array) $coupon->exclude_product_categories), 'exclude_sale_items' => $coupon->exclude_sale_items(), 'minimum_amount' => wc_format_decimal($coupon->minimum_amount, 2), 'customer_emails' => $coupon->customer_email); return array('coupon' => apply_filters('woocommerce_api_coupon_response', $coupon_data, $coupon, $fields, $this->server)); }
/** * Apply sign up fee or recurring fee discount * * @since 1.2 */ public static function apply_subscription_discount($original_price, $cart_item, $cart) { $product_id = $cart_item['data']->is_type(array('subscription_variation')) ? $cart_item['data']->variation_id : $cart_item['data']->id; if (!WC_Subscriptions_Product::is_subscription($product_id)) { return $original_price; } $price = $calculation_price = $original_price; $calculation_type = WC_Subscriptions_Cart::get_calculation_type(); if (!empty($cart->applied_coupons)) { foreach ($cart->applied_coupons as $code) { $coupon = new WC_Coupon($code); if ($coupon->apply_before_tax() && $coupon->is_valid()) { $apply_recurring_coupon = $apply_recurring_percent_coupon = $apply_initial_coupon = $apply_initial_percent_coupon = false; // Apply recurring fee discounts to recurring total calculations if ('recurring_total' == $calculation_type) { $apply_recurring_coupon = 'recurring_fee' == $coupon->type ? true : false; $apply_recurring_percent_coupon = 'recurring_percent' == $coupon->type ? true : false; } if ('none' == $calculation_type) { // If all items have a free trial we don't need to apply recurring coupons to the initial total if (!WC_Subscriptions_Cart::all_cart_items_have_free_trial()) { if ('recurring_fee' == $coupon->type) { $apply_initial_coupon = true; } if ('recurring_percent' == $coupon->type) { $apply_initial_percent_coupon = true; } } // Apply sign-up discounts to initial total if (!empty($cart_item['data']->subscription_sign_up_fee)) { if ('sign_up_fee' == $coupon->type) { $apply_initial_coupon = true; } if ('sign_up_fee_percent' == $coupon->type) { $apply_initial_percent_coupon = true; } $calculation_price = $cart_item['data']->subscription_sign_up_fee; } } if ($apply_recurring_coupon || $apply_initial_coupon) { $discount_amount = $calculation_price < $coupon->amount ? $calculation_price : $coupon->amount; // Recurring coupons only apply when there is no free trial (carts can have a mix of free trial and non free trial items) if ($apply_initial_coupon && 'recurring_fee' == $coupon->type && !empty($cart_item['data']->subscription_trial_length)) { $discount_amount = 0; } $cart->discount_cart = $cart->discount_cart + $discount_amount * $cart_item['quantity']; $cart = self::increase_coupon_discount_amount($cart, $coupon->code, $discount_amount * $cart_item['quantity']); $price = $price - $discount_amount; } elseif ($apply_recurring_percent_coupon) { $discount_amount = round($calculation_price / 100 * $coupon->amount, WC()->cart->dp); $cart->discount_cart = $cart->discount_cart + $discount_amount * $cart_item['quantity']; $cart = self::increase_coupon_discount_amount($cart, $coupon->code, $discount_amount * $cart_item['quantity']); $price = $price - $discount_amount; } elseif ($apply_initial_percent_coupon) { // Recurring coupons only apply when there is no free trial (carts can have a mix of free trial and non free trial items) if ('recurring_percent' == $coupon->type && empty($cart_item['data']->subscription_trial_length)) { $amount_to_discount = $cart_item['data']->subscription_price; } else { $amount_to_discount = 0; } // Sign up fee coupons only apply to sign up fees if ('sign_up_fee_percent' == $coupon->type) { $amount_to_discount = $cart_item['data']->subscription_sign_up_fee; } $discount_amount = round($amount_to_discount / 100 * $coupon->amount, WC()->cart->dp); $cart->discount_cart = $cart->discount_cart + $discount_amount * $cart_item['quantity']; $cart = self::increase_coupon_discount_amount($cart, $coupon->code, $discount_amount * $cart_item['quantity']); $price = $price - $discount_amount; } } } if ($price < 0) { $price = 0; } } return $price; }
/** * Get a coupon value. * * @access public * @param string $coupon */ function wc_cart_totals_coupon_html($coupon) { if (is_string($coupon)) { $coupon = new WC_Coupon($coupon); } $value = array(); if ($amount = WC()->cart->get_coupon_discount_amount($coupon->get_code(), WC()->cart->display_cart_ex_tax)) { $discount_html = '-' . wc_price($amount); } else { $discount_html = ''; } $value[] = apply_filters('woocommerce_coupon_discount_amount_html', $discount_html, $coupon); if ($coupon->get_free_shipping()) { $value[] = __('Free shipping coupon', 'woocommerce'); } // get rid of empty array elements $value = array_filter($value); $value = implode(', ', $value) . ' <a href="' . esc_url(add_query_arg('remove_coupon', urlencode($coupon->get_code()), defined('WOOCOMMERCE_CHECKOUT') ? wc_get_checkout_url() : wc_get_cart_url())) . '" class="woocommerce-remove-coupon" data-coupon="' . esc_attr($coupon->get_code()) . '">' . __('[Remove]', 'woocommerce') . '</a>'; echo apply_filters('woocommerce_cart_totals_coupon_html', $value, $coupon); }
/** * Apply fake coupon to cart * * @access public * @return void */ public function apply_fake_coupon() { global $woocommerce; $the_coupon = new WC_Coupon(apply_filters('woocommerce_coupon_code', $this->opt['settings']['cart_discount_title'])); if ($the_coupon->is_valid() && !$woocommerce->cart->has_discount($this->opt['settings']['cart_discount_title'])) { // Do not apply coupon with individual use coupon already applied if ($woocommerce->cart->applied_coupons) { foreach ($woocommerce->cart->applied_coupons as $code) { $coupon = new WC_Coupon($code); if ($coupon->individual_use == 'yes') { return false; } } } $woocommerce->cart->applied_coupons[] = apply_filters('woocommerce_coupon_code', $this->opt['settings']['cart_discount_title']); return true; } }
$categories = ins_get_categories(); $products = ins_get_products(); $cart_items = $woocommerce->cart->cart_contents; ?> <div class="add_discount" style="padding-top:1em; border-collapse:unset; font-size: 12px;"> <h2 class="label">Add A Coupon</h2> <table id="coupons" style="border-bottom:1px solid #333;"> <tr> <td class="coupon"><label for="coupon_select">Select a Coupon</label></td> <td class="coupon"><select class="chosen_select" style="width:200px;" id="coupon_select" data-placeholder="Select a Coupon" onblur="get_discount_info();" style="width:300px;"> <option></option> <?php if ($coupons) { foreach ($coupons as $coupon) { $coupon = new WC_Coupon($coupon->post_title); if (!$woocommerce->cart->has_discount($coupon->code) && $coupon->is_valid()) { ?> <option value="<?php echo esc_attr($coupon->code); ?> "><?php echo esc_html($coupon->code); ?> </option> <?php } else { var_dump($coupon->error_message); } } }
/** * Decrease applied coupon counts * * @access public * @return void */ public function decrease_coupon_usage_counts() { global $woocommerce; if (get_post_meta($this->id, '_recorded_coupon_usage_counts', true) != 'yes') { return; } if (sizeof($this->get_used_coupons()) > 0) { foreach ($this->get_used_coupons() as $code) { if (!$code) { continue; } $coupon = new WC_Coupon($code); $coupon->dcr_usage_count(); } } delete_post_meta($this->id, '_recorded_coupon_usage_counts'); }
/** * Format posts from WP_Query result to items in which each item contain * common properties of item, for instance `post_title` will be `code`. * * @since 2.5.0 * @param array $posts Array of post * @return array Items */ protected function format_posts_to_items($posts) { $items = array(); foreach ($posts as $post) { $coupon = new WC_Coupon(); $coupon->read($post->ID); $coupon_usage_limit = $coupon->get_usage_limit(); $coupon_usage_limit_per_user = $coupon->get_usage_limit_per_user(); $coupon_date_expires = $coupon->get_date_expires(); $items[] = array('id' => $post->ID, 'code' => $post->post_title, 'type' => $coupon->get_discount_type(), 'created_at' => $this->format_datetime($post->post_date_gmt), 'updated_at' => $this->format_datetime($post->post_modified_gmt), 'amount' => wc_format_decimal($coupon->get_amount(), 2), 'individual_use' => $coupon->get_individual_use(), 'product_ids' => implode(', ', is_array($coupon->get_product_ids()) ? $coupon->get_product_ids() : array()), 'exclude_product_ids' => implode(', ', is_array($coupon->get_excluded_product_ids()) ? $coupon->get_excluded_product_ids() : array()), 'usage_limit' => !empty($coupon_usage_limit) ? $coupon_usage_limit : null, 'usage_limit_per_user' => !empty($coupon_usage_limit_per_user) ? $coupon_usage_limit_per_user : null, 'limit_usage_to_x_items' => (int) $coupon->get_limit_usage_to_x_items(), 'usage_count' => (int) $coupon->get_usage_count(), 'expiry_date' => !empty($coupon_date_expires) ? $this->format_datetime($coupon_date_expires) : null, 'free_shipping' => $coupon->get_free_shipping(), 'product_category_ids' => implode(', ', is_array($coupon->get_product_categories()) ? $coupon->get_product_categories() : array()), 'exclude_product_category_ids' => implode(', ', is_array($coupon->get_excluded_product_categories()) ? $coupon->get_excluded_product_categories() : array()), 'exclude_sale_items' => $coupon->get_exclude_sale_items(), 'minimum_amount' => wc_format_decimal($coupon->get_minimum_amount(), 2), 'maximum_amount' => wc_format_decimal($coupon->get_maximum_amount(), 2), 'customer_emails' => implode(', ', is_array($coupon->get_email_restrictions()) ? $coupon->get_email_restrictions() : array()), 'description' => $post->post_excerpt); } return $items; }
/** * is_available function. * * @access public * @param mixed $package * @return bool */ function is_available($package) { global $woocommerce; if ($this->enabled == "no") { return false; } $ship_to_countries = ''; if ($this->availability == 'specific') { $ship_to_countries = $this->countries; } else { if (get_option('woocommerce_allowed_countries') == 'specific') { $ship_to_countries = get_option('woocommerce_specific_allowed_countries'); } } if (is_array($ship_to_countries)) { if (!in_array($package['destination']['country'], $ship_to_countries)) { return false; } } // Enabled logic $is_available = false; $has_coupon = false; $has_met_min_amount = false; if (in_array($this->requires, array('coupon', 'either', 'both'))) { if ($woocommerce->cart->applied_coupons) { foreach ($woocommerce->cart->applied_coupons as $code) { $coupon = new WC_Coupon($code); if ($coupon->is_valid() && $coupon->enable_free_shipping()) { $has_coupon = true; } } } } if (in_array($this->requires, array('min_amount', 'either', 'both')) && isset($woocommerce->cart->cart_contents_total)) { if ($woocommerce->cart->prices_include_tax) { $total = $woocommerce->cart->cart_contents_total + array_sum($woocommerce->cart->taxes); } else { $total = $woocommerce->cart->cart_contents_total; } if ($total >= $this->min_amount) { $has_met_min_amount = true; } } switch ($this->requires) { case 'min_amount': if ($has_met_min_amount) { $is_available = true; } break; case 'coupon': if ($has_coupon) { $is_available = true; } break; case 'both': if ($has_met_min_amount && $has_coupon) { $is_available = true; } break; case 'either': if ($has_met_min_amount || $has_coupon) { $is_available = true; } break; default: $is_available = true; break; } return apply_filters('woocommerce_shipping_' . $this->id . '_is_available', $is_available); }
/** * Prepare a single coupon for create or update. * * @param WP_REST_Request $request Request object. * @return WP_Error|stdClass $data Post object. */ protected function prepare_item_for_database($request) { global $wpdb; $id = isset($request['id']) ? absint($request['id']) : 0; $coupon = new WC_Coupon($id); $schema = $this->get_item_schema(); $data_keys = array_keys(array_filter($schema['properties'], array($this, 'filter_writable_props'))); // BW compat if ($request['exclude_product_ids']) { $request['excluded_product_ids'] = $request['exclude_product_ids']; } if ($request['expiry_date']) { $request['date_expires'] = $request['expiry_date']; } // Validate required POST fields. if ('POST' === $request->get_method() && 0 === $coupon->get_id()) { if (empty($request['code'])) { return new WP_Error('woocommerce_rest_empty_coupon_code', sprintf(__('The coupon code cannot be empty.', 'woocommerce'), 'code'), array('status' => 400)); } } // Handle all writable props foreach ($data_keys as $key) { $value = $request[$key]; if (!is_null($value)) { switch ($key) { case 'code': $coupon_code = apply_filters('woocommerce_coupon_code', $value); $id = $coupon->get_id() ? $coupon->get_id() : 0; $id_from_code = wc_get_coupon_id_by_code($coupon_code, $id); if ($id_from_code) { return new WP_Error('woocommerce_rest_coupon_code_already_exists', __('The coupon code already exists', 'woocommerce'), array('status' => 400)); } $coupon->set_code($coupon_code); break; case 'meta_data': if (is_array($value)) { foreach ($value as $meta) { $coupon->update_meta_data($meta['key'], $meta['value'], $meta['id']); } } break; case 'description': $coupon->set_description(wp_filter_post_kses($value)); break; default: if (is_callable(array($coupon, "set_{$key}"))) { $coupon->{"set_{$key}"}($value); } break; } } } /** * Filter the query_vars used in `get_items` for the constructed query. * * The dynamic portion of the hook name, $this->post_type, refers to post_type of the post being * prepared for insertion. * * @param WC_Coupon $coupon The coupon object. * @param WP_REST_Request $request Request object. */ return apply_filters("woocommerce_rest_pre_insert_{$this->post_type}", $coupon, $request); }
/** * Apply sign up fee or recurring fee discount before tax is calculated * * @since 1.2 */ public static function apply_subscription_discount_before_tax($original_price, $cart_item, $cart) { global $woocommerce; $product_id = $cart_item['data']->is_type(array('subscription_variation')) ? $cart_item['data']->variation_id : $cart_item['data']->id; if (!WC_Subscriptions_Product::is_subscription($product_id)) { return $original_price; } $price = $original_price; $calculation_type = WC_Subscriptions_Cart::get_calculation_type(); if (!empty($cart->applied_coupons)) { foreach ($cart->applied_coupons as $code) { $coupon = new WC_Coupon($code); if ($coupon->apply_before_tax() && $coupon->is_valid()) { $apply_sign_up_coupon = $apply_sign_up_percent_coupon = $apply_recurring_coupon = $apply_recurring_percent_coupon = $apply_initial_coupon = $apply_initial_percent_coupon = false; // Apply sign-up fee discounts to sign-up total calculations if ('sign_up_fee_total' == $calculation_type) { $apply_sign_up_coupon = 'sign_up_fee' == $coupon->type ? true : false; $apply_sign_up_percent_coupon = 'sign_up_fee_percent' == $coupon->type ? true : false; // Apply recurring fee discounts to recurring total calculations } elseif ('recurring_total' == $calculation_type) { $apply_recurring_coupon = 'recurring_fee' == $coupon->type ? true : false; $apply_recurring_percent_coupon = 'recurring_percent' == $coupon->type ? true : false; } if (in_array($calculation_type, array('combined_total', 'none'))) { if (!WC_Subscriptions_Cart::cart_contains_free_trial()) { // Apply recurring discounts to initial total if ('recurring_fee' == $coupon->type) { $apply_initial_coupon = true; } if ('recurring_percent' == $coupon->type) { $apply_initial_percent_coupon = true; } } if (WC_Subscriptions_Cart::get_cart_subscription_sign_up_fee() > 0) { // Apply sign-up discounts to initial total if ('sign_up_fee' == $coupon->type) { $apply_initial_coupon = true; } if ('sign_up_fee_percent' == $coupon->type) { $apply_initial_percent_coupon = true; } } } if ($apply_sign_up_coupon || $apply_recurring_coupon || $apply_initial_coupon) { $discount_amount = $price < $coupon->amount ? $price : $coupon->amount; // add to discount totals $woocommerce->cart->discount_cart = $woocommerce->cart->discount_cart + $discount_amount * $cart_item['quantity']; WC_Subscriptions_Cart::increase_coupon_discount_amount($coupon->code, $discount_amount * $cart_item['quantity']); $price = $price - $discount_amount; if ($price < 0) { $price = 0; } } elseif ($apply_sign_up_percent_coupon || $apply_recurring_percent_coupon) { $discount_amount = round($cart_item['data']->get_price() / 100 * $coupon->amount, $woocommerce->cart->dp); $woocommerce->cart->discount_cart = $woocommerce->cart->discount_cart + $discount_amount; WC_Subscriptions_Cart::increase_coupon_discount_amount($coupon->code, $discount_amount); $price = $price - $discount_amount; } elseif ($apply_initial_percent_coupon) { // Need to calculate percent from base price // We need to calculate the right amount to discount when the price is the combined sign-up fee and recurring amount if ('combined_total' == $calculation_type && !WC_Subscriptions_Cart::cart_contains_free_trial() && isset($woocommerce->cart->base_sign_up_fees[$product_id]) && $woocommerce->cart->base_sign_up_fees[$product_id] > 0) { $base_total = $woocommerce->cart->base_sign_up_fees[$product_id] + $woocommerce->cart->base_recurring_prices[$product_id]; if ('recurring_percent' == $coupon->type) { $portion_of_total = $woocommerce->cart->base_recurring_prices[$product_id] / $base_total; } if ('sign_up_fee_percent' == $coupon->type) { $portion_of_total = $woocommerce->cart->base_sign_up_fees[$product_id] / $base_total; } $amount_to_discount = WC_Subscriptions_Manager::get_amount_from_proportion($base_total, $portion_of_total); } else { $amount_to_discount = $cart_item['data']->get_price(); } $discount_amount = round($amount_to_discount / 100 * $coupon->amount, $woocommerce->cart->dp); $woocommerce->cart->discount_cart = $woocommerce->cart->discount_cart + $discount_amount; WC_Subscriptions_Cart::increase_coupon_discount_amount($coupon->code, $discount_amount); $price = $price - $discount_amount; } } } } return $price; }
/** * Performs coupon checks after checkout validation. * * @param array $posted posted form data */ public static function woocommerce_after_checkout_validation($posted) { global $woocommerce; if (isset($woocommerce->cart)) { $cart = $woocommerce->cart; if (!empty($cart->applied_coupons)) { if (method_exists('Affiliates_Attributes_WordPress', 'get_affiliate_for_coupon')) { $valid = true; $emails = array($posted['billing_email']); if (is_user_logged_in()) { $current_user = wp_get_current_user(); $emails[] = $current_user->user_email; } $emails = array_map('sanitize_email', array_map('strtolower', $emails)); self::remove_filters(); foreach ($cart->applied_coupons as $key => $code) { $coupon = new WC_Coupon($code); if (!is_wp_error($coupon->is_valid())) { if ($affiliate_id = Affiliates_Attributes_WordPress::get_affiliate_for_coupon($coupon->code)) { if ($user_id = get_current_user_id()) { if ($affiliate_ids = affiliates_get_user_affiliate($user_id)) { if (in_array($affiliate_id, $affiliate_ids)) { $valid = false; break; } } } if ($affiliate = affiliates_get_affiliate($affiliate_id)) { if (isset($affiliate['email']) && in_array(strtolower($affiliate['email']), $emails)) { $valid = false; break; } } } } } self::add_filters(); if (!$valid) { $coupon->add_coupon_message(WC_Coupon::E_WC_COUPON_INVALID_REMOVED); unset($cart->applied_coupons[$key]); $woocommerce->session->coupon_codes = $cart->applied_coupons; $woocommerce->session->refresh_totals = true; } } } } }
public function __construct($code) { _deprecated_function('woocommerce_coupon', '1.4', 'WC_Coupon()'); parent::__construct($code); }
/** * Save meta box data. * * @param int $post_id * @param WP_Post $post */ public static function save($post_id, $post) { global $wpdb; // Check for dupe coupons $coupon_code = apply_filters('woocommerce_coupon_code', $post->post_title); $id_from_code = wc_get_coupon_id_by_code($coupon_code, $post_id); if ($id_from_code) { WC_Admin_Meta_Boxes::add_error(__('Coupon code already exists - customers will use the latest coupon with this code.', 'woocommerce')); } $coupon = new WC_Coupon($post_id); $coupon->set_props(array('code' => $post->post_title, 'discount_type' => wc_clean($_POST['discount_type']), 'amount' => wc_format_decimal($_POST['coupon_amount']), 'date_expires' => wc_clean($_POST['expiry_date']), 'individual_use' => isset($_POST['individual_use']), 'product_ids' => array_filter(array_map('intval', explode(',', $_POST['product_ids']))), 'excluded_product_ids' => array_filter(array_map('intval', explode(',', $_POST['exclude_product_ids']))), 'usage_limit' => absint($_POST['usage_limit']), 'usage_limit_per_user' => absint($_POST['usage_limit_per_user']), 'limit_usage_to_x_items' => absint($_POST['limit_usage_to_x_items']), 'free_shipping' => isset($_POST['free_shipping']), 'product_categories' => array_filter(array_map('intval', (array) $_POST['product_categories'])), 'excluded_product_categories' => array_filter(array_map('intval', (array) $_POST['exclude_product_categories'])), 'exclude_sale_items' => isset($_POST['exclude_sale_items']), 'minimum_amount' => wc_format_decimal($_POST['minimum_amount']), 'maximum_amount' => wc_format_decimal($_POST['maximum_amount']), 'email_restrictions' => array_filter(array_map('trim', explode(',', wc_clean($_POST['customer_email'])))))); $coupon->save(); do_action('woocommerce_coupon_options_save', $post_id); }
/** * Remove coupons from the cart of a defined type. Type 1 is before tax, type 2 is after tax. * * @params int type - 0 for all, 1 for before tax, 2 for after tax */ public function remove_coupons($type = 0) { global $woocommerce; if (1 == $type) { if ($this->applied_coupons) { foreach ($this->applied_coupons as $index => $code) { $coupon = new WC_Coupon($code); if ($coupon->is_valid() && $coupon->apply_before_tax()) { unset($this->applied_coupons[$index]); } } } $woocommerce->session->coupon_codes = $this->applied_coupons; } elseif ($type == 2) { if ($this->applied_coupons) { foreach ($this->applied_coupons as $index => $code) { $coupon = new WC_Coupon($code); if ($coupon->is_valid() && !$coupon->apply_before_tax()) { unset($this->applied_coupons[$index]); } } } $woocommerce->session->coupon_codes = $this->applied_coupons; } else { unset($woocommerce->session->coupon_codes, $woocommerce->session->coupon_amounts); $this->applied_coupons = array(); } }
public function __construct() { _deprecated_function('woocommerce_customer', '1.4', 'WC_Customer()'); parent::__construct(); }
/** * Applies a coupon code passed to the method. * * @param string $coupon_code - The code to apply * @return bool True if the coupon is applied, false if it does not exist or cannot be applied */ public function add_discount($coupon_code) { // Coupons are globally disabled if (!wc_coupons_enabled()) { return false; } // Sanitize coupon code $coupon_code = apply_filters('woocommerce_coupon_code', $coupon_code); // Get the coupon $the_coupon = new WC_Coupon($coupon_code); // Check it can be used with cart if (!$the_coupon->is_valid()) { wc_add_notice($the_coupon->get_error_message(), 'error'); return false; } // Check if applied if ($this->has_discount($coupon_code)) { $the_coupon->add_coupon_message(WC_Coupon::E_WC_COUPON_ALREADY_APPLIED); return false; } // If its individual use then remove other coupons if ($the_coupon->get_individual_use()) { $this->applied_coupons = apply_filters('woocommerce_apply_individual_use_coupon', array(), $the_coupon, $this->applied_coupons); } if ($this->applied_coupons) { foreach ($this->applied_coupons as $code) { $coupon = new WC_Coupon($code); if ($coupon->get_individual_use() && false === apply_filters('woocommerce_apply_with_individual_use_coupon', false, $the_coupon, $coupon, $this->applied_coupons)) { // Reject new coupon $coupon->add_coupon_message(WC_Coupon::E_WC_COUPON_ALREADY_APPLIED_INDIV_USE_ONLY); return false; } } } $this->applied_coupons[] = $coupon_code; // Choose free shipping if ($the_coupon->get_free_shipping()) { $packages = WC()->shipping->get_packages(); $chosen_shipping_methods = WC()->session->get('chosen_shipping_methods'); foreach ($packages as $i => $package) { $chosen_shipping_methods[$i] = 'free_shipping'; } WC()->session->set('chosen_shipping_methods', $chosen_shipping_methods); } $the_coupon->add_coupon_message(WC_Coupon::WC_COUPON_SUCCESS); do_action('woocommerce_applied_coupon', $coupon_code); return true; }
/** * Update used coupon amount for each coupon within an order. * * @since 2.7.0 * @param int $order_id */ function wc_update_coupon_usage_counts($order_id) { if (!($order = wc_get_order($order_id))) { return; } $has_recorded = $order->get_data_store()->get_recorded_coupon_usage_counts($order); if ($order->has_status('cancelled') && $has_recorded) { $action = 'reduce'; $order->get_data_store()->set_recorded_coupon_usage_counts($order, false); } elseif (!$order->has_status('cancelled') && !$has_recorded) { $action = 'increase'; $order->get_data_store()->set_recorded_coupon_usage_counts($order, true); } else { return; } if (sizeof($order->get_used_coupons()) > 0) { foreach ($order->get_used_coupons() as $code) { if (!$code) { continue; } $coupon = new WC_Coupon($code); if (!($used_by = $order->get_user_id())) { $used_by = $order->get_billing_email(); } switch ($action) { case 'reduce': $coupon->dcr_usage_count($used_by); break; case 'increase': $coupon->inc_usage_count($used_by); break; } } } }
/** * Function to apply discounts to a product and get the discounted price (before tax is applied). * * @access public * @param mixed $values * @param mixed $price * @param bool $add_totals (default: false) * @return float price */ public function get_discounted_price($values, $price, $add_totals = false) { if (!$price) { return $price; } if (!empty($this->applied_coupons)) { foreach ($this->applied_coupons as $code) { $coupon = new WC_Coupon($code); if ($coupon->apply_before_tax() && $coupon->is_valid()) { if ($coupon->is_valid_for_product($values['data']) || $coupon->is_valid_for_cart()) { $discount_amount = $coupon->get_discount_amount($price, $values, $single = true); $price = max($price - $discount_amount, 0); if ($add_totals) { $this->discount_cart += $discount_amount * $values['quantity']; $this->increase_coupon_discount_amount($code, $discount_amount * $values['quantity']); $this->increase_coupon_applied_count($code, $values['quantity']); } } } } } return apply_filters('woocommerce_get_discounted_price', $price, $values, $this); }
/** * Function to apply Gift Certificate's credit to cart */ public function apply_smart_coupon_to_cart() { $this->global_wc()->cart->smart_coupon_credit_used = array(); $cart_contains_subscription = false; if (class_exists('WC_Subscriptions_Cart') && WC_Subscriptions_Cart::cart_contains_subscription()) { $cart_contains_subscription = true; } if ($cart_contains_subscription) { $calculation_type = WC_Subscriptions_Cart::get_calculation_type(); if ($calculation_type == 'recurring_total') { return; } } if ($this->global_wc()->cart->applied_coupons) { foreach ($this->global_wc()->cart->applied_coupons as $code) { $smart_coupon = new WC_Coupon($code); if ($smart_coupon->is_valid() && $smart_coupon->discount_type == 'smart_coupon') { $order_total = $this->global_wc()->cart->cart_contents_total + $this->global_wc()->cart->tax_total + $this->global_wc()->cart->shipping_tax_total + $this->global_wc()->cart->shipping_total; if ($this->global_wc()->cart->discount_total != 0 && $this->global_wc()->cart->discount_total + $smart_coupon->amount > $order_total) { $smart_coupon->amount = $order_total - $this->global_wc()->cart->discount_total; } elseif ($smart_coupon->amount > $order_total) { $smart_coupon->amount = $order_total; } $this->global_wc()->cart->discount_total = $this->global_wc()->cart->discount_total + $smart_coupon->amount; if ($cart_contains_subscription) { WC_Subscriptions_Cart::increase_coupon_discount_amount($code, $smart_coupon->amount); } $this->global_wc()->cart->smart_coupon_credit_used[$code] = $smart_coupon->amount; //Code for displaying the price label for the store credit coupons if (empty($this->global_wc()->cart->coupon_discount_amounts)) { $this->global_wc()->cart->coupon_discount_amounts = array(); } $this->global_wc()->cart->coupon_discount_amounts[$code] = $smart_coupon->amount; } } } }
function is_available($package) { global $woocommerce; if ($this->enabled == "no") { return false; } $ship_to_countries = ''; if ($this->availability == 'specific') { $ship_to_countries = $this->countries; } else { if (get_option('woocommerce_allowed_countries') == 'specific') { $ship_to_countries = get_option('woocommerce_specific_allowed_countries'); } } if (is_array($ship_to_countries)) { if (!in_array($package['destination']['country'], $ship_to_countries)) { return false; } } // Enabled logic $is_available = true; if ($this->requires_coupon == "yes") { if ($woocommerce->cart->applied_coupons) { foreach ($woocommerce->cart->applied_coupons as $code) { $coupon = new WC_Coupon($code); if ($coupon->enable_free_shipping()) { return true; } } } // No coupon found, as it stands, free shipping is disabled $is_available = false; } if (isset($woocommerce->cart->cart_contents_total) && !empty($this->min_amount)) { if ($woocommerce->cart->prices_include_tax) { $total = $woocommerce->cart->tax_total + $woocommerce->cart->cart_contents_total; } else { $total = $woocommerce->cart->cart_contents_total; } if ($this->min_amount > $total) { $is_available = false; } else { $is_available = true; } } return apply_filters('woocommerce_shipping_' . $this->id . '_is_available', $is_available); }
/** * Decrease applied coupon counts */ public function decrease_coupon_usage_counts() { if ('yes' != get_post_meta($this->id, '_recorded_coupon_usage_counts', true)) { return; } if (sizeof($this->get_used_coupons()) > 0) { foreach ($this->get_used_coupons() as $code) { if (!$code) { continue; } $coupon = new WC_Coupon($code); $used_by = $this->get_user_id(); if (!$used_by) { $used_by = $this->billing_email; } $coupon->dcr_usage_count($used_by); } delete_post_meta($this->id, '_recorded_coupon_usage_counts'); } }
/** * gets the array of applied coupon codes */ function remove_coupons($type = 0) { if ($type == 1) { if ($this->applied_coupons) { foreach ($this->applied_coupons as $index => $code) { $coupon = new WC_Coupon($code); if ($coupon->apply_before_tax()) { unset($this->applied_coupons[$index]); } } } $_SESSION['coupons'] = $this->applied_coupons; } elseif ($type == 2) { if ($this->applied_coupons) { foreach ($this->applied_coupons as $index => $code) { $coupon = new WC_Coupon($code); if (!$coupon->apply_before_tax()) { unset($this->applied_coupons[$index]); } } } $_SESSION['coupons'] = $this->applied_coupons; } else { unset($_SESSION['coupons']); $this->applied_coupons = array(); } }