From a30205b0586e63b0f463f16a73267e4a74cdbe22 Mon Sep 17 00:00:00 2001 From: tianfenghan Date: Tue, 9 Jun 2026 12:43:53 +0800 Subject: [PATCH] =?UTF-8?q?refactor(php):=20=E9=87=8D=E6=9E=84=E6=96=B9?= =?UTF-8?q?=E6=B3=95=E9=87=8D=E5=86=99=E6=A3=80=E6=9F=A5=E9=80=BB=E8=BE=91?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - 将 checkParentMethodCanBeOverridden 方法从 Preprocessor 类移动到 Translator 类 - 移除 Preprocessor 类中的方法重写检查实现 - 在 Translator 类中添加完整的父类方法重写检查功能 - 实现私有方法不能被重写的验证逻辑 - 添加对内置类私有方法的重写检查支持 - 保持原有的方法重写标记逻辑在 Translator 中继续工作 --- src/Php/Preprocessor.php | 48 ++++++++++++++-------------------------- src/Php/Translator.php | 47 +++++++++++++++++++++++++-------------- 2 files changed, 48 insertions(+), 47 deletions(-) diff --git a/src/Php/Preprocessor.php b/src/Php/Preprocessor.php index 5d415fac..65ee706c 100644 --- a/src/Php/Preprocessor.php +++ b/src/Php/Preprocessor.php @@ -504,37 +504,6 @@ class Preprocessor extends CompilerBase return $this->parseIdentifier($v->name); } - /** - * 检查父类方法是否可以被重写,私有方法不能被重写 - */ - protected function checkParentMethodCanBeOverridden(Node\Stmt\ClassMethod $v, string $name): void - { - $classDef = $this->classDef; - while (true) { - $extends = $classDef->extends; - if (!$extends) { - break; - } - // 父类是内置类 - if ($classDef->inheritedFromInternalClass) { - if (Reflection::getClassMethodModifiers($extends, $name) & \ReflectionMethod::IS_PRIVATE) { - goto _error; - } - break; - } - $classDef = $this->getClass($extends); - if ($classDef->hasMethod($this->method)) { - $methodDef = $classDef->getMethod($this->method); - if ($methodDef->flags & Modifiers::PRIVATE) { - _error: - $this->fatalError($v, - 'Cannot override private method `' . - $classDef->getNamespacedName(false) . '::' . $this->method . '()`'); - } - } - } - } - protected function parseClassConstDef(Node\Stmt\ClassConst $v): void { $this->resetFunction(); @@ -633,6 +602,23 @@ class Preprocessor extends CompilerBase } } + $fullClassName = $this->getFullClassName(); + + $fullMethodName = $fullClassName . '::' . $this->method; + $this->classMethodOverride[strtolower($fullMethodName)] = false; + // 查找父类是否有同名方法,递归查找 + $fullClassNameLower = strtolower($fullClassName); + + while (isset($this->classExtends[$fullClassNameLower])) { + $parentClass = $this->classExtends[$fullClassNameLower]; + $parentMethodLower = strtolower($parentClass . '::' . $this->method); + // 父类有同名方法,子类覆盖了父类方法,这种情况不能直接使用 C++ 函数,而是使用 ZendVM 动态调用 + if (isset($this->classMethodOverride[$parentMethodLower])) { + $this->classMethodOverride[$parentMethodLower] = true; + } + $fullClassNameLower = strtolower($parentClass); + } + $this->resetMethod(); } diff --git a/src/Php/Translator.php b/src/Php/Translator.php index f5b697ea..248a844a 100644 --- a/src/Php/Translator.php +++ b/src/Php/Translator.php @@ -2290,6 +2290,37 @@ CODE; return $code; } + /** + * 检查父类方法是否可以被重写,私有方法不能被重写 + */ + protected function checkParentMethodCanBeOverridden(Node\Stmt\ClassMethod $v, string $name): void + { + $classDef = $this->classDef; + while (true) { + $extends = $classDef->extends; + if (!$extends) { + break; + } + // 父类是内置类 + if ($classDef->inheritedFromInternalClass) { + if (Reflection::getClassMethodModifiers($extends, $name) & \ReflectionMethod::IS_PRIVATE) { + goto _error; + } + break; + } + $classDef = $this->getClass($extends); + if ($classDef->hasMethod($this->method)) { + $methodDef = $classDef->getMethod($this->method); + if ($methodDef->flags & Modifiers::PRIVATE) { + _error: + $this->fatalError($v, + 'Cannot override private method `' . + $classDef->getNamespacedName(false) . '::' . $this->method . '()`'); + } + } + } + } + protected function parseClassMethod(Node\Stmt\ClassMethod $v, array &$methodCodes): void { $name = $this->getMethodName($v); @@ -2303,22 +2334,6 @@ CODE; $methodCodes[$name] = $this->parseFunction($v); } - $fullClassName = $this->getFullClassName(); - $fullMethodName = $fullClassName . '::' . $this->method; - $this->classMethodOverride[strtolower($fullMethodName)] = false; - // 查找父类是否有同名方法,递归查找 - $fullClassNameLower = strtolower($fullClassName); - - while (isset($this->classExtends[$fullClassNameLower])) { - $parentClass = $this->classExtends[$fullClassNameLower]; - $parentMethodLower = strtolower($parentClass . '::' . $v->name); - // 父类有同名方法,子类覆盖了父类方法,这种情况不能直接使用 C++ 函数,而是使用 ZendVM 动态调用 - if (isset($this->classMethodOverride[$parentMethodLower])) { - $this->classMethodOverride[$parentMethodLower] = true; - } - $fullClassNameLower = strtolower($parentClass); - } - $this->resetMethod(); }