title: Issues passing self to class decorator in python
body: <p>I am new to decorators but ideally I wan to use them to simply define a bunch of class functions within class OptionClass, each representing some particular option with a name and description and if it's required. I don't want to modify the operation of the class function at all if that makes sense, I only want to use the decorator to define name, description, and if it's required.</p>
  
  <p>Problem 1: I construct an OptionClass() and I want to call it's option_1. When I do this I receive a TypeError as the <strong>call</strong> decorator is not receiving an instance of OptionClass. Why is this? When I call option_1 passing the instance of OptionClass() it works.  How do I call option_1 without needing to always pass the instance as self.
  The error when received is: </p>
  
  <pre><code>Traceback (most recent call last):
    File "D:/OneDrive_P/OneDrive/projects/python/examples/dec_ex.py", line 110, in &lt;module&gt;
      print(a.option_1("test")) # TypeError: option1() missing 1 required positional argument: 'test_text'
     File "D:/OneDrive_P/OneDrive/projects/python/examples/dec_ex.py", line 80, in __call__
      return self.function_ptr(*args, **kwargs)
  TypeError: option_1() missing 1 required positional argument: 'test_text'
  </code></pre>
  
  <p>Problem 2: How would I run or call methods on the decorator to set_name, set_description, set_required?</p>
  
  <p>Problem 3: Although this is a sample I intend to code an option class using async functions and decorate them. Do I need to make the decorator <strong>call</strong> be <code>async def __call__()</code> or is it fine since it's just returning the function?</p>
  
  <pre><code>class option_decorator(object):
      def __init__(self, function_pt):
          self.function_ptr = function_pt
          self.__required = True
          self.__name = ""
          self.__description = ""
  
      def set_name(self, text):
          self.__name = text
  
      def set_description(self, text):
          self.__description = text
  
      def set_required(self,flag:bool):
          self.__required = flag
  
      def __bool__(self):
          """returns if required"""
          return self.__required
  
      def __call__(self, *args, **kwargs):
          return self.function_ptr(*args, **kwargs)
  
      def __str__(self):
          """prints a description and name of the option """
          return "{} - {}".format(self.__name, self.__description)
  
  
  class OptionClass(object):
      """defines a bunch of options"""
      @option_decorator
      def option_1(self,test_text):
          return("option {}".format(test_text))
  
      @option_decorator
      def option_2(self):
          print("option 2")
  
      def get_all_required(self):
          """would return a list of option functions within the class that have their decorator required flag set to true"""
          pass
  
      def get_all_available(self):
          """would return all options regardless of required flag set"""
          pass
  
      def print_all_functions(self):
          """would call str(option_1) and print {} - {} for example"""
          pass
  
  a = OptionClass()
  print(a.option_1("test")) # TypeError: option1() missing 1 required positional argument: 'test_text'
  print(a.option_1(a,"test")) #Prints: option test
  </code></pre>