How to get the names of the output parameters of a function in Python?

Viewed 60

I have

def foo(arg1, arg2):
    a = 5
    b = "hi"
    return a, b, "c"

I want some magic(foo) that returns ("a", "b", "un-named"), or something similar.

Is there anything like that in Python?


EDIT: why?

To create a logger decorator that gives its readers context for the values in the log.

2 Answers

Okay, since I've been asked by OP to elaborate on the discussion in comments regarding why it is a bad idea and what are the alternatives.

Why not: Once you return the values from the function you should no longer care about what names they had inside. After all, it doesn't matter what the variable was called, all that matters is the value returned. Let's consider the following function:

def ex(foo):
    a = 42
    if foo:
        return a
    else:
        return 6*7
    

Does anything outside of the function care whether a was returned or 6*7? Not really. It is 42 either way. If you do care about that difference you should know that inside the function. Outside, you should refer to whatever is the name of the variable you used to catch the return values.

Alternatives: You said you wanted to do logging without user action, but adding the decorator to a function is not much simpler than explicit logging - and arguably less clear. Again, the same principle applies - you care about the names inside the function - that's where you need to do the logging.

A possible initial implementation using inspect.getsourcelines and trying to find the return keyword. I guess that there might be many border cases where this fails, but here we go:

import inspect


def magic(function):
    return_lines = list()
    for line in inspect.getsourcelines(function)[0]:
        line = line.strip()
        if line.startswith("return"):
            return_lines.append(tuple(line[7:].split(", ")))
    return return_lines

>>> magic(foo)
[('a', 'b', '"c"')]
Related