WooCommerce使用提供的函数/挂钩为用户创建订阅

时间:2013-07-17 作者:Mutant Tech

我必须使用预定义的“免费”产品/订阅为word press中的现有用户创建订单。需要有关示例代码的帮助。

1 个回复
SO网友:Mutant Tech
    private function createWooComSubscription($user_id, $product_name, $total, $payment_id) {
        $arr = explode("-", $product_name);
        $product_title = trim($arr[0]);
        $product_subscription = trim($arr[1]);
        $product = $this->getWooComProduct($product_title);
        if ($product == null) {
            $this->getController()->log("Product not found ! woo com create subscription failed");
            return;
        }
        $variation = $this->getWooComVariation($product, $product_subscription);
        if ($variation == null) {
            $this->getController()->log("Variation not found ! woo com create subscription failed");
            return;
        }           
        // Create default order data
        $order_data = apply_filters( \'woocommerce_new_order_data\', array(
            \'post_type\'     => \'shop_order\',
            \'post_title\'    => sprintf( __( \'Order – %s\', \'woocommerce\' ), strftime( _x( \'%b %d, %Y @ %I:%M %p\', \'Order date parsed by strftime\', \'woocommerce\' ) ) ),
            \'post_status\'   => \'publish\',
            \'ping_status\'   => \'closed\',
            \'post_excerpt\'  => \'Internal order created\',
            \'post_author\'   => 1,
            \'post_password\' => uniqid( \'order_\' )   // Protects the post just in case
        ) );

        // insert order, post
        $order_id = wp_insert_post( $order_data );
        if ( is_wp_error( $order_id ) ) {
                $this->getController()->log("unable to create order");
                return;
            }
        else
            do_action( \'woocommerce_new_order\', $order_id );

        // Add line item
        $item_id = woocommerce_add_order_item( $order_id, array(
            \'order_item_name\'       => $product->get_title(),
            \'order_item_type\'       => \'line_item\'
        ) );
        // product id, variation, quantity
        woocommerce_add_order_item_meta( $item_id, \'_product_id\', $product->id );
        woocommerce_add_order_item_meta( $item_id, \'_variation_id\', $variation[\'variation_id\']);
        woocommerce_add_order_item_meta( $item_id, $variation[\'variation_attr_name\'], $variation[\'variation_attr_name_value\']);
        woocommerce_add_order_item_meta( $item_id, \'_qty\', apply_filters( \'woocommerce_stock_amount\', 1 ) );

        // tax class
        foreach (array(\'_tax_class\') as $nullkey) {
            woocommerce_add_order_item_meta( $item_id, $nullkey, \'\' );
        }
        // line item total values
        foreach (array(\'_line_tax\', \'_line_subtotal_tax\', \'_recurring_line_tax\', \'_recurring_line_subtotal_tax\') as $zero_value_key) {
            woocommerce_add_order_item_meta( $item_id, $zero_value_key, woocommerce_format_total(0) );
        }

        // subscription data values
        woocommerce_add_order_item_meta( $item_id, "_subscription_interval", $variation[\'_subscription_period_interval\'][0] );
        woocommerce_add_order_item_meta( $item_id, "_subscription_sign_up_fee", woocommerce_format_total( 0 ) );
        foreach (array(\'_subscription_length\', \'_subscription_period\', \'_subscription_trial_length\', \'_subscription_trial_period\') as $sub_key) {
            woocommerce_add_order_item_meta( $item_id, $sub_key, $variation[$sub_key][0] );
        }

        // meta to find the order again !!!
        update_post_meta( $order_id, \'_myapi_payment_id\',       $payment_id );
        update_post_meta( $order_id, \'_customer_user\',          $user_id );
        // other order data
        update_post_meta( $order_id, \'_order_key\',              apply_filters(\'woocommerce_generate_order_key\', uniqid(\'order_\') ) );
        update_post_meta( $order_id, \'_order_currency\',         get_woocommerce_currency() );
        update_post_meta( $order_id, \'_prices_include_tax\',     get_option( \'woocommerce_prices_include_tax\' ) );
        update_post_meta( $order_id, \'_customer_ip_address\',    isset( $_SERVER[\'HTTP_X_FORWARDED_FOR\'] ) ? $_SERVER[\'HTTP_X_FORWARDED_FOR\'] : $_SERVER[\'REMOTE_ADDR\'] );
        update_post_meta( $order_id, \'_customer_user_agent\',    isset( $_SERVER[\'HTTP_USER_AGENT\'] ) ? $_SERVER[\'HTTP_USER_AGENT\'] : \'\' );          

        // order total values
        foreach (array(\'_order_shipping\', \'_order_discount\', \'_cart_discount\', \'_order_tax\', \'_order_shipping_tax\', ) as $order_zero_key) {
            update_post_meta( $order_id, $order_zero_key, woocommerce_format_total(0));
        } 
        update_post_meta( $order_id, \'_order_total\', woocommerce_format_total(0) );

        // Order status
        wp_set_object_terms( $order_id, \'pending\', \'shop_order_status\' );
        $order = new WC_Order($order_id);
        $post = get_post($order_id);
        WC_Subscriptions_Order::pre_process_shop_order_meta($post->ID, $post);
        $subscription_key = "{$order->id}_{$product->id}";
        WC_Subscriptions_Manager::create_pending_subscription_for_order($order, $product->id);
        WC_Subscriptions_Manager::activate_subscription(2, $subscription_key);
        WC_Subscriptions_Manager::process_subscription_payment(2, $subscription_key);
        foreach (array(\'_line_subtotal\', \'_line_total\', \'_recurring_line_subtotal\', \'_recurring_line_total\') as $zero_value_key) {
            woocommerce_add_order_item_meta( $item_id, $zero_value_key, woocommerce_format_total($total) );
        }
        update_post_meta( $order_id, \'_order_total\', woocommerce_format_total($total) );    
        update_post_meta( $order_id, \'_order_recurring_total\', woocommerce_format_total($total) );
        WC_Subscriptions_Manager::set_next_payment_date($subscription_key, $user_id);
        woocommerce_add_order_item_meta($item_id, "_subscription_recurring_amount", woocommerce_format_total($total));
        $order = new WC_Order($order_id);
        $order->update_status(\'completed\');
    }

    private function getWooComProduct($product_title) {
        $find_args = array(
            \'post_type\'         => \'product\',
            \'post_status\'       => \'publish\',
            \'posts_per_page\'    => -1,
            \'fields\' => \'ids\'
        );
        $posts = get_posts( $find_args );
        foreach ($posts as $post) {
            $product = get_product($post);
            if (sanitize_title($product->get_title()) == sanitize_title($product_title))
                return $product;
        }
        return null;
    }

    private function getWooComVariation($product, $subscription) {
        $attributes = maybe_unserialize( get_post_meta( $product->id, \'_product_attributes\', true ) );
        $subscription_attr_slug;
        $subscription_attr_name;
        foreach($attributes as $key => $value) {
            if ( isset( $value[\'is_variation\'] ) && $value[\'is_variation\']) {
                $subscription_attr_slug = $key;
                $subscription_attr_name = $value[\'name\'];
                break;
            }
        }
        // Get variations
        $args = array(
            \'post_type\'     => \'product_variation\',
            \'post_status\'   => array( \'private\', \'publish\' ),
            \'numberposts\'   => -1,
            \'orderby\'       => \'menu_order\',
            \'order\'         => \'asc\',
            \'post_parent\'   => $product->id
        );
        $variations = get_posts( $args );
        foreach ( $variations as $variation ) {
            $variation_id           = absint( $variation->ID );
            $variation_post_status  = esc_attr( $variation->post_status );
            $variation_data         = get_post_meta( $variation_id );
            $variation_data[\'variation_id\'] = $variation_id;
            $variation_data[\'variation_attr_name\'] = $subscription_attr_name;
            $variation_data[\'variation_attr_name_value\'] = $subscription;
            if ($variation_data[\'attribute_\'.$subscription_attr_slug][0] == sanitize_title($subscription))
                return $variation_data;
        }           
        return null;
    }
结束