adachsoft/filesystem

There is no license information available for the latest version (1.0.0) of this package.

A flexible and powerful PHP filesystem library for handling files and directories

1.0.0 2025-09-03 10:59 UTC

This package is not auto-updated.

Last update: 2025-09-15 09:02:09 UTC


README

PHP Version License

A robust PHP filesystem abstraction library providing both physical and in-memory filesystem implementations with security features and comprehensive error handling.

๐Ÿš€ Features

  • Dual filesystem implementations: Physical filesystem and in-memory filesystem
  • Security-first design: Path traversal protection and input validation
  • Immutable models: Path, FileInfo, and FileSearchCriteria classes
  • Comprehensive error handling: Custom exception hierarchy
  • Collection support: PathCollection integration with AdachSoft Collection
  • File search capabilities: Advanced file filtering with criteria
  • Cross-platform compatibility: Unix and Windows path normalization
  • PSR-4 autoloading: Modern PHP standards

๐Ÿ“ฆ Installation

Method 1: Composer Configuration via CLI (Recommended)

Add the private repository and install:

# Add the filesystem repository
composer config repositories.adachsoft/filesystem vcs https://gitlab.com/a.adach/filesystem.git

# Add the collections dependency repository
composer config repositories.adachsoft/collection vcs https://gitlab.com/a.adach/collections.git

# Install the package
composer require adachsoft/filesystem

Method 2: Manual composer.json Configuration

Add the repositories to your composer.json:

{
    "repositories": [
        {
            "type": "vcs",
            "url": "https://gitlab.com/a.adach/filesystem.git"
        },
        {
            "type": "vcs", 
            "url": "https://gitlab.com/a.adach/collections.git"
        }
    ],
    "require": {
        "adachsoft/filesystem": "^1.0"
    }
}

Then run:

composer install

Method 3: One-liner Command

Execute all commands at once:

composer config repositories.adachsoft/filesystem vcs https://gitlab.com/a.adach/filesystem.git && composer config repositories.adachsoft/collection vcs https://gitlab.com/a.adach/collections.git && composer require adachsoft/filesystem

๐ŸŽฏ Quick Start

Physical FileSystem

<?php

use AdachSoft\FileSystem\PhysicalFileSystem;
use AdachSoft\FileSystem\Model\Path;

// Create filesystem instance with base directory
$fs = new PhysicalFileSystem('/var/www/project');

// Write a file
$fs->writeFile(new Path('config/app.yml'), 'database: mysql');

// Read a file
$content = $fs->readFile(new Path('config/app.yml'));

// Check if file exists
if ($fs->fileExists(new Path('config/app.yml'))) {
    echo "File exists!";
}

// Create directory
$fs->createDirectory(new Path('uploads/images'));

// List directory contents
$contents = $fs->listContents(new Path('uploads'));
foreach ($contents as $path) {
    echo $path->toString() . "\n";
}

In-Memory FileSystem

<?php

use AdachSoft\FileSystem\InMemoryFileSystem;
use AdachSoft\FileSystem\Model\Path;

// Create in-memory filesystem
$fs = new InMemoryFileSystem();

// All operations work the same as PhysicalFileSystem
$fs->writeFile(new Path('test.txt'), 'Hello World');
$fs->createDirectory(new Path('docs'));

// Reset filesystem (clear all data)
$fs->reset();

Working with Paths

<?php

use AdachSoft\FileSystem\Model\Path;

// Create path objects
$path = new Path('config/database.yml');

// Get path components
$basename = $path->getBasename(); // 'database.yml'
$parent = $path->getParent();     // Path('config')

// Join paths
$newPath = $path->getParent()->join('cache.yml'); // Path('config/cache.yml')

// String representation
echo $path->toString(); // 'config/database.yml'

File Search with Criteria

<?php

use AdachSoft\FileSystem\PhysicalFileSystem;
use AdachSoft\FileSystem\Model\Path;
use AdachSoft\FileSystem\Model\FileSearchCriteria;

$fs = new PhysicalFileSystem('/var/www/project');

// Create search criteria
$criteria = new FileSearchCriteria(
    directory: new Path('src'),
    filename: '*.php',
    extension: 'php',
    recursive: true
);

// Find all PHP files
$phpFiles = $fs->findFiles($criteria);

// Find files with specific pattern
$criteria = FileSearchCriteria::create(new Path('tests'))
    ->withFilename('Test.php')
    ->withExtension('php')
    ->withRecursive(false);

$testFiles = $fs->findFiles($criteria);

Working with File Information

<?php

use AdachSoft\FileSystem\PhysicalFileSystem;
use AdachSoft\FileSystem\Model\Path;

