From d9d241a750c0b0adfc42b25a86a97169ac68f34f Mon Sep 17 00:00:00 2001 From: Yanuar Date: Tue, 14 Jul 2026 16:20:25 +0700 Subject: [PATCH] fix(RequestPickup): destination_zipcode payload not stored properly --- inc/Controllers/CheckoutController.php | 35 +++++++++ .../CreateTransactionService.php | 3 + .../SendRequestPickupTransactionService.php | 38 +++++++++- tests/RequestPickupPaymentFlowTest.php | 74 +++++++++++++++++++ 4 files changed, 148 insertions(+), 2 deletions(-) diff --git a/inc/Controllers/CheckoutController.php b/inc/Controllers/CheckoutController.php index 153484f..acb318d 100644 --- a/inc/Controllers/CheckoutController.php +++ b/inc/Controllers/CheckoutController.php @@ -392,6 +392,14 @@ private function kiriof_resolve_destination_area( $destination_area, $destinatio return array( $destination_area, $destination_name ); } + private function kiriof_extract_postcode_from_destination_name( $destination_name ): string { + if ( preg_match( '/(?:^|,\s*)(\d{5})\s*$/', (string) $destination_name, $matches ) ) { + return $matches[1]; + } + + return ''; + } + private function kiriof_is_store_api_request() { if ( ! defined( 'REST_REQUEST' ) || ! REST_REQUEST ) { return false; @@ -962,6 +970,7 @@ function afterCheckoutAfterCreated( $order_id, $posted_data, $order ){ 'wc_cart_contents' => WC()->cart->cart_contents, 'woo_discount_amount' => (float) $woo_discount_amount, 'woo_discount_description' => (string) $woo_discount_description, + 'destination_zipcode' => $order ? (string) $order->get_meta( '_kiriof_checkout_postcode', true ) : '', ]))->call(); (new \KiriminAjaOfficial\Base\BaseInit())->logThis('afterCheckoutAfterCreated',[$createTransaction]); } catch (\Throwable $th){ @@ -979,6 +988,7 @@ function afterCheckoutAfterCreated( $order_id, $posted_data, $order ){ $order->delete_meta_data( '_kiriof_checkout_force_insurance' ); $order->delete_meta_data( '_kiriof_checkout_woocommerce_discount_amount' ); $order->delete_meta_data( '_kiriof_checkout_woocommerce_discount_description' ); + $order->delete_meta_data( '_kiriof_checkout_postcode' ); $order->save(); } } @@ -1084,6 +1094,31 @@ function afterCheckoutBeforeCreated($order,$data ){ $order->update_meta_data( '_kiriof_checkout_force_insurance', $kiriof_force_insurance_post ); $order->update_meta_data( '_kiriof_checkout_woocommerce_discount_amount', $woo_discount_amount ); $order->update_meta_data( '_kiriof_checkout_woocommerce_discount_description', $woo_discount_description ); + $kiriof_checkout_postcode = ''; + if ( empty( $_POST['ship_to_different_address'] ) ) { + $kiriof_checkout_postcode = isset( $_POST['billing_postcode'] ) ? sanitize_text_field( wp_unslash( $_POST['billing_postcode'] ) ) : ''; + } else { + $kiriof_checkout_postcode = isset( $_POST['shipping_postcode'] ) ? sanitize_text_field( wp_unslash( $_POST['shipping_postcode'] ) ) : ''; + } + $kiriof_checkout_postcode = trim( preg_replace( '/\s+/', '', (string) $kiriof_checkout_postcode ) ); + if ( '' === $kiriof_checkout_postcode ) { + $kiriof_checkout_postcode = sanitize_text_field( (string) WC()->session->get( 'kiriof_checkout_postcode', '' ) ); + $kiriof_checkout_postcode = trim( preg_replace( '/\s+/', '', (string) $kiriof_checkout_postcode ) ); + } + if ( '' === $kiriof_checkout_postcode ) { + $kiriof_checkout_postcode = $this->kiriof_extract_postcode_from_destination_name( $destinasi_name ); + } + if ( '' !== $kiriof_checkout_postcode ) { + $order->update_meta_data( '_kiriof_checkout_postcode', $kiriof_checkout_postcode ); + if ( empty( $_POST['ship_to_different_address'] ) ) { + $order->set_billing_postcode( $kiriof_checkout_postcode ); + if ( '' === (string) $order->get_shipping_postcode() ) { + $order->set_shipping_postcode( $kiriof_checkout_postcode ); + } + } else { + $order->set_shipping_postcode( $kiriof_checkout_postcode ); + } + } /** * save to custom order metadata * field kelurahan diff --git a/inc/Services/CheckoutServices/CreateTransactionService.php b/inc/Services/CheckoutServices/CreateTransactionService.php index cbf49d9..bdc7d18 100644 --- a/inc/Services/CheckoutServices/CreateTransactionService.php +++ b/inc/Services/CheckoutServices/CreateTransactionService.php @@ -45,6 +45,9 @@ public function call(){ if (!$requiredPostMeta['status']){ return self::error([],$requiredPostMeta['message']); } + if ( ! empty( $this->payload['destination_zipcode'] ) ) { + $requiredPostMeta['data']['_kiriof_checkout_postcode'] = sanitize_text_field( (string) $this->payload['destination_zipcode'] ); + } /** Generating Payload*/ $calcResult = $checkoutCalc['data']['calculation_result']; $cartsAttr = $checkoutCalc['data']['carts_attribute']; diff --git a/inc/Services/TransactionProcessServices/SendRequestPickupTransactionService.php b/inc/Services/TransactionProcessServices/SendRequestPickupTransactionService.php index 32d3a6c..9f53658 100644 --- a/inc/Services/TransactionProcessServices/SendRequestPickupTransactionService.php +++ b/inc/Services/TransactionProcessServices/SendRequestPickupTransactionService.php @@ -85,13 +85,38 @@ private function readShippingInfoValue($shippingInfo, array $keys): string return ''; } + private function readOrderMetaValue($order, array $keys): string + { + if (!$order || !method_exists($order, 'get_meta')) { + return ''; + } + + foreach ($keys as $key) { + $value = trim((string) $order->get_meta($key, true)); + if ('' !== $value) { + return $value; + } + } + + return ''; + } + + private function extractPostcodeFromDestinationText($destinationText): string + { + if (preg_match('/(?:^|,\s*)(\d{5})\s*$/', (string) $destinationText, $matches)) { + return $matches[1]; + } + + return ''; + } + private function buildDestinationData($shippingInfo, $order, $transaction): array { $billingFirstName = $this->readShippingInfoValue($shippingInfo, ['_billing_first_name', 'billing_first_name', 'first_name']); $billingLastName = $this->readShippingInfoValue($shippingInfo, ['_billing_last_name', 'billing_last_name', 'last_name']); $billingAddress1 = $this->readShippingInfoValue($shippingInfo, ['_billing_address_1', 'billing_address_1', 'address_1']); $billingAddress2 = $this->readShippingInfoValue($shippingInfo, ['_billing_address_2', 'billing_address_2', 'address_2']); - $billingPostcode = $this->readShippingInfoValue($shippingInfo, ['_billing_postcode', 'billing_postcode', 'postcode']); + $billingPostcode = $this->readShippingInfoValue($shippingInfo, ['_billing_postcode', 'billing_postcode', 'postcode', '_kiriof_checkout_postcode', 'kiriof_checkout_postcode']); $billingPhone = $this->readShippingInfoValue($shippingInfo, ['_billing_phone', 'billing_phone', 'phone']); $shippingFirstName = $this->readShippingInfoValue($shippingInfo, ['_shipping_first_name', 'shipping_first_name']); @@ -101,7 +126,7 @@ private function buildDestinationData($shippingInfo, $order, $transaction): arra $shippingCity = $this->readShippingInfoValue($shippingInfo, ['_shipping_city', 'shipping_city', '_billing_city', 'billing_city', 'city']); $shippingState = $this->readShippingInfoValue($shippingInfo, ['_shipping_state', 'shipping_state', '_billing_state', 'billing_state', 'state']); $shippingCountry = $this->readShippingInfoValue($shippingInfo, ['_shipping_country', 'shipping_country', '_billing_country', 'billing_country', 'country']); - $shippingPostcode = $this->readShippingInfoValue($shippingInfo, ['_shipping_postcode', 'shipping_postcode', '_billing_postcode', 'billing_postcode', 'postcode']); + $shippingPostcode = $this->readShippingInfoValue($shippingInfo, ['_shipping_postcode', 'shipping_postcode', '_billing_postcode', 'billing_postcode', 'postcode', '_kiriof_checkout_postcode', 'kiriof_checkout_postcode']); $shippingPhone = $this->readShippingInfoValue($shippingInfo, ['_shipping_phone', 'shipping_phone', '_billing_phone', 'billing_phone', 'phone']); $billingAddressData = $order && method_exists($order, 'get_address') ? (array) $order->get_address('billing') : []; $shippingAddressData = $order && method_exists($order, 'get_address') ? (array) $order->get_address('shipping') : []; @@ -137,6 +162,9 @@ private function buildDestinationData($shippingInfo, $order, $transaction): arra if ('' === $billingPostcode) { $billingPostcode = (string) $order->get_billing_postcode(); } + if ('' === $billingPostcode) { + $billingPostcode = $this->readOrderMetaValue($order, ['_billing_postcode', 'billing_postcode', '_kiriof_checkout_postcode', 'kiriof_checkout_postcode']); + } if ('' === $billingPhone) { $billingPhone = trim((string) ($billingAddressData['phone'] ?? '')); } @@ -191,6 +219,12 @@ private function buildDestinationData($shippingInfo, $order, $transaction): arra if ('' === $shippingPostcode) { $shippingPostcode = (string) $order->get_shipping_postcode(); } + if ('' === $shippingPostcode) { + $shippingPostcode = $this->readOrderMetaValue($order, ['_shipping_postcode', 'shipping_postcode', '_billing_postcode', 'billing_postcode', '_kiriof_checkout_postcode', 'kiriof_checkout_postcode']); + } + if ('' === $shippingPostcode) { + $shippingPostcode = $this->extractPostcodeFromDestinationText($transaction->destination_sub_district ?? ''); + } if ('' === $shippingPhone) { $shippingPhone = trim((string) ($shippingAddressData['phone'] ?? '')); } diff --git a/tests/RequestPickupPaymentFlowTest.php b/tests/RequestPickupPaymentFlowTest.php index d3a969e..42c4753 100644 --- a/tests/RequestPickupPaymentFlowTest.php +++ b/tests/RequestPickupPaymentFlowTest.php @@ -273,6 +273,80 @@ public function payment_list_fees_column_subtracts_platform_shipping_discount(): ); } + #[Test] + public function request_pickup_preserves_checkout_postcode_for_destination_zipcode(): void + { + $checkoutController = file_get_contents(PLUGIN_DIR . '/inc/Controllers/CheckoutController.php'); + $createTransactionService = file_get_contents(PLUGIN_DIR . '/inc/Services/CheckoutServices/CreateTransactionService.php'); + $requestPickupService = file_get_contents(PLUGIN_DIR . '/inc/Services/TransactionProcessServices/SendRequestPickupTransactionService.php'); + + $this->assertStringContainsString( + "\$order->update_meta_data( '_kiriof_checkout_postcode', \$kiriof_checkout_postcode );", + $checkoutController, + 'Checkout must persist the buyer postcode on the order before transaction creation' + ); + + $this->assertStringContainsString( + "\$order->set_billing_postcode( \$kiriof_checkout_postcode );", + $checkoutController, + 'Checkout must mirror the resolved postcode into WooCommerce billing postcode' + ); + + $this->assertStringContainsString( + "\$order->set_shipping_postcode( \$kiriof_checkout_postcode );", + $checkoutController, + 'Checkout must mirror the resolved postcode into WooCommerce shipping postcode' + ); + + $this->assertStringContainsString( + 'private function kiriof_extract_postcode_from_destination_name( $destination_name ): string', + $checkoutController, + 'Classic checkout must extract postcode from KiriminAja district labels when no postcode field exists' + ); + + $this->assertStringContainsString( + "\$kiriof_checkout_postcode = \$this->kiriof_extract_postcode_from_destination_name( \$destinasi_name );", + $checkoutController, + 'Checkout postcode must fall back to the trailing postal code in the selected district name' + ); + + $this->assertStringContainsString( + "'destination_zipcode' => \$order ? (string) \$order->get_meta( '_kiriof_checkout_postcode', true ) : '',", + $checkoutController, + 'Checkout must pass the persisted postcode into transaction creation' + ); + + $this->assertStringContainsString( + "\$requiredPostMeta['data']['_kiriof_checkout_postcode'] = sanitize_text_field( (string) \$this->payload['destination_zipcode'] );", + $createTransactionService, + 'Transaction shipping_info must keep checkout postcode for later request pickup payloads' + ); + + $this->assertStringContainsString( + 'private function readOrderMetaValue($order, array $keys): string', + $requestPickupService, + 'Request pickup destination zipcode must support WooCommerce order meta fallbacks' + ); + + $this->assertStringContainsString( + "\$shippingPostcode = \$this->readOrderMetaValue(\$order, ['_shipping_postcode', 'shipping_postcode', '_billing_postcode', 'billing_postcode', '_kiriof_checkout_postcode', 'kiriof_checkout_postcode']);", + $requestPickupService, + 'Request pickup destination zipcode must fall back to WooCommerce shipping and billing postcode meta' + ); + + $this->assertStringContainsString( + "\$shippingPostcode = \$this->extractPostcodeFromDestinationText(\$transaction->destination_sub_district ?? '');", + $requestPickupService, + 'Existing request pickup transactions must recover destination zipcode from trailing postal code in district text' + ); + + $this->assertStringContainsString( + '"destination_zipcode" => $destinationData[\'zipcode\']', + $requestPickupService, + 'Request pickup package payload must send destination_zipcode from resolved destination data' + ); + } + #[Test] public function platform_shipping_discount_label_distinguishes_from_user_coupon(): void {