16
votes

I'm trying to setup a simple API using Django Rest Framework, the problem is that my API does not have any database but the framework won't work without database setting.

Here is my Django Rest Framework configuration in settings.py:

INSTALLED_APPS = [
    'provider',
    'django_nose',
    'rest_framework',
    'django.contrib.contenttypes',
]

REST_FRAMEWORK = {
    'DEFAULT_AUTHENTICATION_CLASSES': [],
    'DEFAULT_PERMISSION_CLASSES': [],
}

The error which I got is:

ImproperlyConfigured("settings.DATABASES is improperly configured. "django.core.exceptions.ImproperlyConfigured: settings.DATABASES is improperly configured. Please supply the ENGINE value. Check settings documentation for more details.

Is there any minimal settings which does not include django.contrib.contenttypes and django.contrib.auth?

4
When did you get that error ? Why do you need contenttypes application ? - Linovia
Note that I have some API that don't use DB and haven't ran into that issue. - Linovia
@Linovia I don't need contenttypes application and auth application, but it won't work without them, can you post a minimal django rest framework settings which does not hav any DB and will be only used as an API? - Kian Ahrabian
@Linovia It occurs when the view is trying to perform authentication - Kian Ahrabian
You can't have default authentication without DB. You'll have to write your own. - Linovia

4 Answers

18
votes

The actual cause of the problem is that DRF trys to add a user attribute to the request. Briefly mentioned in the documentation, the mechanism is as follows:

How authentication is determined

If no class authenticates, request.user will be set to an instance of django.contrib.auth.models.AnonymousUser

So it needed the django.contrib.auth application to run correctly, consequently django.contrib.auth requires a working configuration of Database to be able to perform.

The solution to this problem is to set the settings UNAUTHENTICATED_USER property to None.

Configuration will be like this after the changes:

REST_FRAMEWORK = {
    'DEFAULT_AUTHENTICATION_CLASSES': [],
    'DEFAULT_PERMISSION_CLASSES': [],
    'UNAUTHENTICATED_USER': None,
}
13
votes

If you are really forced to use a database but you don't want to, you can use :memory: with the SQLite backend, like this:

DATABASES = {
    'default': {
        'ENGINE': 'django.db.backends.sqlite3',
        'NAME': ':memory:',
    }
}

This uses an in-memory database, so that your filesystem won't be touched.

Because memory is volatile, you might need to run migrations automatically every time your web app starts.

2
votes

You don't have any option. DATABASES dict should be in settings.py. You can use this:

DATABASES = {
    'default': {
        'ENGINE': 'django.db.backends.sqlite3',
        'NAME': os.path.join(BASE_DIR, 'db.sqlite3'),
    }
}
-2
votes

[not tested] maybe you could use a dummy backend. I see there's one from django:

DATABASES = {
    'default': {
        'ENGINE': 'django.db.backends.dummy',
    }
}