Restrict the creation of objects in python - part 2

Restrict the Creation of Objects - Step 2

Now only methods of Manager can construct the __Worker. However, the restriction was that __Worker can be created only in the hire method.

Find the Caller of a Function

To enforce this we will use the following function which return the caller of the function which it invoked in:

Sample #3 - _find_callee
 import traceback
 import sys

 def _find_callee():
     frames = traceback.extract_stack() # <== D
     return frames[-3].name if len(frames) >= 2 else ""

Let's see why this will work. Suppose we the following code:

Sample #3 - _find_callee example
 def function_0():
     function_1()          # <== B
 def function_1():
     print(_find_callee()) # <== C
 function_0()              # <== A

The following shows the state of the call stack when A,B,C and D statements are executed:

At D - The traceback.extract_stack returns the current traceback from the current stack frame. As we can see, the caller of the function_1 which call _find_callee is located at position 3 from the end of the stack.

Checking the Caller

Now, with this function at hand, we can update the __Worker constructor:

Sample #3 - Checking the callee
 class Manager:
     class __Worker:
         def __init__(self,name):
             if _find_callee() != 'hire':
                 raise BaseException('Authorization error : only Manager.hire can construct me')
             self.name = name
         ...
     ...

Now, only a fuction named hire can construct __Worker as the test2.py shows:

Sample #3 - test
 import world
 print( "I can create a worker : {0}".format(str(world.Manager._Manager__Worker('1')) ) )
Sample #3 - test output
 $ python test2.py
 Traceback (most recent call last):
   File "test2.py", line 2, in <module>
     print( "I can create a worker : {0}".format(str(world.Manager._Manager__Worker('1')) ) )
   File "F:/03/world.py", line 12, in __init__
     raise BaseException('Authorization error : only Manager.hire can construct me')
 BaseException: Authorization error : only Manager.hire can construct me

Note, that the user can read the above code and bypass the our authorization system by calling the construction code from a function named hire.

Summery

Although, the authorization system can be easily skipped, It valuable tool for the programmers who use our module to avoid accidents and using our inner implementation details.