PluginProbe
Formidable Forms – WordPress Form Builder for Contact Forms, Calculators, Quizzes & More / 5.2.07
Formidable Forms – WordPress Form Builder for Contact Forms, Calculators, Quizzes & More v5.2.07
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/helpers/FrmXMLHelper.php +40 -345 6.5.35.2.07 View file →
@@ -32,25 +32,13 @@
32 32 define( 'WP_IMPORTING', true );
33 33 }
34 34
35 35 if ( ! class_exists( 'DOMDocument' ) ) {
36 - $error_message = sprintf(
37 - /* translators: 1: Documentation link */
38 - __( 'In order to install XML, your server must have DOMDocument installed. Follow our documentation on %1$s to ensure DOMDocument is properly set up and XML support is enabled.', 'formidable' ),
39 - '<a href="https://formidableforms.com/knowledgebase/import-forms-entries-and-views/#kb-your-server-does-not-have-xml-enabled" target="_blank">Importing Forms, Entries, and Views</a>'
40 - );
41 -
42 - return new WP_Error( 'SimpleXML_parse_error', $error_message, libxml_get_errors() );
36 + return new WP_Error( 'SimpleXML_parse_error', __( 'Your server does not have XML enabled', 'formidable' ), libxml_get_errors() );
43 37 }
44 38
45 - $xml_string = file_get_contents( $file );
46 - self::maybe_fix_xml( $xml_string );
47 -
48 - $dom = new DOMDocument();
49 -
50 - // LIBXML_COMPACT activates small nodes allocation optimization.
51 - // Use LIBXML_PARSEHUGE to avoid "parser error : internal error: Huge input lookup" for large (300MB) files.
52 - $success = $dom->loadXML( $xml_string, LIBXML_COMPACT | LIBXML_PARSEHUGE );
39 + $dom = new DOMDocument();
40 + $success = $dom->loadXML( file_get_contents( $file ) );
53 41 if ( ! $success ) {
54 42 return new WP_Error( 'SimpleXML_parse_error', __( 'There was an error when reading this XML file', 'formidable' ), libxml_get_errors() );
55 43 }
56 44
@@ -69,35 +57,8 @@
69 57 return self::import_xml_now( $xml );
70 58 }
71 59
72 60 /**
73 - * @since 6.2.3
74 - *
75 - * @param string $xml_string
76 - * @return void
77 - */
78 - private static function maybe_fix_xml( &$xml_string ) {
79 - if ( '<?xml' !== substr( $xml_string, 0, 5 ) ) {
80 - // Some XML files have may have unexpected characters at the start.
81 - $xml_string = substr( $xml_string, strpos( $xml_string, '<?xml' ) );
82 - }
83 -
84 - // The Equity theme adds a <meta name="generator" content="Equity 1.7.13" /> tag using the "the_generator" filter.
85 - // Strip that out as it breaks the XML import.
86 - $channel_start_position = strpos( $xml_string, '<channel>' );
87 - $content_before_channel_tag = substr( $xml_string, 0, $channel_start_position );
88 - if ( 0 !== strpos( $content_before_channel_tag, '<meta name="generator" ' ) ) {
89 - $content_before_channel_tag = preg_replace(
90 - '/<meta\s+[^>]*name="generator"[^>]*\/>/i',
91 - '',
92 - $content_before_channel_tag,
93 - 1
94 - );
95 - $xml_string = $content_before_channel_tag . substr( $xml_string, $channel_start_position );
96 - }
97 - }
98 -
99 - /**
100 61 * Add terms, forms (form and field ids), posts (post ids), and entries to db, in that order
101 62 *
102 63 * @since 3.06
103 64 *
@@ -126,9 +87,9 @@
126 87
127 88 if ( ! isset( $imported['form_status'] ) || empty( $imported['form_status'] ) ) {
128 89 // Check for an error message in the XML.
129 90 if ( isset( $xml->Code ) && isset( $xml->Message ) ) { // phpcs:ignore WordPress.NamingConventions
130 - $imported['error'] = (string) $xml->Message; // phpcs:ignore WordPress.NamingConventions
91 + $imported['error'] = reset( $xml->Message ); // phpcs:ignore WordPress.NamingConventions
131 92 }
132 93 }
133 94
134 95 return $imported;
@@ -303,15 +264,9 @@
303 264 }
304 265
305 266 $edit_query = apply_filters( 'frm_match_xml_form', $edit_query, $form );
306 267
307 - $form = FrmForm::getAll( $edit_query, '', 1 );
308 - if ( is_object( $form ) && $form->status === 'trash' ) {
309 - FrmForm::destroy( $form->id );
310 - return false;
311 - }
312 -
313 - return $form;
268 + return FrmForm::getAll( $edit_query, '', 1 );
314 269 }
315 270
316 271 private static function update_form( $this_form, $form, &$imported ) {
317 272 $form_id = $this_form->id;
@@ -673,12 +628,8 @@
673 628 private static function create_imported_field( $f, &$imported ) {
674 629 $defaults = self::default_field_options( $f['type'] );
675 630 $f['field_options'] = array_merge( $defaults, $f['field_options'] );
676 631
677 - if ( is_callable( 'FrmProFileImport::import_attachment' ) ) {
678 - $f = self::maybe_import_images_for_options( $f );
679 - }
680 -
681 632 $new_id = FrmField::create( $f );
682 633 if ( $new_id != false ) {
683 634 $imported['imported']['fields'] ++;
684 635 do_action( 'frm_after_field_is_imported', $f, $new_id );
@@ -685,40 +636,8 @@
685 636 }
686 637 }
687 638
688 639 /**
689 - * Import images for radio buttons and checkboxes from image src if available.
690 - *
691 - * @since 5.5.1
692 - *
693 - * @param array $field
694 - * @return array
695 - */
696 - private static function maybe_import_images_for_options( $field ) {
697 - if ( empty( $field['options'] ) || ! is_array( $field['options'] ) ) {
698 - return $field;
699 - }
700 -
701 - foreach ( $field['options'] as $key => $option ) {
702 - if ( ! is_array( $option ) || empty( $option['src'] ) ) {
703 - continue;
704 - }
705 -
706 - $field_object = (object) $field;
707 - $field_object->type = 'file'; // Fake the file type as FrmProImport::import_attachment checks for file type.
708 -
709 - $image_id = FrmProFileImport::import_attachment( $option['src'], $field_object );
710 - unset( $field['options'][ $key ]['src'] ); // Remove the src from options as it isn't required after import.
711 -
712 - if ( is_numeric( $image_id ) ) {
713 - $field['options'][ $key ]['image'] = $image_id;
714 - }
715 - }
716 -
717 - return $field;
718 - }
719 -
720 - /**
721 640 * Fix field ids for fields that already exist prior to import.
722 641 *
723 642 * @since 4.07
724 643 * @param int $form_id
@@ -769,9 +688,9 @@
769 688 if ( ! isset( $form['options']['custom_style'] ) ) {
770 689 return;
771 690 }
772 691
773 - if ( is_numeric( $form['options']['custom_style'] ) && 1 === intval( $form['options']['custom_style'] ) ) {
692 + if ( is_numeric( $form['options']['custom_style'] ) ) {
774 693 // Set to default
775 694 $form['options']['custom_style'] = 1;
776 695 } else {
777 696 // Replace the style name with the style ID on import
@@ -826,11 +745,8 @@
826 745 $form_action_type => 'actions',
827 746 'frm_styles' => 'styles',
828 747 );
829 748
830 - $view_ids = array();
831 - $posts_with_shortcodes = array();
832 -
833 749 foreach ( $views as $item ) {
834 750 $post = array(
835 751 'post_title' => (string) $item->title,
836 752 'post_name' => (string) $item->post_name,
@@ -853,10 +769,8 @@
853 769 'layout' => array(),
854 770 'tax_input' => array(),
855 771 );
856 772
857 - $post['post_content'] = self::switch_form_ids( $post['post_content'], $imported['forms'] );
858 -
859 773 $old_id = $post['post_id'];
860 774 self::populate_post( $post, $item, $imported );
861 775
862 776 unset( $item );
@@ -861,26 +775,26 @@
861 775
862 776 unset( $item );
863 777
864 778 $post_id = false;
865 - if ( $post['post_type'] === $form_action_type ) {
779 + if ( $post['post_type'] == $form_action_type ) {
866 780 $action_control = FrmFormActionsController::get_form_actions( $post['post_excerpt'] );
867 781 if ( $action_control && is_object( $action_control ) ) {
868 782 $post_id = $action_control->maybe_create_action( $post, $imported['form_status'] );
869 783 }
870 784 unset( $action_control );
871 - } elseif ( $post['post_type'] === 'frm_styles' ) {
785 + } elseif ( $post['post_type'] == 'frm_styles' ) {
872 786 // Properly encode post content before inserting the post
873 787 $post['post_content'] = FrmAppHelper::maybe_json_decode( $post['post_content'] );
788 + $custom_css = isset( $post['post_content']['custom_css'] ) ? $post['post_content']['custom_css'] : '';
874 789 $post['post_content'] = FrmAppHelper::prepare_and_encode( $post['post_content'] );
875 790
876 791 // Create/update post now
877 792 $post_id = wp_insert_post( $post );
793 + self::maybe_update_custom_css( $custom_css );
878 794 } else {
879 795 if ( $post['post_type'] === 'frm_display' ) {
880 796 $post['post_content'] = self::maybe_prepare_json_view_content( $post['post_content'] );
881 - } elseif ( 'page' === $post['post_type'] && isset( $imported['posts'][ $post['post_parent'] ] ) ) {
882 - $post['post_parent'] = $imported['posts'][ $post['post_parent'] ];
883 797 }
884 798 // Create/update post now
885 799 $post_id = wp_insert_post( $post );
886 800 }
@@ -888,12 +802,8 @@
888 802 if ( ! is_numeric( $post_id ) ) {
889 803 continue;
890 804 }
891 805
892 - if ( false !== strpos( $post['post_content'], '[display-frm-data' ) || false !== strpos( $post['post_content'], '[formidable' ) ) {
893 - $posts_with_shortcodes[ $post_id ] = $post;
894 - }
895 -
896 806 self::update_postmeta( $post, $post_id );
897 807 self::update_layout( $post, $post_id );
898 808
899 809 $this_type = 'posts';
@@ -908,154 +818,19 @@
908 818 }
909 819
910 820 $imported['posts'][ (int) $old_id ] = $post_id;
911 821
912 - if ( $post['post_type'] === 'frm_display' ) {
913 - $view_ids[ (int) $old_id ] = $post_id;
914 - }
915 -
916 822 do_action( 'frm_after_import_view', $post_id, $post );
917 823
918 824 unset( $post );
919 825 }
920 826
921 - if ( $posts_with_shortcodes && $view_ids ) {
922 - self::maybe_switch_view_ids_after_importing_posts( $posts_with_shortcodes, $view_ids );
923 - }
924 - unset( $posts_with_shortcodes, $view_ids );
925 -
926 - if ( ! empty( $imported['forms'] ) ) {
927 - // clear imported forms style cache to make sure the new styles are applied to the forms
928 - self::clear_forms_style_caches( $imported['forms'] );
929 - }
930 -
931 827 self::maybe_update_stylesheet( $imported );
932 828
933 - flush_rewrite_rules();
934 -
935 829 return $imported;
936 830 }
937 831
938 832 /**
939 - * Clears styles from cache for imported forms
940 - *
941 - * @param array $imported_forms
942 - */
943 - private static function clear_forms_style_caches( $imported_forms ) {
944 - $where = array(
945 - 'id' => $imported_forms,
946 - 'options LIKE' => '"old_style"',
947 - );
948 - $forms = FrmDb::get_results( 'frm_forms', $where );
949 -
950 - foreach ( $forms as $form ) {
951 - FrmAppHelper::unserialize_or_decode( $form->options );
952 - if ( ! $form->options ) {
953 - continue;
954 - }
955 - $where = array(
956 - 'post_name' => $form->options['old_style'],
957 - 'post_type' => FrmStylesController::$post_type,
958 - );
959 -
960 - $select = 'ID';
961 -
962 - $cache_key = FrmDb::generate_cache_key( $where, array( 'limit' => 1 ), $select, 'var' );
963 - FrmDb::delete_cache_and_transient( $cache_key, 'post' );
964 - }
965 - }
966 -
967 - /**
968 - * Replace old form ids with new ones in a string.
969 - *
970 - * @param string $string
971 - * @param array<int> $form_ids new form ids indexed by old form id.
972 - * @return string
973 - */
974 - private static function switch_form_ids( $string, $form_ids ) {
975 - if ( false === strpos( $string, '[formidable' ) ) {
976 - // Skip string replacing if there are no form shortcodes in string.
977 - return $string;
978 - }
979 -
980 - foreach ( $form_ids as $old_id => $new_id ) {
981 - $string = str_replace(
982 - array(
983 - '[formidable id="' . $old_id . '"',
984 - '[formidable id=' . $old_id . ']',
985 - '[formidable id=' . $old_id . ' ',
986 - '"formId":"' . $old_id . '"',
987 - ),
988 - array(
989 - '[formidable id="' . $new_id . '"',
990 - '[formidable id=' . $new_id . ']',
991 - '[formidable id=' . $new_id . ' ',
992 - '"formId":"' . $new_id . '"',
993 - ),
994 - $string
995 - );
996 - }
997 -
998 - return $string;
999 - }
1000 -
1001 - /**
1002 - * @param array<array> $posts_with_shortcodes indexed by current post id.
1003 - * @param array<int> $view_ids new view ids indexed by old view id.
1004 - * @return void
1005 - */
1006 - private static function maybe_switch_view_ids_after_importing_posts( $posts_with_shortcodes, $view_ids ) {
1007 - foreach ( $posts_with_shortcodes as $imported_post_id => $post ) {
1008 - $post_content = self::switch_view_ids( $post['post_content'], $view_ids );
1009 - if ( $post_content === $post['post_content'] ) {
1010 - continue;
1011 - }
1012 -
1013 - wp_update_post(
1014 - array(
1015 - 'ID' => $imported_post_id,
1016 - 'post_content' => $post_content,
1017 - )
1018 - );
1019 - }
1020 - }
1021 -
1022 - /**
1023 - * Replace old view ids with new ones in a string.
1024 - *
1025 - * @param string $string
1026 - * @param array<int> $view_ids new view ids indexed by old view id.
1027 - * @return string
1028 - */
1029 - private static function switch_view_ids( $string, $view_ids ) {
1030 - if ( false === strpos( $string, '[display-frm-data' ) ) {
1031 - // Skip string replacing if there are no view shortcodes in string.
1032 - return $string;
1033 - }
1034 -
1035 - foreach ( $view_ids as $old_id => $new_id ) {
1036 - $string = str_replace(
1037 - array(
1038 - '[display-frm-data id="' . $old_id . '"',
1039 - '[display-frm-data id=' . $old_id . ']',
1040 - '[display-frm-data id=' . $old_id . ' ',
1041 - '"viewId":"' . $old_id . '"',
1042 - ),
1043 - array(
1044 - '[display-frm-data id="' . $new_id . '"',
1045 - '[display-frm-data id=' . $new_id . ']',
1046 - '[display-frm-data id=' . $new_id . ' ',
1047 - '"viewId":"' . $new_id . '"',
1048 - ),
1049 - $string
1050 - );
1051 - unset( $old_id, $new_id );
1052 - }
1053 -
1054 - return $string;
1055 - }
1056 -
1057 - /**
1058 833 * @param string $content
1059 834 * @return string
1060 835 */
1061 836 private static function maybe_prepare_json_view_content( $content ) {
@@ -1220,40 +995,24 @@
1220 995 $post['ID'] = current( $editing )->ID;
1221 996 }
1222 997 }
1223 998
1224 - /**
1225 - * @param array $post
1226 - * @param int $post_id
1227 - * @return void
1228 - */
1229 999 private static function update_postmeta( &$post, $post_id ) {
1230 1000 foreach ( $post['postmeta'] as $k => $v ) {
1231 - switch ( $k ) {
1232 - case '_edit_last':
1233 - $v = FrmAppHelper::get_user_id_param( $v );
1234 - break;
1001 + if ( '_edit_last' == $k ) {
1002 + $v = FrmAppHelper::get_user_id_param( $v );
1003 + } elseif ( '_thumbnail_id' == $k && FrmAppHelper::pro_is_installed() ) {
1004 + // Change the attachment ID.
1005 + $field_obj = FrmFieldFactory::get_field_type( 'file' );
1006 + $v = $field_obj->get_file_id( $v );
1007 + }
1235 1008
1236 - case '_thumbnail_id':
1237 - if ( FrmAppHelper::pro_is_installed() ) {
1238 - // Change the attachment ID.
1239 - $field_obj = FrmFieldFactory::get_field_type( 'file' );
1240 - $v = $field_obj->get_file_id( $v );
1241 - }
1242 - break;
1243 -
1244 - case 'frm_dyncontent':
1245 - if ( is_array( $v ) ) {
1246 - $v = json_encode( $v );
1247 - }
1248 - break;
1249 -
1250 - case 'frm_param':
1251 - add_rewrite_endpoint( $v, EP_PERMALINK | EP_PAGES );
1252 - break;
1009 + if ( 'frm_dyncontent' === $k && is_array( $v ) ) {
1010 + $v = json_encode( $v );
1253 1011 }
1254 1012
1255 1013 update_post_meta( $post_id, $k, $v );
1014 +
1256 1015 unset( $k, $v );
1257 1016 }
1258 1017 }
1259 1018
@@ -1270,8 +1029,25 @@
1270 1029 }
1271 1030 }
1272 1031 }
1273 1032
1033 + /**
1034 + * If a template includes custom css, let's include it.
1035 + * The custom css is included on the default style.
1036 + *
1037 + * @since 2.03
1038 + */
1039 + private static function maybe_update_custom_css( $custom_css ) {
1040 + if ( empty( $custom_css ) ) {
1041 + return;
1042 + }
1043 +
1044 + $frm_style = new FrmStyle();
1045 + $default_style = $frm_style->get_default_style();
1046 + $default_style->post_content['custom_css'] .= "\r\n\r\n" . $custom_css;
1047 + $frm_style->save( $default_style );
1048 + }
1049 +
1274 1050 private static function maybe_update_stylesheet( $imported ) {
1275 1051 $new_styles = isset( $imported['imported']['styles'] ) && ! empty( $imported['imported']['styles'] );
1276 1052 $updated_styles = isset( $imported['updated']['styles'] ) && ! empty( $imported['updated']['styles'] );
1277 1053 if ( $new_styles || $updated_styles ) {
@@ -1290,29 +1066,8 @@
1290 1066 */
1291 1067 public static function parse_message( $result, &$message, &$errors ) {
1292 1068 if ( is_wp_error( $result ) ) {
1293 1069 $errors[] = $result->get_error_message();
1294 -
1295 - // Remove the SimpleXML_parse_error from the WP_Error object to avoid
1296 - // displaying duplicate error messages from $result->get_error_message()
1297 - $error_codes = $result->get_error_codes();
1298 - $error_details = array();
1299 - foreach ( $error_codes as $error_code ) {
1300 - // Clone WP_Error data because WP_Error removes all error messages and data
1301 - // associated with the specified error code when an item is removed.
1302 - // Source: https://developer.wordpress.org/reference/classes/wp_error/remove/#source
1303 - $error_details = $result->get_error_data( $error_code );
1304 - if ( $error_code === 'SimpleXML_parse_error' ) {
1305 - $result->remove( $error_code );
1306 - break;
1307 - }
1308 - }
1309 -
1310 - if ( ! empty( $error_details ) ) {
1311 - $errors[] = '<br />' . esc_html_x( 'Error details:', 'import xml message', 'formidable' ) . '<br />' . esc_html( print_r( $error_details, 1 ) );
1312 - }
1313 -
1314 - return;
1315 1070 } elseif ( ! $result ) {
1316 1071 return;
1317 1072 }
1318 1073
@@ -1352,24 +1107,12 @@
1352 1107 $errors[] = __( 'Nothing was imported or updated', 'formidable' );
1353 1108 } else {
1354 1109 self::add_form_link_to_message( $result, $message );
1355 1110
1356 - /**
1357 - * @since 5.3
1358 - *
1359 - * @param string $message
1360 - * @param array $result
1361 - */
1362 - $message = apply_filters( 'frm_xml_parsed_message', $message, $result );
1363 1111 $message .= '</ul>';
1364 1112 }
1365 1113 }
1366 1114
1367 - /**
1368 - * @param int $m
1369 - * @param string $type
1370 - * @param array<string> $s_message
1371 - */
1372 1115 public static function item_count_message( $m, $type, &$s_message ) {
1373 1116 if ( ! $m ) {
1374 1117 return;
1375 1118 }
@@ -1383,9 +1126,9 @@
1383 1126 'items' => sprintf( _n( '%1$s Entry', '%1$s Entries', $m, 'formidable' ), $m ),
1384 1127 /* translators: %1$s: Number of items */
1385 1128 'views' => sprintf( _n( '%1$s View', '%1$s Views', $m, 'formidable' ), $m ),
1386 1129 /* translators: %1$s: Number of items */
1387 - 'posts' => sprintf( _n( '%1$s Page/Post', '%1$s Pages/Posts', $m, 'formidable' ), $m ),
1130 + 'posts' => sprintf( _n( '%1$s Post', '%1$s Posts', $m, 'formidable' ), $m ),
1388 1131 /* translators: %1$s: Number of items */
1389 1132 'styles' => sprintf( _n( '%1$s Style', '%1$s Styles', $m, 'formidable' ), $m ),
1390 1133 /* translators: %1$s: Number of items */
1391 1134 'terms' => sprintf( _n( '%1$s Term', '%1$s Terms', $m, 'formidable' ), $m ),
@@ -1392,23 +1135,9 @@
1392 1135 /* translators: %1$s: Number of items */
1393 1136 'actions' => sprintf( _n( '%1$s Form Action', '%1$s Form Actions', $m, 'formidable' ), $m ),
1394 1137 );
1395 1138
1396 - if ( isset( $strings[ $type ] ) ) {
1397 - $s_message[] = $strings[ $type ];
1398 - } else {
1399 - $string = ' ' . $m . ' ' . ucfirst( $type );
1400 -
1401 - /**
1402 - * @since 5.3
1403 - *
1404 - * @param string $string Message string for imported item.
1405 - * @param int $m Number of item that was imported.
1406 - * }
1407 - */
1408 - $string = apply_filters( 'frm_xml_' . $type . '_count_message', $string, $m );
1409 - $s_message[] = $string;
1410 - }
1139 + $s_message[] = isset( $strings[ $type ] ) ? $strings[ $type ] : ' ' . $m . ' ' . ucfirst( $type );
1411 1140 }
1412 1141
1413 1142 /**
1414 1143 * If a single form was imported, include a link in the success message.
@@ -1485,9 +1214,8 @@
1485 1214 * @since 3.06
1486 1215 */
1487 1216 public static function prepare_field_for_export( &$field ) {
1488 1217 self::remove_default_field_options( $field );
1489 - self::add_image_src_to_image_options( $field );
1490 1218 }
1491 1219
1492 1220 /**
1493 1221 * Remove defaults from field options too
@@ -1519,41 +1247,8 @@
1519 1247 $field->field_options = serialize( $options );
1520 1248 }
1521 1249
1522 1250 /**
1523 - * Add image "src" key to each image option so the image can be imported to another website.
1524 - *
1525 - * @since 5.5.1
1526 - *
1527 - * @param stdClass $field
1528 - * @return void
1529 - */
1530 - private static function add_image_src_to_image_options( $field ) {
1531 - if ( empty( $field->options ) || false === strpos( $field->options, 'image' ) ) {
1532 - return;
1533 - }
1534 -
1535 - $updated = false;
1536 - $options = $field->options;
1537 - FrmAppHelper::unserialize_or_decode( $options );
1538 -
1539 - if ( ! $options || ! is_array( $options ) ) {
1540 - return;
1541 - }
1542 -
1543 - foreach ( $options as $key => $option ) {
1544 - if ( is_array( $option ) && ! empty( $option['image'] ) ) {
1545 - $options[ $key ]['src'] = wp_get_attachment_url( $option['image'] );
1546 - $updated = true;
1547 - }
1548 - }
1549 -
1550 - if ( $updated ) {
1551 - $field->options = maybe_serialize( $options );
1552 - }
1553 - }
1554 -
1555 - /**
1556 1251 * @since 3.06.03
1557 1252 */
1558 1253 private static function default_field_options( $type ) {
1559 1254 $defaults = FrmFieldsHelper::get_default_field_options( $type );
@@ -1606,9 +1301,9 @@
1606 1301 FrmAppHelper::unserialize_or_decode( $str );
1607 1302 if ( is_array( $str ) ) {
1608 1303 $str = json_encode( $str );
1609 1304 } elseif ( seems_utf8( $str ) === false ) {
1610 - $str = FrmAppHelper::maybe_utf8_encode( $str );
1305 + $str = utf8_encode( $str );
1611 1306 }
1612 1307
1613 1308 if ( is_numeric( $str ) ) {
1614 1309 return $str;