eee
This commit is contained in:
+8
-103
@@ -8,6 +8,7 @@ use DirectoryIterator;
|
||||
use Kiri\Abstracts\Component;
|
||||
use Kiri\Di\Inject\Container;
|
||||
use Kiri\Di\Inject\Skip;
|
||||
use Kiri\Di\Interface\InjectMethodInterface;
|
||||
use Psr\Container\ContainerInterface;
|
||||
use ReflectionClass;
|
||||
use ReflectionMethod;
|
||||
@@ -41,7 +42,6 @@ class Scanner extends Component
|
||||
'cache_enabled' => false,
|
||||
'cache_ttl' => 3600,
|
||||
'debug' => false,
|
||||
'class_name_strategy' => 'auto',
|
||||
];
|
||||
|
||||
public function __construct()
|
||||
@@ -239,9 +239,12 @@ class Scanner extends Component
|
||||
private function loadAndParseFile(string $path): array
|
||||
{
|
||||
$this->optimizeWithOpcache($path);
|
||||
require_once $path;
|
||||
|
||||
$classes = $this->getClassNamesForFile($path);
|
||||
$before = get_declared_classes();
|
||||
require_once $path;
|
||||
$after = get_declared_classes();
|
||||
|
||||
$classes = array_values(array_diff($after, $before));
|
||||
foreach ($classes as $class) {
|
||||
if (class_exists($class)) {
|
||||
$this->analyzeClass($class);
|
||||
@@ -251,104 +254,6 @@ class Scanner extends Component
|
||||
return $classes;
|
||||
}
|
||||
|
||||
private function getClassNamesForFile(string $path): array
|
||||
{
|
||||
$strategy = $this->config['class_name_strategy'];
|
||||
$classes = [];
|
||||
|
||||
if (in_array($strategy, ['auto', 'extract', 'both'], true)) {
|
||||
$class = $this->extractClassNameFromFile($path);
|
||||
if ($class !== null) {
|
||||
$classes[] = $class;
|
||||
}
|
||||
}
|
||||
|
||||
if ($classes === [] || in_array($strategy, ['rename', 'both'], true)) {
|
||||
$classes[] = $this->renamePathToClassName($path);
|
||||
}
|
||||
|
||||
return array_values(array_unique(array_filter($classes)));
|
||||
}
|
||||
|
||||
private function canExtractClassName(): bool
|
||||
{
|
||||
return function_exists('token_get_all');
|
||||
}
|
||||
|
||||
private function extractClassNameFromFile(string $path): ?string
|
||||
{
|
||||
if (!$this->canExtractClassName()) {
|
||||
return null;
|
||||
}
|
||||
|
||||
$content = @file_get_contents($path);
|
||||
if ($content === false || $content === '') {
|
||||
return null;
|
||||
}
|
||||
|
||||
$tokens = @token_get_all($content);
|
||||
if (!$tokens) {
|
||||
return null;
|
||||
}
|
||||
|
||||
$namespace = '';
|
||||
$class = '';
|
||||
$collectingNamespace = false;
|
||||
$collectingClass = false;
|
||||
$previousToken = null;
|
||||
|
||||
foreach ($tokens as $token) {
|
||||
if (is_array($token)) {
|
||||
$text = $token[1];
|
||||
|
||||
if ($token[0] === T_NAMESPACE) {
|
||||
$namespace = '';
|
||||
$collectingNamespace = true;
|
||||
} elseif ($collectingNamespace && in_array($token[0], [T_STRING, T_NAME_QUALIFIED, T_NS_SEPARATOR], true)) {
|
||||
$namespace .= $text;
|
||||
} elseif ($collectingNamespace && $token[0] === T_WHITESPACE) {
|
||||
} elseif (in_array($token[0], [T_CLASS, T_INTERFACE, T_TRAIT, T_ENUM], true) && $previousToken !== T_DOUBLE_COLON && $previousToken !== T_NEW) {
|
||||
$collectingClass = true;
|
||||
} elseif ($collectingClass && $token[0] === T_STRING) {
|
||||
$class = $text;
|
||||
break;
|
||||
} elseif ($collectingNamespace) {
|
||||
$collectingNamespace = false;
|
||||
}
|
||||
|
||||
if ($token[0] !== T_WHITESPACE) {
|
||||
$previousToken = $token[0];
|
||||
}
|
||||
continue;
|
||||
}
|
||||
|
||||
if ($collectingNamespace && ($token === ';' || $token === '{')) {
|
||||
$collectingNamespace = false;
|
||||
}
|
||||
if ($token === '{') {
|
||||
$collectingClass = false;
|
||||
}
|
||||
$previousToken = $token;
|
||||
}
|
||||
|
||||
if ($class === '') {
|
||||
return null;
|
||||
}
|
||||
|
||||
return $namespace !== '' ? $namespace . '\\' . $class : $class;
|
||||
}
|
||||
|
||||
private function renamePathToClassName(string $path): string
|
||||
{
|
||||
$relativePath = str_replace($this->basePath, '', $this->normalizePath($path));
|
||||
$relativePath = str_replace('.php', '', $relativePath);
|
||||
$parts = explode('/', trim($relativePath, '/\\'));
|
||||
$parts = array_values(array_filter($parts, fn(string $part) => $part !== ''));
|
||||
$parts = array_map('ucfirst', $parts);
|
||||
|
||||
return implode('\\', $parts);
|
||||
}
|
||||
|
||||
private function optimizeWithOpcache(string $path): void
|
||||
{
|
||||
if ($this->hasOpcache === null) {
|
||||
@@ -403,7 +308,7 @@ class Scanner extends Component
|
||||
|
||||
private function analyzeClassMethods(ReflectionClass $reflect, string $class): void
|
||||
{
|
||||
foreach ($reflect->getMethods(ReflectionMethod::IS_PUBLIC) as $method) {
|
||||
foreach ($reflect->getMethods() as $method) {
|
||||
if ($method->isStatic() || $method->getDeclaringClass()->getName() !== $class) {
|
||||
continue;
|
||||
}
|
||||
@@ -422,7 +327,7 @@ class Scanner extends Component
|
||||
|
||||
try {
|
||||
$instance = $attribute->newInstance();
|
||||
if (method_exists($instance, 'dispatch')) {
|
||||
if ($instance instanceof InjectMethodInterface) {
|
||||
$instance->dispatch($class, $method->getName());
|
||||
}
|
||||
} catch (Throwable $e) {
|
||||
|
||||
Reference in New Issue
Block a user