AssertionError: View function mapping is overwriting an existing endpoint function: main

This same issue happened to me when I had more than one API function in the module and tried to wrap each function with 2 decorators:

  1. @app.route()
  2. My custom @exception_handler decorator

I got this same exception because I tried to wrap more than one function with those two decorators:

@app.route("/path1")
@exception_handler
def func1():
    pass

@app.route("/path2")
@exception_handler
def func2():
    pass

Specifically, it is caused by trying to register a few functions with the name wrapper:

def exception_handler(func):
  def wrapper(*args, **kwargs):
    try:
        return func(*args, **kwargs)
    except Exception as e:
        error_code = getattr(e, "code", 500)
        logger.exception("Service exception: %s", e)
        r = dict_to_json({"message": e.message, "matches": e.message, "error_code": error_code})
        return Response(r, status=error_code, mimetype='application/json')
  return wrapper

Changing the name of the function solved it for me (wrapper.__name__ = func.__name__):

def exception_handler(func):
  def wrapper(*args, **kwargs):
    try:
        return func(*args, **kwargs)
    except Exception as e:
        error_code = getattr(e, "code", 500)
        logger.exception("Service exception: %s", e)
        r = dict_to_json({"message": e.message, "matches": e.message, "error_code": error_code})
        return Response(r, status=error_code, mimetype='application/json')
  # Renaming the function name:
  wrapper.__name__ = func.__name__
  return wrapper

Then, decorating more than one endpoint worked.


Your view names need to be unique even if they are pointing to the same view method.

app.add_url_rule('/',
                 view_func=Main.as_view('main'),
                 methods = ['GET'])

app.add_url_rule('/<page>/',
                 view_func=Main.as_view('page'),
                 methods = ['GET'])

For users that use @app.route it is better to use the key-argument endpoint rather then chaning the value of __name__ like Roei Bahumi stated. Taking his example will be:

@app.route("/path1", endpoint='func1')
@exception_handler
def func1():
    pass

@app.route("/path2", endpoint='func2')
@exception_handler
def func2():
    pass

Tags:

Python

Flask