Sistema de Apoio ao Processo Legislativo
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 

456 lines
16 KiB

import json
from django.contrib import messages
from django.contrib.auth.decorators import user_passes_test
from django.core.exceptions import ObjectDoesNotExist
from django.core.urlresolvers import reverse
from django.db.models import Q
from django.http import HttpResponse, JsonResponse
from django.http.response import Http404, HttpResponseRedirect
from django.shortcuts import render
from django.utils.translation import ugettext_lazy as _
from sapl.crud.base import Crud
from sapl.painel.apps import AppConfig
from sapl.parlamentares.models import Votante
from sapl.sessao.models import (ExpedienteMateria, OrdemDia, PresencaOrdemDia,
RegistroVotacao, SessaoPlenaria,
SessaoPlenariaPresenca, VotoParlamentar)
from sapl.utils import filiacao_data, get_client_ip, sort_lista_chave
from .models import Cronometro
VOTACAO_NOMINAL = 2
CronometroPainelCrud = Crud.build(Cronometro, '')
# FIXME mudar lógica
def check_permission(user):
return user.has_module_perms(AppConfig.label)
def votacao_aberta(request):
'''
Função que verifica se há somente 1 uma matéria aberta ou
nenhuma. É utilizada como uma função auxiliar para a view
votante_view.
'''
votacoes_abertas = SessaoPlenaria.objects.filter(
Q(ordemdia__votacao_aberta=True) |
Q(expedientemateria__votacao_aberta=True)).distinct()
if len(votacoes_abertas) > 1:
msg_abertas = []
for v in votacoes_abertas:
msg_abertas.append('''<li><a href="%s">%s</a></li>''' % (
reverse('sapl.sessao:sessaoplenaria_detail',
kwargs={'pk': v.id}),
v.__str__()))
msg = _('Existe mais de uma votações aberta. Elas se encontram '
'nas seguintes Sessões: ' + ', '.join(msg_abertas) + '. '
'Para votar, peça para que o Operador feche-as.')
messages.add_message(request, messages.INFO, msg)
return None, msg
elif len(votacoes_abertas) == 1:
ordens = OrdemDia.objects.filter(
sessao_plenaria=votacoes_abertas.first(),
votacao_aberta=True)
expedientes = ExpedienteMateria.objects.filter(
sessao_plenaria=votacoes_abertas.first(),
votacao_aberta=True)
numero_materias_abertas = len(ordens) + len(expedientes)
if numero_materias_abertas > 1:
msg = _('Existe mais de uma votação aberta na Sessão: ' +
('''<li><a href="%s">%s</a></li>''' % (
reverse('sapl.sessao:sessaoplenaria_detail',
kwargs={'pk': votacoes_abertas.first().id}),
votacoes_abertas.first().__str__())) +
'Para votar, peça para que o Operador as feche.')
messages.add_message(request, messages.INFO, msg)
return None, msg
return votacoes_abertas.first(), None
def votante_view(request):
# Pega o votante relacionado ao usuário
try:
votante = Votante.objects.get(user=request.user)
except ObjectDoesNotExist:
raise Http404()
context = {'head_title': str(_('Votação Individual'))}
# Verifica se usuário possui permissão para votar
if 'parlamentares.can_vote' in request.user.get_all_permissions():
context.update({'permissao': True})
# Pega sessão
sessao, msg = votacao_aberta(request)
if sessao and not msg:
pk = sessao.pk
context.update({'sessao_id': pk})
context.update({'sessao': sessao,
'data': sessao.data_inicio,
'hora': sessao.hora_inicio})
# Inicializa presentes
presentes = []
# Verifica votação aberta
# Se aberta, verifica se é nominal. ID nominal == 2
ordem_dia = get_materia_aberta(pk)
expediente = get_materia_expediente_aberta(pk)
materia_aberta = None
if ordem_dia:
materia_aberta = ordem_dia
presentes = PresencaOrdemDia.objects.filter(
sessao_plenaria_id=pk).values_list(
'parlamentar_id', flat=True).distinct()
elif expediente:
materia_aberta = expediente
presentes = SessaoPlenariaPresenca.objects.filter(
sessao_plenaria_id=pk).values_list(
'parlamentar_id', flat=True).distinct()
if materia_aberta:
if materia_aberta.tipo_votacao == VOTACAO_NOMINAL:
context.update({'materia': materia_aberta.materia,
'ementa': materia_aberta.materia.ementa})
parlamentar = votante.parlamentar
parlamentar_presente = False
if parlamentar.id in presentes:
parlamentar_presente = True
else:
context.update({'error_message':
'Não há presentes na Sessão com a '
'matéria em votação.'})
if parlamentar_presente:
voto = []
if ordem_dia:
voto = VotoParlamentar.objects.filter(
ordem=ordem_dia)
elif expediente:
voto = VotoParlamentar.objects.filter(
expediente=expediente)
if voto:
try:
voto = voto.get(parlamentar=parlamentar)
context.update({'voto_parlamentar': voto.voto})
except ObjectDoesNotExist:
context.update(
{'voto_parlamentar': 'Voto não '
'computado.'})
else:
context.update({'error_message':
'Você não está presente na '
'Ordem do Dia/Expediente em votação.'})
else:
context.update(
{'error_message': 'A matéria aberta não é do tipo '
'votação nominal.'})
else:
context.update(
{'error_message': 'Não há nenhuma matéria aberta.'})
elif not sessao and msg:
return HttpResponseRedirect('/')
else:
context.update(
{'error_message': 'Não há nenhuma sessão com matéria aberta.'})
else:
context.update({'permissao': False,
'error_message': 'Usuário sem permissão para votar.'})
# Salva o voto
if request.method == 'POST':
if ordem_dia:
try:
voto = VotoParlamentar.objects.get(
parlamentar=parlamentar,
ordem=ordem_dia)
except ObjectDoesNotExist:
voto = VotoParlamentar.objects.create(
parlamentar=parlamentar,
voto=request.POST['voto'],
user=request.user,
ip=get_client_ip(request),
ordem=ordem_dia)
else:
voto.voto = request.POST['voto']
voto.ip = get_client_ip(request)
voto.user = request.user
voto.save()
elif expediente:
try:
voto = VotoParlamentar.objects.get(
parlamentar=parlamentar,
expediente=expediente)
except ObjectDoesNotExist:
voto = VotoParlamentar.objects.create(
parlamentar=parlamentar,
voto=request.POST['voto'],
user=request.user,
ip=get_client_ip(request),
expediente=expediente)
else:
voto.voto = request.POST['voto']
voto.ip = get_client_ip(request)
voto.user = request.user
voto.save()
return HttpResponseRedirect(
reverse('sapl.painel:voto_individual'))
return render(request, 'painel/voto_nominal.html', context)
@user_passes_test(check_permission)
def painel_view(request, pk):
context = {'head_title': str(_('Painel Plenário')), 'sessao_id': pk}
return render(request, 'painel/index.html', context)
@user_passes_test(check_permission)
def switch_painel(request):
sessao = SessaoPlenaria.objects.get(id=request.POST['pk_sessao'])
switch = json.loads(request.POST['aberto'])
if switch:
sessao.painel_aberto = True
else:
sessao.painel_aberto = False
sessao.save()
return JsonResponse({})
@user_passes_test(check_permission)
def verifica_painel(request):
sessao = SessaoPlenaria.objects.get(id=request.GET['pk_sessao'])
status = sessao.painel_aberto
resposta = JsonResponse(dict(status=status))
return resposta
@user_passes_test(check_permission)
def painel_mensagem_view(request):
return render(request, 'painel/mensagem.html')
@user_passes_test(check_permission)
def painel_parlamentar_view(request):
return render(request, 'painel/parlamentares.html')
@user_passes_test(check_permission)
def painel_votacao_view(request):
return render(request, 'painel/votacao.html')
@user_passes_test(check_permission)
def cronometro_painel(request):
request.session[request.GET['tipo']] = request.GET['action']
return HttpResponse({})
def get_cronometro_status(request, name):
try:
cronometro = request.session[name]
except KeyError:
cronometro = ''
return cronometro
def get_materia_aberta(pk):
return OrdemDia.objects.filter(
sessao_plenaria_id=pk, votacao_aberta=True).last()
def get_presentes(pk, response, materia):
if type(materia) == OrdemDia:
presentes = PresencaOrdemDia.objects.filter(
sessao_plenaria_id=pk)
else:
presentes = SessaoPlenariaPresenca.objects.filter(
sessao_plenaria_id=pk)
sessao = SessaoPlenaria.objects.get(id=pk)
num_presentes = len(presentes)
data_sessao = sessao.data_inicio
presentes_list = []
for p in presentes:
filiacao = filiacao_data(p.parlamentar, data_sessao, data_sessao)
if not filiacao:
partido = 'Sem Registro'
else:
partido = filiacao
presentes_list.append(
{'id': p.id,
'parlamentar_id': p.parlamentar.id,
'nome': p.parlamentar.nome_parlamentar,
'partido': partido,
'voto': ''
})
if materia:
if materia.tipo_votacao == 1:
tipo_votacao = 'Simbólica'
elif materia.tipo_votacao == 2:
tipo_votacao = 'Nominal'
elif materia.tipo_votacao == 3:
tipo_votacao = 'Secreta'
response.update({
'tipo_resultado': materia.resultado,
'observacao_materia': materia.observacao,
'tipo_votacao': tipo_votacao,
'materia_legislativa_texto': str(materia.materia)
})
presentes_list = sort_lista_chave(presentes_list, 'nome')
response.update({
'presentes': presentes_list,
'num_presentes': num_presentes,
'msg_painel': str(_('Votação aberta!')),
})
return response
def get_materia_expediente_aberta(pk):
return ExpedienteMateria.objects.filter(
sessao_plenaria_id=pk, votacao_aberta=True).last()
def response_nenhuma_materia(response):
response.update({
'msg_painel': str(_('Nenhuma matéria disponivel para votação.'))})
return JsonResponse(response)
def get_votos(response, materia):
if type(materia) == OrdemDia:
registro = RegistroVotacao.objects.filter(
ordem=materia, materia=materia.materia).last()
elif type(materia) == ExpedienteMateria:
registro = RegistroVotacao.objects.filter(
expediente=materia, materia=materia.materia).last()
if not registro:
response.update({
'numero_votos_sim': 0,
'numero_votos_nao': 0,
'numero_abstencoes': 0,
'registro': None,
'total_votos': 0,
'tipo_resultado': 'Ainda não foi votada.',
})
else:
total = (registro.numero_votos_sim +
registro.numero_votos_nao +
registro.numero_abstencoes)
if materia.tipo_votacao == 2:
votos_parlamentares = VotoParlamentar.objects.filter(
votacao_id=registro.id).order_by(
'parlamentar__nome_parlamentar')
for i, p in enumerate(response['presentes']):
try:
response['presentes'][i]['voto'] = votos_parlamentares.get(
parlamentar_id=p['parlamentar_id']).voto
except ObjectDoesNotExist:
response['presentes'][i]['voto'] = None
response.update({
'numero_votos_sim': registro.numero_votos_sim,
'numero_votos_nao': registro.numero_votos_nao,
'numero_abstencoes': registro.numero_abstencoes,
'registro': True,
'total_votos': total,
'tipo_resultado': registro.tipo_resultado_votacao.nome,
})
return response
@user_passes_test(check_permission)
def get_dados_painel(request, pk):
sessao = SessaoPlenaria.objects.get(id=pk)
response = {
'sessao_plenaria': str(sessao),
'sessao_plenaria_data': sessao.data_inicio.strftime('%d/%m/%Y'),
'sessao_plenaria_hora_inicio': sessao.hora_inicio,
'cronometro_aparte': get_cronometro_status(request, 'aparte'),
'cronometro_discurso': get_cronometro_status(request, 'discurso'),
'cronometro_ordem': get_cronometro_status(request, 'ordem'),
'status_painel': sessao.painel_aberto
}
ordem_dia = get_materia_aberta(pk)
expediente = get_materia_expediente_aberta(pk)
# Caso tenha alguma matéria com votação aberta, ela é mostrada no painel
# com prioridade para Ordem do Dia.
if ordem_dia:
return JsonResponse(get_votos(
get_presentes(pk, response, ordem_dia),
ordem_dia))
elif expediente:
return JsonResponse(get_votos(
get_presentes(pk, response, expediente),
expediente))
# Caso não tenha nenhuma aberta,
# a matéria a ser mostrada no Painel deve ser a última votada
last_ordem_voto = RegistroVotacao.objects.filter(
ordem__sessao_plenaria=sessao).last()
last_expediente_voto = RegistroVotacao.objects.filter(
expediente__sessao_plenaria=sessao).last()
if last_ordem_voto:
ultima_ordem_votada = last_ordem_voto.ordem
if last_expediente_voto:
ultimo_expediente_votado = last_expediente_voto.expediente
if last_ordem_voto or last_expediente_voto:
# Se alguma ordem E algum expediente já tiver sido votado...
if last_ordem_voto and last_expediente_voto:
materia = ultima_ordem_votada\
if last_ordem_voto.pk >= last_expediente_voto.pk\
else ultimo_expediente_votado
# Caso somente um deles tenha resultado, prioriza a Ordem do Dia
elif last_ordem_voto:
materia = ultima_ordem_votada
# Caso a Ordem do dia não tenha resultado, mostra o último expediente
elif last_expediente_voto:
materia = ultimo_expediente_votado
return JsonResponse(get_votos(
get_presentes(pk, response, materia),
materia))
# Retorna que não há nenhuma matéria já votada ou aberta
return response_nenhuma_materia(get_presentes(pk, response, None))