docs: def maybe_coroutine(decide):
      """
      Either be a coroutine or not.
  
      Use as a decorator:
      @maybe_coroutine(lambda maybeAPromise: return isinstance(maybeAPromise, Promise))
      def foo(maybeAPromise):
          result = yield maybeAPromise
          print("hello")
          return result
  
      The function passed should be a generator yielding either only Promises or whatever
      you feel like.
      The decide parameter must be a function which gets called with the same parameters as
      the function to decide whether this is a coroutine or not.
      Using this it is possible to either make the function a coroutine or not based on a
      parameter to the function call.
      Let's explain the example above:
  
      # If the maybeAPromise is an instance of Promise,
      # we want the foo function to act as a coroutine.
      # If the maybeAPromise is not an instance of Promise,
      # we want the foo function to act like any other normal synchronous function.
      @maybe_coroutine(lambda maybeAPromise: return isinstance(maybeAPromise, Promise))
      def foo(maybeAPromise):
          # If isinstance(maybeAPromise, Promise), foo behaves like a coroutine,
          # thus maybeAPromise will get resolved asynchronously and the result will be
          # pushed back here.
          # Otherwise, foo behaves like no_coroutine,
          # just pushing the exact value of maybeAPromise back into the generator.
          result = yield maybeAPromise
          print("hello")
          return result
      """
  
      def _maybe_coroutine(f):
          @functools.wraps(f)
          def __maybe_coroutine(*args, **kwargs):
              if decide(*args, **kwargs):
                  return coroutine(f)(*args, **kwargs)
              else:
                  return no_coroutine(f)(*args, **kwargs)
          return __maybe_coroutine
      return _maybe_coroutine