diff --git a/.github/workflows/testing.yml b/.github/workflows/testing.yml index e8a9942c8d..9a1c284e51 100644 --- a/.github/workflows/testing.yml +++ b/.github/workflows/testing.yml @@ -35,6 +35,37 @@ jobs: coverage report -m bash <(curl -s https://codecov.io/bash) + test_check_unapplied_migrations_middleware: + name: test CheckUnappliedMigrationsMiddleware + runs-on: ubuntu-latest + strategy: + matrix: + python-version: [3.7] + + steps: + - uses: actions/checkout@v2 + + - name: Set up Python ${{ matrix.python-version }} + uses: actions/setup-python@v1 + with: + python-version: ${{ matrix.python-version }} + + - name: Install Python dependencies + run: | + sudo apt-get install libkrb5-dev gettext + pip install -r requirements/devel.txt + pushd tcms/ && npm install && popd + + - name: Run test + run: | + export LANG=en-us + ./manage.py migrate --settings=$(DJANGO_SETTINGS_MODULE) auth + ./manage.py migrate --settings=$(DJANGO_SETTINGS_MODULE) sites + ./manage.py migrate --settings=$(DJANGO_SETTINGS_MODULE) sessions + + export TEST_CHECK_UNAPPLIED_MIGRATIONS_MIDDLEWARE=1 + make test + without_internal_bugtracker: name: without internal bugtracker runs-on: ubuntu-latest diff --git a/tcms/core/middleware.py b/tcms/core/middleware.py index 2464b96d91..07ea60a95b 100644 --- a/tcms/core/middleware.py +++ b/tcms/core/middleware.py @@ -7,6 +7,8 @@ from django.utils.deprecation import MiddlewareMixin from django.utils.safestring import mark_safe from django.utils.translation import gettext_lazy as _ +from django.db import DEFAULT_DB_ALIAS, connections +from django.db.migrations.executor import MigrationExecutor class CsrfDisableMiddleware(MiddlewareMixin): @@ -29,6 +31,26 @@ def process_request(self, request): 'change it') % { 'doc_url': doc_url, 'admin_url': reverse('admin:sites_site_change', args=[site.pk]) - } + } + ) + ) + + +class CheckUnappliedMigrationsMiddleware(MiddlewareMixin): + def process_request(self, request): + doc_url = ('https://kiwitcms.readthedocs.io/en/latest/installing_' + 'docker.html#initial-configuration-of-running-container') + executor = MigrationExecutor(connections[DEFAULT_DB_ALIAS]) + plan = executor.migration_plan(executor.loader.graph.leaf_nodes()) + if plan: + messages.add_message( + request, + messages.ERROR, + mark_safe( + _('You have %(unapplied_migration_count)s unapplied migration(s). ' + 'See documentation') % { + "unapplied_migration_count": len(plan), + "doc_url": doc_url, + } ) ) diff --git a/tcms/core/tests/test_middleware.py b/tcms/core/tests/test_middleware.py new file mode 100644 index 0000000000..8eac9dbd91 --- /dev/null +++ b/tcms/core/tests/test_middleware.py @@ -0,0 +1,23 @@ +import os +import unittest +from django.test import TransactionTestCase +from django.contrib.messages import get_messages + + +@unittest.skipUnless( + os.getenv('TEST_CHECK_UNAPPLIED_MIGRATIONS_MIDDLEWARE'), + 'CheckUnappliedMigrationsMiddleware testing not enabled') +class TestCheckUnappliedMigrationsMiddleware(TransactionTestCase): + @classmethod + def setUpClass(cls): + cls.unapplied_migration_message = ('You have 41 unapplied migration(s)' + '. See documentat' + 'ion') + + def test_unapplied_migrations(self): + response = self.client.get('/') + messages = list(get_messages(response.wsgi_request)) + self.assertEqual(str(messages[0]), self.unapplied_migration_message) diff --git a/tcms/settings/common.py b/tcms/settings/common.py index c9933ccc45..471f9aa72c 100644 --- a/tcms/settings/common.py +++ b/tcms/settings/common.py @@ -130,6 +130,7 @@ 'global_login_required.GlobalLoginRequiredMiddleware', 'simple_history.middleware.HistoryRequestMiddleware', 'tcms.core.middleware.CheckSettingsMiddleware', + 'tcms.core.middleware.CheckUnappliedMigrationsMiddleware' ]