PluginProbe
StoreEngine — Complete eCommerce Solution with Memberships, Licensing, Affiliates & More / 2.2.0
StoreEngine — Complete eCommerce Solution with Memberships, Licensing, Affiliates & More v2.2.0
2.3.0 2.2.0 2.1.1 2.1.0 2.0.0 1.10.0 1.9.1 1.9.0 1.2.1 1.2.2 1.3.0 1.3.1 1.3.2 1.3.3 1.4.0 1.5.0 1.5.1 1.5.2 1.5.3 1.5.4 1.5.5 1.5.6 1.5.7 1.5.8 1.6.0 All 59 releases
storeengine / includes / classes / refund.php

refund.php in StoreEngine — Complete eCommerce Solution with Memberships, Licensing, Affiliates & More 2.2.0, at includes/classes/refund.php

284 lines 7.5 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2
3 namespace StoreEngine\Classes;
4
5 use StoreEngine\Classes\Exceptions\StoreEngineException;
6 use StoreEngine\Classes\OrderStatus\OrderStatus;
7 use StoreEngine\Utils\Formatting;
8 use StoreEngine\Utils\Helper;
9
10 /**
11 * Represents an order refund.
12 */
13 class Refund extends AbstractOrder {
14
15 /**
16 * This is the name of this object type.
17 *
18 * @var string
19 */
20 protected string $object_type = 'refund_order';
21
22 /**
23 * Order meta-data with key => value.
24 *
25 * @var array
26 *
27 * @TODO move to extra.
28 * this is a placeholder for meta-data objects not k->v pair.
29 */
30 protected array $extra_data = [
31 //'amount' => '',
32 'reason' => '',
33 'refunded_by' => 0,
34 'refunded_payment' => false,
35 ];
36
37 protected bool $allow_trash = false;
38
39 public function __construct( $read = 0 ) {
40 $this->internal_meta_keys[] = '_reason';
41 $this->internal_meta_keys[] = '_refunded_by';
42 $this->internal_meta_keys[] = '_refunded_payment';
43 $this->meta_key_to_props['_reason'] = 'reason';
44 $this->meta_key_to_props['_refunded_by'] = 'refunded_by';
45 $this->meta_key_to_props['_refunded_payment'] = 'refunded_payment';
46
47 unset( $this->data['payment_method'], $this->data['payment_method_title'] );
48
49 parent::__construct( $read );
50 }
51
52 protected function read_db_data( $value, string $field = 'id' ): array {
53 return array_merge(
54 parent::read_db_data( $value, $field ),
55 [
56 'reason' => $this->get_metadata( '_reason' ),
57 'refunded_by' => $this->get_metadata( '_refunded_by' ),
58 'refunded_payment' => $this->get_metadata( '_refunded_payment' ),
59 ]
60 );
61 }
62
63 /**
64 * Get status - always completed for refunds.
65 *
66 * @param string $context What the value is for. Valid values are view and edit.
67 *
68 * @return string
69 */
70 public function get_status( string $context = 'view' ): ?string { // phpcs:ignore Generic.CodeAnalysis.UnusedFunctionParameter.FoundInExtendedClass
71 return OrderStatus::COMPLETED;
72 }
73
74 /**
75 * Get refunded amount.
76 *
77 * @param string $context What the value is for. Valid values are view and edit.
78 *
79 * @return float|string
80 */
81 public function get_amount( string $context = 'view' ) {
82 return $this->get_total_amount( $context );
83 }
84
85 public function get_total_amount( string $context = 'view' ) {
86 return $this->get_total( $context );
87 }
88
89 public function get_tax_amount( string $context = 'view' ) {
90 return $this->get_total_tax( $context );
91 }
92
93
94 /**
95 * Get refund reason.
96 *
97 * @param string $context What the value is for. Valid values are view and edit.
98 *
99 * @return string
100 */
101 public function get_reason( string $context = 'view' ): string {
102 return (string) $this->get_prop( 'reason', $context );
103 }
104
105 /**
106 * Get ID of user who did the refund.
107 *
108 * @param string $context What the value is for. Valid values are view and edit.
109 *
110 * @return int
111 */
112 public function get_refunded_by( string $context = 'view' ): int {
113 return (int) $this->get_prop( 'refunded_by', $context );
114 }
115
116 protected ?Customer $user = null;
117
118 public function get_refunded_by_user() {
119 if ( ! $this->user || ( is_a( $this->user, '\StoreEngine\Classes\Customer' ) && $this->user->get_id() !== $this->get_refunded_by() ) ) {
120 $this->user = Helper::get_customer( $this->get_refunded_by() );
121 }
122
123 return $this->user;
124 }
125
126 /**
127 * Return if the payment was refunded via API.
128 *
129 * @param string $context What the value is for. Valid values are view and edit.
130 *
131 * @return bool
132 */
133 public function get_refunded_payment( string $context = 'view' ): bool {
134 return Formatting::string_to_bool( $this->get_prop( 'refunded_payment', $context ) );
135 }
136
137 /**
138 * Get formatted refunded amount.
139 *
140 * @return string
141 */
142 public function get_formatted_refund_amount(): string {
143 return apply_filters( 'storeengine/formatted_refund_amount', Formatting::price( $this->get_amount(), [ 'currency' => $this->get_currency() ] ), $this );
144 }
145
146 /**
147 * Set refunded amount.
148 *
149 * @param string|float|int $value Value to set.
150 */
151 public function set_amount( $value ) {
152 $this->set_total_amount( $value );
153 }
154
155 public function set_total_amount( $amount ) {
156 $this->set_total( $amount );
157 }
158
159 /**
160 * Set refund reason.
161 *
162 * @param string $value Value to set.
163 */
164 public function set_reason( string $value ) {
165 $this->set_prop( 'reason', $value );
166 }
167
168 /**
169 * Set refunded by.
170 *
171 * @param int|string $value Value to set.
172 */
173 public function set_refunded_by( $value ) {
174 $this->set_prop( 'refunded_by', absint( $value ) );
175 }
176
177 /**
178 * Set if the payment was refunded via API.
179 *
180 * @param bool|string $value Value to set. (yes|no|1|0|true|false)
181 */
182 public function set_refunded_payment( $value ) {
183 $this->set_prop( 'refunded_payment', Formatting::string_to_bool( $value ) );
184 }
185
186 protected function query(): ?string {
187 global $wpdb;
188
189 return "
190 SELECT
191 o.id as o_id,
192 o.parent_order_id as parent_order_id,
193 o.*,
194 p.id as operational_id,
195 p.*
196 FROM {$wpdb->prefix}storeengine_orders o
197 LEFT JOIN {$wpdb->prefix}storeengine_order_operational_data p ON p.order_id = o.id
198 LEFT JOIN {$wpdb->prefix}storeengine_orders_meta m ON m.order_id = o.id
199 ";
200 }
201
202 protected function prepare_for_db( string $context = 'create' ): array {
203 $data = [];
204 $format = [];
205
206 $props = [
207 'status',
208 'currency',
209 'type',
210 'tax_amount',
211 'total_amount',
212 'customer_id',
213 'date_created_gmt',
214 'date_updated_gmt',
215 'parent_order_id',
216 ];
217
218 if ( 'create' === $context ) {
219 $this->set_date_prop( 'date_created_gmt', current_time( 'mysql', 1 ) );
220 }
221
222 // Always set.
223 $this->set_date_prop( 'date_updated_gmt', current_time( 'mysql', 1 ) );
224
225 foreach ( $props as $prop ) {
226 $value = $this->{"get_$prop"}( 'edit' );
227
228 if ( $value && is_a( $value, StoreengineDatetime::class ) ) {
229 $value = $this->prepare_date_for_db( $value );
230 }
231
232 $format[] = $this->predict_format( $prop, $value );
233 $data[ $prop ] = $value;
234 }
235
236 return [
237 'data' => apply_filters( 'storeengine/' . $this->object_type . '/db/' . $context, $data, $this ),
238 'format' => $format,
239 ];
240 }
241
242 protected function prepare_operational_data_for_db( string $context = 'create' ): array {
243 $data = [];
244 $format = [];
245
246 $props = [
247 'storeengine_version' => 'version',
248 'prices_include_tax' => 'prices_include_tax',
249 'coupon_usages_are_counted' => 'coupon_usages_are_counted',
250 'download_permission_granted' => 'download_permission_granted',
251 'cart_hash' => 'cart_hash',
252 'new_order_email_sent' => 'new_order_email_sent',
253 'order_key' => 'order_key',
254 'date_paid_gmt' => 'date_paid_gmt',
255 'date_completed_gmt' => 'date_completed_gmt',
256 'shipping_tax_amount' => 'shipping_tax_amount',
257 'shipping_total_amount' => 'shipping_total_amount',
258 'discount_tax_amount' => 'discount_tax_amount',
259 'discount_total_amount' => 'discount_total_amount',
260 'recorded_sales' => 'recorded_sales',
261 ];
262
263 if ( 'create' === $context ) {
264 $props['order_id'] = 'id';
265 }
266
267 foreach ( $props as $key => $prop ) {
268 $value = $this->{"get_$prop"}( 'edit' );
269
270 if ( $value && is_a( $value, StoreengineDatetime::class ) ) {
271 $value = $this->prepare_date_for_db( $value );
272 }
273
274 $format[] = $this->predict_format( $key, $value );
275 $data[ $key ] = $value;
276 }
277
278 return [
279 'data' => apply_filters( 'storeengine/' . $this->object_type . '_operational_data/db/' . $context, $data, $this ),
280 'format' => $format,
281 ];
282 }
283 }
284