wagtail-localize icon indicating copy to clipboard operation
wagtail-localize copied to clipboard

TranslationSource uniqueness issue

Open krieghan opened this issue 2 years ago • 4 comments

We noted a traceback recently when editing pages. We're using:

wagtail==3.0.1 wagtail-localize==1.2.1

Traceback
Traceback (most recent call last):
  File "/usr/local/lib/python3.8/site-packages/django/core/handlers/exception.py", line 47, in inner
    response = get_response(request)
  File "/usr/local/lib/python3.8/site-packages/django/core/handlers/base.py", line 181, in _get_response
    response = wrapped_callback(request, *callback_args, **callback_kwargs)
  File "/usr/local/lib/python3.8/site-packages/sentry_sdk/integrations/django/views.py", line 67, in sentry_wrapped_callback
    return callback(request, *args, **kwargs)
  File "/usr/local/lib/python3.8/site-packages/django/views/decorators/cache.py", line 44, in _wrapped_view_func
    response = view_func(request, *args, **kwargs)
  File "/usr/local/lib/python3.8/site-packages/wagtail/admin/urls/__init__.py", line 161, in wrapper
    return view_func(request, *args, **kwargs)
  File "/usr/local/lib/python3.8/site-packages/wagtail/admin/auth.py", line 182, in decorated_view
    response = view_func(request, *args, **kwargs)
  File "/usr/local/lib/python3.8/site-packages/django/views/generic/base.py", line 70, in view
    return self.dispatch(request, *args, **kwargs)
  File "/usr/local/lib/python3.8/site-packages/wagtail/admin/views/pages/edit.py", line 341, in dispatch
    response = self.run_hook("before_edit_page", self.request, self.page)
  File "/usr/local/lib/python3.8/site-packages/wagtail/admin/views/generic/hooks.py", line 16, in run_hook
    result = fn(*args, **kwargs)
  File "/usr/local/lib/python3.8/site-packages/wagtail_localize/wagtail_hooks.py", line 259, in before_edit_page
    return edit_translation.edit_translation(request, translation, page)
  File "/usr/local/lib/python3.8/site-packages/wagtail_localize/views/edit_translation.py", line 912, in edit_translation
    locale_id=TranslationSource.objects.get(
  File "/usr/local/lib/python3.8/site-packages/django/db/models/manager.py", line 85, in manager_method
    return getattr(self.get_queryset(), name)(*args, **kwargs)
  File "/usr/local/lib/python3.8/site-packages/django/db/models/query.py", line 439, in get
    raise self.model.MultipleObjectsReturned(
wagtail_localize.models.TranslationSource.MultipleObjectsReturned: get() returned more than one TranslationSource -- it returned 2!

It was a minor emergency, and we had to delete a lot of the data in question, and we're not entirely sure how the data got into this state. We've been on the lookout for recurrences, but so far we haven't been able to reproduce it, and I haven't found any similar issues logged here. My question for your project is about potential uniqueness constraints. The statement which causes the exception is this:

        add_convert_to_alias_url = (
            Page.objects.filter(
                translation_key=instance.translation_key,
                locale_id=TranslationSource.objects.get(
                    object_id=instance.translation_key,
                    specific_content_type=instance.content_type_id,
                    translations__target_locale=instance.locale,
                ).locale_id,
            )
            .exclude(pk=instance.pk)
            .exists()
        )

The call to get a TranslationSource is assuming that there will be only one for each object_id, specific_content_type, and target_locale. Is enforcing uniqueness on this model possible, or desirable?

krieghan avatar Nov 30 '22 16:11 krieghan