George Sotiropoulos
George Sotiropoulos

Reputation: 2133

python monkey patch a new class and import it

I want to monkey patch a new class and then import that class but I get an error ModuleNotFoundError. At the same time I can use the new patched function. I believe that I miss how to add it in the "init" file.

See the following simplified example:

import numpy
class wrong_functions():
    def wrong_add(num1, num2):
        return num1 + num2 + 1

numpy.random.wrong_functions = wrong_functions
numpy.random.wrong_functions.wrong_add(1,1) # works
from numpy.random.wrong_functions import wrong_add # does not work
from numpy.random.wrong_functions import * # does not work

What do you think? Is that possible?

Upvotes: 0

Views: 638

Answers (1)

crissal
crissal

Reputation: 2647

This is because of the import system.

Reading through the doc, you can find this paragraph:

[...] the statement from spam.ham import eggs, sausage as saus results in

_temp = __import__('spam.ham', globals(), locals(), ['eggs', 'sausage'], 0)
eggs = _temp.eggs
saus = _temp.sausage

The problem is: what does __import__() does?

The import statement combines two operations; it searches for the named module, then it binds the results of that search to a name in the local scope. [...]

A direct call to __import__() performs only the module search and, if found, the module creation operation.

So, when you re-import the module, your customization will be lost.

To ensure it stays on, you can import numpy as np and then, when using np - after you assing this new class - you can always access wrong_add.

>>> import numpy as np
>>> np.random.wrong_functions = wrong_functions
>>> np.random.wrong_function.wrong_add(1, 1)
3

EDIT: If you need/want to just call wrong_add instead of full package path to function, you can always assign it to a variable.

>>> wrong_add = np.random.wrong_function.wrong_add
>>> wrong_add(2, 2)
5

Upvotes: 1

Related Questions