4

I'm trying to write and run tests for a Django project, but running

$ python manage.py test apps/actions/tests

gives the following error:

django.db.utils.ProgrammingError: relation "django_content_type" does not exist

This only happens when I try to run the tests. Running python manage.py runserver gives me no error whatsoever and everything works fine. I'm using Django 3.1.3

Here's the full traceback:

Traceback (most recent call last):
  File "C:\Users\Kamil\Projekty\random\venv\lib\site-packages\django\db\backends\utils.py", line 84, in _execute
    return self.cursor.execute(sql, params)
psycopg2.errors.UndefinedTable: relation "django_content_type" does not exist


The above exception was the direct cause of the following exception:

Traceback (most recent call last):
  File "C:\Users\Kamil\Projekty\random\manage.py", line 22, in <module>
    main()
  File "C:\Users\Kamil\Projekty\random\manage.py", line 18, in main
    execute_from_command_line(sys.argv)
  File "C:\Users\Kamil\Projekty\random\venv\lib\site-packages\django\core\management\__init__.py", line 401, in execute_from_command_line
    utility.execute()
  File "C:\Users\Kamil\Projekty\random\venv\lib\site-packages\django\core\management\__init__.py", line 395, in execute
    self.fetch_command(subcommand).run_from_argv(self.argv)
  File "C:\Users\Kamil\Projekty\random\venv\lib\site-packages\django\core\management\commands\test.py", line 23, in run_from_argv
    super().run_from_argv(argv)
  File "C:\Users\Kamil\Projekty\random\venv\lib\site-packages\django\core\management\base.py", line 330, in run_from_argv
    self.execute(*args, **cmd_options)
  File "C:\Users\Kamil\Projekty\random\venv\lib\site-packages\django\core\management\base.py", line 371, in execute
    output = self.handle(*args, **options)
  File "C:\Users\Kamil\Projekty\random\venv\lib\site-packages\django\core\management\commands\test.py", line 53, in handle
    failures = test_runner.run_tests(test_labels)
  File "C:\Users\Kamil\Projekty\random\venv\lib\site-packages\django\test\runner.py", line 695, in run_tests
    old_config = self.setup_databases(aliases=databases)
  File "C:\Users\Kamil\Projekty\random\venv\lib\site-packages\django\test\runner.py", line 614, in setup_databases
    return _setup_databases(
  File "C:\Users\Kamil\Projekty\random\venv\lib\site-packages\django\test\utils.py", line 170, in setup_databases
    connection.creation.create_test_db(
  File "C:\Users\Kamil\Projekty\random\venv\lib\site-packages\django\db\backends\base\creation.py", line 72, in create_test_db
    call_command(
  File "C:\Users\Kamil\Projekty\random\venv\lib\site-packages\django\core\management\__init__.py", line 168, in call_command
    return command.execute(*args, **defaults)
  File "C:\Users\Kamil\Projekty\random\venv\lib\site-packages\django\core\management\base.py", line 371, in execute
    output = self.handle(*args, **options)
  File "C:\Users\Kamil\Projekty\random\venv\lib\site-packages\django\core\management\base.py", line 85, in wrapped
    res = handle_func(*args, **kwargs)
  File "C:\Users\Kamil\Projekty\random\venv\lib\site-packages\django\core\management\commands\migrate.py", line 214, in handle
    self.sync_apps(connection, executor.loader.unmigrated_apps)
  File "C:\Users\Kamil\Projekty\random\venv\lib\site-packages\django\core\management\commands\migrate.py", line 352, in sync_apps
    self.stdout.write('    Running deferred SQL...')
  File "C:\Users\Kamil\Projekty\random\venv\lib\site-packages\django\db\backends\base\schema.py", line 115, in __exit__
    self.execute(sql)
  File "C:\Users\Kamil\Projekty\random\venv\lib\site-packages\django\db\backends\base\schema.py", line 142, in execute
    cursor.execute(sql, params)
  File "C:\Users\Kamil\Projekty\random\venv\lib\site-packages\django\db\backends\utils.py", line 66, in execute
    return self._execute_with_wrappers(sql, params, many=False, executor=self._execute)
  File "C:\Users\Kamil\Projekty\random\venv\lib\site-packages\django\db\backends\utils.py", line 75, in _execute_with_wrappers
    return executor(sql, params, many, context)
  File "C:\Users\Kamil\Projekty\random\venv\lib\site-packages\django\db\backends\utils.py", line 84, in _execute
    return self.cursor.execute(sql, params)
  File "C:\Users\Kamil\Projekty\random\venv\lib\site-packages\django\db\utils.py", line 90, in __exit__
    raise dj_exc_value.with_traceback(traceback) from exc_value
  File "C:\Users\Kamil\Projekty\random\venv\lib\site-packages\django\db\backends\utils.py", line 84, in _execute
    return self.cursor.execute(sql, params)
django.db.utils.ProgrammingError: relation "django_content_type" does not exist

I have already tried deleting and recreating my migrations. I have django.contrib.contenttypes in my INSTALLED_APPS. Traceback doesn't point me anywhere specific in my code, so I have no clue where to look.

Here's the output of python manage.py showmigrations if that helps.

actions
 [X] 0001_initial
admin
 [X] 0001_initial
 [X] 0002_logentry_remove_auto_add
 [X] 0003_logentry_add_action_flag_choices
auth
 [X] 0001_initial
 [X] 0002_alter_permission_name_max_length
 [X] 0003_alter_user_email_max_length
 [X] 0004_alter_user_username_opts
 [X] 0005_alter_user_last_login_null
 [X] 0006_require_contenttypes_0002
 [X] 0007_alter_validators_add_error_messages
 [X] 0008_alter_user_username_max_length
 [X] 0009_alter_user_last_name_max_length
 [X] 0010_alter_group_name_max_length
 [X] 0011_update_proxy_permissions
 [X] 0012_alter_user_first_name_max_length
contenttypes
 [X] 0001_initial
 [X] 0002_remove_content_type_name
guardian
 [X] 0001_initial
 [X] 0002_generic_permissions_index
integrations
 [X] 0001_initial
links
 [X] 0001_initial
sessions
 [X] 0001_initial
triggers
 [X] 0001_initial
users
 [X] 0001_initial
workers
 [X] 0001_initial
exler
  • 93
  • 9

3 Answers3

4

I figured it out. I didn't run makemigration <app> for one of my apps which used the from django.contrib.contenttypes.models import ContentType model.

Somehow it didn't matter when running the local server via runserver, but did not pass when running the test command.

exler
  • 93
  • 9
0

This could also mean, the db is not accessible, say we override the setup_database method of the DiscoverTestRunner class, we will encounter the same error.

0

Not directly relevant for the OP, but the following edge case caused the exact same error and traceback:

In one of our legacy test suites, a "test-only" model is defined, without any migrations, but with a foreign key to ContentType and a GenericForeignKey (a generic relation). This test-only model obviously depends on the django_content_type table.

For some reason, this is not a problem if we run tests using a local SQLite database (in memory): all tests run normally.

However, after switching to a local PostgreSQL database, we get the error when trying to run tests:

django.db.utils.ProgrammingError: relation "django_content_type" does not exist

Like the OP, manage.py migrate and runserver work without issue. We also confirmed that django can create and drop the test database, so the PostgreSQL database configuration and access privileges are fine.

The problem arises when Django tries to create the test-database tables, in the syncdb phase, because Django first tries to create tables for models that have no migrations: In our case, one of the models without migrations actually depends on the ContentType model, which does require a migration.

One workaround is to create migrations for the test-only models, e.g. as described here.

I'm not sure yet why this error does not arise when using SQLite.

(Django 3.2, psycopg2 2.8, PostgreSQL 12)

djvg
  • 11,722
  • 5
  • 72
  • 103