Browse Source

Transfere migrações de Bancada e CargoBancada (#2761)

Fix #1798
pull/2776/head
Vinícius Cantuária 6 years ago
committed by Edward
parent
commit
399458c158
  1. 3
      sapl/base/tests/test_view_base.py
  2. 29
      sapl/base/views.py
  3. 9
      sapl/legacy/test_renames.py
  4. 57
      sapl/parlamentares/forms.py
  5. 58
      sapl/parlamentares/migrations/0032_auto_20190619_1509.py
  6. 57
      sapl/parlamentares/models.py
  7. 58
      sapl/parlamentares/tests/test_parlamentares.py
  8. 22
      sapl/parlamentares/urls.py
  9. 21
      sapl/parlamentares/views.py
  10. 5
      sapl/rules/map_rules.py
  11. 55
      sapl/sessao/forms.py
  12. 34
      sapl/sessao/migrations/0043_auto_20190506_1452.py
  13. 55
      sapl/sessao/models.py
  14. 58
      sapl/sessao/tests/test_sessao.py
  15. 9
      sapl/sessao/urls.py
  16. 46
      sapl/sessao/views.py
  17. 4
      sapl/templates/menu_tabelas_auxiliares.yaml
  18. 11
      sapl/templates/parlamentares/layouts.yaml
  19. 11
      sapl/templates/sessao/layouts.yaml
  20. 4
      sapl/templates/sistema.html

3
sapl/base/tests/test_view_base.py

@ -7,12 +7,11 @@ from model_mommy import mommy
from sapl.base.models import Autor, TipoAutor
from sapl.comissoes.models import Comissao, TipoComissao
from sapl.sessao.models import Bancada
from sapl.protocoloadm.models import (Protocolo, DocumentoAdministrativo,
TipoDocumentoAdministrativo, Anexado)
from sapl.materia.models import (TipoMateriaLegislativa, RegimeTramitacao,
MateriaLegislativa, Anexada)
from sapl.parlamentares.models import (Parlamentar, Partido, Filiacao,
from sapl.parlamentares.models import (Bancada, Parlamentar, Partido, Filiacao,
Legislatura, Mandato)
from sapl.base.views import (protocolos_duplicados, protocolos_com_materias,

29
sapl/base/views.py

@ -41,12 +41,13 @@ from sapl.crud.base import CrudAux, make_pagination
from sapl.materia.models import (Autoria, MateriaLegislativa, Proposicao, Anexada,
TipoMateriaLegislativa, StatusTramitacao, UnidadeTramitacao)
from sapl.norma.models import (NormaJuridica, NormaEstatisticas)
from sapl.parlamentares.models import Parlamentar, Legislatura, Mandato, Filiacao, SessaoLegislativa
from sapl.protocoloadm.models import (Protocolo, TipoDocumentoAdministrativo,
StatusTramitacaoAdministrativo,
from sapl.parlamentares.models import (Parlamentar, Legislatura, Mandato,
Filiacao, SessaoLegislativa, Bancada)
from sapl.protocoloadm.models import (Protocolo, TipoDocumentoAdministrativo,
StatusTramitacaoAdministrativo,
DocumentoAdministrativo, Anexado)
from sapl.sessao.models import (PresencaOrdemDia, SessaoPlenaria,
SessaoPlenariaPresenca, Bancada)
SessaoPlenariaPresenca)
from sapl.utils import (parlamentares_ativos, gerar_hash_arquivo, SEPARADOR_HASH_PROPOSICAO,
show_results_filter_set, mail_service_configured,
intervalos_tem_intersecao, remover_acentos)
@ -320,7 +321,7 @@ class RelatoriosListView(TemplateView):
context = super(TemplateView, self).get_context_data(**kwargs)
estatisticas_acesso_normas = AppConfig.objects.first().estatisticas_acesso_normas
context['estatisticas_acesso_normas'] = True if estatisticas_acesso_normas == 'S' else False
return context
@ -364,7 +365,7 @@ class RelatorioPresencaSessaoView(FilterView):
# Verifica se os campos foram preenchidos
if not self.filterset.form.is_valid():
return context
cd = self.filterset.form.cleaned_data
if not cd['data_inicio'] and not cd['sessao_legislativa'] \
and not cd['legislatura']:
@ -408,13 +409,13 @@ class RelatorioPresencaSessaoView(FilterView):
elif legislatura_pk and not sessao_legislativa_pk:
_range = [legislatura.data_inicio, legislatura.data_fim]
elif sessao_legislativa_pk:
_range = [sessao_legislativa.data_inicio, sessao_legislativa.data_fim]
param0 = {'sessao_plenaria__data_inicio__range': _range}
# Parlamentares com Mandato no intervalo de tempo (Ativos)
parlamentares_qs = parlamentares_ativos(
_range[0], _range[1]).order_by('nome_parlamentar')
@ -1105,7 +1106,7 @@ class ListarInconsistenciasView(PermissionRequiredMixin, ListView):
def anexados_ciclicos(ofMateriaLegislativa):
ciclicos = []
if ofMateriaLegislativa:
principais = Anexada.objects.values(
'materia_principal'
@ -1201,7 +1202,7 @@ class ListarAnexadasCiclicasView(PermissionRequiredMixin, ListView):
paginator = context['paginator']
page_obj = context['page_obj']
context['page_range'] = make_pagination(
page_obj.number, paginator.num_pages
)
@ -1357,7 +1358,7 @@ class ListarParlFiliacoesIntersecaoView(PermissionRequiredMixin, ListView):
context[
'NO_ENTRIES_MSG'
] = 'Nenhum encontrado.'
return context
return context
def parlamentares_mandatos_intersecao():
@ -1508,7 +1509,7 @@ class ListarFiliacoesSemDataFiliacaoView(PermissionRequiredMixin, ListView):
def get_queryset(self):
return filiacoes_sem_data_filiacao()
def get_context_data(self, **kwargs):
context = super(
ListarFiliacoesSemDataFiliacaoView, self
@ -2004,7 +2005,7 @@ def pesquisa_textual(request):
# Index and db are out of sync. Object has been deleted from database
continue
dici = filtro_campos(e.object.__dict__)
sec_dict['objeto'] = str(dici)
sec_dict['objeto'] = str(dici)
sec_dict['text'] = str(e.object.ementa)
sec_dict['model'] = str(type(e.object))
@ -2060,4 +2061,4 @@ class RelatorioHistoricoTramitacaoAdmView(FilterView):
else:
context['tramitacaoadministrativo__unidade_tramitacao_destino'] = ''
return context
return context

9
sapl/legacy/test_renames.py

@ -12,20 +12,19 @@ from sapl.materia.models import (AcompanhamentoMateria, DocumentoAcessorio,
Tramitacao)
from sapl.norma.models import (AnexoNormaJuridica, NormaJuridica,
NormaRelacionada, TipoVinculoNormaJuridica)
from sapl.parlamentares.models import (Frente, Mandato, Parlamentar, Partido,
from sapl.parlamentares.models import (Bancada, CargoBancada, Frente, Mandato, Parlamentar, Partido,
TipoAfastamento, Votante, Bloco)
from sapl.protocoloadm.models import DocumentoAdministrativo
from sapl.sessao.models import (Bancada, CargoBancada,
ExpedienteMateria, Orador, OradorExpediente,
from sapl.sessao.models import (ExpedienteMateria, Orador, OradorExpediente,
OrdemDia, RegistroVotacao, ResumoOrdenacao,
SessaoPlenaria, TipoResultadoVotacao,
VotoParlamentar)
RENAMING_IGNORED_MODELS = [
Votante, Frente, Bancada, Bloco, Votante, # parlamentares
Votante, Frente, Bancada, CargoBancada, Bloco, Votante, # parlamentares
Composicao, Reuniao, DocumentoAcessorioComissoes, # commissoes
AppConfig, CasaLegislativa, # base
CargoBancada, ResumoOrdenacao, # sessao
ResumoOrdenacao, # sessao
AnexoNormaJuridica, TipoVinculoNormaJuridica, # norma
]

57
sapl/parlamentares/forms.py

@ -23,7 +23,7 @@ from sapl.rules import SAPL_GROUP_VOTANTE
import django_filters
from .models import (ComposicaoColigacao, Filiacao, Frente, Legislatura,
Mandato, Parlamentar, Votante, Bloco)
Mandato, Parlamentar, Votante, Bloco, Bancada)
class ImageThumbnailFileInput(ClearableFileInput):
@ -617,4 +617,57 @@ class BlocoForm(ModelForm):
tipo=tipo,
nome=bloco.nome
)
return bloco
return bloco
class BancadaForm(ModelForm):
class Meta:
model = Bancada
fields = ['legislatura', 'nome', 'partido', 'data_criacao',
'data_extincao', 'descricao']
def clean(self):
super(BancadaForm, self).clean()
if not self.is_valid():
return self.cleaned_data
data = self.cleaned_data
legislatura = data['legislatura']
data_criacao = data['data_criacao']
if data_criacao:
if (data_criacao < legislatura.data_inicio or
data_criacao > legislatura.data_fim):
raise ValidationError(_("Data de criação da bancada fora do intervalo"
" de legislatura informada"))
data_extincao = data['data_extincao']
if data_extincao:
if (data_extincao < legislatura.data_inicio or
data_extincao > legislatura.data_fim):
raise ValidationError(_("Data fim da bancada fora do intervalo de"
" legislatura informada"))
if self.cleaned_data['data_extincao']:
if (self.cleaned_data['data_extincao'] <
self.cleaned_data['data_criacao']):
msg = _('Data de extinção não pode ser menor que a de criação')
raise ValidationError(msg)
return self.cleaned_data
@transaction.atomic
def save(self, commit=True):
bancada = super(BancadaForm, self).save(commit)
content_type = ContentType.objects.get_for_model(Bancada)
object_id = bancada.pk
tipo = TipoAutor.objects.get(content_type=content_type)
Autor.objects.create(
content_type=content_type,
object_id=object_id,
tipo=tipo,
nome=bancada.nome
)
return bancada

58
sapl/parlamentares/migrations/0032_auto_20190619_1509.py

@ -0,0 +1,58 @@
# -*- coding: utf-8 -*-
# Generated by Django 1.11.21 on 2019-06-19 18:09
from __future__ import unicode_literals
from django.db import migrations, models
import django.db.models.deletion
class Migration(migrations.Migration):
dependencies = [
('parlamentares', '0031_auto_20190614_1203'),
('sessao', '0043_auto_20190506_1452'),
]
state_operations = [
migrations.CreateModel(
name='Bancada',
fields=[
('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('nome', models.CharField(max_length=80, verbose_name='Nome da Bancada')),
('data_criacao', models.DateField(null=True, verbose_name='Data Criação')),
('data_extincao', models.DateField(blank=True, null=True, verbose_name='Data Extinção')),
('descricao', models.TextField(blank=True, verbose_name='Descrição')),
('legislatura',
models.ForeignKey(on_delete=django.db.models.deletion.PROTECT, to='parlamentares.Legislatura',
verbose_name='Legislatura')),
('partido', models.ForeignKey(blank=True, null=True, on_delete=django.db.models.deletion.PROTECT,
to='parlamentares.Partido', verbose_name='Partido')),
],
options={
'db_table': 'parlamentares_bancada',
'verbose_name': 'Bancada Parlamentar',
'verbose_name_plural': 'Bancadas Parlamentares',
'ordering': ('-legislatura__numero',),
},
bases=(models.Model,),
),
migrations.CreateModel(
name='CargoBancada',
fields=[
('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('nome_cargo', models.CharField(max_length=80, verbose_name='Cargo de Bancada')),
('cargo_unico', models.BooleanField(choices=[(True, 'Sim'), (False, 'Não')], default=False,
verbose_name='Cargo Único ?')),
],
options={
'db_table': 'parlamentares_cargobancada',
'verbose_name': 'Cargo de Bancada',
'verbose_name_plural': 'Cargos de Bancada',
},
bases=(models.Model,),
),
]
operations = [
migrations.SeparateDatabaseAndState(state_operations=state_operations)
]

57
sapl/parlamentares/models.py

@ -657,3 +657,60 @@ class Bloco(models.Model):
def __str__(self):
return self.nome
@reversion.register()
class Bancada(models.Model):
legislatura = models.ForeignKey(Legislatura,
on_delete=models.PROTECT,
verbose_name=_('Legislatura'))
nome = models.CharField(
max_length=80,
verbose_name=_('Nome da Bancada'))
partido = models.ForeignKey(Partido,
blank=True,
null=True,
on_delete=models.PROTECT,
verbose_name=_('Partido'))
data_criacao = models.DateField(blank=False, null=True,
verbose_name=_('Data Criação'))
data_extincao = models.DateField(blank=True, null=True,
verbose_name=_('Data Extinção'))
descricao = models.TextField(blank=True, verbose_name=_('Descrição'))
# campo conceitual de reversão genérica para o model Autor que dá a
# o meio possível de localização de tipos de autores.
autor = SaplGenericRelation(Autor, related_query_name='bancada_set',
fields_search=(
('nome', '__icontains'),
('descricao', '__icontains'),
('partido__sigla', '__icontains'),
('partido__nome', '__icontains'),
))
class Meta:
db_table = 'parlamentares_bancada'
verbose_name = _('Bancada Parlamentar')
verbose_name_plural = _('Bancadas Parlamentares')
ordering = ('-legislatura__numero', )
def __str__(self):
return self.nome
@reversion.register()
class CargoBancada(models.Model):
nome_cargo = models.CharField(max_length=80,
verbose_name=_('Cargo de Bancada'))
cargo_unico = models.BooleanField(default=False,
choices=YES_NO_CHOICES,
verbose_name=_('Cargo Único ?'))
class Meta:
db_table = 'parlamentares_cargobancada'
verbose_name = _('Cargo de Bancada')
verbose_name_plural = _('Cargos de Bancada')
def __str__(self):
return self.nome_cargo

58
sapl/parlamentares/tests/test_parlamentares.py

@ -2,7 +2,9 @@ import pytest
from django.core.urlresolvers import reverse
from django.utils.translation import ugettext_lazy as _
from model_mommy import mommy
from datetime import datetime
from sapl.parlamentares import forms
from sapl.parlamentares.forms import FrenteForm, LegislaturaForm, MandatoForm
from sapl.parlamentares.models import (Dependente, Filiacao, Legislatura,
Mandato, Parlamentar, Partido,
@ -350,3 +352,59 @@ def test_frente_form_valido():
})
assert form.is_valid()
@pytest.mark.django_db(transaction=False)
def test_valida_campos_obrigatorios_bancada_form():
form = forms.BancadaForm(data={})
assert not form.is_valid()
errors = form.errors
assert errors['legislatura'] == [_('Este campo é obrigatório.')]
assert errors['nome'] == [_('Este campo é obrigatório.')]
assert errors['data_criacao'] == [_('Este campo é obrigatório.')]
assert len(errors) == 3
def data(valor):
return datetime.strptime(valor, '%Y-%m-%d').date()
@pytest.mark.django_db(transaction=False)
def test_bancada_form_valido():
legislatura = mommy.make(Legislatura,
data_inicio=data('2017-11-10'),
data_fim=data('2017-12-31'),
)
partido = mommy.make(Partido)
form = forms.BancadaForm(data={'legislatura': str(legislatura.pk),
'nome': 'Nome da Bancada',
'partido': str(partido.pk),
'data_criacao': '10/11/2017',
'data_extincao': '10/12/2017',
'descricao': 'teste'
})
assert form.is_valid()
@pytest.mark.django_db(transaction=False)
def test_bancada_form_datas_invalidas():
legislatura = mommy.make(Legislatura,
data_inicio=data('2017-11-10'),
data_fim=data('2017-12-31'),
)
partido = mommy.make(Partido)
form = forms.BancadaForm(data={'legislatura': str(legislatura.pk),
'nome': 'Nome da Bancada',
'partido': str(partido.pk),
'data_criacao': '2016-11-01',
'data_extincao': '2016-10-01',
'descricao': 'teste'
})
assert not form.is_valid()

22
sapl/parlamentares/urls.py

@ -2,6 +2,7 @@ from django.conf.urls import include, url
from sapl.parlamentares.views import (CargoMesaCrud, ColigacaoCrud,
ComposicaoColigacaoCrud, DependenteCrud,
BancadaCrud, CargoBancadaCrud,
FiliacaoCrud, FrenteCrud, FrenteList,
LegislaturaCrud, MandatoCrud,
MesaDiretoraView, NivelInstrucaoCrud,
@ -21,7 +22,7 @@ from sapl.parlamentares.views import (CargoMesaCrud, ColigacaoCrud,
lista_parlamentares,
parlamentares_filiados,
BlocoCrud,
PesquisarParlamentarView,
PesquisarParlamentarView,
VincularParlamentarView,
deleta_historico_partido,
get_sessoes_legislatura)
@ -41,13 +42,13 @@ urlpatterns = [
)),
url(r'^parlamentar/lista$', lista_parlamentares, name='lista_parlamentares'),
url(r'^parlamentar/pesquisar-parlamentar/',
PesquisarParlamentarView.as_view(), name='pesquisar_parlamentar'),
url(r'^parlamentar/deleta_partido/(?P<pk>\d+)/$',
deleta_historico_partido, name='deleta_historico_partido'),
url(r'^parlamentar/(?P<pk>\d+)/materias$',
ParlamentarMateriasView.as_view(), name='parlamentar_materias'),
@ -56,9 +57,16 @@ urlpatterns = [
url(r'^sistema/coligacao/',
include(ColigacaoCrud.get_urls() +
ComposicaoColigacaoCrud.get_urls())),
ComposicaoColigacaoCrud.get_urls())),
url(r'^sistema/bancada/',
include(BancadaCrud.get_urls())),
url(r'^sistema/cargo-bancada/',
include(CargoBancadaCrud.get_urls())),
url(r'^sistema/bloco/',
include(BlocoCrud.get_urls())),
url(r'^sistema/frente/',
include(FrenteCrud.get_urls())),
url(r'^sistema/frente/atualiza-lista-parlamentares',
@ -101,7 +109,7 @@ urlpatterns = [
url(r'^mesa-diretora/remove-parlamentar-composicao/$',
remove_parlamentar_composicao, name='remove_parlamentar_composicao'),
url(r'^parlamentar/get-sessoes-legislatura/$',
url(r'^parlamentar/get-sessoes-legislatura/$',
get_sessoes_legislatura, name='get_sessoes_legislatura'),
]

21
sapl/parlamentares/views.py

@ -33,18 +33,17 @@ from sapl.materia.models import Autoria, Proposicao, Relatoria
from sapl.parlamentares.apps import AppConfig
from sapl.utils import (parlamentares_ativos, show_results_filter_set)
from .forms import (FiliacaoForm, FrenteForm, LegislaturaForm, MandatoForm,
ParlamentarCreateForm, ParlamentarForm, VotanteForm,
ParlamentarFilterSet, VincularParlamentarForm,
BlocoForm)
from .models import (CargoMesa, Coligacao, ComposicaoColigacao, ComposicaoMesa,
from .forms import (BancadaForm, FiliacaoForm, FrenteForm, LegislaturaForm, MandatoForm,
ParlamentarCreateForm, ParlamentarForm, VotanteForm, ParlamentarFilterSet,
VincularParlamentarForm, BlocoForm)
from .models import (Bancada, CargoBancada, CargoMesa, Coligacao, ComposicaoColigacao, ComposicaoMesa,
Dependente, Filiacao, Frente, Legislatura, Mandato,
NivelInstrucao, Parlamentar, Partido, SessaoLegislativa,
SituacaoMilitar, TipoAfastamento, TipoDependente, Votante,
Bloco, HistoricoPartido)
CargoBancadaCrud = CrudAux.build(CargoBancada, '')
CargoMesaCrud = CrudAux.build(CargoMesa, 'cargo_mesa')
TipoDependenteCrud = CrudAux.build(TipoDependente, 'tipo_dependente')
NivelInstrucaoCrud = CrudAux.build(NivelInstrucao, 'nivel_instrucao')
@ -109,6 +108,16 @@ class VotanteView(MasterDetailCrud):
kwargs={'pk': obj.parlamentar.pk}))
class BancadaCrud(CrudAux):
model = Bancada
class CreateView(CrudAux.CreateView):
form_class = BancadaForm
def get_success_url(self):
return reverse('sapl.parlamentares:bancada_list')
class FrenteList(MasterDetailCrud):
model = Frente
is_m2m = True

5
sapl/rules/map_rules.py

@ -282,11 +282,10 @@ rules_group_geral = {
(parlamentares.ComposicaoMesa, __base__, __perms_publicas__),
(parlamentares.Frente, __base__, __perms_publicas__),
(parlamentares.Votante, __base__, __perms_publicas__),
(parlamentares.Bancada, __base__, __perms_publicas__),
(parlamentares.CargoBancada, __base__, __perms_publicas__),
(parlamentares.Bloco, __base__, __perms_publicas__),
(sessao.CargoBancada, __base__, __perms_publicas__),
(sessao.Bancada, __base__, __perms_publicas__),
(sessao.TipoSessaoPlenaria, __base__, __perms_publicas__),
(sessao.TipoResultadoVotacao, __base__, __perms_publicas__),
(sessao.TipoExpediente, __base__, __perms_publicas__),

55
sapl/sessao/forms.py

@ -23,7 +23,7 @@ from sapl.utils import (RANGE_DIAS_MES, RANGE_MESES,
autor_modal, timezone, choice_anos_com_sessaoplenaria,
FileFieldCheckMixin)
from .models import (Bancada, ExpedienteMateria, JustificativaAusencia,
from .models import (ExpedienteMateria, JustificativaAusencia,
Orador, OradorExpediente, OrdemDia, PresencaOrdemDia, SessaoPlenaria,
SessaoPlenariaPresenca, TipoResultadoVotacao,
OcorrenciaSessao, RetiradaPauta, TipoRetiradaPauta, OradorOrdemDia, ORDENACAO_RESUMO,
@ -259,59 +259,6 @@ class RetiradaPautaForm(ModelForm):
return retirada
class BancadaForm(ModelForm):
class Meta:
model = Bancada
fields = ['legislatura', 'nome', 'partido', 'data_criacao',
'data_extincao', 'descricao']
def clean(self):
super(BancadaForm, self).clean()
if not self.is_valid():
return self.cleaned_data
data = self.cleaned_data
legislatura = data['legislatura']
data_criacao = data['data_criacao']
if data_criacao:
if (data_criacao < legislatura.data_inicio or
data_criacao > legislatura.data_fim):
raise ValidationError(_("Data de criação da bancada fora do intervalo"
" de legislatura informada"))
data_extincao = data['data_extincao']
if data_extincao:
if (data_extincao < legislatura.data_inicio or
data_extincao > legislatura.data_fim):
raise ValidationError(_("Data fim da bancada fora do intervalo de"
" legislatura informada"))
if self.cleaned_data['data_extincao']:
if (self.cleaned_data['data_extincao'] <
self.cleaned_data['data_criacao']):
msg = _('Data de extinção não pode ser menor que a de criação')
raise ValidationError(msg)
return self.cleaned_data
@transaction.atomic
def save(self, commit=True):
bancada = super(BancadaForm, self).save(commit)
content_type = ContentType.objects.get_for_model(Bancada)
object_id = bancada.pk
tipo = TipoAutor.objects.get(content_type=content_type)
Autor.objects.create(
content_type=content_type,
object_id=object_id,
tipo=tipo,
nome=bancada.nome
)
return bancada
class ExpedienteMateriaForm(ModelForm):
_model = ExpedienteMateria

34
sapl/sessao/migrations/0043_auto_20190506_1452.py

@ -0,0 +1,34 @@
# -*- coding: utf-8 -*-
# Generated by Django 1.11.20 on 2019-05-06 17:52
from __future__ import unicode_literals
from django.db import migrations
class Migration(migrations.Migration):
dependencies = [
('sessao', '0042_merge_20190612_0925'),
]
database_operations = [
migrations.AlterModelTable('Bancada', 'parlamentares_bancada'),
migrations.AlterModelTable('CargoBancada', 'parlamentares_cargobancada')
]
state_operations = [
migrations.DeleteModel('Bancada'),
migrations.DeleteModel('CargoBancada')
]
operations = [
migrations.SeparateDatabaseAndState(
database_operations=database_operations,
state_operations=state_operations
),
migrations.RunSQL(
"""UPDATE django_content_type SET app_label = 'parlamentares'
WHERE app_label = 'sessao'
AND (model = 'bancada' OR model = 'cargobancada');"""
),
]

55
sapl/sessao/models.py

@ -17,61 +17,6 @@ from sapl.utils import (YES_NO_CHOICES, SaplGenericRelation,
restringe_tipos_de_arquivo_txt, texto_upload_path)
@reversion.register()
class CargoBancada(models.Model):
nome_cargo = models.CharField(max_length=80,
verbose_name=_('Cargo de Bancada'))
cargo_unico = models.BooleanField(default=False,
choices=YES_NO_CHOICES,
verbose_name=_('Cargo Único ?'))
class Meta:
verbose_name = _('Cargo de Bancada')
verbose_name_plural = _('Cargos de Bancada')
def __str__(self):
return self.nome_cargo
@reversion.register()
class Bancada(models.Model):
legislatura = models.ForeignKey(Legislatura,
on_delete=models.PROTECT,
verbose_name=_('Legislatura'))
nome = models.CharField(
max_length=80,
verbose_name=_('Nome da Bancada'))
partido = models.ForeignKey(Partido,
blank=True,
null=True,
on_delete=models.PROTECT,
verbose_name=_('Partido'))
data_criacao = models.DateField(blank=False, null=True,
verbose_name=_('Data Criação'))
data_extincao = models.DateField(blank=True, null=True,
verbose_name=_('Data Extinção'))
descricao = models.TextField(blank=True, verbose_name=_('Descrição'))
# campo conceitual de reversão genérica para o model Autor que dá a
# o meio possível de localização de tipos de autores.
autor = SaplGenericRelation(Autor, related_query_name='bancada_set',
fields_search=(
('nome', '__icontains'),
('descricao', '__icontains'),
('partido__sigla', '__icontains'),
('partido__nome', '__icontains'),
))
class Meta:
verbose_name = _('Bancada Parlamentar')
verbose_name_plural = _('Bancadas Parlamentares')
ordering = ('-legislatura__numero', )
def __str__(self):
return self.nome
@reversion.register()
class TipoSessaoPlenaria(models.Model):

58
sapl/sessao/tests/test_sessao.py

@ -1,11 +1,10 @@
import pytest
from datetime import datetime
from django.core.exceptions import ValidationError
from django.utils.translation import ugettext_lazy as _
from model_mommy import mommy
from sapl.materia.models import MateriaLegislativa, TipoMateriaLegislativa
from sapl.parlamentares.models import Legislatura, Parlamentar, Partido,SessaoLegislativa
from sapl.parlamentares.models import Legislatura, Parlamentar, Partido, SessaoLegislativa
from sapl.sessao import forms
from sapl.sessao.models import (ExpedienteMateria, ExpedienteSessao,
IntegranteMesa, Orador, OrdemDia,
@ -76,61 +75,6 @@ def test_numero_duplicado_sessao_plenaria_form():
"número distinto."]
@pytest.mark.django_db(transaction=False)
def test_valida_campos_obrigatorios_bancada_form():
form = forms.BancadaForm(data={})
assert not form.is_valid()
errors = form.errors
assert errors['legislatura'] == [_('Este campo é obrigatório.')]
assert errors['nome'] == [_('Este campo é obrigatório.')]
assert errors['data_criacao'] == [_('Este campo é obrigatório.')]
assert len(errors) == 3
def data(valor):
return datetime.strptime(valor, '%Y-%m-%d').date()
@pytest.mark.django_db(transaction=False)
def test_bancada_form_valido():
legislatura = mommy.make(Legislatura,
data_inicio=data('2017-11-10'),
data_fim=data('2017-12-31'),
)
partido = mommy.make(Partido)
form = forms.BancadaForm(data={'legislatura': str(legislatura.pk),
'nome': 'Nome da Bancada',
'partido': str(partido.pk),
'data_criacao': '10/11/2017',
'data_extincao': '10/12/2017',
'descricao': 'teste'
})
assert form.is_valid()
@pytest.mark.django_db(transaction=False)
def test_bancada_form_datas_invalidas():
legislatura = mommy.make(Legislatura,
data_inicio=data('2017-11-10'),
data_fim=data('2017-12-31'),
)
partido = mommy.make(Partido)
form = forms.BancadaForm(data={'legislatura': str(legislatura.pk),
'nome': 'Nome da Bancada',
'partido': str(partido.pk),
'data_criacao': '2016-11-01',
'data_extincao': '2016-10-01',
'descricao': 'teste'
})
assert not form.is_valid()
@pytest.mark.django_db(transaction=False)
def test_expediente_materia_form_valido():
tipo_materia = mommy.make(TipoMateriaLegislativa)

9
sapl/sessao/urls.py

@ -1,9 +1,8 @@
from django.conf.urls import include, url
from sapl.sessao.views import (AdicionarVariasMateriasExpediente,
AdicionarVariasMateriasOrdemDia, BancadaCrud,
CargoBancadaCrud, ExpedienteMateriaCrud,
ExpedienteView, JustificativaAusenciaCrud,
AdicionarVariasMateriasOrdemDia,
ExpedienteMateriaCrud, ExpedienteView, JustificativaAusenciaCrud,
OcorrenciaSessaoView, MateriaOrdemDiaCrud, OradorOrdemDiaCrud,
MesaView, OradorCrud,
OradorExpedienteCrud, PainelView,
@ -99,10 +98,6 @@ urlpatterns = [
include(TipoJustificativaCrud.get_urls())),
url(r'^sistema/sessao-plenaria/tipo-retirada-pauta/',
include(TipoRetiradaPautaCrud.get_urls())),
url(r'^sistema/bancada/',
include(BancadaCrud.get_urls())),
url(r'^sistema/cargo-bancada/',
include(CargoBancadaCrud.get_urls())),
url(r'^sistema/resumo-ordenacao/',
resumo_ordenacao,
name='resumo_ordenacao'),

46
sapl/sessao/views.py

@ -40,14 +40,13 @@ from sapl.sessao.apps import AppConfig
from sapl.sessao.forms import ExpedienteMateriaForm, OrdemDiaForm
from sapl.utils import show_results_filter_set, remover_acentos, get_client_ip, filiacao_data
from .forms import (AdicionarVariasMateriasFilterSet, BancadaForm,
ExpedienteForm, JustificativaAusenciaForm, OcorrenciaSessaoForm, ListMateriaForm,
from .forms import (AdicionarVariasMateriasFilterSet, ExpedienteForm,
JustificativaAusenciaForm, OcorrenciaSessaoForm, ListMateriaForm,
MesaForm, OradorExpedienteForm, OradorForm, PautaSessaoFilterSet,
PresencaForm, SessaoPlenariaFilterSet,
SessaoPlenariaForm, VotacaoEditForm, VotacaoForm,
VotacaoNominalForm, RetiradaPautaForm, OradorOrdemDiaForm)
from .models import (Bancada, CargoBancada, CargoMesa,
ExpedienteMateria, ExpedienteSessao, OcorrenciaSessao, IntegranteMesa,
from .models import (CargoMesa, ExpedienteMateria, ExpedienteSessao, OcorrenciaSessao, IntegranteMesa,
MateriaLegislativa, Orador, OradorExpediente, OrdemDia,
PresencaOrdemDia, RegistroVotacao, ResumoOrdenacao,
SessaoPlenaria, SessaoPlenariaPresenca, TipoExpediente,
@ -57,7 +56,6 @@ from .models import (Bancada, CargoBancada, CargoMesa,
TipoSessaoCrud = CrudAux.build(TipoSessaoPlenaria, 'tipo_sessao_plenaria')
TipoJustificativaCrud = CrudAux.build(TipoJustificativa, 'tipo_justificativa')
CargoBancadaCrud = CrudAux.build(CargoBancada, '')
TipoResultadoVotacaoCrud = CrudAux.build(
TipoResultadoVotacao, 'tipo_resultado_votacao')
TipoRetiradaPautaCrud = CrudAux.build(TipoRetiradaPauta, 'tipo_retirada_pauta')
@ -473,11 +471,11 @@ class TipoExpedienteCrud(CrudAux):
model = TipoExpediente
class DeleteView(CrudAux.DeleteView):
def delete(self, *args, **kwargs):
self.object = self.get_object()
# Se todas as referências a este tipo forem de conteúdo vazio,
# Se todas as referências a este tipo forem de conteúdo vazio,
# significa que pode ser apagado
if self.object.expedientesessao_set.filter(conteudo='').count() == \
self.object.expedientesessao_set.all().count():
@ -693,7 +691,7 @@ class OradorExpedienteCrud(OradorCrud):
context.update({'subnav_template_name': 'sessao/subnav-solene.yaml'})
return context
class DetailView(MasterDetailCrud.DetailView):
def get_context_data(self, **kwargs):
@ -737,7 +735,7 @@ class OradorExpedienteCrud(OradorCrud):
if tipo_sessao.nome == "Solene":
context.update({'subnav_template_name': 'sessao/subnav-solene.yaml'})
return context
def get_success_url(self):
return reverse('sapl.sessao:oradorexpediente_list',
@ -810,16 +808,6 @@ class OradorOrdemDiaCrud(OradorCrud):
return initial
class BancadaCrud(CrudAux):
model = Bancada
class CreateView(CrudAux.CreateView):
form_class = BancadaForm
def get_success_url(self):
return reverse('sapl.sessao:bancada_list')
def recuperar_numero_sessao_view(request):
try:
tipo = TipoSessaoPlenaria.objects.get(pk=request.GET.get('tipo', '0'))
@ -1331,7 +1319,7 @@ class MesaView(FormMixin, DetailView):
if tipo_sessao.nome == "Solene":
context.update({'subnav_template_name': 'sessao/subnav-solene.yaml'})
return context
def get_success_url(self):
pk = self.kwargs['pk']
return reverse('sapl.sessao:mesa', kwargs={'pk': pk})
@ -1513,7 +1501,7 @@ def resumo_ordenacao(request):
}
if request.method == 'GET':
return render(request, 'sessao/resumo_ordenacao.html', context)
elif request.method == 'POST':
elif request.method == 'POST':
ordenacao.primeiro = ast.literal_eval(request.POST['0'])[0]
ordenacao.segundo = ast.literal_eval(request.POST['1'])[0]
ordenacao.terceiro = ast.literal_eval(request.POST['2'])[0]
@ -2328,7 +2316,7 @@ class VotacaoView(SessaoPermissionMixin):
ordem_id = kwargs['oid']
ordem = OrdemDia.objects.get(id=ordem_id)
presentes_id = [
presente.parlamentar.id for presente in PresencaOrdemDia.objects.filter(
sessao_plenaria_id=self.kwargs['pk']
@ -3013,7 +3001,7 @@ class VotacaoExpedienteView(SessaoPermissionMixin):
expediente_id = kwargs['oid']
expediente = ExpedienteMateria.objects.get(id=expediente_id)
presentes_id = [
presente.parlamentar.id for presente in SessaoPlenariaPresenca.objects.filter(
sessao_plenaria_id=self.kwargs['pk']
@ -3834,7 +3822,7 @@ class VotacaoEmBlocoSimbolicaView(PermissionRequiredForAppCrudMixin, TemplateVie
if request.POST['origem'] == 'ordem':
ordens = OrdemDia.objects.filter(
id__in=request.POST.getlist('marcadas_1'))
presentes_id = [
presente.parlamentar.id for presente in PresencaOrdemDia.objects.filter(
sessao_plenaria_id=self.kwargs['pk']
@ -3853,7 +3841,7 @@ class VotacaoEmBlocoSimbolicaView(PermissionRequiredForAppCrudMixin, TemplateVie
else:
expedientes = ExpedienteMateria.objects.filter(
id__in=request.POST.getlist('marcadas_1'))
presentes_id = [
presente.parlamentar.id for presente in SessaoPlenariaPresenca.objects.filter(
sessao_plenaria_id=self.kwargs['pk']
@ -3993,7 +3981,7 @@ class VotacaoEmBlocoSimbolicaView(PermissionRequiredForAppCrudMixin, TemplateVie
if self.request.POST['origem'] == 'ordem':
ordens = OrdemDia.objects.filter(
id__in=self.request.POST.getlist('ordens'))
presentes_id = [
presente.parlamentar.id for presente in PresencaOrdemDia.objects.filter(
sessao_plenaria_id=self.kwargs['pk']
@ -4007,12 +3995,12 @@ class VotacaoEmBlocoSimbolicaView(PermissionRequiredForAppCrudMixin, TemplateVie
qtde_ativos = len(presenca_ativos)
context.update({'ordens': ordens,
'total_presentes': qtde_presentes,
'total_presentes': qtde_presentes,
'total_votantes': qtde_ativos})
elif self.request.POST['origem'] == 'expediente':
expedientes = ExpedienteMateria.objects.filter(
id__in=self.request.POST.getlist('expedientes'))
presentes_id = [
presente.parlamentar.id for presente in SessaoPlenariaPresenca.objects.filter(
sessao_plenaria_id=self.kwargs['pk']

4
sapl/templates/menu_tabelas_auxiliares.yaml

@ -69,10 +69,10 @@
css_class: head_title
children:
- title: {% trans 'Bancadas Parlamentares' %}
url: sapl.sessao:bancada_list
url: sapl.parlamentares:bancada_list
css_class: btn btn-link
- title: {% trans 'Cargo de Bancada Parlamentar' %}
url: sapl.sessao:cargobancada_list
url: sapl.parlamentares:cargobancada_list
css_class: btn btn-link
- title: {% trans 'Frente Parlamentar' %}
url: sapl.parlamentares:frente_list

11
sapl/templates/parlamentares/layouts.yaml

@ -116,6 +116,17 @@ ComposicaoColigacao:
{% trans 'Nome do Partido' %}:
- partido
Bancada:
{% trans 'Bancada' %}:
- legislatura
- nome partido
- data_criacao data_extincao
- descricao
CargoBancada:
{% trans 'Cargo de Bancada' %}:
- nome_cargo:8 cargo_unico
Frente:
{% trans 'Frente' %}:
- nome

11
sapl/templates/sessao/layouts.yaml

@ -82,17 +82,6 @@ OrdemDiaDetail:
- tipo_votacao
- observacao
Bancada:
{% trans 'Bancada' %}:
- legislatura
- nome partido
- data_criacao data_extincao
- descricao
CargoBancada:
{% trans 'Cargo de Bancada' %}:
- nome_cargo:8 cargo_unico
TipoJustificativa:
{% trans 'Tipo de Justificativa' %}:
- descricao

4
sapl/templates/sistema.html

@ -50,8 +50,8 @@
<h2>Módulo Bancadas Parlamentares</h2>
<div class="row">
<div class="col-md-6"><a href="{% url 'sapl.sessao:bancada_list' %}" class="btn btn-link">Bancadas Parlamentares</a></div>
<div class="col-md-6"><a href="{% url 'sapl.sessao:cargobancada_list' %}" class="btn btn-link">Cargo de Bancada Parlamentar</a></div>
<div class="col-md-6"><a href="{% url 'sapl.parlamentares:bancada_list' %}" class="btn btn-link">Bancadas Parlamentares</a></div>
<div class="col-md-6"><a href="{% url 'sapl.parlamentares:cargobancada_list' %}" class="btn btn-link">Cargo de Bancada Parlamentar</a></div>
<div class="col-md-6"><a href="{% url 'sapl.parlamentares:frente_list' %}" class="btn btn-link">Frente Parlamentar</a></div>
<div class="col-md-6"><a href="{% url 'sapl.parlamentares:bloco_list' %}" class="btn btn-link">Bloco Parlamentar</a></div>
</div>

Loading…
Cancel
Save