php - 基于 WooCommerce 产品的当前库存值(value)的自定义库存字段计算

标签 php wordpress woocommerce product stock

我正在努力改进我的库存管理,并直接从 WooCommerce 进行(这样就无需使用外部 CSV 文件计算)

我需要知道我需要订购的每种产品的数量(缺少库存)。 为了确定这一点,我使用 _stock 原生值和 2 个自定义字段进行计算:

_missing_stock:缺少库存的数量/我需要订购多少库存

_ref_stock:引用库存编号(手动设置,仓库中所需的库存数量)

所以:缺失股票=引用股票-股票值(value)


目的是根据已设置的引用库存和产品的当前库存自动计算和更新缺失库存值。 由于产品库存随着购买而减少,因此我可以快速查看每种产品需要订购的库存量。

基于Product regular price calculation based on 2 custom fields in Woocommerce 3答案代码有一些相似之处,我已经设法创建自定义字段并到目前为止。

但是我无法弄清楚如何最终自动更新 _missing_stock 值。

这是我设法得出的代码,自然(并且可能)不完全正确。

// Adding and displaying additional Stock custom fields
add_action( 'woocommerce_product_options_stock_status', 'additional_product_stock_option_fields', 50 );
function additional_product_stock_option_fields() {
    $domain = "woocommerce";
    global $post;

    echo '</div><div class="options_group stock show_if_simple show_if_external show_if_composite">';

    woocommerce_wp_text_input( array(
        'id'            => '_ref_stock',
        'label'         => __("Reference Stock", $domain ),
        'placeholder'   => '',
        'description'   => __("Amount of desired target stock in warehouse )", $domain ),
        'desc_tip'      => true,
    ) );


    woocommerce_wp_text_input( array(
        'id'            => '_missing_stock',
        'label'         => __("Missing Stock", $domain ) . ' ('. get_woocommerce_currency_symbol() . ')',
        'placeholder'   => '',
        'description'   => __("Amount of stock that needs to be ordered", $domain ),
        'desc_tip'      => true,
    ) );

    echo '<input type="hidden" name="_custom_stock_nonce" value="' . wp_create_nonce() . '">';

}

// Utility function that save "Reference Stock" and "missing_stock" custom fields values
function saving_ref_stock_and_missing_stock( $product ) {
    // Security check
    if ( isset($_POST['_custom_stock_nonce']) && ! wp_verify_nonce($_POST['_custom_stock_nonce']) ) {
        return;
    }

    // Save "Reference Stock" and "missing_stock" custom fields values
    if( isset($_POST['_ref_stock']) && isset($_POST['_missing_stock']) ) {
        $product->update_meta_data('_ref_stock', sanitize_text_field( (float) $_POST['_ref_stock'] ) );
        $product->update_meta_data('_missing_stock', sanitize_text_field( (float) $_POST['_missing_stock'] ) );
    }
}

// Utility function: Calculate and save product "missing stock" custom field from the "Reference Stock" custom field and the "Stock" field
function calculate_and_save_new_product_stock( $product ) {

// Check if product stock management is enabled
 if ( !$product->managing_stock() ) {
    // Calculate and save the missing stock
    if( isset($_POST['_ref_stock']) && isset($_POST['_missing_stock'])
    && $_POST['_ref_stock'] > 0 && $_POST['_missing_stock'] > 0 ) {

        // Catch the stock data
        $ref_stock    = (float) $_POST['_ref_stock'];
        $missing_stock = (float) $_POST['_missing_stock'];
        $current_stock   = (float) $product->get_stock_quantity();

        // Calculating missing stock
        $missing_stock  = $ref_stock - $current_stock;

     
        }
    }
}

// Saving and calculating Stock values
add_action( 'woocommerce_admin_process_product_object', 'update_product_meta_data', 100, 1 );
function update_product_meta_data( $product ) {

    // Saving "Reference Stock" and "missing_stock" custom fields values
    saving_ref_stock_and_missing_stock( $product ); // <== To be removed if not used with the first function

    // Calculate and save Missing Stock from the "Reference Stock" and the "Stock" custom fields
    calculate_and_save_new_product_missing_stock( $product );
}

预先感谢您的关注和建议。

最佳答案

