PluginProbe
Formidable Forms – WordPress Form Builder for Contact Forms, Calculators, Quizzes & More / trunk
Formidable Forms – WordPress Form Builder for Contact Forms, Calculators, Quizzes & More vtrunk
6.35 6.34 6.33.1 6.33 6.32.1 6.32 6.31 6.25 6.25.1 6.26 6.26.1 6.27 6.28 6.29 6.3 6.3.1 6.3.2 6.30 6.4 6.4.1 6.4.2 6.5 6.5.1 6.5.2 6.5.3 All 141 releases
← All changes | classes/models/FrmEntryMeta.php +266 -85 6.3 → trunk View file →
@@ -5,18 +5,24 @@
5 5
6 6 class FrmEntryMeta {
7 7
8 8 /**
9 - * @param int $entry_id
10 - * @param int $field_id
11 - * @param string $meta_key usually set to '' as this parameter is no longer used.
12 - * @param mixed $meta_value
9 + * @since 6.35 Added the $field parameter.
10 + *
11 + * @param int $entry_id
12 + * @param int $field_id
13 + * @param string $meta_key usually set to '' as this parameter is no longer used.
14 + * @param mixed $meta_value
15 + * @param stdClass|null $field The field $field_id belongs to, when the caller already has
16 + * it loaded. Looked up here when it is not passed.
17 + *
18 + * @return int
13 19 */
14 - public static function add_entry_meta( $entry_id, $field_id, $meta_key, $meta_value ) {
20 + public static function add_entry_meta( $entry_id, $field_id, $meta_key, $meta_value, $field = null ) {
15 21 global $wpdb;
16 22
17 23 if ( FrmAppHelper::is_empty_value( $meta_value ) ) {
18 - // don't save blank fields
24 + // Don't save blank fields
19 25 return 0;
20 26 }
21 27
22 28 $new_values = array(
@@ -25,33 +31,34 @@
25 31 'field_id' => $field_id,
26 32 'created_at' => current_time( 'mysql', 1 ),
27 33 );
28 34
29 - self::set_value_before_save( $new_values );
30 - $new_values = apply_filters( 'frm_add_entry_meta', $new_values );
31 -
35 + self::set_value_before_save( $new_values, $field );
36 + $new_values = apply_filters( 'frm_add_entry_meta', $new_values );
32 37 $query_results = $wpdb->insert( $wpdb->prefix . 'frm_item_metas', $new_values );
33 38
34 39 if ( $query_results ) {
35 40 self::clear_cache();
36 41 wp_cache_delete( $entry_id, 'frm_entry' );
37 - $id = $wpdb->insert_id;
38 - } else {
39 - $id = 0;
42 + return $wpdb->insert_id;
40 43 }
41 44
42 - return $id;
45 + return 0;
43 46 }
44 47
45 48 /**
46 - * @param int $entry_id
47 - * @param int $field_id
48 - * @param string $meta_key deprecated
49 - * @param array|string $meta_value
49 + * @since 6.35 Added the $field parameter.
50 50 *
51 - * @return bool|false|int
51 + * @param int $entry_id
52 + * @param int $field_id
53 + * @param string $meta_key Deprecated.
54 + * @param array|string $meta_value
55 + * @param stdClass|null $field The field $field_id belongs to, when the caller already has
56 + * it loaded. Looked up here when it is not passed.
57 + *
58 + * @return bool|int
52 59 */
53 - public static function update_entry_meta( $entry_id, $field_id, $meta_key, $meta_value ) {
60 + public static function update_entry_meta( $entry_id, $field_id, $meta_key, $meta_value, $field = null ) {
54 61 if ( ! $field_id ) {
55 62 return false;
56 63 }
57 64
@@ -62,14 +69,15 @@
62 69 'field_id' => $field_id,
63 70 );
64 71 $where_values = $values;
65 72 $values['meta_value'] = $meta_value;
66 - self::set_value_before_save( $values );
73 + self::set_value_before_save( $values, $field );
67 74 $values = apply_filters( 'frm_update_entry_meta', $values );
68 75
69 76 if ( is_array( $values['meta_value'] ) ) {
70 77 $values['meta_value'] = array_filter( $values['meta_value'], 'FrmAppHelper::is_not_empty_value' );
71 78 }
79 +
72 80 $meta_value = maybe_serialize( $values['meta_value'] );
73 81
74 82 wp_cache_delete( $entry_id, 'frm_entry' );
75 83 self::clear_cache();
@@ -78,20 +86,36 @@
78 86 }
79 87
80 88 /**
81 89 * @since 3.0
90 + * @since 6.35 Added the $field parameter.
91 + *
92 + * @param array $values
93 + * @param stdClass|null $field The field for $values['field_id'], when the caller already has
94 + * it loaded. Looked up here when it is not passed.
95 + *
96 + * @return void
82 97 */
83 - private static function set_value_before_save( &$values ) {
84 - $field = FrmField::getOne( $values['field_id'] );
85 - if ( $field ) {
86 - $field_obj = FrmFieldFactory::get_field_object( $field );
98 + private static function set_value_before_save( &$values, $field = null ) {
99 + if ( ! is_object( $field ) ) {
100 + $field = FrmField::getOne( $values['field_id'] );
101 + }
87 102
88 - $values['meta_value'] = $field_obj->set_value_before_save( $values['meta_value'] );
103 + if ( ! $field ) {
104 + return;
89 105 }
106 +
107 + $field_obj = FrmFieldFactory::get_field_object( $field );
108 + $values['meta_value'] = $field_obj->set_value_before_save( $values['meta_value'] );
90 109 }
91 110
92 111 /**
93 112 * @since 3.0
113 + *
114 + * @param array $atts
115 + * @param mixed $value
116 + *
117 + * @return void
94 118 */
95 119 private static function get_value_to_save( $atts, &$value ) {
96 120 if ( is_object( $atts['field'] ) ) {
97 121 $field_obj = FrmFieldFactory::get_field_object( $atts['field'] );
@@ -106,13 +130,19 @@
106 130
107 131 $value = apply_filters( 'frm_prepare_data_before_db', $value, $atts['field_id'], $atts['entry_id'], array( 'field' => $atts['field'] ) );
108 132 }
109 133
134 + /**
135 + * @param int|string $entry_id
136 + * @param array $values Either indexed by field ID or field key.
137 + *
138 + * @return void
139 + */
110 140 public static function update_entry_metas( $entry_id, $values ) {
111 141 global $wpdb;
112 142
113 - $prev_values = FrmDb::get_col(
114 - $wpdb->prefix . 'frm_item_metas',
143 + $previous_field_ids = FrmDb::get_col(
144 + 'frm_item_metas',
115 145 array(
116 146 'item_id' => $entry_id,
117 147 'field_id !' => 0,
118 148 ),
@@ -118,53 +148,69 @@
118 148 ),
119 149 'field_id'
120 150 );
121 151
122 - foreach ( $values as $field_id => $meta_value ) {
123 - $field = false;
124 - if ( ! empty( $field_id ) ) {
125 - $field = FrmField::getOne( $field_id );
152 + $values_indexed_by_field_id = array();
153 +
154 + foreach ( $values as $field_id_or_key => $meta_value ) {
155 + $field_id = $field_id_or_key;
156 + $field = null;
157 +
158 + if ( $field_id_or_key ) {
159 + $field = FrmField::getOne( $field_id_or_key );
160 +
161 + if ( is_object( $field ) ) {
162 + $field_id = $field->id;
163 + }
126 164 }
127 165
166 + $values_indexed_by_field_id[ $field_id ] = $meta_value;
167 +
128 168 self::get_value_to_save( compact( 'field', 'field_id', 'entry_id' ), $meta_value );
129 169
130 - if ( $prev_values && in_array( $field_id, $prev_values ) ) {
170 + if ( ! $previous_field_ids || ! in_array( $field_id, $previous_field_ids, true ) ) {
171 + // If value does not exist, then create it
172 + self::add_entry_meta( $entry_id, $field_id, '', $meta_value, $field );
173 + continue;
174 + }
131 175
132 - if ( ( is_array( $meta_value ) && empty( $meta_value ) ) || ( ! is_array( $meta_value ) && trim( $meta_value ) == '' ) ) {
133 - // remove blank fields
134 - unset( $values[ $field_id ] );
135 - } else {
136 - // if value exists, then update it
137 - self::update_entry_meta( $entry_id, $field_id, '', $meta_value );
138 - }
176 + if ( $meta_value === array() || ( ! is_array( $meta_value ) && trim( $meta_value ) === '' ) ) {
177 + // Remove blank fields.
178 + unset( $values_indexed_by_field_id[ $field_id ] );
139 179 } else {
140 - // if value does not exist, then create it
141 - self::add_entry_meta( $entry_id, $field_id, '', $meta_value );
180 + // If value exists, then update it
181 + self::update_entry_meta( $entry_id, $field_id, '', $meta_value, $field );
142 182 }
143 - }
183 + }//end foreach
144 184
145 - if ( empty( $prev_values ) ) {
185 + if ( ! $previous_field_ids ) {
146 186 return;
147 187 }
148 188
149 - $prev_values = array_diff( $prev_values, array_keys( $values ) );
189 + $field_ids_to_remove = array_diff( $previous_field_ids, array_keys( $values_indexed_by_field_id ) );
150 190
151 - if ( empty( $prev_values ) ) {
191 + if ( ! $field_ids_to_remove ) {
152 192 return;
153 193 }
154 194
155 - // prepare the query
195 + // Prepare the query
156 196 $where = array(
157 197 'item_id' => $entry_id,
158 - 'field_id' => $prev_values,
198 + 'field_id' => $field_ids_to_remove,
159 199 );
160 200 FrmDb::get_where_clause_and_values( $where );
161 201
162 202 // Delete any leftovers
163 - $wpdb->query( $wpdb->prepare( 'DELETE FROM ' . $wpdb->prefix . 'frm_item_metas ' . $where['where'], $where['values'] ) ); // phpcs:ignore WordPress.DB.PreparedSQL.NotPrepared
203 + $wpdb->query( $wpdb->prepare( 'DELETE FROM ' . $wpdb->prefix . 'frm_item_metas ' . $where['where'], $where['values'] ) ); // phpcs:ignore WordPress.DB.PreparedSQL.NotPrepared, SlevomatCodingStandard.Files.LineLength.LineTooLong
164 204 self::clear_cache();
165 205 }
166 206
207 + /**
208 + * @param int $old_id
209 + * @param int $new_id
210 + *
211 + * @return void
212 + */
167 213 public static function duplicate_entry_metas( $old_id, $new_id ) {
168 214 $metas = self::get_entry_meta_info( $old_id );
169 215
170 216 /**
@@ -174,8 +220,9 @@
174 220 *
175 221 * @param array $metas The list of entry meta values.
176 222 */
177 223 $metas = apply_filters( 'frm_before_duplicate_entry_values', $metas );
224 +
178 225 foreach ( $metas as $meta ) {
179 226 self::add_entry_meta( $new_id, $meta->field_id, '', $meta->meta_value );
180 227 unset( $meta );
181 228 }
@@ -181,8 +228,14 @@
181 228 }
182 229 self::clear_cache();
183 230 }
184 231
232 + /**
233 + * @param int $entry_id
234 + * @param int $field_id
235 + *
236 + * @return false|int
237 + */
185 238 public static function delete_entry_meta( $entry_id, $field_id ) {
186 239 global $wpdb;
187 240 self::clear_cache();
188 241
@@ -193,8 +246,10 @@
193 246 * Clear entry meta caching
194 247 * Called when a meta is added or changed
195 248 *
196 249 * @since 2.0.5
250 + *
251 + * @return void
197 252 */
198 253 public static function clear_cache() {
199 254 FrmDb::cache_delete_group( 'frm_entry_meta' );
200 255 FrmDb::cache_delete_group( 'frm_item_meta' );
@@ -201,17 +256,27 @@
201 256 }
202 257
203 258 /**
204 259 * @since 2.0.9
260 + *
261 + * @param stdClass $entry
262 + * @param int|string $field_id
263 + *
264 + * @return mixed
205 265 */
206 266 public static function get_meta_value( $entry, $field_id ) {
207 267 if ( isset( $entry->metas ) ) {
208 - return isset( $entry->metas[ $field_id ] ) ? $entry->metas[ $field_id ] : false;
209 - } else {
210 - return self::get_entry_meta_by_field( $entry->id, $field_id );
268 + return $entry->metas[ $field_id ] ?? false;
211 269 }
270 + return self::get_entry_meta_by_field( $entry->id, $field_id );
212 271 }
213 272
273 + /**
274 + * @param int|object|string $entry_id
275 + * @param int|string $field_id This function supports field keys as field id.
276 + *
277 + * @return mixed
278 + */
214 279 public static function get_entry_meta_by_field( $entry_id, $field_id ) {
215 280 global $wpdb;
216 281
217 282 if ( is_object( $entry_id ) ) {
@@ -224,28 +289,38 @@
224 289 }
225 290
226 291 if ( $cached && isset( $cached->metas ) && isset( $cached->metas[ $field_id ] ) ) {
227 292 $result = $cached->metas[ $field_id ];
228 -
229 293 return wp_unslash( $result );
230 294 }
231 295
232 296 $get_table = $wpdb->prefix . 'frm_item_metas';
233 297 $query = array( 'item_id' => $entry_id );
298 +
234 299 if ( is_numeric( $field_id ) ) {
300 + // Query by field ID.
235 301 $query['field_id'] = $field_id;
236 302 } else {
237 - $get_table .= ' it LEFT OUTER JOIN ' . $wpdb->prefix . 'frm_fields fi ON it.field_id=fi.id';
303 + // Query by field key.
304 + $get_table .= ' it JOIN ' . $wpdb->prefix . 'frm_fields fi ON it.field_id=fi.id';
238 305 $query['fi.field_key'] = $field_id;
239 306 }
240 307
241 - $result = FrmDb::get_var( $get_table, $query, 'meta_value' );
242 - FrmAppHelper::unserialize_or_decode( $result );
243 - $result = wp_unslash( $result );
308 + $result = FrmDb::get_var( $get_table, $query, 'meta_value' );
309 + $field_type = FrmField::get_type( $field_id );
310 + FrmFieldsHelper::prepare_field_value( $result, $field_type );
244 311
245 - return $result;
312 + return wp_unslash( $result );
246 313 }
247 314
315 + /**
316 + * @param int|string $field_id
317 + * @param string $order
318 + * @param string $limit
319 + * @param array $args
320 + *
321 + * @return array
322 + */
248 323 public static function get_entry_metas_for_field( $field_id, $order = '', $limit = '', $args = array() ) {
249 324 $defaults = array(
250 325 'value' => false,
251 326 'unique' => false,
@@ -252,13 +327,11 @@
252 327 'stripslashes' => true,
253 328 'is_draft' => false,
254 329 );
255 330 $args = wp_parse_args( $args, $defaults );
256 -
257 - $query = array();
331 + $query = array();
258 332 self::meta_field_query( $field_id, $order, $limit, $args, $query );
259 - $query = implode( ' ', $query );
260 -
333 + $query = implode( ' ', $query );
261 334 $cache_key = 'entry_metas_for_field_' . $field_id . $order . $limit . FrmAppHelper::maybe_json_encode( $args );
262 335 $values = FrmDb::check_cache( $cache_key, 'frm_entry', $query, 'get_col' );
263 336
264 337 if ( ! $args['stripslashes'] ) {
@@ -274,10 +347,15 @@
274 347 return wp_unslash( $values );
275 348 }
276 349
277 350 /**
278 - * @param string $order
279 - * @param string $limit
351 + * @param int|string $field_id
352 + * @param string $order
353 + * @param string $limit
354 + * @param array $args
355 + * @param array $query
356 + *
357 + * @return void
280 358 */
281 359 private static function meta_field_query( $field_id, $order, $limit, $args, array &$query ) {
282 360 global $wpdb;
283 361 $query[] = 'SELECT';
@@ -300,24 +378,40 @@
300 378
301 379 if ( $args['value'] ) {
302 380 $query[] = $wpdb->prepare( ' AND meta_value=%s', $args['value'] );
303 381 }
382 +
304 383 $query[] = $order . $limit;
305 384 }
306 385
386 + /**
387 + * @param int|string $entry_id
388 + *
389 + * @return array
390 + */
307 391 public static function get_entry_meta_info( $entry_id ) {
308 392 return FrmDb::get_results( 'frm_item_metas', array( 'item_id' => $entry_id ) );
309 393 }
310 394
395 + /**
396 + * @param array $where
397 + * @param string $order_by
398 + * @param string $limit
399 + * @param bool $stripslashes
400 + *
401 + * @return mixed
402 + */
311 403 public static function getAll( $where = array(), $order_by = '', $limit = '', $stripslashes = false ) {
312 404 global $wpdb;
405 + // phpcs:disable Generic.WhiteSpace.ScopeIndent
313 406 $query = 'SELECT it.*, fi.type as field_type, fi.field_key as field_key,
314 407 fi.required as required, fi.form_id as field_form_id, fi.name as field_name, fi.options as fi_options
315 408 FROM ' . $wpdb->prefix . 'frm_item_metas it LEFT OUTER JOIN ' . $wpdb->prefix . 'frm_fields fi ON it.field_id=fi.id' .
316 409 FrmDb::prepend_and_or_where( ' WHERE ', $where ) . $order_by . $limit;
410 + // phpcs:enable Generic.WhiteSpace.ScopeIndent
317 411
318 412 $cache_key = 'all_' . FrmAppHelper::maybe_json_encode( $where ) . $order_by . $limit;
319 - $results = FrmDb::check_cache( $cache_key, 'frm_entry', $query, ( $limit == ' LIMIT 1' ? 'get_row' : 'get_results' ) );
413 + $results = FrmDb::check_cache( $cache_key, 'frm_entry', $query, $limit === ' LIMIT 1' ? 'get_row' : 'get_results' );
320 414
321 415 if ( ! $results || ! $stripslashes ) {
322 416 return $results;
323 417 }
@@ -330,8 +424,17 @@
330 424
331 425 return $results;
332 426 }
333 427
428 + /**
429 + * @param array|string $where
430 + * @param string $order_by
431 + * @param string $limit
432 + * @param bool $unique
433 + * @param array $args
434 + *
435 + * @return array|string|null
436 + */
334 437 public static function getEntryIds( $where = array(), $order_by = '', $limit = '', $unique = true, $args = array() ) {
335 438 $defaults = array(
336 439 'is_draft' => false,
337 440 'user_id' => '',
@@ -337,13 +440,11 @@
337 440 'user_id' => '',
338 441 'group_by' => '',
339 442 );
340 443 $args = wp_parse_args( $args, $defaults );
341 -
342 - $query = array();
444 + $query = array();
343 445 self::get_ids_query( $where, $order_by, $limit, $unique, $args, $query );
344 - $query = implode( ' ', $query );
345 -
446 + $query = implode( ' ', $query );
346 447 $cache_key = 'ids_' . FrmAppHelper::maybe_json_encode( $where ) . $order_by . 'l' . $limit . 'u' . $unique . FrmAppHelper::maybe_json_encode( $args );
347 448 $type = 'get_' . ( ' LIMIT 1' === $limit ? 'var' : 'col' );
348 449 return FrmDb::check_cache( $cache_key, 'frm_entry', $query, $type );
349 450 }
@@ -353,8 +454,9 @@
353 454 * If a child entry id is matched, its parent will be returned in its place
354 455 *
355 456 * @param array $query
356 457 * @param array $args
458 + *
357 459 * @return array
358 460 */
359 461 public static function get_top_level_entry_ids( $query, $args ) {
360 462 $args['return_parent_id_if_0_return_id'] = true;
@@ -361,13 +463,54 @@
361 463 return self::getEntryIds( $query, '', '', true, $args );
362 464 }
363 465
364 466 /**
365 - * @param string|array $where
366 - * @param string $order_by
367 - * @param string $limit
467 + * Returns true if the where clause refers to a field table column that is not form_id. It also updates
468 + * the where clause to refer to the entry table for form_id if fields table should not be joined.
469 + *
470 + * @since 6.16.1
471 + *
472 + * @param array|string $where
473 + *
474 + * @return bool
368 475 */
369 - private static function get_ids_query( $where, $order_by, $limit, $unique, $args, array &$query ) {
476 + private static function should_join_fields_table( &$where ) {
477 + if ( is_string( $where ) ) {
478 + if ( preg_match( '/\bfi\.(?!form_id)\w+/i', $where ) ) {
479 + return true;
480 + }
481 +
482 + $where = str_ireplace( 'fi.form_id', 'e.form_id', $where );
483 + return false;
484 + }
485 +
486 + $where_fields = array_keys( $where );
487 +
488 + foreach ( $where_fields as $where_field ) {
489 + if ( str_starts_with( $where_field, 'fi.' ) && 'fi.form_id' !== $where_field ) {
490 + return true;
491 + }
492 + }
493 +
494 + if ( isset( $where['fi.form_id'] ) ) {
495 + $where['e.form_id'] = $where['fi.form_id'];
496 + unset( $where['fi.form_id'] );
497 + }
498 +
499 + return false;
500 + }
501 +
502 + /**
503 + * @param array|string $where
504 + * @param string $order_by
505 + * @param string $limit
506 + * @param bool $unique
507 + * @param array $args
508 + * @param array $query
509 + *
510 + * @return void
511 + */
512 + private static function get_ids_query( $where, $order_by, $limit, $unique, $args, array &$query ) { // phpcs:ignore SlevomatCodingStandard.Complexity.Cognitive.ComplexityTooHigh, SlevomatCodingStandard.Files.LineLength.LineTooLong
370 513 global $wpdb;
371 514 $query[] = 'SELECT';
372 515 $defaults = array(
373 516 'return_parent_id' => false,
@@ -386,21 +529,45 @@
386 529 } else {
387 530 $query[] = 'it.item_id';
388 531 }
389 532
390 - $query[] = 'FROM ' . $wpdb->prefix . 'frm_item_metas it LEFT OUTER JOIN ' . $wpdb->prefix . 'frm_fields fi ON it.field_id=fi.id';
533 + $from = 'FROM ' . $wpdb->prefix . 'frm_item_metas it';
391 534
535 + if ( self::should_join_fields_table( $where ) || self::should_join_fields_table( $order_by ) ) {
536 + $from .= ' LEFT OUTER JOIN ' . $wpdb->prefix . 'frm_fields fi ON it.field_id=fi.id';
537 + }
538 +
539 + $query[] = $from;
392 540 $query[] = 'INNER JOIN ' . $wpdb->prefix . 'frm_items e ON (e.id=it.item_id)';
541 +
393 542 if ( is_array( $where ) ) {
394 543 if ( ! $args['is_draft'] ) {
395 544 $where['e.is_draft'] = 0;
396 - } elseif ( $args['is_draft'] == 1 ) {
397 - $where['e.is_draft'] = 1;
398 - }
545 + } elseif ( is_numeric( $args['is_draft'] ) ) {
546 + $where['e.is_draft'] = class_exists( 'FrmAbandonmentHooksController', false ) ? absint( $args['is_draft'] ) : 1;
547 + } elseif ( 'both' === $args['is_draft'] && class_exists( 'FrmAbandonmentHooksController', false ) ) {
548 + $where['e.is_draft'] = array( 0, 1 );
549 + } elseif ( str_contains( $args['is_draft'], ',' ) ) {
550 + $is_draft = array_reduce(
551 + explode( ',', $args['is_draft'] ),
552 + function ( $total, $current ) {
553 + if ( is_numeric( $current ) ) {
554 + $total[] = absint( $current );
555 + }
556 + return $total;
557 + },
558 + array()
559 + );
399 560
561 + if ( $is_draft ) {
562 + $where['e.is_draft'] = $is_draft;
563 + }
564 + }//end if
565 +
400 566 if ( ! empty( $args['user_id'] ) ) {
401 567 $where['e.user_id'] = $args['user_id'];
402 568 }
569 +
403 570 $query[] = FrmDb::prepend_and_or_where( ' WHERE ', $where ) . $order_by . $limit;
404 571
405 572 if ( $args['group_by'] ) {
406 573 $query[] = ' GROUP BY ' . sanitize_text_field( $args['group_by'] );
@@ -406,15 +573,16 @@
406 573 $query[] = ' GROUP BY ' . sanitize_text_field( $args['group_by'] );
407 574 }
408 575
409 576 return;
410 - }
577 + }//end if
411 578
412 579 $draft_where = '';
413 580 $user_where = '';
581 +
414 582 if ( ! $args['is_draft'] ) {
415 583 $draft_where = $wpdb->prepare( ' AND e.is_draft=%d', 0 );
416 - } elseif ( $args['is_draft'] == 1 ) {
584 + } elseif ( $args['is_draft'] == 1 ) { // phpcs:ignore Universal.Operators.StrictComparisons
417 585 $draft_where = $wpdb->prepare( ' AND e.is_draft=%d', 1 );
418 586 }
419 587
420 588 if ( ! empty( $args['user_id'] ) ) {
@@ -420,10 +588,10 @@
420 588 if ( ! empty( $args['user_id'] ) ) {
421 589 $user_where = $wpdb->prepare( ' AND e.user_id=%d', $args['user_id'] );
422 590 }
423 591
424 - if ( strpos( $where, ' GROUP BY ' ) ) {
425 - // don't inject WHERE filtering after GROUP BY
592 + if ( str_contains( $where, ' GROUP BY ' ) ) {
593 + // Don't inject WHERE filtering after GROUP BY
426 594 $parts = explode( ' GROUP BY ', $where );
427 595 $where = $parts[0];
428 596 $where .= $draft_where . $user_where;
429 597 $where .= ' GROUP BY ' . $parts[1];
@@ -434,20 +602,30 @@
434 602 // The query has already been prepared
435 603 $query[] = FrmDb::prepend_and_or_where( ' WHERE ', $where ) . $order_by . $limit;
436 604 }
437 605
606 + /**
607 + * @param array|string $search
608 + * @param int|string $field_id
609 + * @param string $operator
610 + *
611 + * @return array
612 + */
438 613 public static function search_entry_metas( $search, $field_id, $operator ) {
439 614 $cache_key = 'search_' . FrmAppHelper::maybe_json_encode( $search ) . $field_id . $operator;
440 615 $results = wp_cache_get( $cache_key, 'frm_entry' );
616 +
441 617 if ( false !== $results ) {
442 618 return $results;
443 619 }
444 620
445 621 global $wpdb;
622 +
446 623 if ( is_array( $search ) ) {
447 624 $where = '';
625 +
448 626 foreach ( $search as $field => $value ) {
449 - if ( $value <= 0 || ! in_array( $field, array( 'year', 'month', 'day' ) ) ) {
627 + if ( $value <= 0 || ! in_array( $field, array( 'year', 'month', 'day' ), true ) ) {
450 628 continue;
451 629 }
452 630
453 631 switch ( $field ) {
@@ -459,18 +637,21 @@
459 637 break;
460 638 case 'day':
461 639 $value = '%' . $value . '%';
462 640 }
641 +
463 642 $where .= $wpdb->prepare( ' meta_value ' . $operator . ' %s and', $value ); // phpcs:ignore WordPress.DB.PreparedSQL.NotPrepared
464 643 }
644 +
465 645 $where .= $wpdb->prepare( ' field_id=%d', $field_id );
466 - $query = 'SELECT DISTINCT item_id FROM ' . $wpdb->prefix . 'frm_item_metas' . FrmDb::prepend_and_or_where( ' WHERE ', $where );
646 + $query = 'SELECT DISTINCT item_id FROM ' . $wpdb->prefix . 'frm_item_metas' . FrmDb::prepend_and_or_where( ' WHERE ', $where );
467 647 } else {
468 - if ( $operator == 'LIKE' ) {
648 + if ( $operator === 'LIKE' ) {
469 649 $search = '%' . $search . '%';
470 650 }
471 - $query = $wpdb->prepare( "SELECT DISTINCT item_id FROM {$wpdb->prefix}frm_item_metas WHERE meta_value {$operator} %s and field_id = %d", $search, $field_id ); // phpcs:ignore WordPress.DB.PreparedSQL.NotPrepared, WordPress.DB.PreparedSQL.InterpolatedNotPrepared
472 - }
651 +
652 + $query = $wpdb->prepare( "SELECT DISTINCT item_id FROM {$wpdb->prefix}frm_item_metas WHERE meta_value {$operator} %s and field_id = %d", $search, $field_id ); // phpcs:ignore WordPress.DB.PreparedSQL.NotPrepared, WordPress.DB.PreparedSQL.InterpolatedNotPrepared, SlevomatCodingStandard.Files.LineLength.LineTooLong
653 + }//end if
473 654
474 655 $results = $wpdb->get_col( $query, 0 ); // phpcs:ignore WordPress.DB.PreparedSQL.NotPrepared
475 656 FrmDb::set_cache( $cache_key, $results, 'frm_entry' );
476 657