Installation:
composer require riimu/kit-pathjoin:^1.2
Ensure vendor/autoload.php is included in your project (Laravel handles this automatically via composer.json).
First Usage:
use Riimu\Kit\PathJoin\Path;
// Normalize a path (resolves `.`, `..`, and redundant separators)
$normalized = Path::normalize('/app/../resources/./config');
// Join paths (cross-platform, handles absolute/relative paths)
$joined = Path::join('storage', 'logs', 'app.log');
First Laravel Use Case:
Use in config/filesystems.php or service providers to ensure consistent path handling across environments:
$path = Path::join(storage_path(), 'app', 'logs', 'debug.log');
Path Normalization:
Path::normalize() for cleaning up user-provided paths (e.g., form inputs, API responses).$cleanPath = Path::normalize($request->input('file_path'));
Path Joining:
Path::join() for constructing paths dynamically (e.g., config paths, asset paths).// In a service provider or helper
function configPath(...$segments) {
return Path::join(config_path(), ...$segments);
}
Cross-Platform Consistency:
Storage::put()):
$filePath = Path::normalize($request->file('document')->store('uploads'));
Absolute vs. Relative Handling:
Path::join() is absolute if needed (e.g., for root-level paths):
$absolutePath = Path::join('/var', 'app', 'logs');
Service Provider Bootstrapping:
boot() methods to ensure consistency:
public function boot() {
$this->app->bind('path.normalizer', function() {
return new class {
public function normalize(string $path) {
return Path::normalize($path);
}
};
});
}
Middleware for Path Sanitization:
public function handle($request, Closure $next) {
$request->merge([
'sanitized_path' => Path::normalize($request->path())
]);
return $next($request);
}
Artisan Commands:
protected function getLogPath() {
return Path::join(storage_path(), 'logs', 'command.log');
}
View Composers:
public function compose(View $view) {
$view->with('cssPath', Path::join(public_path(), 'css', 'app.css'));
}
Drive Letter Handling on Windows:
Path::normalize('/foo/bar') may prepend the current drive (e.g., C:\foo\bar). Use the second parameter to control this:
Path::normalize('/foo/bar', false); // Returns '\foo\bar'
Empty Paths:
Path::join('foo', '..') returns . (current directory), not an empty string. Mimic PHP’s dirname() behavior:
$parentDir = Path::join('foo/bar', '..'); // Returns 'foo'
Trailing Slashes:
$normalized = rtrim(Path::normalize($path), DIRECTORY_SEPARATOR);
PHP 5.6+ Requirement:
Verify Path Behavior:
Path::join('//', 'path') (should return /path on Unix, \path on Windows).Compare with realpath():
realpath() (where applicable) to ensure correctness:
$normalized = Path::normalize('/app/../../var');
$realPath = realpath($normalized); // Verify filesystem existence
Logging Normalized Paths:
\Log::debug('Normalized path:', ['path' => Path::normalize($inputPath)]);
Custom Normalization Rules:
class CustomPath {
public static function normalize(string $path) {
$normalized = Path::normalize($path);
// Add custom rules (e.g., replace spaces with underscores)
return str_replace(' ', '_', $normalized);
}
}
Integration with Laravel Filesystem:
Filesystem::path() to use Path::join():
// In a service provider
$this->app->extend('path', function($path) {
return Path::join(...func_get_args());
});
Testing:
Path in unit tests to isolate path logic:
$this->partialMock(Path::class, ['normalize'])
->shouldReceive('normalize')
->with('/test/path')
->andReturn('/normalized/path');
Performance:
$cacheKey = 'path.normalized:'.$inputPath;
$normalized = Cache::remember($cacheKey, 3600, function() use ($inputPath) {
return Path::normalize($inputPath);
});
How can I help you explore Laravel packages today?