Code Coverage |
||||||||||
Lines |
Functions and Methods |
Classes and Traits |
||||||||
| Total | |
100.00% |
30 / 30 |
|
100.00% |
6 / 6 |
CRAP | |
100.00% |
1 / 1 |
| File | |
100.00% |
30 / 30 |
|
100.00% |
6 / 6 |
16 | |
100.00% |
1 / 1 |
| mustExist | |
100.00% |
3 / 3 |
|
100.00% |
1 / 1 |
2 | |||
| mustBeReadable | |
100.00% |
5 / 5 |
|
100.00% |
1 / 1 |
3 | |||
| openReadOnly | |
100.00% |
2 / 2 |
|
100.00% |
1 / 1 |
1 | |||
| open | |
100.00% |
8 / 8 |
|
100.00% |
1 / 1 |
4 | |||
| close | |
100.00% |
5 / 5 |
|
100.00% |
1 / 1 |
3 | |||
| getContents | |
100.00% |
7 / 7 |
|
100.00% |
1 / 1 |
3 | |||
| 1 | <?php |
| 2 | |
| 3 | declare(strict_types=1); |
| 4 | |
| 5 | namespace pvc\storage\filesys; |
| 6 | |
| 7 | use pvc\storage\filesys\err\FileDoesNotExistException; |
| 8 | use pvc\storage\filesys\err\FileGetContentsException; |
| 9 | use pvc\storage\filesys\err\FileNotReadableException; |
| 10 | use pvc\storage\filesys\err\FileOpenException; |
| 11 | use pvc\storage\filesys\err\InvalidFileHandleException; |
| 12 | use pvc\storage\filesys\err\InvalidFileModeException; |
| 13 | use pvc\storage\resource\err\InvalidResourceException; |
| 14 | use Throwable; |
| 15 | |
| 16 | class File |
| 17 | { |
| 18 | /** |
| 19 | * @param string $localFileName |
| 20 | * @return true |
| 21 | * @throws FileDoesNotExistException |
| 22 | */ |
| 23 | public static function mustExist(string $localFileName): true |
| 24 | { |
| 25 | /** |
| 26 | * type checker is not aware that file |
| 27 | */ |
| 28 | if (!file_exists($localFileName)) { |
| 29 | throw new FileDoesNotExistException($localFileName); |
| 30 | } |
| 31 | return true; |
| 32 | } |
| 33 | |
| 34 | /** |
| 35 | * @param string $filePath |
| 36 | * @return true |
| 37 | * @throws FileNotReadableException |
| 38 | * @throws FileDoesNotExistException |
| 39 | */ |
| 40 | public static function mustBeReadable(string $filePath): true |
| 41 | { |
| 42 | if (!file_exists($filePath)) { |
| 43 | throw new FileDoesNotExistException($filePath); |
| 44 | } |
| 45 | if (!is_readable($filePath)) { |
| 46 | throw new FileNotReadableException($filePath); |
| 47 | } |
| 48 | return true; |
| 49 | } |
| 50 | |
| 51 | |
| 52 | /** |
| 53 | * @param string $filePath |
| 54 | * @return resource |
| 55 | * adds a specific test to ensure the file is readable |
| 56 | */ |
| 57 | public static function openReadOnly(string $filePath) |
| 58 | { |
| 59 | self::mustBeReadable($filePath); |
| 60 | return self::open($filePath, FileMode::READ); |
| 61 | } |
| 62 | |
| 63 | /** |
| 64 | * @param string $filePath |
| 65 | * @param string $mode |
| 66 | * @return resource |
| 67 | */ |
| 68 | public static function open(string $filePath, string $mode = 'r') |
| 69 | { |
| 70 | if (!FileMode::isDefined($mode)) { |
| 71 | throw new InvalidFileModeException($mode); |
| 72 | } |
| 73 | |
| 74 | /** |
| 75 | * this may seem a bit laborious, but the VfsStream wrapper will throw its own error or exception |
| 76 | * if it fails because of permissions so we need to catch it. |
| 77 | */ |
| 78 | try { |
| 79 | $handle = fopen($filePath, $mode); |
| 80 | } catch (Throwable $e) { |
| 81 | throw new FileOpenException($filePath, $mode, $e); |
| 82 | } |
| 83 | |
| 84 | if ($handle === false) { |
| 85 | throw new FileOpenException($filePath, $mode); |
| 86 | } |
| 87 | |
| 88 | return $handle; |
| 89 | } |
| 90 | |
| 91 | /** |
| 92 | * @param resource $handle |
| 93 | * @return void |
| 94 | * @throws InvalidFileHandleException |
| 95 | * @throws InvalidResourceException |
| 96 | */ |
| 97 | public static function close($handle): void |
| 98 | { |
| 99 | if (!is_resource($handle)) { |
| 100 | throw new InvalidResourceException(); |
| 101 | } |
| 102 | if (get_resource_type($handle) !== 'stream') { |
| 103 | throw new InvalidFileHandleException(); |
| 104 | } |
| 105 | fclose($handle); |
| 106 | } |
| 107 | |
| 108 | /** |
| 109 | * @param string $filePath |
| 110 | * @return string |
| 111 | * @throws FileGetContentsException |
| 112 | * @throws FileNotReadableException |
| 113 | */ |
| 114 | public static function getContents(string $filePath): string |
| 115 | { |
| 116 | self::mustBeReadable($filePath); |
| 117 | try { |
| 118 | $contents = file_get_contents($filePath); |
| 119 | } catch (Throwable $e) { |
| 120 | throw new FileGetContentsException($filePath, $e); |
| 121 | } |
| 122 | if ($contents === false) { |
| 123 | throw new FileGetContentsException($filePath); |
| 124 | } |
| 125 | return $contents; |
| 126 | } |
| 127 | } |