From d3d3d341164ab1ad4e6ab5050dfda08418aee7da Mon Sep 17 00:00:00 2001 From: mappu Date: Sat, 11 Apr 2020 12:44:37 +1200 Subject: [PATCH] node: emit static ::class as class name string literal --- fixtures/0011-magic-consts.php | 3 ++- node.go | 22 ++++++++++++++++++++++ 2 files changed, 24 insertions(+), 1 deletion(-) diff --git a/fixtures/0011-magic-consts.php b/fixtures/0011-magic-consts.php index 64dc8e3..1ac9340 100644 --- a/fixtures/0011-magic-consts.php +++ b/fixtures/0011-magic-consts.php @@ -17,7 +17,8 @@ function Foo() { class Bar { function Baz() { echo __CLASS__ . "::" . __METHOD__ ; - echo Baz::class; + echo Bar::class; + // echo $this::class; } } diff --git a/node.go b/node.go index c5e000d..ec58faf 100644 --- a/node.go +++ b/node.go @@ -1012,6 +1012,28 @@ func (this *conversionState) convertNoFreeFloating(n_ node.Node) (string, error) constName := n.ConstantName.(*node.Identifier).Value // TODO fix up visibility modifier + // Special case: `::class` is just the string name of the class + if constName == `class` { + // This can be known statically (e.g. MyClass::class --> "MyClass") but + // isn't generally known non-statically + if _, ok := n.Class.(*name.Name); ok { + // Static + return strconv.Quote(className), nil + + } else if className == `self` { + return strconv.Quote(this.currentClassName), nil + + } else { + // Dynamic + // Translate to reflect + // this.importPackages["reflect"] = struct{}{} + // return `reflect.TypeOf(` + className + `).String()`, nil + + // Actually PHP doesn't support using ::class on variables + return "", parseErr{n, fmt.Errorf(`PHP Fatal error: Dynamic class names are not allowed in compile-time ::class fetch`)} + } + } + return className + constName, nil case *expr.Exit: