PluginProbe
TablePress – Tables in WordPress made easy / 1.12
TablePress – Tables in WordPress made easy v1.12
3.3.4 3.3.3 3.3.2 3.3.1 trunk 1.12 1.14 1.9.2 2.0.4 2.1.7 2.1.8 2.2 2.2.1 2.2.2 2.2.3 2.2.4 2.2.5 2.3 2.3.1 2.3.2 2.4 2.4.1 2.4.2 2.4.3 2.4.4 All 44 releases
tablepress / classes / class-export.php

class-export.php in TablePress – Tables in WordPress made easy 1.12, at classes/class-export.php

197 lines 5.8 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 /**
3 * TablePress Table Export Class
4 *
5 * @package TablePress
6 * @subpackage Export/Import
7 * @author Tobias Bäthge
8 * @since 1.0.0
9 */
10
11 // Prohibit direct script loading.
12 defined( 'ABSPATH' ) || die( 'No direct script access allowed!' );
13
14 /**
15 * TablePress Table Export Class
16 * @package TablePress
17 * @subpackage Export/Import
18 * @author Tobias Bäthge
19 * @since 1.0.0
20 */
21 class TablePress_Export {
22
23 /**
24 * File/Data Formats that are available for the export.
25 *
26 * @since 1.0.0
27 * @var array
28 */
29 public $export_formats = array();
30
31 /**
32 * Delimiters for the CSV export.
33 *
34 * @since 1.0.0
35 * @var array
36 */
37 public $csv_delimiters = array();
38
39 /**
40 * Whether ZIP archive support is available in the PHP installation on the server.
41 *
42 * @since 1.0.0
43 * @var bool
44 */
45 public $zip_support_available = false;
46
47 /**
48 * Initialize the Export class.
49 *
50 * @since 1.0.0
51 */
52 public function __construct() {
53 // Initiate here, because function call not possible outside a class method.
54 $this->export_formats = array(
55 'csv' => __( 'CSV - Character-Separated Values', 'tablepress' ),
56 'html' => __( 'HTML - Hypertext Markup Language', 'tablepress' ),
57 'json' => __( 'JSON - JavaScript Object Notation', 'tablepress' ),
58 );
59 $this->csv_delimiters = array(
60 ';' => __( '; (semicolon)', 'tablepress' ),
61 ',' => __( ', (comma)', 'tablepress' ),
62 'tab' => __( '\t (tabulator)', 'tablepress' ),
63 );
64
65 /** This filter is documented in the WordPress function unzip_file() in wp-admin/includes/file.php */
66 if ( class_exists( 'ZipArchive', false ) && apply_filters( 'unzip_file_use_ziparchive', true ) ) {
67 $this->zip_support_available = true;
68 }
69 }
70
71 /**
72 * Export a table.
73 *
74 * @since 1.0.0
75 *
76 * @param array $table Table to be exported.
77 * @param string $export_format Format for the export ('csv', 'html', 'json').
78 * @param string $csv_delimiter Delimiter for CSV export.
79 * @return string Exported table (only data for CSV and HTML, full tables (including options) for JSON).
80 */
81 public function export_table( array $table, $export_format, $csv_delimiter ) {
82 switch ( $export_format ) {
83 case 'csv':
84 $output = '';
85 if ( 'tab' === $csv_delimiter ) {
86 $csv_delimiter = "\t";
87 }
88 foreach ( $table['data'] as $row_idx => $row ) {
89 $csv_row = array();
90 foreach ( $row as $column_idx => $cell_content ) {
91 $csv_row[] = $this->csv_wrap_and_escape( $cell_content, $csv_delimiter );
92 }
93 $output .= implode( $csv_delimiter, $csv_row );
94 $output .= "\n";
95 }
96 break;
97 case 'html':
98 $num_rows = count( $table['data'] );
99 $last_row_idx = $num_rows - 1;
100 $thead = '';
101 $tfoot = '';
102 $tbody = array();
103
104 foreach ( $table['data'] as $row_idx => $row ) {
105 // First row, need to check for head (but only if at least two rows).
106 if ( 0 === $row_idx && $table['options']['table_head'] && $num_rows > 1 ) {
107 $thead = $this->html_render_row( $row, 'th' );
108 continue;
109 }
110 // Last row, need to check for footer (but only if at least two rows).
111 if ( $last_row_idx === $row_idx && $table['options']['table_foot'] && $num_rows > 1 ) {
112 $tfoot = $this->html_render_row( $row, 'th' );
113 continue;
114 }
115 // Neither first nor last row (with respective head/foot enabled), so render as body row.
116 $tbody[] = $this->html_render_row( $row, 'td' );
117 }
118
119 // <thead>, <tfoot>, and <tbody> tags.
120 if ( ! empty( $thead ) ) {
121 $thead = "\t<thead>\n{$thead}\t</thead>\n";
122 }
123 if ( ! empty( $tfoot ) ) {
124 $tfoot = "\t<tfoot>\n{$tfoot}\t</tfoot>\n";
125 }
126 $tbody = "\t<tbody>\n" . implode( '', $tbody ) . "\t</tbody>\n";
127
128 $output = "<table>\n" . $thead . $tfoot . $tbody . "</table>\n";
129 break;
130 case 'json':
131 $output = wp_json_encode( $table, TABLEPRESS_JSON_OPTIONS );
132 break;
133 default:
134 $output = '';
135 }
136
137 return $output;
138 }
139
140 /**
141 * Wrap and escape a cell for CSV export.
142 *
143 * @since 1.0.0
144 *
145 * @param string $string Content of a cell.
146 * @param string $delimiter CSV delimiter character.
147 * @return string Wrapped string for CSV export
148 */
149 protected function csv_wrap_and_escape( $string, $delimiter ) {
150 // Escape CSV delimiter for RegExp (e.g. '|').
151 $delimiter = preg_quote( $delimiter, '#' );
152 if ( 1 === preg_match( '#' . $delimiter . '|"|\n|\r#i', $string ) || ' ' === substr( $string, 0, 1 ) || ' ' === substr( $string, -1 ) ) {
153 // Escape single " as double "".
154 $string = str_replace( '"', '""', $string );
155 // Wrap string in "".
156 $string = '"' . $string . '"';
157 }
158 return $string;
159 }
160
161 /**
162 * Generate the HTML of a row.
163 *
164 * @since 1.0.0
165 *
166 * @param array $row Cells of the row to be rendered.
167 * @param string $tag HTML tag to use for the cells (td or th).
168 * @return string HTML code for the row.
169 */
170 protected function html_render_row( array $row, $tag ) {
171 $output = "\t\t<tr>\n";
172 array_walk( $row, array( $this, 'html_wrap_and_escape' ), $tag );
173 $output .= implode( '', $row );
174 $output .= "\t\t</tr>\n";
175 return $output;
176 }
177
178 /**
179 * Wrap and escape a cell for HTML export.
180 *
181 * @since 1.0.0
182 *
183 * @param string $cell_content Content of a cell.
184 * @param int|null $column_idx Column index, or null if omitted. Unused, but defined to be able to use function as callback in array_walk().
185 * @param string $html_tag HTML tag that shall be used for the cell.
186 */
187 protected function html_wrap_and_escape( &$cell_content, $column_idx, $html_tag ) {
188 /*
189 * Replace any & with &amp; that is not already an encoded entity (from function htmlentities2 in WP 2.8).
190 * A complete htmlentities2() or htmlspecialchars() would encode <HTML> tags, which we don't want.
191 */
192 $cell_content = preg_replace( '/&(?![A-Za-z]{0,4}\w{2,3};|#[0-9]{2,4};)/', '&amp;', $cell_content );
193 $cell_content = "\t\t\t<{$html_tag}>{$cell_content}</{$html_tag}>\n";
194 }
195
196 } // class TablePress_Export
197