/wp-content/plugins/wp-ajax-edit-comments/lib/class.file.php

https://github.com/livinglab/openlab · PHP · 582 lines · 376 code · 127 blank · 79 comment · 119 complexity · 97d1e268f617ab6c45d72e90df27c42a MD5 · raw file

  1. <?php
  2. //Code from iThemes Builder
  3. class AECFile {
  4. public static function get_writable_directory( $args ) {
  5. if ( is_string( $args ) )
  6. $args = array( 'name' => $args );
  7. else if ( ! is_array( $args ) )
  8. $args = array();
  9. $default_args = array(
  10. 'name' => '',
  11. 'create_new' => false,
  12. 'rename' => false,
  13. 'random' => false,
  14. 'permissions' => 0755,
  15. 'default_search_paths' => array( 'uploads_basedir', 'uploads_path', 'wp-content', 'abspath' ),
  16. 'custom_search_paths' => array(),
  17. );
  18. $args = array_merge( $default_args, $args );
  19. if ( empty( $args['name'] ) && ( true === $args['create_new'] ) && ( false === $args['random'] ) )
  20. return new WP_Error( 'get_writable_directory_no_name', 'The call to AECFile::get_writable_directory is missing the name attribute' );
  21. $uploads = wp_upload_dir();
  22. if ( ! is_array( $uploads ) || ( false !== $uploads['error'] ) )
  23. $uploads = array( 'basedir' => false, 'path' => false );
  24. $default_search_paths = array(
  25. 'uploads_basedir' => $uploads['basedir'],
  26. 'uploads_path' => $uploads['path'],
  27. 'wp-content' => WP_CONTENT_DIR,
  28. 'abspath' => ABSPATH,
  29. );
  30. $search_paths = array_merge( (array) $args['custom_search_paths'], (array) $args['default_search_paths'] );
  31. $path = false;
  32. foreach ( (array) $search_paths as $search_path ) {
  33. if ( isset( $default_search_paths[$search_path] ) ) {
  34. if ( false === $default_search_paths[$search_path] )
  35. continue;
  36. $search_path = $default_search_paths[$search_path];
  37. }
  38. if ( is_dir( $search_path ) && is_writable( $search_path ) ) {
  39. $path = $search_path;
  40. break;
  41. }
  42. }
  43. if ( false === $path )
  44. return new WP_Error( 'get_writable_base_directory_failed', 'Unable to find a writable base directory' );
  45. if ( empty( $args['name'] ) && ( false === $args['random'] ) )
  46. return $path;
  47. if ( true === $args['random'] ) {
  48. $name = ( isset( $args['name'] ) ) ? $args['name'] : '';
  49. $uid = uniqid( "$name-", true );
  50. while ( is_dir( "$path/$uid" ) )
  51. $uid = uniqid( "$name-", true );
  52. $name = $uid;
  53. }
  54. else
  55. $name = $args['name'];
  56. if ( is_dir( "$path/$name" ) ) {
  57. if ( true === $args['create_new'] ) {
  58. if ( false === $args['rename'] )
  59. return new WP_Error( 'get_writable_directory_no_rename', 'Unable to create the named writable directory' );
  60. $name = AECFile::get_unique_name( $path, $name );
  61. }
  62. else {
  63. if ( is_writable( "$path/$name" ) )
  64. return "$path/$name";
  65. return new WP_Error( 'get_writable_directory_cannot_write', 'Required directory exists but is not writable' );
  66. }
  67. }
  68. else if ( false === $args['create_new'] )
  69. return new WP_Error( 'get_writable_directory_does_not_exist', 'Required writable directory does not exist' );
  70. if ( true === AECFile::mkdir( "$path/$name", $args['permissions'] ) )
  71. return "$path/$name";
  72. return new WP_Error( 'get_writable_directory_failed', 'Unable to create a writable directory' );
  73. } //end get_writable_directory
  74. public static function create_writable_directory( $args ) {
  75. if ( is_string( $args ) )
  76. $args = array( 'name' => $args );
  77. else if ( ! is_array( $args ) )
  78. $args = array();
  79. $default_args = array(
  80. 'create_new' => true,
  81. 'rename' => true,
  82. 'random' => false,
  83. );
  84. $args = array_merge( $default_args, $args );
  85. return AECFile::get_writable_directory( $args );
  86. } //end create_writable_directory
  87. public static function get_writable_file( $args, $extension = null ) {
  88. if ( is_string( $args ) )
  89. $args = array( 'name' => $args );
  90. else if ( ! is_array( $args ) )
  91. $args = array();
  92. $default_args = array(
  93. 'name' => '',
  94. 'extension' => '',
  95. 'create_new' => false,
  96. 'rename' => false,
  97. 'permissions' => 0644,
  98. 'path_permissions' => 0755,
  99. 'default_search_paths' => array( 'uploads_basedir', 'uploads_path', 'wp-content', 'abspath' ),
  100. 'custom_search_paths' => array(),
  101. );
  102. $args = array_merge( $default_args, $args );
  103. if ( empty( $args['name'] ) )
  104. return new WP_Error( 'get_writable_file_no_name', 'The call to AECFile::get_writable_file is missing the name attribute' );
  105. if ( is_null( $extension ) )
  106. $extension = $args['extension'];
  107. if ( ! empty( $extension ) && ! preg_match( '/^\./', $extension ) )
  108. $extension = ".$extension";
  109. $base_path = AECFile::get_writable_directory( array( 'permissions' => $args['path_permissions'], 'default_search_paths' => $args['default_search_paths'], 'custom_search_paths' => $args['custom_search_paths'] ) );
  110. if ( is_wp_error( $base_path ) )
  111. return $base_path;
  112. $name = $args['name'];
  113. if ( preg_match( '|/|', $name ) ) {
  114. $base_path .= '/' . dirname( $name );
  115. $name = basename( $name );
  116. }
  117. $file = "$base_path/$name$extension";
  118. if ( is_file( $file ) ) {
  119. if ( true === $args['create_new'] ) {
  120. if ( false === $args['rename'] )
  121. return new WP_Error( 'get_writable_file_no_rename', 'Unable to create the named writable file' );
  122. $name = AECFile::get_unique_name( $base_path, $name, $extension );
  123. $file = "$base_path/$name";
  124. }
  125. else {
  126. if ( is_writable( $file ) )
  127. return $file;
  128. return new WP_Error( 'get_writable_file_cannot_write', 'Required file exists but is not writable' );
  129. }
  130. }
  131. else if ( false === $args['create_new'] )
  132. return new WP_Error( 'get_writable_file_does_not_exist', 'Required writable file does not exist' );
  133. if ( true === AECFile::is_file_writable( $file ) ) {
  134. @chmod( $file, $args['permissions'] );
  135. return $file;
  136. }
  137. return new WP_Error( 'get_writable_file_failed', 'Unable to create a writable file' );
  138. } //end create_writable_directory
  139. public static function create_writable_file( $args, $extension = null ) {
  140. if ( is_string( $args ) )
  141. $args = array( 'name' => $args );
  142. else if ( ! is_array( $args ) )
  143. $args = array();
  144. $default_args = array(
  145. 'create_new' => true,
  146. 'rename' => true,
  147. );
  148. $args = array_merge( $default_args, $args );
  149. return AECFile::get_writable_file( $args, $extension );
  150. } //end create_writable_file
  151. public static function get_url_from_file( $file ) {
  152. $url = '';
  153. if ( ( $uploads = wp_upload_dir() ) && ( false === $uploads['error'] ) ) {
  154. if ( 0 === strpos( $file, $uploads['basedir'] ) )
  155. $url = str_replace( $uploads['basedir'], $uploads['baseurl'], $file );
  156. else if ( false !== strpos( $file, 'wp-content/uploads' ) )
  157. $url = $uploads['baseurl'] . substr( $file, strpos( $file, 'wp-content/uploads' ) + 18 );
  158. }
  159. //Store an AEC site option of the basename of the file directory
  160. if ( empty( $url ) )
  161. $url = get_option( 'siteurl' ) . str_replace( '\\', '/', str_replace( rtrim( ABSPATH, '\\\/' ), '', $file ) );
  162. if ( is_network_admin() ) {
  163. $dependency_upload_dir = str_replace( basename( $url ), '', $url );
  164. update_site_option( 'aec_dependency_upload_dir', $dependency_upload_dir );
  165. }
  166. //Try to get the site option
  167. $dependency_url = get_site_option( 'aec_dependency_upload_dir' );
  168. if ( $dependency_url ) {
  169. $url = $dependency_url . basename( $url );
  170. }
  171. return $url;
  172. } //end get_url_from_file
  173. public static function get_writable_uploads_directory( $directory ) {
  174. $uploads = wp_upload_dir();
  175. if ( ! is_array( $uploads ) || ( false !== $uploads['error'] ) )
  176. return false;
  177. $path = "{$uploads['basedir']}/$directory";
  178. if ( ! is_dir( $path ) ) {
  179. AECFile::mkdir( $path );
  180. if ( ! is_dir( $path ) )
  181. return false;
  182. }
  183. if ( ! is_writable( $path ) )
  184. return false;
  185. $directory_info = array(
  186. 'path' => $path,
  187. 'url' => "{$uploads['baseurl']}/$directory",
  188. );
  189. return $directory_info;
  190. } //end get_writable_uploads_directory
  191. public static function find_writable_path( $args = array(), $vars = array() ) {
  192. $default_args = array(
  193. 'private' => true,
  194. 'possible_paths' => array(),
  195. 'permissions' => 0755,
  196. );
  197. $args = array_merge( $default_args, $args );
  198. $uploads_dir_data = wp_upload_dir();
  199. $default_vars = array(
  200. 'uploads_basedir' => $uploads_dir_data['basedir'],
  201. 'uploads_path' => $uploads_dir_data['path'],
  202. );
  203. $vars = array_merge( $default_vars, $vars );
  204. foreach ( (array) $args['possible_paths'] as $path ) {
  205. foreach ( (array) $vars as $var => $val )
  206. $path = preg_replace( '/%' . preg_quote( $var, '/' ) . '%/', $val, $path );
  207. if ( ! is_dir( $path ) )
  208. AECFile::mkdir( $path, $args['permissions'] );
  209. $path = realpath( $path );
  210. if ( ! empty( $path ) && is_writable( $path ) ) {
  211. $writable_dir = $path;
  212. break;
  213. }
  214. }
  215. if ( empty( $writable_dir ) || ! is_writable( $writable_dir ) ) {
  216. if ( is_writable( $uploads_dir_data['basedir'] ) )
  217. $writable_dir = $uploads_dir_data['basedir'];
  218. else if ( is_writable( $uploads_dir_data['path'] ) )
  219. $writable_dir = $uploads_dir_data['path'];
  220. else if ( is_writable( dirname( __FILE__ ) ) )
  221. $writable_dir = dirname( __FILE__ );
  222. else if ( is_writable( ABSPATH ) )
  223. $writable_dir = ABSPATH;
  224. else if ( true === $args['private'] )
  225. return new WP_Error( 'no_private_writable_path', 'Unable to find a writable path within the private space' );
  226. else
  227. $writable_dir = sys_get_temp_dir();
  228. }
  229. if ( empty( $writable_dir ) || ! is_dir( $writable_dir ) || ! is_writable( $writable_dir ) )
  230. return new WP_Error( 'no_writable_path', 'Unable to find a writable path' );
  231. $writable_dir = preg_replace( '|/+$|', '', $writable_dir );
  232. return $writable_dir;
  233. } //end find_writable_path
  234. public static function create_writable_path( $args = array() ) {
  235. if ( is_string( $args ) )
  236. $args = array( 'name' => $args );
  237. else if ( ! is_array( $args ) )
  238. $args = array();
  239. $default_args = array(
  240. 'name' => 'temp-deleteme',
  241. 'private' => true,
  242. 'possible_paths' => array(),
  243. 'permissions' => 0755,
  244. 'rename' => false,
  245. );
  246. $args = array_merge( $default_args, $args );
  247. $writable_dir = AECFile::find_writable_path( array( 'private' => $args['private'], 'possible_paths' => $args['possible_paths'], 'permissions' => $args['permissions'] ) );
  248. if ( is_wp_error( $writable_dir ) )
  249. return $writable_dir;
  250. $test_dir_name = $args['name'];
  251. $path = "$writable_dir/$test_dir_name";
  252. if ( file_exists( $path ) && ( false === $args['rename'] ) ) {
  253. if ( is_writable( $path ) )
  254. return $path;
  255. else
  256. return new WP_Error( 'create_writable_path_failed', 'Requested path exists and cannot be written to' );
  257. }
  258. $count = 0;
  259. while ( is_dir( "$writable_dir/$test_dir_name" ) ) {
  260. $count++;
  261. $test_dir_name = "{$args['name']}-$count";
  262. }
  263. $path = "$writable_dir/$test_dir_name";
  264. if ( false === AECFile::mkdir( $path, $args['permissions'] ) )
  265. return new WP_Error( 'create_path_failed', 'Unable to create a writable path' );
  266. if ( ! is_writable( $path ) )
  267. return new WP_Error( 'create_writable_path_failed', 'Unable to create a writable path' );
  268. return $path;
  269. } //end create_writable_path
  270. public static function create_writable_file_old( $args ) {
  271. $default_args = array(
  272. 'name' => 'deleteme',
  273. 'extension' => '.tmp',
  274. 'path_name' => '',
  275. 'private' => true,
  276. 'possible_paths' => array(),
  277. 'permissions' => 0644,
  278. 'path_permissions' => 0755,
  279. 'overwrite' => false,
  280. 'rename' => true,
  281. );
  282. $args = array_merge( $default_args, $args );
  283. if ( empty( $args['path_name'] ) )
  284. $writable_dir = AECFile::find_writable_path( array( 'private' => $args['private'], 'possible_paths' => $args['possible_paths'], 'permissions' => $args['path_permissions'] ) );
  285. else
  286. $writable_dir = AECFile::create_writable_path( array( 'name' => $args['path_name'], 'private' => $args['private'], 'possible_paths' => $args['possible_paths'], 'permissions' => $args['path_permissions'] ) );
  287. if ( is_wp_error( $writable_dir ) )
  288. return $writable_dir;
  289. $test_file_name = "{$args['name']}{$args['extension']}";
  290. if ( file_exists( "$writable_dir/$test_file_name" ) ) {
  291. if ( false === $args['overwrite'] ) {
  292. if ( false === $args['rename'] )
  293. return new WP_Error( 'requested_file_exists', 'The requested file exists and settings don\'t allow overwriting' );
  294. $count = 0;
  295. while ( is_file( "$writable_dir/$test_file_name" ) ) {
  296. $count++;
  297. $test_file_name = "{$args['name']}-$count{$args['extension']}";
  298. }
  299. }
  300. }
  301. $file = "$writable_dir/$test_file_name";
  302. if ( false === AECFile::is_file_writable( $file ) )
  303. return new WP_Error( 'create_file_failed', 'Unable to create the file' );
  304. @chmod( $file, $args['permissions'] );
  305. if ( ! is_writable( $file ) )
  306. return new WP_Error( 'create_writable_file_failed', 'The file was successfully created but cannot be written to' );
  307. return $file;
  308. } //end create_writable_file_old
  309. public static function mkdir( $directory, $args = array() ) {
  310. if ( is_dir( $directory ) )
  311. return true;
  312. if ( is_file( $directory ) )
  313. return false;
  314. if ( is_int( $args ) )
  315. $args = array( 'permissions' => $args );
  316. if ( is_bool( $args ) )
  317. $args = array( 'create_index' => false );
  318. $default_args = array(
  319. 'permissions' => 0755,
  320. 'create_index' => true,
  321. );
  322. $args = array_merge( $default_args, $args );
  323. if ( ! is_dir( dirname( $directory ) ) ) {
  324. if ( false === AECFile::mkdir( dirname( $directory ), $args ) )
  325. return false;
  326. }
  327. if ( false === @mkdir( $directory, $args['permissions'] ) )
  328. return false;
  329. if ( true === $args['create_index'] )
  330. AECFile::write( "$directory/index.php", '<?php // Silence is golden.' );
  331. return true;
  332. } //end mkdir
  333. public static function copy( $source, $destination, $args = array() ) {
  334. $default_args = array(
  335. 'max_depth' => 100,
  336. 'folder_mode' => 0755,
  337. 'file_mode' => 0744,
  338. 'ignore_files' => array(),
  339. );
  340. $args = array_merge( $default_args, $args );
  341. AECFile::_copy( $source, $destination, $args );
  342. } //end copy
  343. public static function _copy( $source, $destination, $args, $depth = 0 ) {
  344. if ( $depth > $args['max_depth'] )
  345. return true;
  346. if ( is_file( $source ) ) {
  347. if ( is_dir( $destination ) || preg_match( '|/$|', $destination ) ) {
  348. $destination = preg_replace( '|/+$|', '', $destination );
  349. $destination = "$destination/" . basename( $source );
  350. }
  351. if ( false === AECFile::mkdir( dirname( $destination ), $args['folder_mode'] ) )
  352. return false;
  353. if ( false === @copy( $source, $destination ) )
  354. return false;
  355. @chmod( $destination, $args['file_mode'] );
  356. return true;
  357. }
  358. else if ( is_dir( $source ) || preg_match( '|/\*$|', $source ) ) {
  359. if ( preg_match( '|/\*$|', $source ) )
  360. $source = preg_replace( '|/\*$|', '', $source );
  361. else if ( preg_match( '|/$|', $destination ) )
  362. $destination = $destination . basename( $source );
  363. $destination = preg_replace( '|/$|', '', $destination );
  364. $files = array_diff( array_merge( glob( $source . '/.*' ), glob( $source . '/*' ) ), array( $source . '/.', $source . '/..' ) );
  365. if ( false === AECFile::mkdir( $destination, $args['folder_mode'] ) )
  366. return false;
  367. $result = true;
  368. foreach ( (array) $files as $file ) {
  369. if ( false === AECFile::_copy( $file, "$destination/", $args, $depth + 1 ) )
  370. $result = false;
  371. }
  372. return $result;
  373. }
  374. return false;
  375. } //end _copy
  376. public static function delete_directory( $path ) {
  377. if ( ! is_dir( $path ) )
  378. return true;
  379. $files = array_merge( glob( "$path/*" ), glob( "$path/.*" ) );
  380. $contents = array();
  381. foreach ( (array) $files as $file ) {
  382. if ( in_array( basename( $file ), array( '.', '..' ) ) )
  383. continue;
  384. if ( is_dir( $file ) )
  385. AECFile::delete_directory( $file );
  386. else if ( is_file( $file ) )
  387. @unlink( $file );
  388. }
  389. @rmdir( $path );
  390. if ( ! is_dir( $path ) )
  391. return true;
  392. return false;
  393. } //end delete_directory
  394. public static function get_unique_name( $path, $prefix, $postfix = '' ) {
  395. $count = 0;
  396. $test_name = "$prefix$postfix";
  397. while ( file_exists( "$path/$test_name" ) ) {
  398. $count++;
  399. $test_name = "$prefix-$count$postfix";
  400. }
  401. return $test_name;
  402. } //end get_unique_name
  403. public static function is_file_writable( $path ) {
  404. return AECFile::write( $path, '', array( 'append' => true ) );
  405. } //end is_file_writable
  406. public static function write( $path, $content, $args = array() ) {
  407. if ( is_bool( $args ) )
  408. $args = array( 'append' => $args );
  409. else if ( is_int( $args ) )
  410. $args = array( 'permissions' => $args );
  411. else if ( ! is_array( $args ) )
  412. $args = array();
  413. $default_args = array(
  414. 'append' => false,
  415. 'permissions' => 0644,
  416. );
  417. $args = array_merge( $default_args, $args );
  418. $mode = ( false === $args['append'] ) ? 'w' : 'a';
  419. if ( ! is_dir( dirname( $path ) ) ) {
  420. AECFile::mkdir( dirname( $path ) );
  421. if ( ! is_dir( dirname( $path ) ) )
  422. return false;
  423. }
  424. $created = ! is_file( $path );
  425. if ( false === ( $handle = fopen( $path, $mode ) ) )
  426. return false;
  427. $result = fwrite( $handle, $content );
  428. fclose( $handle );
  429. if ( false === $result )
  430. return false;
  431. if ( ( true === $created ) && is_int( $args['append'] ) )
  432. @chmod( $path, $args['append'] );
  433. return true;
  434. } //end write
  435. } //end class
  436. ?>