1: <?php
2:
3: namespace ngatngay;
4:
5: use Exception;
6: use FilesystemIterator;
7: use RecursiveCallbackFilterIterator;
8: use RecursiveDirectoryIterator;
9: use RecursiveIteratorIterator;
10: use SplFileInfo;
11:
12: // file system
13: class fs
14: {
15: /*
16: * file, file1, file2...
17: */
18: /**
19: * @param string $file_name_body
20: * @param string $file_ext
21: * @return string
22: */
23: public function name_increment($file_name_body, $file_ext)
24: {
25: $i = 1;
26: $file_exists = true;
27:
28: do {
29: $file_save = $file_name_body . $i . '.' . $file_ext;
30:
31: if (!file_exists($file_save)) {
32: $file_exists = false;
33: }
34:
35: $i++;
36: } while ($file_exists);
37:
38: return $file_save;
39: }
40:
41: /**
42: * @param string $name
43: * @return string
44: */
45: public static function get_extension($name)
46: {
47: return (new SplFileInfo($name))->getExtension();
48: }
49:
50: /**
51: * @param string $path
52: * @return int
53: */
54: public static function size($path)
55: {
56: if (!is_dir($path)) {
57: return filesize($path);
58: }
59:
60: $size = 0;
61:
62: $iterator = new RecursiveIteratorIterator(
63: new RecursiveDirectoryIterator($path, FilesystemIterator::SKIP_DOTS | FilesystemIterator::FOLLOW_SYMLINKS),
64: RecursiveIteratorIterator::LEAVES_ONLY
65: );
66:
67: foreach ($iterator as $file) {
68: if ($file->isFile()) {
69: $size += $file->getSize();
70: }
71: }
72:
73: return $size;
74: }
75:
76: /**
77: * @param int $fileSize
78: * @return string
79: */
80: public static function readable_size($fileSize)
81: {
82: $size = floatval($fileSize);
83:
84: if ($size < 1024) {
85: $s = $size . ' B';
86: } elseif ($size < 1048576) {
87: $s = round($size / 1024, 2) . ' KB';
88: } elseif ($size < 1073741824) {
89: $s = round($size / 1048576, 2) . ' MB';
90: } elseif ($size < 1099511627776) {
91: $s = round($size / 1073741824, 2) . ' GB';
92: } elseif ($size < 1125899906842624) {
93: $s = round($size / 1099511627776, 2) . ' TB';
94: } elseif ($size < 1152921504606846976) {
95: $s = round($size / 1125899906842624, 2) . ' PB';
96: } elseif ($size < 1.1805916207174E+21) {
97: $s = round($size / 1152921504606846976, 2) . ' EB';
98: } elseif ($size < 1.2089258196146E+24) {
99: $s = round($size / 1.1805916207174E+21, 2) . ' ZB';
100: } else {
101: $s = round($size / 1.2089258196146E+24, 2) . ' YB';
102: }
103:
104: return $s;
105: }
106:
107: /**
108: * @param string $path
109: * @return bool
110: */
111: public static function remove($path)
112: {
113: if (is_link($path)) {
114: return unlink($path);
115: }
116:
117: if (is_file($path)) {
118: return unlink($path);
119: }
120:
121: if (is_dir($path)) {
122: $files = array_diff(scandir($path), ['.', '..']);
123: foreach ($files as $file) {
124: $filePath = $path . DIRECTORY_SEPARATOR . $file;
125: if (!self::remove($filePath)) {
126: return false;
127: }
128: }
129: return rmdir($path);
130: }
131:
132: if (!file_exists($path)) {
133: return true;
134: }
135:
136: throw new Exception('remove error, not match file type');
137: }
138:
139: /**
140: * @param string $path
141: * @param array $excludes
142: * @return RecursiveIteratorIterator
143: */
144: public static function read_full_dir($path, $excludes = [])
145: {
146: $directory = new RecursiveDirectoryIterator(
147: $path,
148: FilesystemIterator::UNIX_PATHS
149: | FilesystemIterator::SKIP_DOTS
150: );
151:
152: $filter = new RecursiveCallbackFilterIterator($directory, function ($current, $key, $iterator) use ($path, $excludes) {
153: $relativePath = str::replace_first($path, '', $current->getPathname());
154:
155: foreach ($excludes as $exclude) {
156: if (empty($exclude)) {
157: continue;
158: }
159: //var_dump($relativePath);
160: //var_dump($exclude);
161:
162: $exclude = trim($exclude);
163: $exclude = trim($exclude, '/');
164: $relativePath = trim($relativePath, '/');
165:
166: if (str_ends_with($relativePath, $exclude)) {
167: return false;
168: }
169: }
170:
171: return true;
172: });
173:
174: return new RecursiveIteratorIterator(
175: $filter,
176: RecursiveIteratorIterator::SELF_FIRST
177: );
178: }
179:
180: /**
181: * @param string ...$paths
182: * @return string
183: */
184: public static function join_path(...$paths)
185: {
186: return preg_replace('#/+#', '/', implode('/', $paths));
187: }
188:
189: /**
190: * Lấy tên chủ sở hữu file theo tên file
191: * @param string $filename
192: * @return string
193: */
194: public static function get_owner_name($filename)
195: {
196: $owner_id = @fileowner($filename);
197: if ($owner_id === false) {
198: return '';
199: }
200: return self::get_owner_name_by_id($owner_id);
201: }
202:
203: /**
204: * Lấy tên chủ sở hữu theo user ID
205: * @param int $id
206: * @return string
207: */
208: public static function get_owner_name_by_id($id)
209: {
210: $info = @posix_getpwuid($id);
211: return $info['name'] ?? '';
212: }
213: }
214: