1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
|
<?php /** * ApiUtil class file. */
namespace Automattic\WooCommerce\Internal;
/** * Helper methods for the REST API. * * Class ApiUtil * * @package Automattic\WooCommerce\Internal */ class RestApiParameterUtil {
/** * Converts a create refund request from the public API format: * * [ * "reason" => "", * "api_refund" => "x", * "api_restock" => "x", * "line_items" => [ * "id" => "111", * "quantity" => 222, * "refund_total" => 333, * "refund_tax" => [ * [ * "id": "444", * "refund_total": 555 * ],... * ],... * ] * * ...to the internally used format: * * [ * "reason" => null, (if it's missing or any empty value, set as null) * "api_refund" => true, (if it's missing or non-bool, set as "true") * "api_restock" => true, (if it's missing or non-bool, set as "true") * "line_items" => [ (convert sequential array to associative based on "id") * "111" => [ * "qty" => 222, (rename "quantity" to "qty") * "refund_total" => 333, * "refund_tax" => [ (convert sequential array to associative based on "id" and "refund_total) * "444" => 555,... * ],... * ] * ] * * It also calculates the amount if missing and whenever possible, see maybe_calculate_refund_amount_from_line_items. * * The conversion is done in a way that if the request is already in the internal format, * then nothing is changed for compatibility. For example, if the line items array * is already an associative array or any of its elements * is missing the "id" key, then the entire array is left unchanged. * Same for the "refund_tax" array inside each line item. * * @param \WP_REST_Request $request The request to adjust. */ public static function adjust_create_refund_request_parameters( \WP_REST_Request &$request ) { if ( empty( $request['reason'] ) ) { $request['reason'] = null; }
if ( ! is_bool( $request['api_refund'] ) ) { $request['api_refund'] = true; }
if ( ! is_bool( $request['api_restock'] ) ) { $request['api_restock'] = true; }
if ( empty( $request['line_items'] ) ) { $request['line_items'] = array(); } else { $request['line_items'] = self::adjust_line_items_for_create_refund_request( $request['line_items'] ); }
if ( ! isset( $request['amount'] ) ) { $amount = self::calculate_refund_amount_from_line_items( $request ); if ( null !== $amount ) { $request['amount'] = strval( $amount ); } } }
/** * Calculate the "amount" parameter for the request based on the amounts found in line items. * This will ONLY be possible if ALL of the following is true: * * - "line_items" in the request is a non-empty array. * - All line items have a "refund_total" field with a numeric value. * - All values inside "refund_tax" in all line items are a numeric value. * * The request is assumed to be in internal format already. * * @param \WP_REST_Request $request The request to maybe calculate the total amount for. * @return number|null The calculated amount, or null if it can't be calculated. */ private static function calculate_refund_amount_from_line_items( $request ) { $line_items = $request['line_items'];
if ( ! is_array( $line_items ) || empty( $line_items ) ) { return null; }
$amount = 0;
foreach ( $line_items as $item ) { if ( ! isset( $item['refund_total'] ) || ! is_numeric( $item['refund_total'] ) ) { return null; }
$amount += $item['refund_total'];
if ( ! isset( $item['refund_tax'] ) ) { continue; }
foreach ( $item['refund_tax'] as $tax ) { if ( ! is_numeric( $tax ) ) { return null; } $amount += $tax; } }
return $amount; }
/** * Convert the line items of a refund request to internal format (see adjust_create_refund_request_parameters). * * @param array $line_items The line items to convert. * @return array The converted line items. */ private static function adjust_line_items_for_create_refund_request( $line_items ) { if ( ! is_array( $line_items ) || empty( $line_items ) || self::is_associative( $line_items ) ) { return $line_items; }
$new_array = array(); foreach ( $line_items as $item ) { if ( ! isset( $item['id'] ) ) { return $line_items; }
if ( isset( $item['quantity'] ) && ! isset( $item['qty'] ) ) { $item['qty'] = $item['quantity']; } unset( $item['quantity'] );
if ( isset( $item['refund_tax'] ) ) { $item['refund_tax'] = self::adjust_taxes_for_create_refund_request_line_item( $item['refund_tax'] ); }
$id = $item['id']; $new_array[ $id ] = $item;
unset( $new_array[ $id ]['id'] ); }
return $new_array; }
/** * Adjust the taxes array from a line item in a refund request, see adjust_create_refund_parameters. * * @param array $taxes_array The array to adjust. * @return array The adjusted array. */ private static function adjust_taxes_for_create_refund_request_line_item( $taxes_array ) { if ( ! is_array( $taxes_array ) || empty( $taxes_array ) || self::is_associative( $taxes_array ) ) { return $taxes_array; }
$new_array = array(); foreach ( $taxes_array as $item ) { if ( ! isset( $item['id'] ) || ! isset( $item['refund_total'] ) ) { return $taxes_array; }
$id = $item['id']; $refund_total = $item['refund_total']; $new_array[ $id ] = $refund_total; }
return $new_array; }
/** * Is an array sequential or associative? * * @param array $the_array The array to check. * @return bool True if the array is associative, false if it's sequential. */ private static function is_associative( array $the_array ) { return array_keys( $the_array ) !== range( 0, count( $the_array ) - 1 ); } }
|