diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index 8abe853..4403685 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -10,7 +10,7 @@ jobs: runs-on: ubuntu-latest strategy: matrix: - python-version: ['3.6', '3.9', '3.10'] + python-version: ['3.7', '3.8', '3.9', '3.10'] xapian-version: ['1.4.18'] steps: @@ -41,13 +41,17 @@ jobs: runs-on: ubuntu-latest strategy: matrix: - python-version: ['3.6', '3.9'] - django-version: ['2.2', '3.1', '3.2'] + python-version: ['3.7', '3.8', '3.9', '3.10'] + django-version: ['2.2', '3.2', '4.0'] xapian-version: ['1.4.18'] - include: + exclude: # Django added python 3.10 support in 3.2.9 - python-version: '3.10' - django-version: '3.2' + django-version: '2.2' + xapian-version: '1.4.18' + # Django dropped python 3.7 support in 4.0 + - python-version: '3.7' + django-version: '4.0' xapian-version: '1.4.18' steps: diff --git a/CHANGELOG.rst b/CHANGELOG.rst index 7cb2c55..47026bb 100644 --- a/CHANGELOG.rst +++ b/CHANGELOG.rst @@ -2,6 +2,11 @@ xapian-haystack Changelog ========================= +Unreleased +---------- + +- Dropped support for Python 3.6. + v3.0.1 (2021-11-12) ------------------- diff --git a/setup.py b/setup.py index ccd924f..871773d 100644 --- a/setup.py +++ b/setup.py @@ -18,11 +18,11 @@ setup( 'License :: OSI Approved :: GNU General Public License (GPL)', 'Topic :: Internet :: WWW/HTTP :: Indexing/Search', 'Framework :: Django', + 'Programming Language :: Python :: 3 :: Only', ], author='Jorge C. Leitão', author_email='jorgecarleitao@gmail.com', - url='http://github.com/notanumber/xapian-haystack', - download_url='http://github.com/notanumber/xapian-haystack/tarball/2.1.0', + url='https://github.com/notanumber/xapian-haystack', license='GPL2', py_modules=['xapian_backend'], install_requires=[ diff --git a/tests/xapian_tests/tests/test_management_commands.py b/tests/xapian_tests/tests/test_management_commands.py new file mode 100644 index 0000000..da1ed2a --- /dev/null +++ b/tests/xapian_tests/tests/test_management_commands.py @@ -0,0 +1,84 @@ +from unittest import TestCase + +from django.core.management import call_command + +from ..models import BlogEntry +from ..search_indexes import BlogSearchIndex +from .test_backend import BackendFeaturesTestCase, HaystackBackendTestCase + + +class ManagementCommandTestCase(HaystackBackendTestCase, TestCase): + + NUM_BLOG_ENTRIES = 20 + + def get_index(self): + return BlogSearchIndex() + + def setUp(self): + super().setUp() + + self.sample_objs = [] + + for i in range(1, self.NUM_BLOG_ENTRIES + 1): + entry = BackendFeaturesTestCase.get_entry(i) + self.sample_objs.append(entry) + entry.save() + + def verify_indexed_document_count(self, expected): + count = self.backend.document_count() + self.assertEqual(count, expected) + + def verify_indexed_documents(self): + """Confirm that the documents in the search index match the database""" + + count = self.backend.document_count() + self.assertEqual(count, self.NUM_BLOG_ENTRIES) + + pks = set(BlogEntry.objects.values_list("pk", flat=True)) + doc_ids = set() + database = self.backend._database() + for pk in pks: + xapian_doc = database.get_document(pk) + doc_id = xapian_doc.get_docid() + doc_ids.add(doc_id) + database.close() + + self.assertSetEqual(pks, doc_ids) + + def test_clear(self): + self.backend.update(self.index, BlogEntry.objects.all()) + self.verify_indexed_documents() + + call_command("clear_index", interactive=False, verbosity=0) + self.verify_indexed_document_count(0) + + def test_update(self): + self.verify_indexed_document_count(0) + + call_command("update_index", verbosity=0) + self.verify_indexed_documents() + + def test_rebuild(self): + self.verify_indexed_document_count(0) + + call_command("rebuild_index", interactive=False, verbosity=0) + self.verify_indexed_documents() + + def test_remove(self): + self.verify_indexed_document_count(0) + + call_command("update_index", verbosity=0) + self.verify_indexed_documents() + + # Remove three instances. + three_pks = BlogEntry.objects.all()[:3].values_list("pk", flat=True) + BlogEntry.objects.filter(pk__in=three_pks).delete() + self.verify_indexed_document_count(self.NUM_BLOG_ENTRIES) + + # Plain ``update_index`` doesn't fix it. + call_command("update_index", verbosity=0) + self.verify_indexed_document_count(self.NUM_BLOG_ENTRIES) + + # … but remove does: + call_command("update_index", remove=True, verbosity=0) + self.verify_indexed_document_count(self.NUM_BLOG_ENTRIES - 3) diff --git a/xapian_backend.py b/xapian_backend.py index f48b002..f94e51a 100755 --- a/xapian_backend.py +++ b/xapian_backend.py @@ -152,13 +152,7 @@ class XapianSearchBackend(BaseSearchBackend): `SearchBackend` defines the Xapian search backend for use with the Haystack API for Django search. - It uses the Xapian Python bindings to interface with Xapian, and as - such is subject to this bug: when - Django is running with mod_python or mod_wsgi under Apache. - - Until this issue has been fixed by Xapian, it is neccessary to set - `WSGIApplicationGroup to %{GLOBAL}` when using mod_wsgi, or - `PythonInterpreter main_interpreter` when using mod_python. + It uses the Xapian Python bindings to interface with Xapian. In order to use this backend, `PATH` must be included in the `connection_options`. This should point to a location where you would your