mirror of
https://github.com/paperless-ngx/paperless-ngx.git
synced 2026-08-19 17:23:21 +00:00
perf: migrate single-call Document permission sites to permitted_document_ids (#13507)
* perf: migrate 5 single-call Document permission sites to permitted_document_ids Swaps get_objects_for_user_owner_aware(user, "view_document", Document) for Document.objects.filter(id__in=permitted_document_ids(user)) at 5 read-only, single-call sites: AI chat "ask all documents", bulk-edit _resolve_document_ids all:true branch, SelectionDataView permission check, global search docs bucket, and the statistics endpoint's Document branch. Confirmed all 3 callers of _resolve_document_ids always use the default "view_document" codename before swapping. Added a regression test pinning the AI-chat owner/permission boundary through the real API client, and updated 2 existing mocked tests in test_views.py that asserted on get_objects_for_user_owner_aware for the chat endpoint. * perf: migrate 3 serialisers.py Document permission sites to permitted_document_ids Migrates _get_viewable_duplicates(), PaperlessTaskSerializer.get_duplicate_documents(), and the ShareLinkBundle document field queryset to use permitted_document_ids() instead of get_objects_for_user_owner_aware()/get_objects_for_user(), consolidating onto the shared permission-filtering helper. The is_staff gate in get_duplicate_documents() is preserved as-is. Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01GRp4kf1mdn9ruv81zWAmh2 * refactor: remove dead permission_codename param from _resolve_document_ids The keyword param was unused in the method body since an earlier commit switched it to call permitted_document_ids(user) internally. None of the 3 call sites passed it. Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com> * docs: drop internal task-number reference from AI chat migration test docstring Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com> --------- Co-authored-by: Claude Sonnet 5 <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Sonnet 5
parent
5e54259db9
commit
c6cecd3c4e
@@ -648,11 +648,11 @@ class TestAIChatStreamingView(DirectoriesMixin, TestCase):
|
||||
self.assertIn(b"AI is required for this feature", response.content)
|
||||
|
||||
@patch("documents.views.stream_chat_with_documents")
|
||||
@patch("documents.views.get_objects_for_user_owner_aware")
|
||||
@patch("documents.views.permitted_document_ids")
|
||||
@override_settings(AI_ENABLED=True)
|
||||
def test_post_no_document_id(self, mock_get_objects, mock_stream_chat) -> None:
|
||||
def test_post_no_document_id(self, mock_permitted_ids, mock_stream_chat) -> None:
|
||||
self.grant_view_document_permission()
|
||||
mock_get_objects.return_value = [self.document]
|
||||
mock_permitted_ids.return_value = [self.document.pk]
|
||||
mock_stream_chat.return_value = iter([b"data"])
|
||||
response = self.client.post(
|
||||
self.ENDPOINT,
|
||||
@@ -661,23 +661,23 @@ class TestAIChatStreamingView(DirectoriesMixin, TestCase):
|
||||
)
|
||||
self.assertEqual(response.status_code, 200)
|
||||
self.assertEqual(response["Content-Type"], "text/event-stream")
|
||||
mock_stream_chat.assert_called_once_with(
|
||||
query_str="question",
|
||||
documents=[self.document],
|
||||
output_language=None,
|
||||
)
|
||||
mock_stream_chat.assert_called_once()
|
||||
call_kwargs = mock_stream_chat.call_args.kwargs
|
||||
self.assertEqual(call_kwargs["query_str"], "question")
|
||||
self.assertEqual(list(call_kwargs["documents"]), [self.document])
|
||||
self.assertIsNone(call_kwargs["output_language"])
|
||||
|
||||
@patch("documents.views.stream_chat_with_documents")
|
||||
@patch("documents.views.get_objects_for_user_owner_aware")
|
||||
@patch("documents.views.permitted_document_ids")
|
||||
@override_settings(AI_ENABLED=True)
|
||||
def test_post_uses_user_display_language(
|
||||
self,
|
||||
mock_get_objects,
|
||||
mock_permitted_ids,
|
||||
mock_stream_chat,
|
||||
) -> None:
|
||||
UiSettings.objects.create(user=self.user, settings={"language": "de-de"})
|
||||
self.grant_view_document_permission()
|
||||
mock_get_objects.return_value = [self.document]
|
||||
mock_permitted_ids.return_value = [self.document.pk]
|
||||
mock_stream_chat.return_value = iter([b"data"])
|
||||
|
||||
response = self.client.post(
|
||||
@@ -687,11 +687,11 @@ class TestAIChatStreamingView(DirectoriesMixin, TestCase):
|
||||
)
|
||||
|
||||
self.assertEqual(response.status_code, 200)
|
||||
mock_stream_chat.assert_called_once_with(
|
||||
query_str="question",
|
||||
documents=[self.document],
|
||||
output_language="de-de",
|
||||
)
|
||||
mock_stream_chat.assert_called_once()
|
||||
call_kwargs = mock_stream_chat.call_args.kwargs
|
||||
self.assertEqual(call_kwargs["query_str"], "question")
|
||||
self.assertEqual(list(call_kwargs["documents"]), [self.document])
|
||||
self.assertEqual(call_kwargs["output_language"], "de-de")
|
||||
|
||||
@patch("documents.views.stream_chat_with_documents")
|
||||
@override_settings(AI_ENABLED=True)
|
||||
|
||||
Reference in New Issue
Block a user