/wp-content/plugins/download-monitor/src/FileManager.php

https://github.com/livinglab/openlab · PHP · 242 lines · 124 code · 37 blank · 81 comment · 25 complexity · f4c9d974129706e290fde5fc1ff17c39 MD5 · raw file

  1. <?php
  2. if ( ! defined( 'ABSPATH' ) ) {
  3. exit;
  4. } // Exit if accessed directly
  5. class DLM_File_Manager {
  6. /**
  7. * Returns a listing of all files in the specified folder and all subdirectories up to 100 levels deep.
  8. * The depth of the recursiveness can be controlled by the $levels param.
  9. *
  10. * @access public
  11. *
  12. * @param string $folder (default: '')
  13. *
  14. * @return array|bool
  15. */
  16. public function list_files( $folder = '' ) {
  17. if ( empty( $folder ) ) {
  18. return false;
  19. }
  20. // A listing of all files and dirs in $folder, excepting . and ..
  21. // By default, the sorted order is alphabetical in ascending order
  22. $files = array_diff( scandir( $folder ), array( '..', '.' ) );
  23. $dlm_files = array();
  24. foreach ( $files as $file ) {
  25. $dlm_files[] = array(
  26. 'type' => ( is_dir( $folder . '/' . $file ) ? 'folder' : 'file' ),
  27. 'path' => $folder . '/' . $file
  28. );
  29. }
  30. return $dlm_files;
  31. }
  32. /**
  33. * Parse a file path and return the new path and whether or not it's remote
  34. *
  35. * @param string $file_path
  36. *
  37. * @return array
  38. */
  39. public function parse_file_path( $file_path ) {
  40. $remote_file = true;
  41. $parsed_file_path = parse_url( $file_path );
  42. $wp_uploads = wp_upload_dir();
  43. $wp_uploads_dir = $wp_uploads['basedir'];
  44. $wp_uploads_url = $wp_uploads['baseurl'];
  45. // Fix for plugins that modify the uploads dir
  46. // add filter in order to return files
  47. if ( apply_filters( 'dlm_check_file_paths', false, $file_path, $remote_file ) ) {
  48. return array( $file_path, $remote_file );
  49. }
  50. if ( ( ! isset( $parsed_file_path['scheme'] ) || ! in_array( $parsed_file_path['scheme'], array(
  51. 'http',
  52. 'https',
  53. 'ftp'
  54. ) ) ) && isset( $parsed_file_path['path'] ) && file_exists( $parsed_file_path['path'] )
  55. ) {
  56. /** This is an absolute path */
  57. $remote_file = false;
  58. } elseif ( strpos( $file_path, $wp_uploads_url ) !== false ) {
  59. /** This is a local file given by URL so we need to figure out the path */
  60. $remote_file = false;
  61. $file_path = trim( str_replace( $wp_uploads_url, $wp_uploads_dir, $file_path ) );
  62. $file_path = realpath( $file_path );
  63. } elseif ( is_multisite() && ( ( strpos( $file_path, network_site_url( '/', 'http' ) ) !== false ) || ( strpos( $file_path, network_site_url( '/', 'https' ) ) !== false ) ) ) {
  64. /** This is a local file outside of wp-content so figure out the path */
  65. $remote_file = false;
  66. // Try to replace network url
  67. $file_path = str_replace( network_site_url( '/', 'https' ), ABSPATH, $file_path );
  68. $file_path = str_replace( network_site_url( '/', 'http' ), ABSPATH, $file_path );
  69. // Try to replace upload URL
  70. $file_path = str_replace( $wp_uploads_url, $wp_uploads_dir, $file_path );
  71. $file_path = realpath( $file_path );
  72. } elseif ( strpos( $file_path, site_url( '/', 'http' ) ) !== false || strpos( $file_path, site_url( '/', 'https' ) ) !== false ) {
  73. /** This is a local file outside of wp-content so figure out the path */
  74. $remote_file = false;
  75. $file_path = str_replace( site_url( '/', 'https' ), ABSPATH, $file_path );
  76. $file_path = str_replace( site_url( '/', 'http' ), ABSPATH, $file_path );
  77. $file_path = realpath( $file_path );
  78. } elseif ( file_exists( ABSPATH . $file_path ) ) {
  79. /** Path needs an abspath to work */
  80. $remote_file = false;
  81. $file_path = ABSPATH . $file_path;
  82. $file_path = realpath( $file_path );
  83. }
  84. return array( $file_path, $remote_file );
  85. }
  86. /**
  87. * Gets the filesize of a path or URL.
  88. *
  89. * @access public
  90. *
  91. * @param string $file_path
  92. *
  93. * @return string size on success, -1 on failure
  94. */
  95. public function get_file_size( $file_path ) {
  96. if ( $file_path ) {
  97. list( $file_path, $remote_file ) = $this->parse_file_path( $file_path );
  98. if ( ! empty( $file_path ) ) {
  99. if ( $remote_file ) {
  100. $file = wp_remote_head( $file_path );
  101. if ( ! is_wp_error( $file ) && ! empty( $file['headers']['content-length'] ) ) {
  102. return $file['headers']['content-length'];
  103. }
  104. } else {
  105. if ( file_exists( $file_path ) && ( $filesize = filesize( $file_path ) ) ) {
  106. return $filesize;
  107. }
  108. }
  109. }
  110. }
  111. return - 1;
  112. }
  113. /**
  114. * Encode files for storage
  115. *
  116. * @param array $files
  117. *
  118. * @return string
  119. */
  120. public function json_encode_files( $files ) {
  121. if ( version_compare( phpversion(), "5.4.0", ">=" ) ) {
  122. $files = json_encode( $files, JSON_UNESCAPED_UNICODE );
  123. } else {
  124. $files = json_encode( $files );
  125. if ( function_exists( 'mb_convert_encoding' ) ) {
  126. $files = preg_replace_callback( '/\\\\u([0-9a-f]{4})/i', array(
  127. $this,
  128. 'json_unscaped_unicode_fallback'
  129. ), $files );
  130. }
  131. }
  132. return $files;
  133. }
  134. /**
  135. * Fallback for PHP < 5.4 where JSON_UNESCAPED_UNICODE does not exist.
  136. *
  137. * @param array $matches
  138. *
  139. * @return string
  140. */
  141. public function json_unscaped_unicode_fallback( $matches ) {
  142. $sym = mb_convert_encoding(
  143. pack( 'H*', $matches[1] ),
  144. 'UTF-8',
  145. 'UTF-16'
  146. );
  147. return $sym;
  148. }
  149. /**
  150. * Multi-byte-safe pathinfo replacement.
  151. *
  152. * @param $filepath
  153. *
  154. * @return mixed
  155. */
  156. public function mb_pathinfo( $filepath ) {
  157. $ret = array();
  158. preg_match( '%^(.*?)[\\\\/]*(([^/\\\\]*?)(\.([^\.\\\\/]+?)|))[\\\\/\.]*$%im', $filepath, $m );
  159. if ( isset( $m[1] ) ) {
  160. $ret['dirname'] = $m[1];
  161. }
  162. if ( isset( $m[2] ) ) {
  163. $ret['basename'] = $m[2];
  164. }
  165. if ( isset( $m[5] ) ) {
  166. $ret['extension'] = $m[5];
  167. }
  168. if ( isset( $m[3] ) ) {
  169. $ret['filename'] = $m[3];
  170. }
  171. return $ret;
  172. }
  173. /**
  174. * Get file name for given path
  175. *
  176. * @param string $file_path
  177. *
  178. * @return string
  179. */
  180. public function get_file_name( $file_path ) {
  181. return current( explode( '?', DLM_Utils::basename( $file_path ) ) );
  182. }
  183. /**
  184. * Get file type of give file name
  185. *
  186. * @param string $file_name
  187. *
  188. * @return string
  189. */
  190. public function get_file_type( $file_name ) {
  191. return strtolower( substr( strrchr( $file_name, "." ), 1 ) );
  192. }
  193. /**
  194. * Gets md5, sha1 and crc32 hashes for a file and store it.
  195. *
  196. * @deprecated use hasher service get_file_hashes() instead
  197. *
  198. * @param string $file_path
  199. *
  200. * @return array of sizes
  201. */
  202. public function get_file_hashes( $file_path ) {
  203. return download_monitor()->service( 'hasher' )->get_file_hashes( $file_path );
  204. }
  205. }