Authenticating an internal API with Flask
Just because you don't have many people using this API now, this does not mean that this will always be the case.

In addition, you might want to discriminate between the users of the API for various reasons:


To know how many there actually are
To know which user/application is generating all those requests suddenly
To rate-throttle some of them if needed
To disallow access for someone who abused the API or just left the company or an obsolete application


I would at least set this up in a very barebone way to have different API keys. For now you can just hardcode them in a dictionary in the config file, but this allows you to easily extract them to a database at some future point (which may never come). You can manually add users when needed (if it is only a few), or write a page that adds a user (if the manual task becomes too much).

In your config just have something like this:

config.yml

api_keys:
    08zEk8IC0le3I0kPwSF1g4XU9R5WgbpUq2vZkZ0pkQU: User 1
    ZtRE7FXwZdtCLMfFHWPTom7_d-4XFbXEkHR5bIdG2TM: User 2
    Wg1vaDs8uqFbYtNDsJ8H3gKjl_oI0T_O6Jg8qNLWJcU: App 1
    ...


Your code needs to be only minimally changed:

auth.py

def valid_auth(func):
    @wraps(func)
    def func_wrapper(*args, **kwargs):
        if 'x-api-key' not in request.headers:
            return "Credentials not present in request", 401
        elif request.headers['x-api-key'] not in config['api_keys']:
            return "Credentials not valid", 401
        else:
            return func(*args, **kwargs)
    return func_wrapper


Note that () around tuples are not needed in return since it is an expression and not a function.



Returning a tuple of message, status code to raise in one case and the result of the function in another case can also be a potential source of bugs. If the using code expects the return value to be a single value, checking for there being two and those two being a string and an int is not very fool-proof. Even worse if the function actually also returns a string and int tuple.

Instead, raise exceptions, which you can then deal with in api_function. Use custom classes inheriting from Exception:

class NoCredentials(Exception):
    status_code = 401

class WrongCredentials(Exception):
    status_code = 401

...
if 'x-api-key' not in request.headers:
    raise NoCredentials("Credentials not present in request")


This page in the official documentation explains in more detail how to use custom exceptions correctly in flask.