From 1e4bf50d57df2c6a8f04d22fa4c88423fcdfa778 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o=20Moraes?= Date: Mon, 3 Aug 2026 16:43:21 -0300 Subject: [PATCH] =?UTF-8?q?Troca=20custom=20manager=20por=20fun=C3=A7?= =?UTF-8?q?=C3=A3o=20utilit=C3=A1ria=20de=20visibilidade?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Atende à revisão do PR: substitui a subclasse SessaoPlenariaQuerySet e o método .visiveis_para() por uma função restringe_sessoes_visiveis(qs, user), chamada como wrapper nos pontos de acesso público. Mantém a mesma regra de filtragem e o comportamento de fundir as cadeias de filter em um único SQL. --- sapl/sessao/models.py | 38 ++++++++++++--------------- sapl/sessao/tests/test_sessao_view.py | 9 ++++--- sapl/sessao/views.py | 12 +++++---- 3 files changed, 30 insertions(+), 29 deletions(-) diff --git a/sapl/sessao/models.py b/sapl/sessao/models.py index 054c8cf62..ad71be072 100644 --- a/sapl/sessao/models.py +++ b/sapl/sessao/models.py @@ -153,26 +153,24 @@ def anexo_upload_path(instance, filename): # return get_sessao_media_path(instance, 'anexo', filename) -class SessaoPlenariaQuerySet(models.QuerySet): - - def visiveis_para(self, user): - """Restringe às sessões que o usuário pode ver na consulta pública. - - Usuário autenticado enxerga todas. Para o público, ficam ocultas as - sessões cadastradas com antecedência, ou seja, as marcadas como não - iniciadas e sem pauta publicada. - - `iniciada` nulo conta como visível: o default do campo só surgiu na - migração 0027, que não preencheu as linhas já existentes, então bases - antigas têm sessões realizadas com o campo em NULL. - """ - if user.is_authenticated: - return self +def restringe_sessoes_visiveis(qs, user): + """Restringe o queryset às sessões visíveis na consulta pública. + + Usuário autenticado enxerga todas. Para o público, ficam ocultas as + sessões cadastradas com antecedência, ou seja, as marcadas como não + iniciadas e sem pauta publicada. + + `iniciada` nulo conta como visível: o default do campo só surgiu na + migração 0027, que não preencheu as linhas já existentes, então bases + antigas têm sessões realizadas com o campo em NULL. + """ + if user.is_authenticated: + return qs - return self.filter( - Q(publicar_pauta=True) | - Q(iniciada=True) | - Q(iniciada__isnull=True)) + return qs.filter( + Q(publicar_pauta=True) | + Q(iniciada=True) | + Q(iniciada__isnull=True)) class SessaoPlenaria(models.Model): @@ -277,8 +275,6 @@ class SessaoPlenaria(models.Model): ) ) - objects = SessaoPlenariaQuerySet.as_manager() - class Meta: verbose_name = _('Sessão Plenária') verbose_name_plural = _('Sessões Plenárias') diff --git a/sapl/sessao/tests/test_sessao_view.py b/sapl/sessao/tests/test_sessao_view.py index 267903843..70bb920a9 100644 --- a/sapl/sessao/tests/test_sessao_view.py +++ b/sapl/sessao/tests/test_sessao_view.py @@ -11,7 +11,8 @@ from sapl.sessao.models import (SessaoPlenaria, TipoSessaoPlenaria, IntegranteMesa, SessaoPlenariaPresenca, JustificativaAusencia, ExpedienteSessao, TipoExpediente, ExpedienteMateria, - Orador, OcorrenciaSessao) + Orador, OcorrenciaSessao, + restringe_sessoes_visiveis) from sapl.parlamentares.models import Parlamentar, CargoMesa, Filiacao @@ -160,7 +161,8 @@ def test_visiveis_para_oculta_do_anonimo_apenas_a_sessao_previa(): # Sessões anteriores à migração 0027 ficaram com `iniciada` em NULL. legada = baker.make(SessaoPlenaria, iniciada=None, publicar_pauta=False) - visiveis = SessaoPlenaria.objects.visiveis_para(AnonymousUser()) + visiveis = restringe_sessoes_visiveis( + SessaoPlenaria.objects.all(), AnonymousUser()) assert previa not in visiveis assert com_pauta in visiveis @@ -174,7 +176,8 @@ def test_visiveis_para_nao_oculta_nada_de_usuario_autenticado(): operador = baker.make(get_user_model()) - assert previa in SessaoPlenaria.objects.visiveis_para(operador) + assert previa in restringe_sessoes_visiveis( + SessaoPlenaria.objects.all(), operador) @pytest.mark.django_db(transaction=False) diff --git a/sapl/sessao/views.py b/sapl/sessao/views.py index 14813ab90..64f7ce7c1 100755 --- a/sapl/sessao/views.py +++ b/sapl/sessao/views.py @@ -64,7 +64,7 @@ from .models import (Bancada, CargoBancada, CargoMesa, SessaoPlenaria, SessaoPlenariaPresenca, TipoExpediente, TipoResultadoVotacao, TipoSessaoPlenaria, VotoParlamentar, TipoRetiradaPauta, RetiradaPauta, TipoJustificativa, JustificativaAusencia, OradorOrdemDia, - ORDENACAO_RESUMO, RegistroLeitura) + ORDENACAO_RESUMO, RegistroLeitura, restringe_sessoes_visiveis) TipoSessaoCrud = CrudAux.build(TipoSessaoPlenaria, 'tipo_sessao_plenaria') TipoJustificativaCrud = CrudAux.build(TipoJustificativa, 'tipo_justificativa') @@ -1349,8 +1349,9 @@ class SessaoCrud(Crud): class DetailView(Crud.DetailView): def get(self, request, *args, **kwargs): - if not SessaoPlenaria.objects.visiveis_para( - request.user).filter(pk=kwargs.get('pk')).exists(): + if not restringe_sessoes_visiveis( + SessaoPlenaria.objects.filter(pk=kwargs.get('pk')), + request.user).exists(): raise Http404() return super().get(request, *args, **kwargs) @@ -2334,7 +2335,8 @@ class ResumoView(DetailView): logger = logging.getLogger(__name__) def get_queryset(self): - return SessaoPlenaria.objects.visiveis_para(self.request.user) + return restringe_sessoes_visiveis( + SessaoPlenaria.objects.all(), self.request.user) def get_context(self, *args, **kwargs): self.object = self.get_object() @@ -4043,7 +4045,7 @@ class PesquisarSessaoPlenariaView(MultiFormatOutputMixin, FilterView): qs = self.get_queryset().select_related( 'tipo', 'sessao_legislativa', 'legislatura') - qs = qs.visiveis_para(self.request.user) + qs = restringe_sessoes_visiveis(qs, self.request.user) qs = qs.distinct().order_by( '-legislatura__numero', '-data_inicio', '-hora_inicio')