您已经使用并已调整的代码比您的问题稍微广泛一些,因此下面是一个简化版本。

当您要在后端保存调整以确定自定义字段的值时,您确实可以使用 woocommerce_admin_process_product_object

但是,下单后当库存发生调整时,您的自定义字段的值将不会自动调整。

为此,您可以使用 woocommerce_product_set_stock 操作 Hook 。

此代码是为“简单”产品编写的,但如果需要,可以轻松扩展到其他类型的产品。

通过代码中添加的注释标签进行解释

// Adding and displaying additional custom fields
function action_woocommerce_product_options_stock_status() {
    $domain = 'woocommerce';
    
    echo '</div><div class="options_group">';
    
    woocommerce_wp_text_input( array(
        'id'                 => '_ref_stock',
        'label'              => __( 'Reference Stock', $domain ),
        'placeholder'        => '',
        'description'        => __( 'Amount of desired target stock in warehouse', $domain ),
        'desc_tip'           => true,
    ));

    woocommerce_wp_text_input( array(
        'id'                 => '_missing_stock',
        'label'              => __( 'Missing Stock', $domain ),
        'placeholder'        => '',
        'description'        => __( 'Amount of stock that needs to be ordered', $domain ),
        'desc_tip'           => true,
        'custom_attributes'  => array( 'readonly' => 'readonly' ),
    ));
}
add_action( 'woocommerce_product_options_stock_status', 'action_woocommerce_product_options_stock_status', 10, 1 );

// Save custom field
function action_woocommerce_admin_process_product_object( $product ) {
    // Isset
    if ( isset( $_POST['_ref_stock'] ) ) {
        // ID & value
        $ref_stock_id = '_ref_stock';
        $ref_stock_val = sanitize_text_field( $_POST['_ref_stock'] );
        
        // Update ref stock
        $product->update_meta_data( $ref_stock_id, $ref_stock_val );
        
        // Get stock quantity
        $current_stock = (float) $product->get_stock_quantity();

        // NOT empty
        if ( ! empty ( $current_stock ) ) {
            // ID
            $missing_stock_id = '_missing_stock';
            
            // Calculating missing stock
            $missing_stock_val = $ref_stock_val - $current_stock;
            
            // Update missing stock
            $product->update_meta_data( $missing_stock_id, $missing_stock_val );
        }
    }
}
add_action( 'woocommerce_admin_process_product_object', 'action_woocommerce_admin_process_product_object', 10, 1 );

// When the stock changed
function action_woocommerce_product_set_stock ( $product_with_stock ) {
    global $pagenow;

    // Exit
    if ( is_admin() && $pagenow === 'post.php' )
        return;
    
    // Get meta
    $ref_stock_val = $product_with_stock->get_meta( '_ref_stock' );
    
    // NOT empty
    if ( ! empty ( $ref_stock_val ) ) {
        // Get stock quantity
        $current_stock = (float) $product_with_stock->get_stock_quantity();

        // NOT empty
        if ( ! empty ( $current_stock ) ) {
            // ID
            $missing_stock_id = '_missing_stock';
            
            // Calculating missing stock
            $missing_stock_val = $ref_stock_val - $current_stock;
            
            // Update missing stock
            $product_with_stock->update_meta_data( $missing_stock_id, $missing_stock_val );
            
            // Save
            $product_with_stock->save();
        }       
    }
}
add_action( 'woocommerce_product_set_stock', 'action_woocommerce_product_set_stock', 10, 1 );

关于php - 基于 WooCommerce 产品的当前库存值(value)的自定义库存字段计算,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/65054066/

相关文章:

javascript - Axios Put 请求在 Vue.js 中给出 404 错误

php - 根据用户角色和产品类别应用不同的税收 (Woocommerce)

javascript - 无法正确提醒已选中复选框的 ID

php - 无法传递字符串参数

php - 主题更新时,子主题中的 header.php 会更新吗?

wordpress - 在哪里保存 openshift wordpress 安装的插件

php - 在 Woocommerce 中显示客户订单评论(客户备注)

javascript - Ajax:ajax 响应中的链接不起作用

php - PHP 是否处理多维 $_REQUEST 数组?

php - $wpdb 在 WordPress 插件文件中不起作用