|
@@ -1,23 +1,41 @@
|
|
|
-<?php
|
|
|
+<?php declare (strict_types = 1);
|
|
|
|
|
|
namespace ePHPic\Autload;
|
|
|
|
|
|
-/**
|
|
|
+/*******************************************************************************
|
|
|
* Class Autoloader
|
|
|
- *
|
|
|
- * A simple autoloader for loading PHP classes based on a defined mapping and base directory.
|
|
|
- *
|
|
|
- * @package ePHPic\Autload
|
|
|
- */
|
|
|
+ * *****************************************************************************
|
|
|
+ * A simple autoloader for loading PHP classes based on a defined mapping and
|
|
|
+ * base directory.
|
|
|
+ *
|
|
|
+ * @package ePHPic\Autoload
|
|
|
+ * @author Sina Kuhestani <sina@ephpic.org>
|
|
|
+ * @license MIT License
|
|
|
+ * @copyright 2025 © Sina Kuhestani
|
|
|
+ * @link https://code.ephpic.org/ephpic/autoload
|
|
|
+ ******************************************************************************/
|
|
|
class Autoloader
|
|
|
{
|
|
|
/**
|
|
|
- * @var string The base directory for the autoloader.
|
|
|
+ * The base directory for the application.
|
|
|
+ *
|
|
|
+ * This static property holds the absolute path to the base directory where
|
|
|
+ * the application files are located. It is used for resolving paths to
|
|
|
+ * resources and ensuring that file operations are performed in the
|
|
|
+ * correct directory.
|
|
|
+ *
|
|
|
+ * @var string
|
|
|
*/
|
|
|
- private static $baseDir = "/var/www/html";
|
|
|
+ private static $baseDirectory = '/var/www/html';
|
|
|
|
|
|
/**
|
|
|
- * @var array A mapping of class names to file paths.
|
|
|
+ * A mapping of class names to file paths.
|
|
|
+ *
|
|
|
+ * This static property stores an associative array that maps fully
|
|
|
+ * qualified class names to their corresponding file paths. This allows for
|
|
|
+ * quick resolution of class locations when autoloading.
|
|
|
+ *
|
|
|
+ * @var array
|
|
|
*/
|
|
|
private static $map = [];
|
|
|
|
|
@@ -32,20 +50,108 @@ class Autoloader
|
|
|
* @param string|null $path An optional additional path to append.
|
|
|
* @return string The resolved file path for the class.
|
|
|
*/
|
|
|
- public static function resolve($class, $path = null)
|
|
|
+ public static function resolve (string $class, ?string $path = null): string
|
|
|
{
|
|
|
- if(isset(static::$map[$class]))
|
|
|
- {
|
|
|
- return static::$baseDir . "/" . static::$map[$class] . ($path ? "/$path" : "") . ".php";
|
|
|
+ /* Boolean var, indicates if the class name is present in class map */
|
|
|
+ $isClassInMap = key_exists (
|
|
|
+ key: $class,
|
|
|
+ array: static::$map
|
|
|
+ );
|
|
|
+
|
|
|
+ /* When class name is explicitly present in the class map */
|
|
|
+ if (true === $isClassInMap)
|
|
|
+ {/* ⚠️ NOT COMMON CASE */
|
|
|
+ /* Use path from class map to create full path of the class file */
|
|
|
+ return static::buildPath($class, $path, true);
|
|
|
}
|
|
|
- $lastBackslashPos = strrpos($class, '\\');
|
|
|
- if ($lastBackslashPos !== false) {
|
|
|
- $path = substr($class, $lastBackslashPos+1, strlen($class) - 1) . ($path ? "/$path" : "");
|
|
|
- $class = substr($class, 0, $lastBackslashPos);
|
|
|
+
|
|
|
+ /* Get position of last backslash in the class name */
|
|
|
+ $lastBackslashPos = strrpos (
|
|
|
+ haystack: $class,
|
|
|
+ needle: '\\'
|
|
|
+ );
|
|
|
+
|
|
|
+ /* Boolean var, indicates if class name has backslash */
|
|
|
+ $hasBackSlash = false !== $lastBackslashPos;
|
|
|
+
|
|
|
+ /* When class name has backslashes */
|
|
|
+ if (true === $hasBackSlash)
|
|
|
+ { /* 🚀 COMMON CASE */
|
|
|
+ /* Remove last section of calss name and add to expected file path */
|
|
|
+ $subString = substr (
|
|
|
+ string: $class,
|
|
|
+ offset: $lastBackslashPos+1,
|
|
|
+ length: strlen ($class) - 1
|
|
|
+ );
|
|
|
+ $suffix = $path ? DIRECTORY_SEPARATOR . $path : '';
|
|
|
+
|
|
|
+ /* This is expected path for file location */
|
|
|
+ $path = $subString . $suffix;
|
|
|
+
|
|
|
+ /* This is shortened class name to resolve again */
|
|
|
+ $class = substr (
|
|
|
+ string: $class,
|
|
|
+ offset: 0,
|
|
|
+ length: $lastBackslashPos
|
|
|
+ );
|
|
|
+
|
|
|
+ /* Retry to resolve new shortened $class */
|
|
|
return static::resolve($class, $path);
|
|
|
}
|
|
|
|
|
|
- return static::$baseDir . "/" . str_replace("\\","/",$class) . ($path ? "/$path" : "") . ".php";
|
|
|
+ /* Return completely expected file path */
|
|
|
+ return static::buildPath($class, $path, false);
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * Constructs the full file path for a given class name.
|
|
|
+ *
|
|
|
+ * This method builds the file path for the specified class based on the
|
|
|
+ * provided parameters. It can either use a mapping of class names to file
|
|
|
+ * paths or construct the path directly from the class name. The resulting
|
|
|
+ * path is suitable for including the class file.
|
|
|
+ *
|
|
|
+ * @param string $class The fully qualified class name for which to build
|
|
|
+ * the path.
|
|
|
+ * @param string $path A path to append to the base path.
|
|
|
+ * @param bool $useMap Indicates whether to use the mapping of class names
|
|
|
+ * to file paths. If true, the method will use the mapping to resolve the
|
|
|
+ * file path. If false, it will construct the path based on the class name.
|
|
|
+ * @return string The constructed file path for the class.
|
|
|
+ */
|
|
|
+ private static function buildPath(string $class, string $path, bool $useMap = true): string
|
|
|
+ {
|
|
|
+ /* When $useMap is true, then it uses class map to expect file path */
|
|
|
+ if (true === $useMap)
|
|
|
+ {
|
|
|
+ $filePathArray = [
|
|
|
+ static::$baseDirectory,
|
|
|
+ DIRECTORY_SEPARATOR,
|
|
|
+ static::$map[$class],
|
|
|
+ $path ? DIRECTORY_SEPARATOR . $path : '',
|
|
|
+ '.php'
|
|
|
+ ];
|
|
|
+ }
|
|
|
+ /* When $useMap is false, it expects the file path following PSR-4 */
|
|
|
+ else
|
|
|
+ {
|
|
|
+ $filePathArray = [
|
|
|
+ static::$baseDirectory,
|
|
|
+ DIRECTORY_SEPARATOR,
|
|
|
+ str_replace ('\\', DIRECTORY_SEPARATOR, $class),
|
|
|
+ $path ? DIRECTORY_SEPARATOR . $path : '',
|
|
|
+ '.php'
|
|
|
+ ];
|
|
|
+ }
|
|
|
+
|
|
|
+ /* Merge filePath segments and create full path */
|
|
|
+ $filePath = implode (
|
|
|
+ separator: '',
|
|
|
+ array: $filePathArray
|
|
|
+ );
|
|
|
+
|
|
|
+ /* Return the expected class file path */
|
|
|
+ return $filePath;
|
|
|
}
|
|
|
|
|
|
/**
|
|
@@ -56,12 +162,23 @@ class Autoloader
|
|
|
* @param string $class The fully qualified class name to autoload.
|
|
|
* @return void
|
|
|
*/
|
|
|
- public static function autoload($class)
|
|
|
+ public static function autoload ($class): void
|
|
|
{
|
|
|
- $filePath = static::resolve($class);
|
|
|
- if(@file_exists($filePath))
|
|
|
+ /* Get expected class file */
|
|
|
+ $filePath = static::resolve (
|
|
|
+ class: $class,
|
|
|
+ path: null
|
|
|
+ );
|
|
|
+
|
|
|
+ /* Boolean var, indicates if class file exists */
|
|
|
+ $fileExists = @file_exists (
|
|
|
+ filename: $filePath
|
|
|
+ );
|
|
|
+
|
|
|
+ /* When class file exists simply include it */
|
|
|
+ if (true === $fileExists)
|
|
|
{
|
|
|
- include_once $filePath;
|
|
|
+ require_once $filePath;
|
|
|
}
|
|
|
}
|
|
|
|
|
@@ -71,16 +188,21 @@ class Autoloader
|
|
|
* This method allows the autoloader to be registered so that it can be used
|
|
|
* to automatically load classes when they are referenced.
|
|
|
*
|
|
|
- * @param string $baseDir The base directory for the autoloader.
|
|
|
+ * @param string $baseDirectory The base directory for the autoloader.
|
|
|
* @param array $map An associative array mapping class names to file paths.
|
|
|
* @return void
|
|
|
*/
|
|
|
- public static function register($baseDir, $map)
|
|
|
+ public static function register ($baseDirectory, $map): void
|
|
|
{
|
|
|
- spl_autoload_register(
|
|
|
- [static::class, "autoload"],
|
|
|
- true,
|
|
|
- true
|
|
|
+ /* Initialize Autoloader class map and base directory */
|
|
|
+ static::$baseDirectory = $baseDirectory;
|
|
|
+ static::$map = $map;
|
|
|
+
|
|
|
+ /* Register the method autoload as php autoloader */
|
|
|
+ spl_autoload_register (
|
|
|
+ callback: [static::class, 'autoload'],
|
|
|
+ throw: true,
|
|
|
+ prepend: true
|
|
|
);
|
|
|
}
|
|
|
}
|