PageRenderTime 24ms CodeModel.GetById 24ms RepoModel.GetById 0ms app.codeStats 0ms

/usr/share/squirrelmail/plugins/multiple_attachments/functions.php

https://gitlab.com/thiagotalma/stalag13
PHP | 431 lines | 203 code | 110 blank | 118 comment | 47 complexity | f1ee0bc9fc7c0b23a2d7f574d8293d14 MD5 | raw file
  1. <?php
  2. /**
  3. * SquirrelMail Multiple Attachments Plugin
  4. *
  5. * Copyright (c) 2012-2012 Paul Lesniewski <paul@squirrelmail.org>
  6. *
  7. * Licensed under the GNU GPL. For full terms see the file COPYING.
  8. *
  9. * @package plugins
  10. * @subpackage multiple_attachments
  11. *
  12. */
  13. /**
  14. * Validate that this plugin is configured correctly
  15. *
  16. * @return boolean Whether or not there was a
  17. * configuration error for this plugin.
  18. *
  19. */
  20. function multiple_attachments_check_configuration()
  21. {
  22. // make sure base config is available
  23. //
  24. if (!multiple_attachments_init())
  25. {
  26. do_err('Multiple Attachments plugin is missing its main configuration file', FALSE);
  27. return TRUE;
  28. }
  29. }
  30. /**
  31. * Initialize this plugin (load config values)
  32. *
  33. * @return boolean FALSE if no configuration file could be loaded, TRUE otherwise
  34. *
  35. */
  36. function multiple_attachments_init()
  37. {
  38. if (!@include_once (SM_PATH . 'config/config_multiple_attachments.php'))
  39. if (!@include_once (SM_PATH . 'plugins/multiple_attachments/config.php'))
  40. if (!@include_once (SM_PATH . 'plugins/multiple_attachments/config_default.php'))
  41. return FALSE;
  42. return TRUE;
  43. /* ---------- This is how to do the same thing using the Compatibility plugin
  44. return load_config('multiple_attachments',
  45. array('../../config/config_multiple_attachments.php',
  46. 'config.php',
  47. 'config_default.php'),
  48. TRUE, TRUE);
  49. ----------- */
  50. }
  51. /**
  52. * Start output caching so we can alter it before sending to client
  53. *
  54. */
  55. function ma_start_output_cache()
  56. {
  57. if (check_sm_version(1, 5, 2)) return;
  58. global $data_dir, $username, $number_of_attachment_inputs,
  59. $allow_dynamic_input_addition, $javascript_on,
  60. $number_of_attachment_inputs_allow_override;
  61. multiple_attachments_init();
  62. if ($number_of_attachment_inputs_allow_override)
  63. $number_of_attachment_inputs = getPref($data_dir, $username, 'number_of_attachment_inputs', $number_of_attachment_inputs);
  64. if (!(bool)ini_get('file_uploads')
  65. || ($number_of_attachment_inputs < 2
  66. && (!$javascript_on || !$allow_dynamic_input_addition)))
  67. return;
  68. ob_start();
  69. }
  70. /**
  71. * Add multiple attachment inputs to output for SquirrelMail versions 1.4.x
  72. *
  73. */
  74. function ma_add_attachment_inputs_1_4()
  75. {
  76. global $data_dir, $username, $number_of_attachment_inputs,
  77. $allow_dynamic_input_addition, $javascript_on,
  78. $number_of_attachment_inputs_allow_override;
  79. multiple_attachments_init();
  80. if ($number_of_attachment_inputs_allow_override)
  81. $number_of_attachment_inputs = getPref($data_dir, $username, 'number_of_attachment_inputs', $number_of_attachment_inputs);
  82. if (!(bool)ini_get('file_uploads')
  83. || ($number_of_attachment_inputs < 2
  84. && (!$javascript_on || !$allow_dynamic_input_addition)))
  85. return;
  86. $output .= ob_get_contents();
  87. ob_end_clean();
  88. $attachment_input = $dynamic_link = $script = '';
  89. // add dynamic link
  90. //
  91. if ($javascript_on && $allow_dynamic_input_addition)
  92. {
  93. // "more" is actually in the SquirrelMail domain, but
  94. // due to its context (for viewing more message recipients),
  95. // its translation in some languages doesn't work here
  96. //
  97. sq_change_text_domain('multiple_attachments');
  98. $more = _("more");
  99. sq_change_text_domain('squirrelmail');
  100. $dynamic_link = '&nbsp; <small><a href="javascript:void(0)" onclick="var row = document.getElementById(\'attachment_table\').insertRow(1); var cell = row.insertCell(0); cell.align = \'right\'; cell.valign = \'middle\'; cell.innerHTML = \'' . _("Attach:") . '\'; cell = row.insertCell(1); cell.align = \'left\'; cell.valign = \'middle\'; cell.innerHTML = get_new_attachment_input();">' . $more . "</a></small>\n";
  101. // small global JavaScript to initialize counter variable
  102. // and provide easy function for getting new attachment input tags
  103. //
  104. $script = "\n<script type=\"text/javascript\" language=\"JavaScript\">\n<!--\n"
  105. . "var attachment_counter = " . ($number_of_attachment_inputs - 1) . ";\n"
  106. . "function get_new_attachment_input()\n"
  107. . "{\n"
  108. . ' return \'<input name="attachfile_\' + (++attachment_counter) + \'" size="48" type="file" />\';'
  109. . "\n}"
  110. . "\n// -->\n</script>\n";
  111. }
  112. // add default inputs
  113. //
  114. for ($i = 0; $i < $number_of_attachment_inputs - 1; $i++)
  115. // note that we are intentionally in SquirrelMail text domain
  116. $attachment_input .= "<tr>\n"
  117. . html_tag('td', '', 'right', '', 'valign="middle"')
  118. . _("Attach:") . "</td>\n"
  119. . html_tag('td', '', 'left', '', 'valign="middle"')
  120. . '<input name="attachfile_' . ($i + 1) . '" size="48" type="file" />'
  121. . "\n</td>\n</tr>\n";
  122. // older SquirrelMail versions - need to insert it into cached output...
  123. //
  124. // adds name to table containing the inputs, then adds
  125. // the "dynamic" link after the first input and any
  126. // more default inputs in subsequent table rows if so configured
  127. //
  128. echo preg_replace('|(.*)<table (.*?<input name="attachfile" size="48" type="file".*?)</td>\s*</tr>|s',
  129. '$1' . $script . '<table id="attachment_table" $2' . $dynamic_link . "</td>\n</tr>" . $attachment_input,
  130. $output);
  131. }
  132. /**
  133. * Add multiple attachment inputs to output for SquirrelMail versions 1.5.x
  134. *
  135. */
  136. function ma_add_attachment_inputs_1_5()
  137. {
  138. global $data_dir, $username, $number_of_attachment_inputs,
  139. $allow_dynamic_input_addition, $javascript_on,
  140. $number_of_attachment_inputs_allow_override;
  141. multiple_attachments_init();
  142. if ($number_of_attachment_inputs_allow_override)
  143. $number_of_attachment_inputs = getPref($data_dir, $username, 'number_of_attachment_inputs', $number_of_attachment_inputs);
  144. if (!(bool)ini_get('file_uploads')
  145. || ($number_of_attachment_inputs < 2
  146. && (!$javascript_on || !$allow_dynamic_input_addition)))
  147. return;
  148. $attachment_input = $dynamic_link = $script = '';
  149. // add dynamic link
  150. //
  151. if ($javascript_on && $allow_dynamic_input_addition)
  152. {
  153. // "more" is actually in the SquirrelMail domain, but
  154. // due to its context (for viewing more message recipients),
  155. // its translation in some languages doesn't work here
  156. //
  157. sq_change_text_domain('multiple_attachments');
  158. $more = _("more");
  159. sq_change_text_domain('squirrelmail');
  160. $dynamic_link = '&nbsp; <small><a href="javascript:void(0)" onclick="var row = document.getElementById(\'attachment_table\').insertRow(1); row.className = \'header\'; var cell = row.insertCell(0); cell.className = \'fieldName\'; cell.width=\'1%\'; cell.style.whiteSpace=\'nowrap\'; cell.innerHTML = \'' . _("New attachment") . ':\'; cell = row.insertCell(1); cell.className = \'fieldValue\'; cell.innerHTML = get_new_attachment_input();">' . $more . "</a></small>\n";
  161. // small global JavaScript to initialize counter variable
  162. // and provide easy function for getting new attachment input tags
  163. //
  164. $script = "\n<script type=\"text/javascript\" language=\"JavaScript\">\n<!--\n"
  165. . "var attachment_counter = " . ($number_of_attachment_inputs - 1) . ";\n"
  166. . "function get_new_attachment_input()\n"
  167. . "{\n"
  168. . ' return \'<input name="attachfile_\' + (++attachment_counter) + \'" size="48" type="file" />\';'
  169. . "\n}"
  170. . "\n// -->\n</script>\n";
  171. }
  172. // add default inputs
  173. //
  174. for ($i = 0; $i < $number_of_attachment_inputs - 1; $i++)
  175. // note that we are intentionally in SquirrelMail text domain
  176. $attachment_input .= '<tr class="header">'
  177. . '<td class="fieldName" style="width: 1%; white-space: nowrap;">'
  178. . _("New attachment")
  179. . ':</td><td class="fieldValue">'
  180. . '<input type="file" name="attachfile_' . ($i + 1) . '" size="48" />'
  181. . '</td></tr>';
  182. return array('add_attachment_notes' => $script . $dynamic_link,
  183. 'attachment_inputs' => $attachment_input);
  184. }
  185. /**
  186. * Make sure multiple attachments aren't skipped if first upload input is blank
  187. *
  188. */
  189. function ma_multiple_uploads_fix()
  190. {
  191. // only need to do this one time (1.4.x loading_constants
  192. // hook is only executed once, but for 1.5.x, we use
  193. // prefs_backend, which is run a number of times)
  194. //
  195. static $execute_once = FALSE;
  196. if ($execute_once) return;
  197. $execute_once = TRUE;
  198. // iterate through all the uploaded file inputs
  199. // looking for compose attachment file uploads
  200. // and remove any that don't have an associated
  201. // upload temporary filename
  202. //
  203. global $_FILES;
  204. $new_upload_file_info_array = array();
  205. $i = 0;
  206. foreach ($_FILES as $key => $upload_file_info)
  207. {
  208. // for non-compose attachment uploads, just preserve them
  209. //
  210. if (strpos($key, 'attachfile') !== 0)
  211. {
  212. $new_upload_file_info_array[$key] = $upload_file_info;
  213. continue;
  214. }
  215. // now, handle compose attachment uploads
  216. //
  217. if (!empty($upload_file_info['tmp_name']))
  218. {
  219. if ($i === 0)
  220. $new_upload_file_info_array['attachfile'] = $upload_file_info;
  221. else
  222. $new_upload_file_info_array['attachfile_' . $i] = $upload_file_info;
  223. $i++;
  224. }
  225. }
  226. $_FILES = $new_upload_file_info_array;
  227. }
  228. /**
  229. * Handle multiple attachment file uploads
  230. *
  231. * @return boolean TRUE only if an error occurred trying
  232. * to process an attachment file upload;
  233. * FALSE under normal operation
  234. *
  235. */
  236. function ma_handle_multiple_uploads($session)
  237. {
  238. global $_FILES, $attachment_dir, $username, $composeMessage;
  239. $i = 1;
  240. while (isset($_FILES['attachfile_' . $i])
  241. && $_FILES['attachfile_' . $i]['tmp_name']
  242. && $_FILES['attachfile_' . $i]['tmp_name'] != 'none')
  243. {
  244. // this is just a duplication of the saveAttachedFiles()
  245. // function from src/compose.php, copied and slightly
  246. // modified from version 1.4.23 SVN on 2012-03-03
  247. /* get out of here if no file was attached at all */
  248. if (! is_uploaded_file($_FILES['attachfile_' . $i]['tmp_name']) ) {
  249. return true;
  250. }
  251. $hashed_attachment_dir = getHashedDir($username, $attachment_dir);
  252. $localfilename = GenerateRandomString(32, '', 7);
  253. $full_localfilename = "$hashed_attachment_dir/$localfilename";
  254. while (file_exists($full_localfilename)) {
  255. $localfilename = GenerateRandomString(32, '', 7);
  256. $full_localfilename = "$hashed_attachment_dir/$localfilename";
  257. }
  258. // FIXME: we SHOULD prefer move_uploaded_file over rename because
  259. // m_u_f works better with restricted PHP installs (safe_mode, open_basedir)
  260. if (!@rename($_FILES['attachfile_' . $i]['tmp_name'], $full_localfilename)) {
  261. if (!@move_uploaded_file($_FILES['attachfile_' . $i]['tmp_name'],$full_localfilename)) {
  262. return true;
  263. }
  264. }
  265. $type = strtolower($_FILES['attachfile_' . $i]['type']);
  266. $name = $_FILES['attachfile_' . $i]['name'];
  267. $composeMessage->initAttachment($type, $name, $localfilename);
  268. $i++;
  269. }
  270. return FALSE;
  271. }
  272. /**
  273. * Integrate options into SM options page
  274. *
  275. */
  276. function ma_show_options($args)
  277. {
  278. global $data_dir, $username, $number_of_attachment_inputs,
  279. $number_of_attachment_inputs_allow_override, $optpage_data;
  280. multiple_attachments_init();
  281. // get_current_hook_name() means we require the
  282. // Compatibility plugin, version 2.0.5+
  283. //
  284. $hook_name = get_current_hook_name($args);
  285. // 1.4.x - 1.5.0: options go on display options page
  286. // 1.5.1 and up: options go on compose options page
  287. //
  288. if (check_sm_version(1, 5, 1) && $hook_name != 'optpage_loadhook_compose')
  289. return;
  290. if (!check_sm_version(1, 5, 1) && $hook_name != 'optpage_loadhook_display')
  291. return;
  292. // placement in option groups differs per SM version
  293. //
  294. if ($hook_name == 'optpage_loadhook_display')
  295. $option_index = 2;
  296. else
  297. $option_index = 0;
  298. sq_change_text_domain('multiple_attachments');
  299. if ($number_of_attachment_inputs_allow_override)
  300. {
  301. $number_of_attachment_inputs = getPref($data_dir, $username, 'number_of_attachment_inputs', $number_of_attachment_inputs);
  302. $optpage_data['vals'][$option_index][] = array(
  303. 'name' => 'number_of_attachment_inputs',
  304. 'caption' => _("Number Of Attachment Upload Inputs"),
  305. 'type' => SMOPT_TYPE_STRLIST,
  306. 'initial_value' => $number_of_attachment_inputs,
  307. 'refresh' => SMOPT_REFRESH_NONE,
  308. 'posvals' => array(1 => 1,
  309. 2 => 2,
  310. 3 => 3,
  311. 4 => 4,
  312. 5 => 5,
  313. 6 => 6,
  314. 7 => 7,
  315. 8 => 8,
  316. 9 => 9,
  317. 10 => 10),
  318. );
  319. }
  320. sq_change_text_domain('squirrelmail');
  321. }