PluginProbe
Formidable Forms – WordPress Form Builder for Contact Forms, Calculators, Quizzes & More / 6.30
Formidable Forms – WordPress Form Builder for Contact Forms, Calculators, Quizzes & More v6.30
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 / controllers / FrmXMLController.php

FrmXMLController.php in Formidable Forms – WordPress Form Builder for Contact Forms, Calculators, Quizzes & More 6.30, at classes/controllers/FrmXMLController.php

797 lines 21.2 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 FrmXMLController {
7
8 /**
9 * @return void
10 */
11 public static function menu() {
12 add_submenu_page( 'formidable', 'Formidable | ' . __( 'Import/Export', 'formidable' ), __( 'Import/Export', 'formidable' ), 'frm_edit_forms', 'formidable-import', 'FrmXMLController::route' ); // phpcs:ignore SlevomatCodingStandard.Files.LineLength.LineTooLong
13 }
14
15 /**
16 * @return void
17 */
18 public static function add_default_templates() {
19 if ( FrmXMLHelper::check_if_libxml_disable_entity_loader_exists() ) {
20 // XML import is not enabled on your server.
21 return;
22 }
23
24 $set_err = libxml_use_internal_errors( true );
25 $loader = FrmXMLHelper::maybe_libxml_disable_entity_loader( true );
26 $files = apply_filters( 'frm_default_templates_files', array() );
27
28 foreach ( (array) $files as $file ) {
29 FrmXMLHelper::import_xml( $file );
30 unset( $file );
31 }
32
33 unset( $files );
34
35 libxml_use_internal_errors( $set_err );
36 FrmXMLHelper::maybe_libxml_disable_entity_loader( $loader );
37 }
38
39 /**
40 * Use the template link to install the XML template
41 *
42 * @since 3.06
43 *
44 * @return void
45 */
46 public static function install_template() {
47 FrmAppHelper::permission_check( 'frm_edit_forms' );
48 check_ajax_referer( 'frm_ajax', 'nonce' );
49
50 if ( ! function_exists( 'simplexml_load_string' ) ) {
51 $response = array(
52 'message' => __( 'Your server is missing the Simple XML extension. This is required to install a template.', 'formidable' ),
53 );
54 echo wp_json_encode( $response );
55 wp_die();
56 }
57
58 $form = self::get_posted_form();
59 $url = FrmAppHelper::get_param( 'xml', '', 'post', 'esc_url_raw' );
60 self::override_url( $form, $url );
61
62 if ( ! self::validate_xml_url( $url ) ) {
63 $response = array(
64 'message' => __( 'The template you are trying to install could not be validated.', 'formidable' ),
65 );
66 echo wp_json_encode( $response );
67 wp_die();
68 }
69
70 $response = wp_remote_get( $url );
71 $body = wp_remote_retrieve_body( $response );
72 $xml = simplexml_load_string( $body );
73
74 if ( ! $xml ) {
75 $response = array(
76 'message' => __( 'There was an error reading the form template.', 'formidable' ),
77 );
78 echo wp_json_encode( $response );
79 wp_die();
80 }
81
82 self::set_new_form_name( $xml );
83
84 $imported = FrmXMLHelper::import_xml_now( $xml, true );
85
86 if ( ! empty( $imported['form_status'] ) ) {
87 // Get the last form id in case there are child forms.
88 $form_id = array_key_last( $imported['form_status'] );
89 $response = array(
90 'id' => $form_id,
91 'redirect' => FrmForm::get_edit_link( $form_id ) . '&new_template=true',
92 'success' => 1,
93 );
94
95 if ( ! empty( $imported['imported']['posts'] ) ) {
96 // Return the link to the last page created.
97 $pages = $imported['posts'];
98 }
99
100 if ( $form ) {
101 // Create selected pages with the correct shortcodes.
102 $pages = self::create_pages_for_import( $form );
103 }
104
105 if ( ! empty( $pages ) ) {
106 $post_id = end( $pages );
107 $response['redirect'] = get_permalink( $post_id );
108 }
109 } else {
110 $message = $imported['error'] ?? __( 'There was an error importing form', 'formidable' );
111 $response = array(
112 'message' => $message,
113 );
114 }//end if
115
116 /**
117 * @since 6.18 Added `url` to the $args.
118 */
119 $response = apply_filters( 'frm_xml_response', $response, compact( 'form', 'imported', 'url' ) );
120
121 echo wp_json_encode( $response );
122 wp_die();
123 }
124
125 /**
126 * Make sure that the XML file we're trying to load is in fact an XML file, and that it's coming from our S3 bucket.
127 * This is to make sure that the URL can't be exploited for a SSRF attack.
128 *
129 * @since 5.5.5
130 *
131 * @param string $url
132 *
133 * @return bool True on success, False on error.
134 */
135 private static function validate_xml_url( $url ) {
136 return FrmAppHelper::validate_url_is_in_s3_bucket( $url, 'xml' );
137 }
138
139 /**
140 * @since 4.06.02
141 *
142 * @return mixed
143 */
144 private static function get_posted_form() {
145 $form = FrmAppHelper::get_param( 'form', '', 'post', 'wp_unslash' );
146 return $form ? json_decode( $form, true ) : $form;
147 }
148
149 /**
150 * Get a different URL depending on the selection in the form.
151 *
152 * @since 4.06.02
153 *
154 * @param array $form The posted form values.
155 * @param string $url The URL to override.
156 *
157 * @return void
158 */
159 private static function override_url( $form, &$url ) {
160 $selected_form = self::get_selected_in_form( $form, 'form' );
161
162 if ( ! $selected_form ) {
163 return;
164 }
165
166 $selected_xml = isset( $form['xml'] ) && isset( $form['xml'][ $selected_form ] ) ? $form['xml'][ $selected_form ] : '';
167
168 if ( ! $selected_xml || ! str_starts_with( $selected_xml, 'http' ) ) {
169 return;
170 }
171
172 $url = $selected_xml;
173 }
174
175 /**
176 * @since 4.06.02
177 *
178 * @param array $form
179 * @param string $value
180 *
181 * @return array|string
182 */
183 private static function get_selected_in_form( $form, $value = 'form' ) {
184 if ( $form && ! empty( $form[ $value ] ) ) {
185 return $form[ $value ];
186 }
187
188 return '';
189 }
190
191 /**
192 * @since 4.06.02
193 *
194 * @param array $form The posted form values.
195 *
196 * @return array|null The array of created pages.
197 */
198 private static function create_pages_for_import( $form ) {
199 if ( empty( $form['pages'] ) ) {
200 return null;
201 }
202
203 $form_key = self::get_selected_in_form( $form, 'form' );
204 $view_keys = self::get_selected_in_form( $form, 'view' );
205 $page_ids = array();
206
207 foreach ( (array) $form['pages'] as $for => $name ) {
208 if ( ! $name ) {
209 // Don't create a page if no title is given.
210 continue;
211 }
212
213 if ( $for === 'view' ) {
214 $item_key = is_array( $view_keys ) ? $view_keys[ $form_key ] : $view_keys;
215 $shortcode = '[display-frm-data id=%1$s filter=limited]';
216 } elseif ( $for === 'form' ) {
217 $item_key = $form_key;
218 $shortcode = '[formidable id=%1$s]';
219 } else {
220 $item_key = self::get_selected_in_form( $form, 'form' );
221 $shortcode = '[' . esc_html( $for ) . ' id=%1$s]';
222 }
223
224 if ( empty( $item_key ) ) {
225 // Don't create it if the shortcode won't show anything.
226 continue;
227 }
228
229 $page_ids[ $for ] = wp_insert_post(
230 array(
231 'post_title' => $name,
232 'post_type' => 'page',
233 'post_content' => sprintf( $shortcode, $item_key ),
234 )
235 );
236 }//end foreach
237
238 return $page_ids;
239 }
240
241 /**
242 * Change the name of the last form that is not a child.
243 * This will allow for lookup fields and embedded forms
244 * since we redirect to the last form.
245 *
246 * @since 3.06
247 *
248 * @param object $xml The values included in the XML.
249 *
250 * @return void
251 */
252 private static function set_new_form_name( &$xml ) {
253 if ( ! isset( $xml->form ) ) {
254 return;
255 }
256
257 $name = FrmAppHelper::get_param( 'name', '', 'post', 'sanitize_text_field' );
258 $description = FrmAppHelper::get_param( 'desc', '', 'post', 'sanitize_textarea_field' );
259
260 if ( ! $name && ! $description ) {
261 return;
262 }
263
264 // Get the main form ID.
265 $set_name = 0;
266
267 foreach ( $xml->form as $form ) {
268 if ( empty( $form->parent_form_id ) ) {
269 $set_name = (int) $form->id;
270 }
271 }
272
273 foreach ( $xml->form as $form ) {
274 // Maybe set the form name if this isn't a child form.
275 if ( $set_name === (int) $form->id ) {
276 $form->name = $name;
277 $form->description = $description;
278 }
279
280 // Use a unique key to prevent editing existing form.
281 $sanitized_form_name = sanitize_title( $form->name );
282 $form->form_key = FrmAppHelper::get_unique_key( $sanitized_form_name, 'frm_forms', 'form_key' );
283 }
284 }
285
286 /**
287 * @return void
288 */
289 public static function route() {
290 $action = isset( $_REQUEST['frm_action'] ) ? 'frm_action' : 'action';
291 $action = FrmAppHelper::get_param( $action, '', 'get', 'sanitize_title' );
292 FrmAppHelper::include_svg();
293
294 if ( 'import_xml' === $action ) {
295 self::import_xml();
296 } elseif ( 'export_xml' === $action ) {
297 self::export_xml();
298 } elseif ( apply_filters( 'frm_xml_route', true, $action ) ) {
299 self::form();
300 }
301 }
302
303 /**
304 * @param string[] $errors
305 * @param string $message
306 *
307 * @return void
308 */
309 public static function form( $errors = array(), $message = '' ) {
310 $where = array(
311 'status' => array( null, '', 'published' ),
312 );
313 $forms = FrmForm::getAll( $where, 'name' );
314
315 $export_types = array(
316 'forms' => __( 'Forms', 'formidable' ),
317 'items' => __( 'Entries', 'formidable' ),
318 );
319 $export_types = apply_filters( 'frm_xml_export_types', $export_types );
320
321 $export_format = array(
322 'xml' => array(
323 'name' => 'XML',
324 'support' => 'forms',
325 'count' => 'multiple',
326 ),
327 'csv' => array(
328 'name' => 'CSV',
329 'support' => 'items',
330 'count' => 'single',
331 ),
332 );
333 $export_format = apply_filters( 'frm_export_formats', $export_format );
334
335 include FrmAppHelper::plugin_path() . '/classes/views/xml/import_form.php';
336 }
337
338 /**
339 * @return void
340 */
341 public static function import_xml() {
342 $errors = array();
343 $message = '';
344 $permission_error = FrmAppHelper::permission_nonce_error( 'frm_edit_forms', 'import-xml', 'import-xml-nonce' );
345
346 if ( false !== $permission_error ) {
347 $errors[] = $permission_error;
348 self::form( $errors );
349
350 return;
351 }
352
353 // phpcs:ignore WordPress.Security.NonceVerification.Missing, SlevomatCodingStandard.Files.LineLength.LineTooLong
354 $has_file = ! empty( $_FILES['frm_import_file'] ) && ! empty( $_FILES['frm_import_file']['name'] ) && ! empty( $_FILES['frm_import_file']['size'] ) && (int) $_FILES['frm_import_file']['size'] > 0;
355
356 if ( ! $has_file ) {
357 $errors[] = __( 'Oops, you didn\'t select a file.', 'formidable' );
358 self::form( $errors );
359
360 return;
361 }
362
363 // phpcs:ignore WordPress.Security.ValidatedSanitizedInput.MissingUnslash, WordPress.Security.NonceVerification.Missing
364 $file = isset( $_FILES['frm_import_file']['tmp_name'] ) ? sanitize_option( 'upload_path', $_FILES['frm_import_file']['tmp_name'] ) : '';
365
366 if ( ! is_uploaded_file( $file ) ) {
367 unset( $file );
368 $errors[] = __( 'The file does not exist, please try again.', 'formidable' );
369 self::form( $errors );
370
371 return;
372 }
373
374 $export_format = array(
375 'xml' => array(
376 'name' => 'XML',
377 'support' => 'forms',
378 'count' => 'multiple',
379 ),
380 );
381 $export_format = apply_filters( 'frm_export_formats', $export_format );
382
383 // phpcs:ignore WordPress.Security.ValidatedSanitizedInput.MissingUnslash, WordPress.Security.NonceVerification.Missing
384 $file_type = sanitize_option( 'upload_path', $_FILES['frm_import_file']['name'] );
385 $file_type = strtolower( pathinfo( $file_type, PATHINFO_EXTENSION ) );
386
387 if ( 'xml' !== $file_type && isset( $export_format[ $file_type ] ) ) {
388 // Allow other file types to be imported
389 do_action( 'frm_before_import_' . $file_type );
390
391 return;
392 }
393 unset( $file_type );
394
395 if ( FrmXMLHelper::check_if_libxml_disable_entity_loader_exists() ) {
396 $errors[] = __( 'XML import is not enabled on your server with the libxml_disable_entity_loader function.', 'formidable' );
397 self::form( $errors );
398
399 return;
400 }
401
402 $set_err = libxml_use_internal_errors( true );
403 $loader = FrmXMLHelper::maybe_libxml_disable_entity_loader( true );
404 $result = FrmXMLHelper::import_xml( $file );
405 FrmXMLHelper::parse_message( $result, $message, $errors );
406
407 unset( $file );
408
409 libxml_use_internal_errors( $set_err );
410 FrmXMLHelper::maybe_libxml_disable_entity_loader( $loader );
411
412 self::form( $errors, $message );
413 }
414
415 /**
416 * @return void
417 */
418 public static function export_xml() {
419 $error = FrmAppHelper::permission_nonce_error( 'frm_edit_forms', 'export-xml', 'export-xml-nonce' );
420
421 if ( $error ) {
422 wp_die( esc_html( $error ) );
423 }
424
425 $ids = FrmAppHelper::get_post_param( 'frm_export_forms', array(), 'sanitize_text_field' );
426 $type = FrmAppHelper::get_post_param( 'type', array(), 'sanitize_text_field' );
427 $format = FrmAppHelper::get_post_param( 'format', 'xml', 'sanitize_title' );
428
429 if ( ! headers_sent() && ! $type ) {
430 wp_safe_redirect( esc_url_raw( admin_url( 'admin.php?page=formidable-import' ) ) );
431 die();
432 }
433
434 if ( 'xml' === $format ) {
435 self::generate_xml( $type, compact( 'ids' ) );
436 } elseif ( 'csv' === $format ) {
437 self::generate_csv( compact( 'ids' ) );
438 } else {
439 do_action( 'frm_export_format_' . $format, compact( 'ids' ) );
440 }
441
442 wp_die();
443 }
444
445 /**
446 * @param array<string>|string $type
447 * @param array $args
448 *
449 * @psalm-param array{ids?: mixed} $args
450 *
451 * @return void
452 */
453 public static function generate_xml( $type, $args = array() ) { // phpcs:ignore SlevomatCodingStandard.Complexity.Cognitive.ComplexityTooHigh
454 global $wpdb;
455
456 self::prepare_types_array( $type );
457
458 if ( ! is_array( $type ) ) {
459 // This shouldn't be possible.
460 // It is cast to array in prepare_types_array.
461 // This is just for static analysis.
462 return;
463 }
464
465 $tables = array(
466 'items' => $wpdb->prefix . 'frm_items',
467 'forms' => $wpdb->prefix . 'frm_forms',
468 'posts' => $wpdb->posts,
469 'styles' => $wpdb->posts,
470 'actions' => $wpdb->posts,
471 );
472
473 $defaults = array(
474 'ids' => false,
475 );
476 $args = wp_parse_args( $args, $defaults );
477
478 // Make sure ids are numeric.
479 if ( is_array( $args['ids'] ) && $args['ids'] ) {
480 $args['ids'] = array_filter( $args['ids'], 'is_numeric' );
481 }
482
483 $records = array();
484
485 foreach ( $type as $tb_type ) {
486 $where = array();
487 $join = '';
488 $table = $tables[ $tb_type ];
489 $select = $table . '.id';
490 $query_vars = array();
491
492 switch ( $tb_type ) {
493 case 'forms':
494 // Add forms.
495 if ( $args['ids'] ) {
496 $where[] = array(
497 'or' => 1,
498 $table . '.id' => $args['ids'],
499 $table . '.parent_form_id' => $args['ids'],
500 );
501 } else {
502 $where[ $table . '.status !' ] = 'draft';
503 }
504 break;
505 case 'actions':
506 $select = $table . '.ID';
507 $where['post_type'] = FrmFormActionsController::$action_post_type;
508
509 if ( ! empty( $args['ids'] ) ) {
510 $where['menu_order'] = $args['ids'];
511 }
512 break;
513 case 'items':
514 // $join = "INNER JOIN {$wpdb->prefix}frm_item_metas im ON ($table.id = im.item_id)";
515 if ( $args['ids'] ) {
516 $where[ $table . '.form_id' ] = $args['ids'];
517 }
518 break;
519 case 'styles':
520 // Loop through all exported forms and get their selected style IDs.
521 $frm_style = new FrmStyle();
522 $default_style = $frm_style->get_default_style();
523 $form_ids = $args['ids'];
524 $style_ids = array();
525
526 foreach ( $form_ids as $form_id ) {
527 $form_data = FrmForm::getOne( $form_id );
528
529 // For forms that have not been updated while running 2.0, check if custom_style is set.
530 if ( isset( $form_data->options['custom_style'] ) ) {
531 if ( 1 === absint( $form_data->options['custom_style'] ) ) {
532 $style_ids[] = $default_style->ID;
533 } else {
534 $style_ids[] = $form_data->options['custom_style'];
535 }
536 }
537 unset( $form_id, $form_data );
538 }
539
540 $select = $table . '.ID';
541 $where['post_type'] = 'frm_styles';
542
543 // Only export selected styles.
544 if ( $style_ids ) {
545 $where['ID'] = $style_ids;
546 }
547 break;
548 default:
549 $select = $table . '.ID';
550 $join = ' INNER JOIN ' . $wpdb->postmeta . ' pm ON (pm.post_id=' . $table . '.ID)';
551 $where['pm.meta_key'] = 'frm_form_id';
552
553 if ( empty( $args['ids'] ) ) {
554 $where['pm.meta_value >'] = 1;
555 } else {
556 $where['pm.meta_value'] = $args['ids'];
557 }
558 }//end switch
559
560 $records[ $tb_type ] = FrmDb::get_col( $table . $join, $where, $select );
561 unset( $tb_type );
562 }//end foreach
563
564 $filename = self::get_file_name( $args, $records );
565
566 header( 'Content-Description: File Transfer' );
567 header( 'Content-Disposition: attachment; filename=' . $filename );
568 header( 'Content-Type: text/xml; charset=' . get_option( 'blog_charset' ), true );
569
570 echo '<?xml version="1.0" encoding="' . esc_attr( get_bloginfo( 'charset' ) ) . "\" ?>\n";
571 include FrmAppHelper::plugin_path() . '/classes/views/xml/xml.php';
572 }
573
574 /**
575 * Returns an array that has parent term slugs for the terms provided.
576 *
577 * @since 6.8.3
578 *
579 * @param array $terms
580 *
581 * @return array
582 */
583 public static function get_parent_terms_slugs( $terms ) {
584 $parent_term_ids = array_filter( array_unique( wp_list_pluck( $terms, 'parent' ) ) );
585 $parent_slugs = array();
586
587 if ( ! $parent_term_ids ) {
588 return $parent_slugs;
589 }
590
591 $results = FrmDb::get_results( 'terms', array( 'term_id' => $parent_term_ids ), 'term_id, slug' );
592
593 return wp_list_pluck( $results, 'slug', 'term_id' );
594 }
595
596 /**
597 * Prepare the types array.
598 *
599 * @param array<string>|string $type
600 *
601 * @return void
602 */
603 private static function prepare_types_array( &$type ) {
604 $type = (array) $type;
605
606 if ( ! in_array( 'forms', $type, true ) && ( in_array( 'items', $type, true ) || in_array( 'posts', $type, true ) ) ) {
607 // Make sure the form is included if there are entries
608 $type[] = 'forms';
609 }
610
611 if ( in_array( 'forms', $type, true ) ) {
612 // Include actions with forms
613 $type[] = 'actions';
614 }
615 }
616
617 /**
618 * Use a generic file name if multiple items are exported.
619 * Use the nme of the form if only one form is exported.
620 *
621 * @since 3.06
622 *
623 * @param array $args
624 * @param array $records
625 *
626 * @return string
627 */
628 private static function get_file_name( $args, $records ) {
629 $has_one_form = ! empty( $records['forms'] ) && count( $args['ids'] ) === 1;
630
631 if ( $has_one_form ) {
632 // One form is being exported
633 $selected_form_id = reset( $args['ids'] );
634 $filename = 'form-' . $selected_form_id . '.xml';
635
636 foreach ( $records['forms'] as $form_id ) {
637 $filename = 'form-' . $form_id . '.xml';
638
639 if ( $selected_form_id === $form_id ) {
640 $form = FrmForm::getOne( $form_id );
641 $filename = $form->name !== '' ? $form->name : $form->form_key;
642 $filename = sanitize_title( $filename ) . '-form.xml';
643 break;
644 }
645 }
646 } else {
647 $sitename = sanitize_key( get_bloginfo( 'name' ) );
648
649 if ( $sitename ) {
650 $sitename .= '.';
651 }
652
653 $filename = $sitename . 'formidable.' . gmdate( 'Y-m-d' ) . '.xml';
654 }//end if
655
656 /**
657 * @since 5.3
658 *
659 * @param string $filename
660 */
661 return apply_filters( 'frm_xml_filename', $filename );
662 }
663
664 /**
665 * @param array $atts
666 *
667 * @return void
668 */
669 public static function generate_csv( $atts ) {
670 $form_ids = $atts['ids'];
671
672 if ( ! $form_ids ) {
673 wp_die( esc_html__( 'Please select a form', 'formidable' ) );
674 }
675 self::csv( reset( $form_ids ) );
676 }
677
678 /**
679 * Export to CSV
680 *
681 * @since 2.0.19
682 *
683 * @param false|int|string $form_id
684 * @param string $search
685 * @param string $fid
686 *
687 * @return void
688 */
689 public static function csv( $form_id = false, $search = '', $fid = '' ) {
690 FrmAppHelper::permission_check( 'frm_view_entries' );
691
692 if ( ! $form_id ) {
693 $form_id = FrmAppHelper::get_param( 'form', '', 'get', 'sanitize_text_field' );
694 $search = FrmAppHelper::get_param( isset( $_REQUEST['s'] ) ? 's' : 'search', '', 'get', 'sanitize_text_field' );
695 $fid = FrmAppHelper::get_param( 'fid', '', 'get', 'sanitize_text_field' );
696 }
697
698 // Remove time limit to execute this function.
699 if ( function_exists( 'set_time_limit' ) ) {
700 set_time_limit( 0 );
701 }
702
703 $mem_limit = str_replace( 'M', '', ini_get( 'memory_limit' ) );
704
705 if ( (int) $mem_limit < 256 ) {
706 wp_raise_memory_limit();
707 }
708
709 global $wpdb;
710
711 $form = FrmForm::getOne( $form_id );
712
713 if ( ! $form ) {
714 esc_html_e( 'Form not found.', 'formidable' );
715 wp_die();
716 }
717
718 $form_id = $form->id;
719 $form_cols = self::get_fields_for_csv_export( $form_id, $form );
720 $item_id = FrmAppHelper::get_param( 'item_id', 0, 'get', 'sanitize_text_field' );
721
722 if ( $item_id ) {
723 $item_id = explode( ',', $item_id );
724 }
725
726 $query = array(
727 'form_id' => $form_id,
728 );
729
730 if ( $item_id ) {
731 $query['id'] = $item_id;
732 }
733
734 /**
735 * Allows the query to be changed for fetching the entry ids to include in the export
736 *
737 * $query is the array of options to be filtered. It includes form_id, and maybe id (array of entry ids),
738 * and the search query. This should return an array, but it can be handled as a string as well.
739 */
740 $query = apply_filters( 'frm_csv_where', $query, compact( 'form_id', 'search', 'fid', 'item_id' ) );
741
742 $entry_ids = FrmDb::get_col( $wpdb->prefix . 'frm_items it', $query );
743 unset( $query );
744
745 if ( $entry_ids ) {
746 FrmCSVExportHelper::generate_csv( compact( 'form', 'entry_ids', 'form_cols' ) );
747 } else {
748 esc_html_e( 'There are no entries for that form.', 'formidable' );
749 }
750
751 wp_die();
752 }
753
754 /**
755 * Get the fields that should be included in the CSV export
756 *
757 * @since 2.0.19
758 * @since 5.0.16 function went from private to public.
759 *
760 * @param int $form_id
761 * @param object $form
762 *
763 * @return array CSV fields.
764 */
765 public static function get_fields_for_csv_export( $form_id, $form ) {
766 $csv_fields = FrmField::get_all_for_form( $form_id, '', 'include', 'include' );
767 $no_export_fields = FrmField::no_save_fields();
768
769 foreach ( $csv_fields as $k => $f ) {
770 if ( in_array( $f->type, $no_export_fields, true ) ) {
771 unset( $csv_fields[ $k ] );
772 }
773 }
774
775 return apply_filters( 'frm_fields_for_csv_export', $csv_fields, compact( 'form' ) );
776 }
777
778 /**
779 * @param array $mimes
780 *
781 * @return array
782 */
783 public static function allow_mime( $mimes ) {
784 if ( ! isset( $mimes['csv'] ) ) {
785 // Allow csv files
786 $mimes['csv'] = 'text/csv';
787 }
788
789 if ( ! isset( $mimes['xml'] ) ) {
790 // Allow xml
791 $mimes['xml'] = 'text/xml';
792 }
793
794 return $mimes;
795 }
796 }
797