PluginProbe
Formidable Forms – WordPress Form Builder for Contact Forms, Calculators, Quizzes & More / 5.0.09
Formidable Forms – WordPress Form Builder for Contact Forms, Calculators, Quizzes & More v5.0.09
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
formidable / classes / models / FrmForm.php

FrmForm.php in Formidable Forms – WordPress Form Builder for Contact Forms, Calculators, Quizzes & More 5.0.09, at classes/models/FrmForm.php

1,001 lines 28.0 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 if ( ! defined( 'ABSPATH' ) ) {
3 die( 'You are not allowed to call this page directly.' );
4 }
5
6 class FrmForm {
7
8 /**
9 * @param array $values
10 * @return int|boolean id on success or false on failure
11 */
12 public static function create( $values ) {
13 global $wpdb;
14
15 $values = FrmAppHelper::maybe_filter_array( $values, array( 'name', 'description' ) );
16
17 $new_values = array(
18 'form_key' => FrmAppHelper::get_unique_key( $values['form_key'], $wpdb->prefix . 'frm_forms', 'form_key' ),
19 'name' => $values['name'],
20 'description' => $values['description'],
21 'status' => isset( $values['status'] ) ? $values['status'] : 'published',
22 'logged_in' => isset( $values['logged_in'] ) ? $values['logged_in'] : 0,
23 'is_template' => isset( $values['is_template'] ) ? (int) $values['is_template'] : 0,
24 'parent_form_id' => isset( $values['parent_form_id'] ) ? absint( $values['parent_form_id'] ) : 0,
25 'editable' => isset( $values['editable'] ) ? (int) $values['editable'] : 0,
26 'created_at' => isset( $values['created_at'] ) ? $values['created_at'] : current_time( 'mysql', 1 ),
27 );
28
29 $options = isset( $values['options'] ) ? (array) $values['options'] : array();
30 FrmFormsHelper::fill_form_options( $options, $values );
31
32 $options['before_html'] = isset( $values['options']['before_html'] ) ? $values['options']['before_html'] : FrmFormsHelper::get_default_html( 'before' );
33 $options['after_html'] = isset( $values['options']['after_html'] ) ? $values['options']['after_html'] : FrmFormsHelper::get_default_html( 'after' );
34 $options['submit_html'] = isset( $values['options']['submit_html'] ) ? $values['options']['submit_html'] : FrmFormsHelper::get_default_html( 'submit' );
35
36 $options = apply_filters( 'frm_form_options_before_update', $options, $values );
37 $options = self::maybe_filter_form_options( $options );
38 $new_values['options'] = serialize( $options );
39
40 $wpdb->insert( $wpdb->prefix . 'frm_forms', $new_values );
41
42 $id = $wpdb->insert_id;
43
44 // Clear form caching
45 self::clear_form_cache();
46
47 return $id;
48 }
49
50 /**
51 * @since 5.0.08
52 *
53 * @param array $options
54 * @return array
55 */
56 private static function maybe_filter_form_options( $options ) {
57 return FrmAppHelper::maybe_filter_array( $options, array( 'submit_value', 'success_msg', 'before_html', 'after_html', 'submit_html' ) );
58 }
59
60 /**
61 * @return int|boolean ID on success or false on failure
62 */
63 public static function duplicate( $id, $template = false, $copy_keys = false, $blog_id = false ) {
64 global $wpdb;
65
66 $values = self::getOne( $id, $blog_id );
67 if ( ! $values ) {
68 return false;
69 }
70
71 $new_key = $copy_keys ? $values->form_key : '';
72
73 $new_values = array(
74 'form_key' => FrmAppHelper::get_unique_key( $new_key, $wpdb->prefix . 'frm_forms', 'form_key' ),
75 'name' => $values->name,
76 'description' => $values->description,
77 'status' => $values->status ? $values->status : 'published',
78 'logged_in' => $values->logged_in ? $values->logged_in : 0,
79 'editable' => $values->editable ? $values->editable : 0,
80 'created_at' => current_time( 'mysql', 1 ),
81 'is_template' => $template ? 1 : 0,
82 );
83
84 if ( $blog_id ) {
85 $new_values['status'] = 'published';
86 $new_options = $values->options;
87 FrmAppHelper::unserialize_or_decode( $new_options );
88 $new_options['email_to'] = get_option( 'admin_email' );
89 $new_options['copy'] = false;
90 $new_values['options'] = $new_options;
91 } else {
92 $new_values['options'] = $values->options;
93 }
94
95 if ( is_array( $new_values['options'] ) ) {
96 $new_values['options'] = serialize( $new_values['options'] );
97 }
98
99 $query_results = $wpdb->insert( $wpdb->prefix . 'frm_forms', $new_values );
100
101 if ( $query_results ) {
102 // Clear form caching
103 self::clear_form_cache();
104
105 $form_id = $wpdb->insert_id;
106 FrmField::duplicate( $id, $form_id, $copy_keys, $blog_id );
107
108 // update form settings after fields are created
109 do_action( 'frm_after_duplicate_form', $form_id, $new_values, array( 'old_id' => $id ) );
110
111 return $form_id;
112 }
113
114 return false;
115 }
116
117 public static function after_duplicate( $form_id, $values ) {
118 $new_opts = $values['options'];
119 FrmAppHelper::unserialize_or_decode( $new_opts );
120 $values['options'] = $new_opts;
121
122 if ( isset( $new_opts['success_msg'] ) ) {
123 $new_opts['success_msg'] = FrmFieldsHelper::switch_field_ids( $new_opts['success_msg'] );
124 }
125
126 $new_opts = apply_filters( 'frm_after_duplicate_form_values', $new_opts, $form_id );
127
128 if ( $new_opts != $values['options'] ) {
129 global $wpdb;
130 $wpdb->update( $wpdb->prefix . 'frm_forms', array( 'options' => maybe_serialize( $new_opts ) ), array( 'id' => $form_id ) );
131 }
132 }
133
134 /**
135 * @return int|boolean
136 */
137 public static function update( $id, $values, $create_link = false ) {
138 global $wpdb;
139
140 $values = FrmAppHelper::maybe_filter_array( $values, array( 'name', 'description' ) );
141
142 if ( ! isset( $values['status'] ) && ( $create_link || isset( $values['options'] ) || isset( $values['item_meta'] ) || isset( $values['field_options'] ) ) ) {
143 $values['status'] = 'published';
144 }
145
146 if ( isset( $values['form_key'] ) ) {
147 $values['form_key'] = FrmAppHelper::get_unique_key( $values['form_key'], $wpdb->prefix . 'frm_forms', 'form_key', $id );
148 }
149
150 $form_fields = array( 'form_key', 'name', 'description', 'status', 'parent_form_id' );
151
152 $new_values = self::set_update_options( array(), $values );
153
154 foreach ( $values as $value_key => $value ) {
155 if ( $value_key && in_array( $value_key, $form_fields ) ) {
156 $new_values[ $value_key ] = $value;
157 }
158 }
159
160 if ( isset( $values['new_status'] ) && ! empty( $values['new_status'] ) ) {
161 $new_values['status'] = $values['new_status'];
162 }
163
164 if ( ! empty( $new_values ) ) {
165 $query_results = $wpdb->update( $wpdb->prefix . 'frm_forms', $new_values, array( 'id' => $id ) );
166 if ( $query_results ) {
167 self::clear_form_cache();
168 }
169 } else {
170 $query_results = true;
171 }
172 unset( $new_values );
173
174 $values = self::update_fields( $id, $values );
175
176 do_action( 'frm_update_form', $id, $values );
177 do_action( 'frm_update_form_' . $id, $values );
178
179 return $query_results;
180 }
181
182 /**
183 * @return array
184 */
185 public static function set_update_options( $new_values, $values ) {
186 if ( ! isset( $values['options'] ) ) {
187 return $new_values;
188 }
189
190 $options = isset( $values['options'] ) ? (array) $values['options'] : array();
191 FrmFormsHelper::fill_form_options( $options, $values );
192
193 $options['custom_style'] = isset( $values['options']['custom_style'] ) ? $values['options']['custom_style'] : 0;
194 $options['before_html'] = isset( $values['options']['before_html'] ) ? $values['options']['before_html'] : FrmFormsHelper::get_default_html( 'before' );
195 $options['after_html'] = isset( $values['options']['after_html'] ) ? $values['options']['after_html'] : FrmFormsHelper::get_default_html( 'after' );
196 $options['submit_html'] = ( isset( $values['options']['submit_html'] ) && '' !== $values['options']['submit_html'] ) ? $values['options']['submit_html'] : FrmFormsHelper::get_default_html( 'submit' );
197
198 $options = apply_filters( 'frm_form_options_before_update', $options, $values );
199 $options = self::maybe_filter_form_options( $options );
200 $new_values['options'] = serialize( $options );
201
202 return $new_values;
203 }
204
205 /**
206 * @return array
207 */
208 public static function update_fields( $id, $values ) {
209
210 if ( ! isset( $values['item_meta'] ) && ! isset( $values['field_options'] ) ) {
211 return $values;
212 }
213
214 $all_fields = FrmField::get_all_for_form( $id );
215 if ( empty( $all_fields ) ) {
216 return $values;
217 }
218
219 if ( ! isset( $values['item_meta'] ) ) {
220 $values['item_meta'] = array();
221 }
222
223 $field_array = array();
224 $existing_keys = array_keys( $values['item_meta'] );
225 foreach ( $all_fields as $fid ) {
226 if ( ! in_array( $fid->id, $existing_keys ) && ( isset( $values['frm_fields_submitted'] ) && in_array( $fid->id, $values['frm_fields_submitted'] ) ) || isset( $values['options'] ) ) {
227 $values['item_meta'][ $fid->id ] = '';
228 }
229 $field_array[ $fid->id ] = $fid;
230 }
231 unset( $all_fields );
232
233 foreach ( $values['item_meta'] as $field_id => $default_value ) {
234 if ( isset( $field_array[ $field_id ] ) ) {
235 $field = $field_array[ $field_id ];
236 } else {
237 $field = FrmField::getOne( $field_id );
238 }
239
240 if ( ! $field ) {
241 continue;
242 }
243
244 $is_settings_page = ( isset( $values['options'] ) || isset( $values['field_options'][ 'custom_html_' . $field_id ] ) );
245 if ( $is_settings_page ) {
246 self::get_settings_page_html( $values, $field );
247
248 if ( ! defined( 'WP_IMPORTING' ) ) {
249 continue;
250 }
251 }
252
253 //updating the form
254 $update_options = FrmFieldsHelper::get_default_field_options_from_field( $field );
255 unset( $update_options['custom_html'] ); // don't check for POST html
256 $update_options = apply_filters( 'frm_field_options_to_update', $update_options );
257
258 foreach ( $update_options as $opt => $default ) {
259 $field->field_options[ $opt ] = isset( $values['field_options'][ $opt . '_' . $field_id ] ) ? $values['field_options'][ $opt . '_' . $field_id ] : $default;
260 self::sanitize_field_opt( $opt, $field->field_options[ $opt ] );
261 }
262
263 $field->field_options = apply_filters( 'frm_update_field_options', $field->field_options, $field, $values );
264
265 $new_field = array(
266 'field_options' => $field->field_options,
267 'default_value' => isset( $values[ 'default_value_' . $field_id ] ) ? FrmAppHelper::maybe_json_encode( $values[ 'default_value_' . $field_id ] ) : '',
268 );
269
270 self::prepare_field_update_values( $field, $values, $new_field );
271
272 FrmField::update( $field_id, $new_field );
273
274 FrmField::delete_form_transient( $field->form_id );
275 }
276 self::clear_form_cache();
277
278 return $values;
279 }
280
281 private static function sanitize_field_opt( $opt, &$value ) {
282 if ( is_string( $value ) ) {
283 if ( $opt === 'calc' ) {
284 $value = self::sanitize_calc( $value );
285 } else {
286 $value = FrmAppHelper::kses( $value, 'all' );
287 }
288 $value = trim( $value );
289 }
290 }
291
292 /**
293 * @param string $value
294 * @return string
295 */
296 private static function sanitize_calc( $value ) {
297 if ( false !== strpos( $value, '<' ) ) {
298 $value = self::normalize_calc_spaces( $value );
299 }
300 $allow = array( '<= ', ' >=' ); // Allow <= and >=
301 $temp = array( '< = ', ' > =' );
302 $value = str_replace( $allow, $temp, $value );
303 $value = strip_tags( $value );
304 $value = str_replace( $temp, $allow, $value );
305 return $value;
306 }
307
308 /**
309 * Format a comparison like 5<10 to 5 < 10. Also works on 5< 10, 5 <10, 5<=10 variations.
310 * This is to avoid an issue with unspaced calculations being recognized as HTML that gets removed when strip_tags is called.
311 *
312 * @param string $calc
313 * @return string
314 */
315 private static function normalize_calc_spaces( $calc ) {
316 // Check for a pattern with 5 parts
317 // $1 \d the first comparison digit.
318 // $2 a space (optional).
319 // $3 an equals sign (optional) that follows the < operator for <= comparisons.
320 // $4 another space (optional).
321 // $5 \d the second comparison digit.
322 return preg_replace( '/(\d)( ){0,1}<(=){0,1}( ){0,1}(\d)/', '$1 <$3 $5', $calc );
323 }
324
325 /**
326 * Updating the settings page
327 */
328 private static function get_settings_page_html( $values, &$field ) {
329 if ( isset( $values['field_options'][ 'custom_html_' . $field->id ] ) ) {
330 $prev_opts = array();
331 $fallback_html = isset( $field->field_options['custom_html'] ) ? $field->field_options['custom_html'] : FrmFieldsHelper::get_default_html( $field->type );
332
333 $field->field_options['custom_html'] = isset( $values['field_options'][ 'custom_html_' . $field->id ] ) ? $values['field_options'][ 'custom_html_' . $field->id ] : $fallback_html;
334 } elseif ( $field->type == 'hidden' || $field->type == 'user_id' ) {
335 $prev_opts = $field->field_options;
336 }
337
338 if ( isset( $prev_opts ) ) {
339 $field->field_options = apply_filters( 'frm_update_form_field_options', $field->field_options, $field, $values );
340 if ( $prev_opts != $field->field_options ) {
341 FrmField::update( $field->id, array( 'field_options' => $field->field_options ) );
342 }
343 }
344 }
345
346 private static function prepare_field_update_values( $field, $values, &$new_field ) {
347 $field_cols = array(
348 'field_order' => 0,
349 'field_key' => '',
350 'required' => false,
351 'type' => '',
352 'description' => '',
353 'options' => '',
354 'name' => '',
355 );
356 foreach ( $field_cols as $col => $default ) {
357 $default = ( $default === '' ) ? $field->{$col} : $default;
358
359 $new_field[ $col ] = isset( $values['field_options'][ $col . '_' . $field->id ] ) ? $values['field_options'][ $col . '_' . $field->id ] : $default;
360 }
361
362 // Don't save the template option.
363 if ( is_array( $new_field['options'] ) && isset( $new_field['options']['000'] ) ) {
364 unset( $new_field['options']['000'] );
365 }
366 }
367
368 /**
369 * Get a list of all form settings that should be translated
370 * on a multilingual site.
371 *
372 * @since 3.06.01
373 * @param object $form - The form object
374 */
375 public static function translatable_strings( $form ) {
376 $strings = array(
377 'name',
378 'description',
379 'submit_value',
380 'submit_msg',
381 'success_msg',
382 );
383
384 return apply_filters( 'frm_form_strings', $strings, $form );
385 }
386
387 /**
388 * @param string $status
389 *
390 * @return int|boolean
391 */
392 public static function set_status( $id, $status ) {
393 if ( 'trash' == $status ) {
394 return self::trash( $id );
395 }
396
397 $statuses = array( 'published', 'draft', 'trash' );
398 if ( ! in_array( $status, $statuses ) ) {
399 return false;
400 }
401
402 global $wpdb;
403
404 if ( is_array( $id ) ) {
405 $where = array(
406 'id' => $id,
407 'parent_form_id' => $id,
408 'or' => 1,
409 );
410 FrmDb::get_where_clause_and_values( $where );
411 array_unshift( $where['values'], $status );
412
413 $query_results = $wpdb->query( $wpdb->prepare( 'UPDATE ' . $wpdb->prefix . 'frm_forms SET status = %s ' . $where['where'], $where['values'] ) ); // WPCS: unprepared SQL ok.
414 } else {
415 $query_results = $wpdb->update( $wpdb->prefix . 'frm_forms', array( 'status' => $status ), array( 'id' => $id ) );
416 $wpdb->update( $wpdb->prefix . 'frm_forms', array( 'status' => $status ), array( 'parent_form_id' => $id ) );
417 }
418
419 if ( $query_results ) {
420 self::clear_form_cache();
421 }
422
423 return $query_results;
424 }
425
426 /**
427 * @return int|boolean
428 */
429 public static function trash( $id ) {
430 if ( ! EMPTY_TRASH_DAYS ) {
431 return self::destroy( $id );
432 }
433
434 $form = self::getOne( $id );
435 if ( ! $form ) {
436 return false;
437 }
438
439 $options = $form->options;
440 $options['trash_time'] = time();
441
442 global $wpdb;
443 $query_results = $wpdb->update(
444 $wpdb->prefix . 'frm_forms',
445 array(
446 'status' => 'trash',
447 'options' => serialize( $options ),
448 ),
449 array(
450 'id' => $id,
451 )
452 );
453
454 $wpdb->update(
455 $wpdb->prefix . 'frm_forms',
456 array(
457 'status' => 'trash',
458 'options' => serialize( $options ),
459 ),
460 array(
461 'parent_form_id' => $id,
462 )
463 );
464
465 if ( $query_results ) {
466 self::clear_form_cache();
467 }
468
469 return $query_results;
470 }
471
472 /**
473 * @return int|boolean
474 */
475 public static function destroy( $id ) {
476 global $wpdb;
477
478 $form = self::getOne( $id );
479 if ( ! $form ) {
480 return false;
481 }
482 $id = $form->id;
483
484 // Disconnect the entries from this form
485 $entries = FrmDb::get_col( $wpdb->prefix . 'frm_items', array( 'form_id' => $id ) );
486 foreach ( $entries as $entry_id ) {
487 FrmEntry::destroy( $entry_id );
488 unset( $entry_id );
489 }
490
491 // Disconnect the fields from this form
492 $wpdb->query( $wpdb->prepare( 'DELETE fi FROM ' . $wpdb->prefix . 'frm_fields AS fi LEFT JOIN ' . $wpdb->prefix . 'frm_forms fr ON (fi.form_id = fr.id) WHERE fi.form_id=%d OR parent_form_id=%d', $id, $id ) );
493
494 $query_results = $wpdb->query( $wpdb->prepare( 'DELETE FROM ' . $wpdb->prefix . 'frm_forms WHERE id=%d OR parent_form_id=%d', $id, $id ) );
495 if ( $query_results ) {
496 // Delete all form actions linked to this form
497 $action_control = FrmFormActionsController::get_form_actions( 'email' );
498 $action_control->destroy( $id, 'all' );
499
500 // Clear form caching
501 self::clear_form_cache();
502
503 do_action( 'frm_destroy_form', $id );
504 do_action( 'frm_destroy_form_' . $id );
505 }
506
507 return $query_results;
508 }
509
510 /**
511 * Delete trashed forms based on how long they have been trashed
512 *
513 * @return int The number of forms deleted
514 */
515 public static function scheduled_delete( $delete_timestamp = '' ) {
516 global $wpdb;
517
518 $trash_forms = FrmDb::get_results( $wpdb->prefix . 'frm_forms', array( 'status' => 'trash' ), 'id, options' );
519
520 if ( ! $trash_forms ) {
521 return 0;
522 }
523
524 if ( empty( $delete_timestamp ) ) {
525 $delete_timestamp = time() - ( DAY_IN_SECONDS * EMPTY_TRASH_DAYS );
526 }
527
528 $count = 0;
529 foreach ( $trash_forms as $form ) {
530 FrmAppHelper::unserialize_or_decode( $form->options );
531 if ( ! isset( $form->options['trash_time'] ) || $form->options['trash_time'] < $delete_timestamp ) {
532 self::destroy( $form->id );
533 $count ++;
534 }
535
536 unset( $form );
537 }
538
539 return $count;
540 }
541
542 /**
543 * @return string form name
544 */
545 public static function getName( $id ) {
546 $form = FrmDb::check_cache( $id, 'frm_form' );
547 if ( $form ) {
548 $r = stripslashes( $form->name );
549
550 return $r;
551 }
552
553 $query_key = is_numeric( $id ) ? 'id' : 'form_key';
554 $r = FrmDb::get_var( 'frm_forms', array( $query_key => $id ), 'name' );
555 $r = stripslashes( $r );
556
557 return $r;
558 }
559
560 /**
561 * @since 3.0
562 *
563 * @param string $key
564 *
565 * @return int form id
566 */
567 public static function get_id_by_key( $key ) {
568 return (int) FrmDb::get_var( 'frm_forms', array( 'form_key' => sanitize_title( $key ) ) );
569 }
570
571 /**
572 * @since 3.0
573 *
574 * @param int $id
575 *
576 * @return string form key
577 */
578 public static function get_key_by_id( $id ) {
579 $id = (int) $id;
580 $cache = FrmDb::check_cache( $id, 'frm_form' );
581 if ( $cache ) {
582 return $cache->form_key;
583 }
584
585 $key = FrmDb::get_var( 'frm_forms', array( 'id' => $id ), 'form_key' );
586
587 return $key;
588 }
589
590 /**
591 * If $form is numeric, get the form object
592 *
593 * @param object|int $form
594 *
595 * @since 2.0.9
596 */
597 public static function maybe_get_form( &$form ) {
598 if ( ! is_object( $form ) && ! is_array( $form ) && ! empty( $form ) ) {
599 $form = self::getOne( $form );
600 }
601 }
602
603 /**
604 * @return object form
605 */
606 public static function getOne( $id, $blog_id = false ) {
607 global $wpdb;
608
609 if ( $blog_id && is_multisite() ) {
610 global $wpmuBaseTablePrefix;
611 $prefix = $wpmuBaseTablePrefix ? $wpmuBaseTablePrefix . $blog_id . '_' : $wpdb->get_blog_prefix( $blog_id );
612
613 $table_name = $prefix . 'frm_forms';
614 } else {
615 $table_name = $wpdb->prefix . 'frm_forms';
616 $cache = wp_cache_get( $id, 'frm_form' );
617 if ( $cache ) {
618 if ( isset( $cache->options ) ) {
619 FrmAppHelper::unserialize_or_decode( $cache->options );
620 }
621
622 return wp_unslash( $cache );
623 }
624 }
625
626 if ( is_numeric( $id ) ) {
627 $where = array( 'id' => $id );
628 } else {
629 $where = array( 'form_key' => $id );
630 }
631
632 $results = FrmDb::get_row( $table_name, $where );
633
634 if ( isset( $results->options ) ) {
635 FrmDb::set_cache( $results->id, $results, 'frm_form' );
636 FrmAppHelper::unserialize_or_decode( $results->options );
637 }
638
639 return apply_filters( 'frm_form_object', wp_unslash( $results ) );
640 }
641
642 /**
643 * @return object|array of objects
644 */
645 public static function getAll( $where = array(), $order_by = '', $limit = '' ) {
646 if ( is_array( $where ) && ! empty( $where ) ) {
647 if ( isset( $where['is_template'] ) && $where['is_template'] && ! isset( $where['status'] ) && ! isset( $where['status !'] ) ) {
648 // don't get trashed templates
649 $where['status'] = array( null, '', 'published' );
650 }
651
652 $results = FrmDb::get_results( 'frm_forms', $where, '*', compact( 'order_by', 'limit' ) );
653 } else {
654 global $wpdb;
655
656 // the query has already been prepared if this is not an array
657 $query = 'SELECT * FROM ' . $wpdb->prefix . 'frm_forms' . FrmDb::prepend_and_or_where( ' WHERE ', $where ) . FrmDb::esc_order( $order_by ) . FrmDb::esc_limit( $limit );
658 $results = $wpdb->get_results( $query ); // WPCS: unprepared SQL ok.
659 }
660
661 if ( $results ) {
662 foreach ( $results as $result ) {
663 FrmDb::set_cache( $result->id, $result, 'frm_form' );
664 FrmAppHelper::unserialize_or_decode( $result->options );
665 }
666 }
667
668 if ( $limit == ' LIMIT 1' || $limit == 1 ) {
669 // return the first form object if we are only getting one form
670 $results = reset( $results );
671 }
672
673 return wp_unslash( $results );
674 }
675
676 /**
677 * Get all published forms
678 *
679 * @since 2.0
680 * @return array of forms
681 */
682 public static function get_published_forms( $query = array(), $limit = 999, $inc_children = 'exclude' ) {
683 $query['is_template'] = 0;
684 $query['status'] = array( null, '', 'published' );
685 if ( $inc_children == 'exclude' ) {
686 $query['parent_form_id'] = array( null, 0 );
687 }
688
689 $forms = self::getAll( $query, 'name', $limit );
690
691 return $forms;
692 }
693
694 /**
695 * @return object count of forms
696 */
697 public static function get_count() {
698 global $wpdb;
699
700 $cache_key = 'frm_form_counts';
701
702 $counts = wp_cache_get( $cache_key, 'frm_form' );
703 if ( false !== $counts ) {
704 return $counts;
705 }
706
707 $results = (array) FrmDb::get_results(
708 'frm_forms',
709 array(
710 'or' => 1,
711 'parent_form_id' => null,
712 'parent_form_id <' => 0,
713 ),
714 'status, is_template'
715 );
716
717 $statuses = array( 'published', 'draft', 'template', 'trash' );
718 $counts = array_fill_keys( $statuses, 0 );
719
720 foreach ( $results as $row ) {
721 if ( 'trash' != $row->status ) {
722 if ( $row->is_template ) {
723 $counts['template'] ++;
724 } else {
725 $counts['published'] ++;
726 }
727 } else {
728 $counts['trash'] ++;
729 }
730
731 if ( 'draft' == $row->status ) {
732 $counts['draft'] ++;
733 }
734
735 unset( $row );
736 }
737
738 $counts = (object) $counts;
739 FrmDb::set_cache( $cache_key, $counts, 'frm_form' );
740
741 return $counts;
742 }
743
744 /**
745 * Clear form caching
746 * Called when a form is created, updated, duplicated, or deleted
747 * or when the form status is changed
748 *
749 * @since 2.0.4
750 */
751 public static function clear_form_cache() {
752 FrmDb::cache_delete_group( 'frm_form' );
753 }
754
755 /**
756 * @return array of errors
757 */
758 public static function validate( $values ) {
759 $errors = array();
760
761 return apply_filters( 'frm_validate_form', $errors, $values );
762 }
763
764 public static function get_params( $form = null ) {
765 global $frm_vars;
766
767 if ( ! $form ) {
768 $form = self::getAll( array(), 'name', 1 );
769 } else {
770 self::maybe_get_form( $form );
771 }
772
773 if ( isset( $frm_vars['form_params'] ) && is_array( $frm_vars['form_params'] ) && isset( $frm_vars['form_params'][ $form->id ] ) ) {
774 return $frm_vars['form_params'][ $form->id ];
775 }
776
777 $action_var = isset( $_REQUEST['frm_action'] ) ? 'frm_action' : 'action'; // WPCS: CSRF ok.
778 $action = apply_filters( 'frm_show_new_entry_page', FrmAppHelper::get_param( $action_var, 'new', 'get', 'sanitize_title' ), $form );
779
780 $default_values = array(
781 'id' => '',
782 'form_name' => '',
783 'paged' => 1,
784 'form' => $form->id,
785 'form_id' => $form->id,
786 'field_id' => '',
787 'search' => '',
788 'sort' => '',
789 'sdir' => '',
790 'action' => $action,
791 );
792
793 $values = array();
794 $values['posted_form_id'] = FrmAppHelper::get_param( 'form_id', '', 'get', 'absint' );
795 if ( ! $values['posted_form_id'] ) {
796 $values['posted_form_id'] = FrmAppHelper::get_param( 'form', '', 'get', 'absint' );
797 }
798
799 if ( $form->id == $values['posted_form_id'] ) {
800 //if there are two forms on the same page, make sure not to submit both
801 foreach ( $default_values as $var => $default ) {
802 if ( $var == 'action' ) {
803 $values[ $var ] = FrmAppHelper::get_param( $action_var, $default, 'get', 'sanitize_title' );
804 } else {
805 $values[ $var ] = FrmAppHelper::get_param( $var, $default, 'get', 'sanitize_text_field' );
806 }
807 unset( $var, $default );
808 }
809 } else {
810 foreach ( $default_values as $var => $default ) {
811 $values[ $var ] = $default;
812 unset( $var, $default );
813 }
814 }
815
816 if ( in_array( $values['action'], array( 'create', 'update' ) ) &&
817 ( ! $_POST || ( ! isset( $_POST['action'] ) && ! isset( $_POST['frm_action'] ) ) ) // WPCS: CSRF ok.
818 ) {
819 $values['action'] = 'new';
820 }
821
822 return $values;
823 }
824
825 public static function list_page_params() {
826 $values = array();
827 $defaults = array(
828 'template' => 0,
829 'id' => '',
830 'paged' => 1,
831 'form' => '',
832 'search' => '',
833 'sort' => '',
834 'sdir' => '',
835 );
836 foreach ( $defaults as $var => $default ) {
837 $values[ $var ] = FrmAppHelper::get_param( $var, $default, 'get', 'sanitize_text_field' );
838 }
839
840 return $values;
841 }
842
843 public static function get_admin_params( $form = null ) {
844 $form_id = $form;
845 if ( $form === null ) {
846 $form_id = self::get_current_form_id();
847 } elseif ( $form && is_object( $form ) ) {
848 $form_id = $form->id;
849 }
850
851 $values = array();
852 $defaults = array(
853 'id' => '',
854 'form_name' => '',
855 'paged' => 1,
856 'form' => $form_id,
857 'field_id' => '',
858 'search' => '',
859 'sort' => '',
860 'sdir' => '',
861 'fid' => '',
862 'keep_post' => '',
863 );
864 foreach ( $defaults as $var => $default ) {
865 $values[ $var ] = FrmAppHelper::get_param( $var, $default, 'get', 'sanitize_text_field' );
866 }
867
868 return $values;
869 }
870
871 public static function get_current_form_id( $default_form = 'none' ) {
872 if ( 'first' == $default_form ) {
873 $form = self::get_current_form();
874 } else {
875 $form = self::maybe_get_current_form();
876 }
877 $form_id = $form ? $form->id : 0;
878
879 return $form_id;
880 }
881
882 public static function maybe_get_current_form( $form_id = 0 ) {
883 global $frm_vars;
884
885 if ( isset( $frm_vars['current_form'] ) && $frm_vars['current_form'] && ( ! $form_id || $form_id == $frm_vars['current_form']->id ) ) {
886 return $frm_vars['current_form'];
887 }
888
889 $form_id = FrmAppHelper::get_param( 'form', $form_id, 'get', 'absint' );
890 if ( $form_id ) {
891 $form_id = self::set_current_form( $form_id );
892 }
893
894 return $form_id;
895 }
896
897 public static function get_current_form( $form_id = 0 ) {
898 $form = self::maybe_get_current_form( $form_id );
899 if ( is_numeric( $form ) ) {
900 $form = self::set_current_form( $form );
901 }
902
903 return $form;
904 }
905
906 public static function set_current_form( $form_id ) {
907 global $frm_vars;
908
909 $query = array();
910 if ( $form_id ) {
911 $query['id'] = $form_id;
912 }
913
914 $frm_vars['current_form'] = self::get_published_forms( $query, 1 );
915
916 return $frm_vars['current_form'];
917 }
918
919 public static function is_form_loaded( $form, $this_load, $global_load ) {
920 global $frm_vars;
921 $small_form = new stdClass();
922 foreach ( array( 'id', 'form_key', 'name' ) as $var ) {
923 $small_form->{$var} = $form->{$var};
924 unset( $var );
925 }
926
927 $frm_vars['forms_loaded'][] = $small_form;
928
929 if ( $this_load && empty( $global_load ) ) {
930 $global_load = true;
931 $frm_vars['load_css'] = true;
932 }
933
934 return ( ( ! isset( $frm_vars['css_loaded'] ) || ! $frm_vars['css_loaded'] ) && $global_load );
935 }
936
937 /**
938 * @since 4.06.03
939 *
940 * @param object $form
941 *
942 * @return bool
943 */
944 public static function &is_visible_to_user( $form ) {
945 if ( $form->logged_in && isset( $form->options['logged_in_role'] ) ) {
946 $visible = FrmAppHelper::user_has_permission( $form->options['logged_in_role'] );
947 } else {
948 $visible = true;
949 }
950
951 return $visible;
952 }
953
954 public static function show_submit( $form ) {
955 $show = ( ! $form->is_template && $form->status == 'published' && ! FrmAppHelper::is_admin() );
956 $show = apply_filters( 'frm_show_submit_button', $show, $form );
957
958 return $show;
959 }
960
961 /**
962 * @since 2.3
963 */
964 public static function get_option( $atts ) {
965 $form = $atts['form'];
966 $default = isset( $atts['default'] ) ? $atts['default'] : '';
967
968 return isset( $form->options[ $atts['option'] ] ) ? $form->options[ $atts['option'] ] : $default;
969 }
970
971 /**
972 * Get the link to edit this form.
973 *
974 * @since 4.0
975 * @param int $form_id The id of the form.
976 */
977 public static function get_edit_link( $form_id ) {
978 return admin_url( 'admin.php?page=formidable&frm_action=edit&id=' . $form_id );
979 }
980
981 /**
982 * @deprecated 3.0
983 * @codeCoverageIgnore
984 *
985 * @param string $key
986 *
987 * @return int form id
988 */
989 public static function getIdByKey( $key ) {
990 return FrmFormDeprecated::getIdByKey( $key );
991 }
992
993 /**
994 * @deprecated 3.0
995 * @codeCoverageIgnore
996 */
997 public static function getKeyById( $id ) {
998 return FrmFormDeprecated::getKeyById( $id );
999 }
1000 }
1001