$fs = new PhysicalFileSystem('/var/www/project');

// Get file information
$fileInfo = $fs->getFileInfo(new Path('composer.json'));

echo "Path: " . $fileInfo->getPath()->toString() . "\n";
echo "Size: " . $fileInfo->getSize() . " bytes\n";
echo "Modified: " . $fileInfo->getLastModified()->format('Y-m-d H:i:s') . "\n";
echo "Is file: " . ($fileInfo->isFile() ? 'Yes' : 'No') . "\n";
echo "Is directory: " . ($fileInfo->isDirectory() ? 'Yes' : 'No') . "\n";

// Get timestamps and sizes directly
$timestamp = $fs->getLastModifiedTime(new Path('composer.json'));
$fileSize = $fs->getFileSize(new Path('composer.json'));

Path Collections

<?php

use AdachSoft\FileSystem\Model\PathCollection;
use AdachSoft\FileSystem\Model\Path;

// Create collection of paths
$paths = new PathCollection([
    new Path('src/FileSystem.php'),
    new Path('src/Model/Path.php'),
    new Path('tests/FileSystemTest.php')
]);

// Iterate over collection
foreach ($paths as $path) {
    echo $path->toString() . "\n";
}

๐Ÿ“š API Reference

FileSystemInterface Methods

MethodDescription
writeFile(Path $path, string $content): voidWrite content to file
readFile(Path $path): stringRead file content
deleteFile(Path $path): voidDelete file
fileExists(Path $path): boolCheck if file exists
createDirectory(Path $path): voidCreate directory
deleteDirectory(Path $path, bool $recursive = false): voidDelete directory
directoryExists(Path $path): boolCheck if directory exists
pathExists(Path $path): boolCheck if path exists
isDir(Path $path): boolCheck if path is directory
isFile(Path $path): boolCheck if path is file
listContents(Path $path): PathCollectionList directory contents
move(Path $source, Path $destination): voidMove/rename file or directory
getFileInfo(Path $path): FileInfoGet file information
getLastModifiedTime(Path $path): intGet last modified timestamp
getFileSize(Path $path): intGet file size in bytes
findFiles(FileSearchCriteria $criteria): PathCollectionFind files by criteria

Model Classes

Path

  • __construct(string $path) - Create path object
  • toString(): string - Get string representation
  • getBasename(): string - Get filename/directory name
  • getParent(): Path - Get parent directory
  • join(string|Path $path): Path - Join with another path

FileInfo

  • getPath(): Path - Get file path
  • getSize(): int - Get file size
  • getLastModified(): DateTimeImmutable - Get modification date
  • isFile(): bool - Check if is file
  • isDirectory(): bool - Check if is directory

FileSearchCriteria

  • create(Path $directory): self - Create search criteria
  • withFilename(string $filename): self - Set filename pattern
  • withExtension(string $extension): self - Set file extension
  • withExcludedDirectories(PathCollection $dirs): self - Set excluded directories
  • withRecursive(bool $recursive): self - Set recursive search

PathCollection

  • Extends AbstractImmutableCollection<Path>
  • Type-safe collection of Path objects

Exception Classes

  • FileSystemException - Base exception class
  • FileNotFoundException - File not found
  • DirectoryNotFoundException - Directory not found
  • FileSystemIOException - I/O operation failed
  • PathTraversalException - Path traversal attempt detected

๐Ÿงช Testing

Run the test suite:

composer test

Run tests with coverage:

composer test-coverage

๐Ÿ”’ Security Features

  • Path traversal protection: All paths are validated against base directory
  • Input sanitization: Windows and Unix path normalization
  • Safe directory operations: Recursive deletion requires explicit flag
  • Immutable models: Prevents accidental state changes

๐Ÿ—๏ธ Development Setup

  1. Clone the repository:

    git clone https://gitlab.com/a.adach/filesystem.git
    cd filesystem
    
  2. Install dependencies:

    composer install
    
  3. Run tests:

    composer test
    

๐Ÿค Contributing

Contributions are welcome! Please feel free to submit a Merge Request.

  1. Fork the repository on GitLab
  2. Create your feature branch (git checkout -b feature/amazing-feature)
  3. Commit your changes (git commit -m 'Add some amazing feature')
  4. Push to the branch (git push origin feature/amazing-feature)
  5. Open a Merge Request on GitLab

๐Ÿ“„ License

This project is licensed under the MIT License - see the LICENSE file for details.

๐Ÿ†˜ Support

For support and questions:

  • Create an issue on GitLab
  • Contact: adachsoft@gmail.com

๐Ÿ”— Links

Made with โค๏ธ by AdachSoft