Merge branch 'QA_5_0'
[phpmyadmin.git] / libraries / classes / Plugins / Transformations / Abs / ExternalTransformationsPlugin.php
blobc8549be9ffa4d205586ec937e073855d3612ca6f
1 <?php
2 /**
3 * Abstract class for the external transformations plugins
4 */
5 declare(strict_types=1);
7 namespace PhpMyAdmin\Plugins\Transformations\Abs;
9 use PhpMyAdmin\Plugins\TransformationsPlugin;
10 use stdClass;
11 use function count;
12 use function fclose;
13 use function feof;
14 use function fgets;
15 use function fwrite;
16 use function htmlspecialchars;
17 use function is_resource;
18 use function proc_close;
19 use function proc_open;
21 /**
22 * Provides common methods for all of the external transformations plugins.
24 abstract class ExternalTransformationsPlugin extends TransformationsPlugin
26 /**
27 * Gets the transformation description of the specific plugin
29 * @return string
31 public static function getInfo()
33 return __(
34 'LINUX ONLY: Launches an external application and feeds it the column'
35 . ' data via standard input. Returns the standard output of the'
36 . ' application. The default is Tidy, to pretty-print HTML code.'
37 . ' For security reasons, you have to manually edit the file'
38 . ' libraries/classes/Plugins/Transformations/Abs/ExternalTransformationsPlugin.php'
39 . ' and list the tools you want to make available.'
40 . ' The first option is then the number of the program you want to'
41 . ' use. The second option should be blank for historical reasons.'
42 . ' The third option, if set to 1, will convert the output using'
43 . ' htmlspecialchars() (Default 1). The fourth option, if set to 1,'
44 . ' will prevent wrapping and ensure that the output appears all on'
45 . ' one line (Default 1).'
49 /**
50 * Enables no-wrapping
52 * @param array $options transformation options
54 * @return bool
56 public function applyTransformationNoWrap(array $options = [])
58 if (! isset($options[3]) || $options[3] == '') {
59 $nowrap = true;
60 } elseif ($options[3] == '1' || $options[3] == 1) {
61 $nowrap = true;
62 } else {
63 $nowrap = false;
66 return $nowrap;
69 /**
70 * Does the actual work of each specific transformations plugin.
72 * @param string $buffer text to be transformed
73 * @param array $options transformation options
74 * @param stdClass|null $meta meta information
76 * @return string
78 public function applyTransformation($buffer, array $options = [], ?stdClass $meta = null)
80 // possibly use a global transform and feed it with special options
82 // further operations on $buffer using the $options[] array.
84 $allowed_programs = [];
86 // WARNING:
88 // It's up to administrator to allow anything here. Note that users may
89 // specify any parameters, so when programs allow output redirection or
90 // any other possibly dangerous operations, you should write wrapper
91 // script that will publish only functions you really want.
93 // Add here program definitions like (note that these are NOT safe
94 // programs):
96 //$allowed_programs[0] = '/usr/local/bin/tidy';
97 //$allowed_programs[1] = '/usr/local/bin/validate';
99 // no-op when no allowed programs
100 if (count($allowed_programs) === 0) {
101 return $buffer;
104 $cfg = $GLOBALS['cfg'];
105 $options = $this->getOptions(
106 $options,
107 $cfg['DefaultTransformations']['External']
110 if (isset($allowed_programs[$options[0]])) {
111 $program = $allowed_programs[$options[0]];
112 } else {
113 $program = $allowed_programs[0];
116 if (isset($options[1]) && strlen((string) $options[1]) > 0) {
117 trigger_error(sprintf(
119 'You are using the external transformation command line options field, which has been deprecated for security reasons. '
120 . 'Add all command line options directly to the definition in %s.'
122 '[code]libraries/classes/Plugins/Transformations/Abs/ExternalTransformationsPlugin.php[/code]'
123 ), E_USER_DEPRECATED);
126 // needs PHP >= 4.3.0
127 $newstring = '';
128 $descriptorspec = [
129 0 => [
130 'pipe',
131 'r',
133 1 => [
134 'pipe',
135 'w',
138 $process = proc_open($program . ' ' . $options[1], $descriptorspec, $pipes);
139 if (is_resource($process)) {
140 fwrite($pipes[0], $buffer);
141 fclose($pipes[0]);
143 while (! feof($pipes[1])) {
144 $newstring .= fgets($pipes[1], 1024);
146 fclose($pipes[1]);
147 // we don't currently use the return value
148 proc_close($process);
151 if ($options[2] == 1 || $options[2] == '2') {
152 $retstring = htmlspecialchars($newstring);
153 } else {
154 $retstring = $newstring;
157 return $retstring;
160 /* ~~~~~~~~~~~~~~~~~~~~ Getters and Setters ~~~~~~~~~~~~~~~~~~~~ */
163 * Gets the transformation name of the specific plugin
165 * @return string
167 public static function getName()
169 return 'External';