Page Menu
Home
DevCentral
Search
Configure Global Search
Log In
Files
F53865575
No One
Temporary
Actions
View File
Edit File
Delete File
View Transforms
Subscribe
Mute Notifications
Award Token
Flag For Later
Size
12 KB
Referenced Files
None
Subscribers
None
View Options
diff --git a/omnitools/src/IO/Directory.php b/omnitools/src/IO/Directory.php
index 177d5dc..cf8efc5 100644
--- a/omnitools/src/IO/Directory.php
+++ b/omnitools/src/IO/Directory.php
@@ -1,121 +1,124 @@
<?php
namespace Keruald\OmniTools\IO;
+use Keruald\OmniTools\Collections\HashMap;
use Keruald\OmniTools\Collections\Vector;
class Directory {
///
/// Constructors
///
public function __construct (
private string $path,
) {}
public static function fromPathFragments (iterable $fragments) : self {
$path = Vector::from($fragments)
->implode(DIRECTORY_SEPARATOR)
->getValue();
return new self($path);
}
///
/// Getters and setters
///
public function getPath () : string {
return $this->path;
}
public function setPath (string $path) : self {
$this->path = $path;
return $this;
}
///
/// Directory properties methods
///
public function exists () : bool {
return is_dir($this->path);
}
public function isReadable () : bool {
return is_readable($this->path);
}
public function isWritable () : bool {
return is_writable($this->path);
}
- /**
- * @return array<string, string>
- */
- public function getPathInfo () : array {
- return pathinfo($this->path);
+ public function getPathInfo () : HashMap {
+ $info = pathinfo($this->path);
+
+ return HashMap::from($info);
}
public function getParentDirectory () : string {
return pathinfo($this->path, PATHINFO_DIRNAME);
}
public function getDirectoryName () : string {
return pathinfo($this->path, PATHINFO_BASENAME);
}
///
/// Search files
///
/**
* Gets files in the directory matching a specific pattern,
* using the PHP glob function.
*
- * @return File[]
+ * @return Vector<File>
+ */
+ public function glob (string $pattern) : Vector {
+ $glob = glob("$this->path/$pattern");
+
+ return Vector::from($glob)
+ ->map(fn ($file) => new File($file));
+ }
+
+ /**
+ * @return Vector<File>
*/
- public function glob (string $pattern) : array {
- return array_map(
- function ($file) {
- return new File($file);
- }, glob("$this->path/$pattern")
- );
+ public function globFiles (string $pattern) : Vector {
+ return $this->glob($pattern)
+ ->filter(fn (File $file) => is_file($file->getPath()));
}
/**
* Count files in the directory matching a specific pattern.
* Non-recursive.
*
* @param string $pattern Glob pattern to match files, defaults to "*"
* @return int
*/
public function countFiles (string $pattern = "*") : int {
- $matches = $this->glob($pattern);
- $filter = fn (File $file) => is_file($file->getPath());
-
- return count(array_filter($matches, $filter));
+ return $this->globFiles($pattern)->count();
}
/**
- * @return Directory[]
+ * @return Vector<Directory>
*/
- public function getSubdirectories () : array {
- return array_map(
- function ($dir) {
- return new Directory($dir);
- }, glob("$this->path/*", GLOB_ONLYDIR)
- );
+ public function getSubdirectories () : Vector {
+ $glob = glob("$this->path/*", GLOB_ONLYDIR);
+
+ return Vector::from($glob)
+ ->map(fn ($dir) => new Directory($dir));
}
///
/// Generate File from path
///
public function getFile (string $filename) : File {
return new File($this->path . DIRECTORY_SEPARATOR . $filename);
}
}
diff --git a/omnitools/src/IO/File.php b/omnitools/src/IO/File.php
index 9cdef8c..cb05e80 100644
--- a/omnitools/src/IO/File.php
+++ b/omnitools/src/IO/File.php
@@ -1,90 +1,94 @@
<?php
declare(strict_types=1);
namespace Keruald\OmniTools\IO;
+use Keruald\OmniTools\Collections\HashMap;
+
use RuntimeException;
class File {
/**
* @var string
*/
private $path;
///
/// Constructors
///
public function __construct (string $path) {
$this->path = $path;
}
/**
* @return static
*/
public static function from (string $path) : self {
return new static($path);
}
///
/// Getters and setters
///
public function getPath () : string {
return $this->path;
}
public function setPath (string $path) : self {
$this->path = $path;
return $this;
}
///
/// File properties methods
///
public function exists () : bool {
return file_exists($this->path);
}
public function isReadable () : bool {
return is_readable($this->path);
}
- public function getPathInfo () : array {
- return pathinfo($this->path);
+ public function getPathInfo () : HashMap {
+ $info = pathinfo($this->path);
+
+ return HashMap::from($info);
}
public function getDirectory () : string {
return pathinfo($this->path, PATHINFO_DIRNAME);
}
public function getFileName () : string {
return pathinfo($this->path, PATHINFO_BASENAME);
}
public function getFileNameWithoutExtension () : string {
return pathinfo($this->path, PATHINFO_FILENAME);
}
public function getExtension () : string {
return pathinfo($this->path, PATHINFO_EXTENSION);
}
///
/// IO helper methods
///
public function read () : string {
$contents = @file_get_contents($this->path);
if ($contents === false) {
throw new RuntimeException("Unable to read file: $this->path");
}
return $contents;
}
}
diff --git a/omnitools/src/Registration/PSR4/PSR4Namespace.php b/omnitools/src/Registration/PSR4/PSR4Namespace.php
index dc096df..34fa328 100644
--- a/omnitools/src/Registration/PSR4/PSR4Namespace.php
+++ b/omnitools/src/Registration/PSR4/PSR4Namespace.php
@@ -1,76 +1,77 @@
<?php
declare(strict_types=1);
namespace Keruald\OmniTools\Registration\PSR4;
+use Keruald\OmniTools\Collections\Vector;
use Keruald\OmniTools\IO\Directory;
use Keruald\OmniTools\IO\File;
class PSR4Namespace {
public function __construct (
public string $namespacePrefix,
public string $baseDirectory,
) {
}
///
/// Auto-discovery
///
/**
* Discover classes in the namespace folder following PSR-4 convention,
* directly at top-level, ignoring subdirectories.
*
* @see discoverRecursive
* @return string[]
*/
public function discover () : array {
- $files = (new Directory($this->baseDirectory))
- ->glob("*.php");
+ $map = fn(File $file) => $this->namespacePrefix
+ . "\\" . $file->getFileNameWithoutExtension();
- return array_map(function (File $file) {
- return $this->namespacePrefix
- . "\\" . $file->getFileNameWithoutExtension();
- }, $files);
+ return (new Directory($this->baseDirectory))
+ ->globFiles("*.php")
+ ->map($map)
+ ->toArray();
}
/**
* Discover classes in the namespace folder following PSR-4 convention,
* including all subfolders.
*
* @return string[]
*/
public function discoverRecursive () : array {
$classes = $this->discover();
$subDirectories = (new Directory($this->baseDirectory))
->getSubdirectories();
foreach ($subDirectories as $dir) {
$ns = new PSR4Namespace(
$this->namespacePrefix . "\\" . $dir->getDirectoryName(),
$dir->getPath(),
);
array_push($classes, ...$ns->discoverRecursive());
}
return $classes;
}
/**
* Discover classes for a specific namespace in a specific folder,
* following the PSR-4 convention, including all subfolders.
*
* @return string[]
*/
public static function discoverAllClasses (
string $namespacePrefix,
string $baseDirectory
) : array {
$ns = new PSR4Namespace($namespacePrefix, $baseDirectory);
return $ns->discoverRecursive();
}
}
diff --git a/omnitools/tests/IO/DirectoryTest.php b/omnitools/tests/IO/DirectoryTest.php
index 7d8a89e..5561934 100644
--- a/omnitools/tests/IO/DirectoryTest.php
+++ b/omnitools/tests/IO/DirectoryTest.php
@@ -1,137 +1,138 @@
<?php
namespace Keruald\OmniTools\Tests\IO;
+use Keruald\OmniTools\Collections\Vector;
use Keruald\OmniTools\IO\Directory;
use Keruald\OmniTools\IO\File;
use Keruald\OmniTools\Tests\WithData;
use PHPUnit\Framework\TestCase;
class DirectoryTest extends TestCase {
use WithData;
const TEST_DIRECTORY = "MockLib";
private string $path;
private Directory $directory;
protected function setUp () : void {
$this->path = $this->getDataPath(self::TEST_DIRECTORY);
$this->directory = new Directory($this->path);
}
public function testFromPathFragments () : void {
$fragments = [
$this->getDataDirectory(),
self::TEST_DIRECTORY,
];
$this->assertEquals(
$this->directory,
Directory::fromPathFragments($fragments)
);
}
public function testFromPathFragmentsWithOnlyOneFragmentEqualsPath () : void {
$fragments = [$this->getDataDirectory()];
$dir = Directory::fromPathFragments($fragments);
$this->assertEquals($this->getDataDirectory(), $dir->getPath());
}
public function testGlob () : void {
- $expected = [
+ $expected = Vector::from([
new File($this->path . '/Bar.php'),
new File($this->path . '/Foo.php'),
- ];
+ ]);
$actual = $this->directory->glob("*.php");
$this->assertEquals($expected, $actual);
}
public function testCountFiles () : void {
$this->assertSame(2, $this->directory->countFiles());
$this->assertSame(2, $this->directory->countFiles("*.php"));
$this->assertSame(1, $this->directory->countFiles("F*.php"));
$this->assertSame(0, $this->directory->countFiles("*.md"));
}
public function testCountFilesIgnoresDirectories () : void {
$path = $this->getDataPath("SolarSystemLib");
$directory = new Directory($path);
$this->assertSame(0, $directory->countFiles("Pl*"),
"Directory should not count directories.");
}
public function testGetFile () : void {
$expected = new File($this->path . DIRECTORY_SEPARATOR . "Foo.php");
$this->assertEquals($expected, $this->directory->getFile("Foo.php"));
}
public function testIsReadable () : void {
$this->assertTrue($this->directory->isReadable());
}
public function testIsWritable () : void {
$result = tempnam($this->path, "test-write-");
if ($result === false) {
$this->markTestSkipped("Can't test write operation.");
}
$canWrite = str_starts_with($result, $this->path);
unlink($result);
$this->assertSame($canWrite, $this->directory->isWritable());
}
public function testExists () : void {
$this->assertTrue($this->directory->exists());
}
public function testExistsWhenItDoesNot () : void {
$directory = new Directory("/nonexistent");
$this->assertFalse($directory->exists());
}
public function testExistsWhenItMatchesFile () : void {
$path = $this->getDataPath(self::TEST_DIRECTORY . "/Foo.php");
$directory = new Directory($path);
$this->assertFalse($directory->exists());
}
public function testSetPath () : void {
$this->directory->setPath("/bar/foo");
$this->assertEquals("/bar/foo", $this->directory->getPath());
}
public function testGetPath () : void {
$this->assertEquals($this->path, $this->directory->getPath());
}
public function testGetDirectoryName () : void {
$actual = $this->directory->getDirectoryName();
$this->assertEquals(self::TEST_DIRECTORY, $actual);
}
public function testGetPathInfo () : void {
$expected = [
'dirname' => $this->getDataDirectory(),
'basename' => self::TEST_DIRECTORY,
'filename' => self::TEST_DIRECTORY,
];
- $this->assertEquals($expected, $this->directory->getPathInfo());
+ $this->assertEquals($expected, $this->directory->getPathInfo()->toArray());
}
public function testGetParentDirectory () : void {
$actual = $this->directory->getParentDirectory();
$this->assertEquals($this->getDataDirectory(), $actual);
}
}
File Metadata
Details
Attached
Mime Type
text/x-diff
Expires
Wed, Oct 14, 20:58 (22 h, 45 m)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
4185836
Default Alt Text
(12 KB)
Attached To
Mode
rKERUALD Keruald libraries development repository
Attached
Detach File
Event Timeline
Log In to Comment