Null data are being saved after validation of post in ACF

ACF post are not saved after validation

I am hooking to the acf/validate_save_post to validate the save post.

// Validate the save post.
$this->loader->add_action( 'acf/validate_save_post', $invoice_post_type, 'validate_save_post', 10, 0 );

/**
     * Validate the save invoice post.
     */
    public function validate_save_post() {
        // Initialize the variable to check for the error in the post.
        $is_valid = true;

        // Invoice items repater and clone field keys.
        $ims_invoice_items_repeater_field_key             = 'field_5c4034030cff9';
        $ims_invoice_items_repeater_field_clone_field_key = 'field_5c443f4dd87de';

        // Field keys for items item.
        $ims_invoice_items_item_key            = $ims_invoice_items_repeater_field_clone_field_key . '_field_5c443eab22fe1';
        $ims_invoice_items_item_quantity_key   = $ims_invoice_items_repeater_field_clone_field_key . '_field_5c443eba22fe2';
        $ims_invoice_items_item_unit_price_key = $ims_invoice_items_repeater_field_clone_field_key . '_field_5c443ec622fe3';
        $ims_invoice_items_item_price_key      = $ims_invoice_items_repeater_field_clone_field_key . '_field_5c443edf22fe4';
        $ims_invoice_items_item_discount_key   = $ims_invoice_items_repeater_field_clone_field_key . '_field_5c443efd22fe5';
        $ims_invoice_items_item_amount_key     = $ims_invoice_items_repeater_field_clone_field_key . '_field_5c443f0a22fe6';

        // Field keys of invoice.
        $ims_invoice_sub_total_key = 'field_5c41b2ff17b09';
        $ims_invoice_discount_key  = 'field_5c41b31a17b0b';
        $ims_invoice_vat_key       = 'field_5c41b32617b0c';
        $ims_invoice_total_key     = 'field_5c41b33317b0d';
        $ims_invoice_paid_key      = 'field_5c41b33b17b0e';
        $ims_invoice_due_key       = 'field_5c41b34517b0f';

        // Get the items list.
        $ims_invoice_items = isset( $_POST['acf'][ $ims_invoice_items_repeater_field_key ] ) ? wp_unslash( $_POST['acf'][ $ims_invoice_items_repeater_field_key ] ) : array();
        // Initialize sub total.
        $calculated_sub_total = 0.0;
        // Stores items id, input key and quantitiy.
        $items_info = [];
        // Loop through each item and validate each item.
        foreach ( $ims_invoice_items as $key => $ims_invoice_item ) {
            // HTML Input key.
            $ims_invoice_items_unit_price_input = 'acf[' . $ims_invoice_items_repeater_field_key . '][' . $key . '][' . $ims_invoice_items_item_unit_price_key . ']';
            $ims_invoice_items_price_input      = 'acf[' . $ims_invoice_items_repeater_field_key . '][' . $key . '][' . $ims_invoice_items_item_price_key . ']';
            $ims_invoice_items_amount_input     = 'acf[' . $ims_invoice_items_repeater_field_key . '][' . $key . '][' . $ims_invoice_items_item_amount_key . ']';
            $ims_invoice_items_quantity_input   = 'acf[' . $ims_invoice_items_repeater_field_key . '][' . $key . '][' . $ims_invoice_items_item_quantity_key . ']';

            // Validate unit price.
            $ims_invoice_items_item_id    = $ims_invoice_items[ $key ][ $ims_invoice_items_item_key ];
            $ims_product_mrp              = round( floatval( get_field( 'ims_product_mrp', $ims_invoice_items_item_id ) ), 2 );
            $ims_invoice_items_unit_price = round( floatval( $ims_invoice_items[ $key ][ $ims_invoice_items_item_unit_price_key ] ), 2 );
            if ( $ims_product_mrp !== $ims_invoice_items_unit_price ) {
                acf_add_validation_error( $ims_invoice_items_unit_price_input, 'Invalid unit price.' );
                $is_valid = false;
            }

            // Validate price which is calculated in the client side.
            $ims_invoice_items_item_quantity = intval( $ims_invoice_items[ $key ][ $ims_invoice_items_item_quantity_key ] );
            $ims_invoice_items_item_price    = round( floatval( $ims_invoice_items[ $key ][ $ims_invoice_items_item_price_key ] ), 2 );
            $calculated_price                = round( $ims_invoice_items_item_quantity * $ims_product_mrp, 2 );
            if ( $calculated_price !== $ims_invoice_items_item_price ) {
                acf_add_validation_error( $ims_invoice_items_price_input, 'Invalid price.' );
                $is_valid = false;
            }

            // Add items id, input key and quantitiy.
            $items_info[] = array(
                'id'       => $ims_invoice_items_item_id,
                'input'    => $ims_invoice_items_quantity_input,
                'quantity' => $ims_invoice_items_item_quantity,
            );

            // Validate amount which is calculated in the client side.
            $ims_invoice_items_item_discount = round( floatval( $ims_invoice_items[ $key ][ $ims_invoice_items_item_discount_key ] ), 2 );
            $ims_invoice_items_item_amount   = round( floatval( $ims_invoice_items[ $key ][ $ims_invoice_items_item_amount_key ] ), 2 );
            $calculated_amount               = round( $calculated_price - $calculated_price * $ims_invoice_items_item_discount / 100.0, 2 );
            // var_dump(array(
            //  'ims_invoice_items_item_quantity' => $ims_invoice_items_item_quantity,
            //  'ims_invoice_items_item_price' => $ims_invoice_items_item_price,
            //  'ims_product_mrp' => $ims_product_mrp,
            //  'ims_invoice_items_unit_price' => $ims_invoice_items_unit_price,
            //  'calculated_price' => $calculated_price,
            //  'ims_invoice_items_item_discount' => $ims_invoice_items_item_discount,
            //  'ims_invoice_items_item_amount' => $ims_invoice_items_item_amount,
            //  'calculated_amount' => $calculated_amount,
            // ));
            if ( $calculated_amount !== $ims_invoice_items_item_amount ) {
                acf_add_validation_error( $ims_invoice_items_amount_input, 'Invalid amount.' );
                $is_valid = false;
            } else {
                $calculated_sub_total += $ims_invoice_items_item_amount;
            }
        }

        // var_dump( $items_info );

        $stored_items_info = [];
        if ( have_rows( 'ims_invoice_items' ) ) {
            while ( have_rows( 'ims_invoice_items' ) ) {
                the_row();
                $stored_items_info[] = array(
                    'id'       => get_sub_field( 'item_item' )->ID,
                    'quantity' => get_sub_field( 'item_quantity' ),
                );
            }
        }

        $available_stock_arr = [];
        $index               = 0;
        foreach ( $items_info as $item_info ) {
            $item_id = $item_info['id'];
            if ( ! isset( $available_stock_arr[ $item_id ] ) ) {
                $available_stock_arr[ $item_id ] = intval( get_field( 'ims_product_available_stock', $item_id ) );
            }
            // var_dump( $available_stock_arr);

            $item_quantity        = $item_info['quantity'];
            $stored_item_quantity = isset( $stored_items_info[ $index ]['quantity'] ) ? $stored_items_info[ $index ]['quantity'] : 0;
            $diff_quantity        = $item_quantity - $stored_item_quantity;

            // var_dump(array(
            //  'item_id' => $item_id,
            //  'item_quantity' => $item_quantity,
            //  'stored_item_quantity' => $stored_item_quantity,
            //  'diff_quantity' => $diff_quantity
            // ));
            if ( $diff_quantity > $available_stock_arr[ $item_id ] ) {
                acf_add_validation_error( $item_info['input'], "Not enough stock. Only {$available_stock_arr[ $item_id ]} available." );
                $is_valid = false;
            } else {
                $available_stock_arr[ $item_id ] -= $diff_quantity;
            }
            ++$index;

        }

        // var_dump( $stored_items_info );
        // exit;

        // Validate sub total.
        $ims_invoice_sub_total = isset( $_POST['acf'][ $ims_invoice_sub_total_key ] ) ? sanitize_text_field( wp_unslash( $_POST['acf'][ $ims_invoice_sub_total_key ] ) ) : null;
        $ims_invoice_sub_total = round( floatval( $ims_invoice_sub_total ), 2 );
        if ( $calculated_sub_total !== $ims_invoice_sub_total ) {
            $ims_invoice_items_sub_total_input = 'acf[' . $ims_invoice_sub_total_key . ']';
            acf_add_validation_error( $ims_invoice_items_sub_total_input, 'Invalid sub total.' );
            $is_valid = false;
        }

        $ims_invoice_discount = isset( $_POST['acf'][ $ims_invoice_discount_key ] ) ? sanitize_text_field( wp_unslash( $_POST['acf'][ $ims_invoice_discount_key ] ) ) : null;
        $ims_invoice_discount = round( floatval( $ims_invoice_discount ), 2 );

        $ims_invoice_vat = isset( $_POST['acf'][ $ims_invoice_vat_key ] ) ? sanitize_text_field( wp_unslash( $_POST['acf'][ $ims_invoice_vat_key ] ) ) : null;
        $ims_invoice_vat = round( floatval( $ims_invoice_vat ), 2 );

        // Validate the total.
        $ims_invoice_total                  = isset( $_POST['acf'][ $ims_invoice_total_key ] ) ? sanitize_text_field( wp_unslash( $_POST['acf'][ $ims_invoice_total_key ] ) ) : null;
        $ims_invoice_total                  = round( floatval( $ims_invoice_total ), 2 );
        $calculated_sub_total_with_discount = $calculated_sub_total - $calculated_sub_total * $ims_invoice_discount / 100.0;
        $calculated_sub_total_with_vat      = $calculated_sub_total_with_discount + $calculated_sub_total_with_discount * $ims_invoice_vat / 100.0;
        $calculated_total                   = round( $calculated_sub_total_with_vat, 2 );
        if ( $calculated_total !== $ims_invoice_total ) {
            $ims_invoice_items_total_input = 'acf[' . $ims_invoice_total_key . ']';
            acf_add_validation_error( $ims_invoice_items_total_input, 'Invalid total.' );
            $is_valid = false;
        }

        // Validate the due.
        $ims_invoice_paid = isset( $_POST['acf'][ $ims_invoice_paid_key ] ) ? sanitize_text_field( wp_unslash( $_POST['acf'][ $ims_invoice_paid_key ] ) ) : null;
        $ims_invoice_paid = floatval( $ims_invoice_paid );
        $ims_invoice_due  = isset( $_POST['acf'][ $ims_invoice_due_key ] ) ? sanitize_text_field( wp_unslash( $_POST['acf'][ $ims_invoice_due_key ] ) ) : null;
        $ims_invoice_due  = floatval( $ims_invoice_due );
        $calculated_due   = round( $calculated_total - $ims_invoice_paid, 2 );
        // var_dump(array(
        //  'ims_invoice_paid' => $ims_invoice_paid,
        //  'calculated_sub_total' => $calculated_sub_total,
        //  'calculate_due' => $calculated_due,
        //  'ims_invoice_due' => $ims_invoice_due,
        // ));
        // exit;

        if ( $calculated_due !== $ims_invoice_due ) {
            $ims_invoice_items_due_input = 'acf[' . $ims_invoice_due_key . ']';
            acf_add_validation_error( $ims_invoice_items_due_input, 'Invalid due.' );
            $is_valid = false;
        }

        if ( $is_valid ) {
            // Update the available stock of the product.
            foreach ( $available_stock_arr as $id => $available_stock ) {
                update_field( 'ims_product_available_stock', $available_stock, $id );
            }
        }

    }

The code runs fine. The validation step is done perfectly. But the post is saved with null fields after validation.

But if I remove the following code from the function it works fine.

if ( $is_valid ) {
            // Update the available stock of the product.
            foreach ( $available_stock_arr as $id => $available_stock ) {
                update_field( 'ims_product_available_stock', $available_stock, $id );
            }
        }

Read more here:: Null data are being saved after validation of post in ACF

Leave a Reply

Your email address will not be published. Required fields are marked *