@Override
  public PyType getType(@NotNull TypeEvalContext context, @NotNull TypeEvalContext.Key key) {
    if (getOperator() == PyTokenTypes.NOT_KEYWORD) {
      final PyExpression operand = getOperand();
      if (operand != null) {
        final PyType operandType = context.getType(operand);
        return (operandType instanceof PyNarrowedType) ? ((PyNarrowedType)operandType).negate()
                                                       : PyBuiltinCache.getInstance(this).getBoolType();
      }
      return PyBuiltinCache.getInstance(this).getBoolType();
    }
    final boolean isAwait = getOperator() == PyTokenTypes.AWAIT_KEYWORD;
    if (isAwait) {
      final PyExpression operand = getOperand();
      if (operand != null) {
        final PyType operandType = context.getType(operand);
        final Ref<PyType> type = getGeneratorReturnType(operandType);
        if (type != null) {
          return type.get();
        }
      }
    }

    return StreamEx
      .of(PyCallExpressionHelper.mapArguments(this, PyResolveContext.defaultContext(context)))
      .map(PyCallExpression.PyArgumentsMapping::getCallableType)
      .nonNull()
      .map(callableType -> callableType.getCallType(context, this))
      .map(callType -> isAwait ? Ref.deref(getGeneratorReturnType(callType)) : callType)
      .collect(PyTypeUtil.toUnion());
  }
@Override
  public PyType getType(@NotNull TypeEvalContext context, @NotNull TypeEvalContext.Key key)