Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

get_method() is not returning the name of the lambda function #73052

Closed
marciodrosa opened this issue Feb 10, 2023 · 2 comments
Closed

get_method() is not returning the name of the lambda function #73052

marciodrosa opened this issue Feb 10, 2023 · 2 comments

Comments

@marciodrosa
Copy link

marciodrosa commented Feb 10, 2023

Godot version

4.0.rc

System information

Windows 10

Issue description

The documentation of the Callable.get_method() says:

"Returns the name of the method represented by this Callable. If the callable is a lambda function, returns the function's name."

However, this is not true, and the function always returns an empty string when the Callable is a lambda, named or not. Also, the string representation of the Callable, although not exactly wrong, seems to be different than the intended by the code.

I already have the solution for this bug, and the PR is ready to be opened. However, I would like to discuss two things before:

1. The current code has the following "if" in the get_as_text function to check if the lambda is an anonymous lambda:

if (function->get_name() != StringName())

However, it doesn't work because the function name is never empty; the GDScript parser always set it to "<anonymous lambda>" in these cases. So, the solution is an uglier, but functional:

if (function->get_name() != "<anonymous lambda>")

2. There is a lot of duplicated code between the classes GDScriptLambdaCallable and GDScriptLambdaSelfCallable. Even this fix should be duplicated in both classes. Is it ok to refactor in order to make both classes inherit from a common base class, like GDScriptLambdaCallableBase? (My proposed fix already does that, actually.)

Steps to reproduce

Run the following GDScript:

var unnamed_lambda: Callable = func(x): return 0
var named_lambda: Callable = func some_lambda(x): return 0
print("unnamed_lambda.get_method(): " + unnamed_lambda.get_method())
print("str(unnamed_lambda): " + str(unnamed_lambda))
print("named_lambda.get_method(): " + named_lambda.get_method())
print("str(named_lambda): " + str(named_lambda))

This is the current result:

unnamed_lambda.get_method(): 
str(unnamed_lambda): <anonymous lambda>(lambda)
named_lambda.get_method(): 
str(named_lambda): some_lambda(lambda)

This is the expected result:

unnamed_lambda.get_method(): 
str(unnamed_lambda): (anonymous lambda)
named_lambda.get_method(): some_lambda
str(named_lambda): some_lambda(lambda)

Notice that get_method is always returning empty currently.
Also, the str(lambda) expected result is what the code seems to by trying to do, but there is a wrong "if" there (as explained above).

Minimal reproduction project

N/A

@MikeSchulze
Copy link

I can confirm, at RC5

func _ready():
	var cb := func predicate(current, expected): return current == null
	prints(cb)
	prints(cb.get_method())
	get_tree().quit()

it ends up in a runtime error

E 0:00:00:0685   test.gd:11 @ _ready(): Can't get method on CallableCustom "predicate(lambda)".
  <C++-Fehler>   Method/function failed. Returning: StringName()
  <C++-Quelle>   core/variant/callable.cpp:377 @ get_method()
  <Stacktrace>   RangeCrash.gd:11 @ _ready()

MikeSchulze added a commit to MikeSchulze/gdUnit4 that referenced this issue Feb 25, 2023
# Why
With RC3, RC4, RC3 some regressions are introduced and needs to be addapt to get GdUnit4 running


# What
- fix bug in releasing internal memory store
- fix function doubling according to fixed issue (godotengine/godot#73046)
- remove custom `is_instanceof` and replace it by new engine function `is_instance_of`
- do code formattings
- use new signal code style to connect/disconnect
- use workaround for `GlobalScript` enums (godotengine/godot#73835)
- use workaround for `Timer.timeout.connect` (godotengine/godot#73889)
- use workarount for `Callable.get_method()` (godotengine/godot#73052)
MikeSchulze added a commit to MikeSchulze/gdUnit4 that referenced this issue Feb 25, 2023
# Why
With RC3, RC4, RC3 some regressions are introduced and needs to be
addapt to get GdUnit4 running


# What
- fix bug in releasing internal memory store
- fix function doubling according to fixed issue
(godotengine/godot#73046)
- remove custom `is_instanceof` and replace it by new engine function
`is_instance_of`
- do code formattings
- use new signal code style to connect/disconnect
- use workaround for `GlobalScript` enums
(godotengine/godot#73835)
- use workaround for `Timer.timeout.connect`
(godotengine/godot#73889)
- use workarount for `Callable.get_method()`
(godotengine/godot#73052)
- switch to RC5 on ci-pr WF
@marciodrosa
Copy link
Author

It seems fixed on branch main, so I'm closing this issue.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

3 participants