From 2e2a4cdc7cdc164074536726248439614b0cb7f5 Mon Sep 17 00:00:00 2001 From: Edward Date: Wed, 20 Sep 2017 13:12:32 -0300 Subject: [PATCH] Fixes #1338 (#1339) * Fixes #1338 * Fix datetime * wip * Fix * Bug fix --- sapl/compilacao/models.py | 15 ++++---- sapl/decorators.py | 4 +- sapl/materia/email_utils.py | 8 ++-- sapl/materia/forms.py | 32 ++++++++-------- sapl/materia/models.py | 5 +-- sapl/materia/views.py | 37 +++++++++++-------- sapl/norma/forms.py | 4 +- sapl/norma/views.py | 4 +- sapl/painel/views.py | 1 - sapl/parlamentares/forms.py | 6 ++- sapl/parlamentares/models.py | 6 +-- sapl/parlamentares/views.py | 13 +++---- sapl/protocoloadm/forms.py | 6 +-- sapl/protocoloadm/tests/test_protocoloadm.py | 22 +++++------ sapl/protocoloadm/views.py | 30 +++++++-------- sapl/relatorios/views.py | 10 +++-- sapl/sessao/forms.py | 4 +- sapl/sessao/views.py | 6 +-- sapl/settings.py | 2 +- .../materia/prop_devolvidas_list.html | 4 +- .../materia/prop_pendentes_list.html | 3 +- .../materia/prop_recebidas_list.html | 3 +- sapl/templates/materia/proposicao_detail.html | 4 +- sapl/templates/materia/recibo_proposicao.html | 3 +- .../protocoloadm/protocolo_filter.html | 2 + .../protocoloadm/protocolo_list.html | 4 +- .../protocoloadm/protocolo_mostrar.html | 3 +- sapl/utils.py | 6 +-- 28 files changed, 132 insertions(+), 115 deletions(-) diff --git a/sapl/compilacao/models.py b/sapl/compilacao/models.py index 2d3d80116..9f38b5def 100644 --- a/sapl/compilacao/models.py +++ b/sapl/compilacao/models.py @@ -1,4 +1,3 @@ -from datetime import datetime import reversion from django.contrib import messages @@ -10,6 +9,7 @@ from django.db.models.aggregates import Max from django.db.models.deletion import PROTECT from django.http.response import Http404 from django.template import defaultfilters +from django.utils import timezone from django.utils.decorators import classonlymethod from django.utils.encoding import force_text from django.utils.translation import ugettext_lazy as _ @@ -357,9 +357,9 @@ class TextoArticulado(TimestampedMixin): if not ta.data: ta.data = getattr(obj, map_fields['data'] if map_fields['data'] else 'xxx', - datetime.now()) + timezone.now()) if not ta.data: - ta.data = datetime.now() + ta.data = timezone.now() ta.ementa = getattr( obj, map_fields['ementa'] @@ -370,15 +370,16 @@ class TextoArticulado(TimestampedMixin): obj, map_fields['observacao'] if map_fields['observacao'] else 'xxx', '') + now = timezone.now() ta.numero = getattr( obj, map_fields['numero'] if map_fields['numero'] else 'xxx', int('%s%s%s' % ( - int(datetime.now().year), - int(datetime.now().month), - int(datetime.now().day)))) + int(now.year), + int(now.month), + int(now.day)))) ta.ano = getattr(obj, map_fields['ano'] - if map_fields['ano'] else 'xxx', datetime.now().year) + if map_fields['ano'] else 'xxx', now.year) ta.save() return ta diff --git a/sapl/decorators.py b/sapl/decorators.py index 0e301565c..fac94344a 100644 --- a/sapl/decorators.py +++ b/sapl/decorators.py @@ -1,6 +1,6 @@ -from datetime import date from functools import wraps +from django.utils import timezone from django.utils.translation import ugettext_lazy as _ @@ -18,7 +18,7 @@ def vigencia_atual(decorated_method): string_displayed = decorated_method(self) if hasattr(self, 'data_inicio') and hasattr(self, 'data_fim'): - today = date.today() + today = timezone.now().today().date() e_atual = self.data_inicio <= today <= self.data_fim string_displayed = "{} {}".format( string_displayed, "(Atual)" if e_atual else "") diff --git a/sapl/materia/email_utils.py b/sapl/materia/email_utils.py index 3cf53423d..9bfe0b66f 100644 --- a/sapl/materia/email_utils.py +++ b/sapl/materia/email_utils.py @@ -1,8 +1,9 @@ -from datetime import datetime +from datetime import datetime as dt from django.core.mail import EmailMultiAlternatives, get_connection, send_mail from django.core.urlresolvers import reverse from django.template import Context, loader +from django.utils import timezone from sapl.base.models import CasaLegislativa from sapl.settings import EMAIL_SEND_USER @@ -150,8 +151,9 @@ def criar_email_tramitacao(base_url, casa_legislativa, materia, status, templates = load_email_templates(['email/tramitacao.txt', 'email/tramitacao.html'], {"casa_legislativa": casa_nome, - "data_registro": datetime.now().strftime( - "%d/%m/%Y"), + "data_registro": dt.strftime( + timezone.now(), + "%d/%m/%Y"), "cod_materia": materia.id, "logotipo": casa_legislativa.logotipo, "descricao_materia": materia.ementa, diff --git a/sapl/materia/forms.py b/sapl/materia/forms.py index 4a0c9b1ec..59391b07d 100644 --- a/sapl/materia/forms.py +++ b/sapl/materia/forms.py @@ -1,6 +1,5 @@ import os -from datetime import date, datetime import django_filters from crispy_forms.bootstrap import Alert, FormActions, InlineRadios @@ -18,6 +17,7 @@ from django.forms import ModelChoiceField, ModelForm, widgets from django.forms.forms import Form from django.forms.models import ModelMultipleChoiceField from django.forms.widgets import CheckboxSelectMultiple, HiddenInput, Select +from django.utils import timezone from django.utils.encoding import force_text from django.utils.html import format_html from django.utils.safestring import mark_safe @@ -215,7 +215,7 @@ class TramitacaoForm(ModelForm): def __init__(self, *args, **kwargs): super(TramitacaoForm, self).__init__(*args, **kwargs) - self.fields['data_tramitacao'].initial = datetime.now().date() + self.fields['data_tramitacao'].initial = timezone.now().date() def clean(self): cleaned_data = super(TramitacaoForm, self).clean() @@ -245,7 +245,7 @@ class TramitacaoForm(ModelForm): 'destino da última adicionada!') raise ValidationError(msg) - if cleaned_data['data_tramitacao'] > datetime.now().date(): + if cleaned_data['data_tramitacao'] > timezone.now().date(): msg = _( 'A data de tramitação deve ser ' + 'menor ou igual a data de hoje!') @@ -1164,10 +1164,10 @@ class ProposicaoForm(forms.ModelForm): return super().save(commit) - inst.ano = datetime.now().year + inst.ano = timezone.now().year numero__max = Proposicao.objects.filter( autor=inst.autor, - ano=datetime.now().year).aggregate(Max('numero_proposicao')) + ano=timezone.now().year).aggregate(Max('numero_proposicao')) numero__max = numero__max['numero_proposicao__max'] inst.numero_proposicao = ( numero__max + 1) if numero__max else 1 @@ -1376,7 +1376,7 @@ class ConfirmarProposicaoForm(ProposicaoForm): cd = self.cleaned_data if 'devolver' in self.data: - self.instance.data_devolucao = datetime.now() + self.instance.data_devolucao = timezone.now() self.instance.data_recebimento = None self.instance.data_envio = None self.instance.save() @@ -1398,7 +1398,7 @@ class ConfirmarProposicaoForm(ProposicaoForm): elif 'incorporar' in self.data: self.instance.justificativa_devolucao = '' self.instance.data_devolucao = None - self.instance.data_recebimento = datetime.now() + self.instance.data_recebimento = timezone.now() self.instance.materia_de_vinculo = cd['materia_de_vinculo'] if self.instance.texto_articulado.exists(): @@ -1435,7 +1435,7 @@ class ConfirmarProposicaoForm(ProposicaoForm): ) == TipoMateriaLegislativa: numero__max = MateriaLegislativa.objects.filter( tipo=proposicao.tipo.tipo_conteudo_related, - ano=datetime.now().year).aggregate(Max('numero')) + ano=timezone.now().year).aggregate(Max('numero')) numero__max = numero__max['numero__max'] # dados básicos @@ -1443,8 +1443,8 @@ class ConfirmarProposicaoForm(ProposicaoForm): materia.numero = (numero__max + 1) if numero__max else 1 materia.tipo = proposicao.tipo.tipo_conteudo_related materia.ementa = proposicao.descricao - materia.ano = datetime.now().year - materia.data_apresentacao = datetime.now() + materia.ano = timezone.now().year + materia.data_apresentacao = timezone.now() materia.em_tramitacao = True materia.regime_tramitacao = cd['regime_tramitacao'] @@ -1483,7 +1483,7 @@ class ConfirmarProposicaoForm(ProposicaoForm): anexada = Anexada() anexada.materia_principal = proposicao.materia_de_vinculo anexada.materia_anexada = materia - anexada.data_anexacao = datetime.now() + anexada.data_anexacao = timezone.now() anexada.save() self.instance.results['messages']['success'].append(_( @@ -1555,18 +1555,18 @@ class ConfirmarProposicaoForm(ProposicaoForm): numeracao = sapl.base.models.AppConfig.attr('sequencia_numeracao') if numeracao == 'A': nm = Protocolo.objects.filter( - ano=date.today().year).aggregate(Max('numero')) + ano=timezone.now().year).aggregate(Max('numero')) elif numeracao == 'U': nm = Protocolo.objects.all().aggregate(Max('numero')) protocolo = Protocolo() protocolo.numero = (nm['numero__max'] + 1) if nm['numero__max'] else 1 - protocolo.ano = date.today().year - protocolo.data = date.today() - protocolo.hora = datetime.now().time() + protocolo.ano = timezone.now().year + protocolo.data = timezone.now() + protocolo.hora = timezone.now().time() # TODO transformar campo timestamp em auto_now_add - protocolo.timestamp = datetime.now() + protocolo.timestamp = timezone.now() protocolo.tipo_protocolo = '1' protocolo.interessado = str(proposicao.autor) diff --git a/sapl/materia/models.py b/sapl/materia/models.py index 0ee067dc3..7859b52d7 100644 --- a/sapl/materia/models.py +++ b/sapl/materia/models.py @@ -1,4 +1,3 @@ -from datetime import datetime import reversion from django.contrib.auth.models import Group @@ -6,7 +5,7 @@ from django.contrib.contenttypes.fields import GenericRelation from django.contrib.contenttypes.models import ContentType from django.core.exceptions import ObjectDoesNotExist from django.db import models -from django.utils import formats +from django.utils import formats, timezone from django.utils.translation import ugettext_lazy as _ from model_utils import Choices @@ -711,7 +710,7 @@ class Proposicao(models.Model): def title_type(self): return '%s nº _____ %s' % ( self.tipo, formats.date_format( - self.data_envio if self.data_envio else datetime.now(), + self.data_envio if self.data_envio else timezone.now(), "\d\e d \d\e F \d\e Y")) class Meta: diff --git a/sapl/materia/views.py b/sapl/materia/views.py index 35dfab49f..9c315be5a 100644 --- a/sapl/materia/views.py +++ b/sapl/materia/views.py @@ -14,7 +14,7 @@ from django.http import HttpResponse, JsonResponse from django.http.response import Http404, HttpResponseRedirect from django.shortcuts import get_object_or_404, redirect from django.template import RequestContext, loader -from django.utils import formats +from django.utils import formats, timezone from django.utils.translation import ugettext_lazy as _ from django.views.generic import CreateView, ListView, TemplateView, UpdateView from django.views.generic.base import RedirectView @@ -284,7 +284,7 @@ def recuperar_materia(request): ano = request.GET.get('ano', '') param = {'tipo': tipo} - param['data_apresentacao__year'] = ano if ano else datetime.now().year + param['data_apresentacao__year'] = ano if ano else timezone.now().year materia = MateriaLegislativa.objects.filter(**param).order_by( 'tipo', 'ano', 'numero').values_list('numero', 'ano').last() @@ -293,7 +293,7 @@ def recuperar_materia(request): 'ano': materia[1]}) else: response = JsonResponse( - {'numero': 1, 'ano': ano if ano else datetime.now().year}) + {'numero': 1, 'ano': ano if ano else timezone.now().year}) return response @@ -323,14 +323,14 @@ def criar_materia_proposicao(proposicao): tipo_materia = TipoMateriaLegislativa.objects.get( descricao=proposicao.tipo.descricao) numero = MateriaLegislativa.objects.filter( - ano=datetime.now().year).order_by('numero').last().numero + 1 + ano=timezone.now().year).order_by('numero').last().numero + 1 regime = RegimeTramitacao.objects.get(descricao='Normal') return MateriaLegislativa.objects.create( tipo=tipo_materia, - ano=datetime.now().year, + ano=timezone.now().year, numero=numero, - data_apresentacao=datetime.now(), + data_apresentacao=timezone.now(), regime_tramitacao=regime, em_tramitacao=True, ementa=proposicao.descricao, @@ -616,7 +616,7 @@ class ProposicaoCrud(Crud): 'Texto associado.') else: p.data_devolucao = None - p.data_envio = datetime.now() + p.data_envio = timezone.now() p.save() if p.texto_articulado.exists(): @@ -940,7 +940,7 @@ class TramitacaoCrud(MasterDetailCrud): ] = local.unidade_tramitacao_destino.pk else: self.initial['unidade_tramitacao_local'] = '' - self.initial['data_tramitacao'] = datetime.now() + self.initial['data_tramitacao'] = timezone.now() return self.initial def get_context_data(self, **kwargs): @@ -1071,7 +1071,7 @@ class DocumentoAcessorioCrud(MasterDetailCrud): super(MasterDetailCrud.CreateView, self).__init__(**kwargs) def get_initial(self): - self.initial['data'] = datetime.now().date() + self.initial['data'] = timezone.now().date() return self.initial @@ -1633,13 +1633,16 @@ class DocumentoAcessorioEmLoteView(PermissionRequiredMixin, FilterView): tipo = TipoDocumento.objects.get(descricao=request.POST['tipo']) + tz = timezone.get_current_timezone() + for materia_id in marcadas: doc = DocumentoAcessorio() doc.materia_id = materia_id doc.tipo = tipo doc.arquivo = request.FILES['arquivo'] doc.nome = request.POST['nome'] - doc.data = datetime.strptime(request.POST['data'], "%d/%m/%Y") + doc.data = tz.localize(datetime.strptime( + request.POST['data'], "%d/%m/%Y")) doc.autor = request.POST['autor'] doc.ementa = request.POST['ementa'] doc.save() @@ -1696,20 +1699,22 @@ class PrimeiraTramitacaoEmLoteView(PermissionRequiredMixin, FilterView): def post(self, request, *args, **kwargs): marcadas = request.POST.getlist('materia_id') + tz = timezone.get_current_timezone() + if len(marcadas) == 0: msg = _('Nenhuma máteria foi selecionada.') messages.add_message(request, messages.ERROR, msg) return self.get(request, self.kwargs) if request.POST['data_encaminhamento']: - data_encaminhamento = datetime.strptime( - request.POST['data_encaminhamento'], "%d/%m/%Y") + data_encaminhamento = tz.localize(datetime.strptime( + request.POST['data_encaminhamento'], "%d/%m/%Y")) else: data_encaminhamento = None if request.POST['data_fim_prazo']: - data_fim_prazo = datetime.strptime( - request.POST['data_fim_prazo'], "%d/%m/%Y") + data_fim_prazo = tz.localize(datetime.strptime( + request.POST['data_fim_prazo'], "%d/%m/%Y")) else: data_fim_prazo = None @@ -1720,8 +1725,8 @@ class PrimeiraTramitacaoEmLoteView(PermissionRequiredMixin, FilterView): for materia_id in marcadas: t = Tramitacao( materia_id=materia_id, - data_tramitacao=datetime.strptime( - request.POST['data_tramitacao'], "%d/%m/%Y"), + data_tramitacao=tz.localize(datetime.strptime( + request.POST['data_tramitacao'], "%d/%m/%Y")), data_encaminhamento=data_encaminhamento, data_fim_prazo=data_fim_prazo, unidade_tramitacao_local_id=request.POST[ diff --git a/sapl/norma/forms.py b/sapl/norma/forms.py index 5149ac926..f5be3f918 100644 --- a/sapl/norma/forms.py +++ b/sapl/norma/forms.py @@ -1,4 +1,3 @@ -from datetime import datetime import django_filters from crispy_forms.helper import FormHelper @@ -7,6 +6,7 @@ from django import forms from django.core.exceptions import ObjectDoesNotExist, ValidationError from django.db import models from django.forms import ModelForm, widgets +from django.utils import timezone from django.utils.translation import ugettext_lazy as _ from sapl.crispy_layout_mixin import form_actions, to_row @@ -154,7 +154,7 @@ class NormaJuridicaForm(ModelForm): def save(self, commit=False): norma = self.instance - norma.timestamp = datetime.now() + norma.timestamp = timezone.now() norma.materia = self.cleaned_data['materia'] norma = super(NormaJuridicaForm, self).save(commit=True) return norma diff --git a/sapl/norma/views.py b/sapl/norma/views.py index 82c21f75c..c374537ed 100644 --- a/sapl/norma/views.py +++ b/sapl/norma/views.py @@ -1,8 +1,8 @@ -from datetime import datetime from django.core.exceptions import ObjectDoesNotExist from django.core.urlresolvers import reverse from django.http import JsonResponse +from django.utils import timezone from django.utils.translation import ugettext_lazy as _ from django.views.generic.base import RedirectView from django_filters.views import FilterView @@ -204,7 +204,7 @@ def recuperar_numero_norma(request): ano = request.GET.get('ano', '') param = {'tipo': tipo} - param['ano'] = ano if ano else datetime.now().year + param['ano'] = ano if ano else timezone.now().year norma = NormaJuridica.objects.filter(**param).order_by( 'tipo', 'ano', 'numero').values_list('numero', 'ano').last() diff --git a/sapl/painel/views.py b/sapl/painel/views.py index 23d7f871c..e4c616512 100644 --- a/sapl/painel/views.py +++ b/sapl/painel/views.py @@ -1,5 +1,4 @@ - from django.contrib import messages from django.contrib.auth.decorators import user_passes_test from django.core.exceptions import ObjectDoesNotExist diff --git a/sapl/parlamentares/forms.py b/sapl/parlamentares/forms.py index 40a8bdb25..efbf6f592 100644 --- a/sapl/parlamentares/forms.py +++ b/sapl/parlamentares/forms.py @@ -1,4 +1,4 @@ -from datetime import date, timedelta +from datetime import timedelta from crispy_forms.helper import FormHelper from crispy_forms.layout import Fieldset, Layout @@ -9,6 +9,7 @@ from django.core.exceptions import ValidationError from django.db import transaction from django.db.models import Q from django.forms import ModelForm +from django.utils import timezone from django.utils.translation import ugettext_lazy as _ from floppyforms.widgets import ClearableFileInput @@ -168,7 +169,8 @@ def validar_datas(data_filiacao, data_desfiliacao, parlamentar, filiacao): return [True, ''] # data ficticia de desfiliacao - df_desfiliacao = data_desfiliacao if data_desfiliacao else date.today() + today = timezone.now() + df_desfiliacao = data_desfiliacao if data_desfiliacao else today # se não puder haver filiação no mesmo dia de desfiliação, basta # retirar os timedelta abaixo diff --git a/sapl/parlamentares/models.py b/sapl/parlamentares/models.py index 5d81dd33b..64ae92c8e 100644 --- a/sapl/parlamentares/models.py +++ b/sapl/parlamentares/models.py @@ -1,7 +1,7 @@ -from datetime import datetime import reversion from django.db import models +from django.utils import timezone from django.utils.translation import ugettext_lazy as _ from model_utils import Choices @@ -26,7 +26,7 @@ class Legislatura(models.Model): verbose_name_plural = _('Legislaturas') def atual(self): - current_year = datetime.now().year + current_year = timezone.now().year return self.data_inicio.year <= current_year <= self.data_fim.year @vigencia_atual @@ -489,7 +489,7 @@ class Mandato(models.Model): self.legislatura.data_inicio, self.legislatura.data_fim, f.data, - f.data_desfiliacao or datetime.max.date())] + f.data_desfiliacao or timezone.datetime.max.date())] @reversion.register() diff --git a/sapl/parlamentares/views.py b/sapl/parlamentares/views.py index 6f4cf4265..02bbfae30 100644 --- a/sapl/parlamentares/views.py +++ b/sapl/parlamentares/views.py @@ -10,6 +10,7 @@ from django.db.models.aggregates import Count from django.http import JsonResponse from django.http.response import HttpResponseRedirect from django.templatetags.static import static +from django.utils import timezone from django.utils.datastructures import MultiValueDictKeyError from django.utils.translation import ugettext_lazy as _ from django.views.decorators.clickjacking import xframe_options_exempt @@ -226,10 +227,8 @@ def json_date_convert(date): string "dd/mm/yyyy" :return: ''' - dia, mes, ano = date.split('/') - return datetime.date(day=int(dia), - month=int(mes), - year=int(ano)) + + return datetime.strptime(date, "%d/%m/%Y").date() def frente_atualiza_lista_parlamentares(request): @@ -660,7 +659,7 @@ class MesaDiretoraView(FormView): sessoes = SessaoLegislativa.objects.filter( legislatura=legislatura).order_by("data_inicio") - year = datetime.now().year + year = timezone.now().year sessao_atual = sessoes.filter(data_inicio__year=year).first() mesa = sessao_atual.composicaomesa_set.all() if sessao_atual else [] @@ -715,7 +714,7 @@ def altera_field_mesa(request): # Caso a mudança tenha sido no campo legislatura, a sessão # atual deve ser a primeira daquela legislatura else: - year = datetime.now().year + year = timezone.now().year try: sessao_selecionada = sessoes.get(data_inicio__year=year).id except ObjectDoesNotExist: @@ -883,7 +882,7 @@ def altera_field_mesa_public_view(request): # atual deve ser a primeira daquela legislatura else: try: - year = datetime.now().year + year = timezone.now().year sessao_selecionada = sessoes.get(data_inicio__year=year).id except ObjectDoesNotExist as e: sessao_selecionada = sessoes.first().id diff --git a/sapl/protocoloadm/forms.py b/sapl/protocoloadm/forms.py index bd0fe3cd6..692a2c4f2 100644 --- a/sapl/protocoloadm/forms.py +++ b/sapl/protocoloadm/forms.py @@ -1,4 +1,3 @@ -from datetime import datetime import django_filters from crispy_forms.bootstrap import InlineRadios @@ -8,6 +7,7 @@ from django import forms from django.core.exceptions import ObjectDoesNotExist, ValidationError from django.db import models from django.forms import ModelForm +from django.utils import timezone from django.utils.translation import ugettext_lazy as _ from sapl.base.models import Autor, TipoAutor @@ -468,7 +468,7 @@ class TramitacaoAdmForm(ModelForm): 'destino da última adicionada!') raise ValidationError(msg) - if self.cleaned_data['data_tramitacao'] > datetime.now().date(): + if self.cleaned_data['data_tramitacao'] > timezone.now().date(): msg = _( 'A data de tramitação deve ser ' + 'menor ou igual a data de hoje!') @@ -540,7 +540,7 @@ class TramitacaoAdmEditForm(TramitacaoAdmForm): class DocumentoAdministrativoForm(ModelForm): - data = forms.DateField(initial=datetime.today) + data = forms.DateField(initial=timezone.now) ano_protocolo = forms.ChoiceField(required=False, label=Protocolo._meta. diff --git a/sapl/protocoloadm/tests/test_protocoloadm.py b/sapl/protocoloadm/tests/test_protocoloadm.py index abf95666c..5bad5585f 100644 --- a/sapl/protocoloadm/tests/test_protocoloadm.py +++ b/sapl/protocoloadm/tests/test_protocoloadm.py @@ -1,4 +1,4 @@ -import datetime +from datetime import datetime, date, timedelta import pytest from django.core.urlresolvers import reverse @@ -145,7 +145,7 @@ def test_create_tramitacao(admin_client): unidade_tramitacao_destino=unidade_tramitacao_destino_1, status=status, documento=documento_adm, - data_tramitacao=datetime.date(2016, 8, 21)) + data_tramitacao=date(2016, 8, 21)) response = admin_client.post( reverse( @@ -155,7 +155,7 @@ def test_create_tramitacao(admin_client): 'unidade_tramitacao_destino': unidade_tramitacao_local_1.pk, 'documento': documento_adm.pk, 'status': status.pk, - 'data_tramitacao': datetime.date(2016, 8, 21)}, + 'data_tramitacao': date(2016, 8, 21)}, follow=True) msg = force_text(_('A origem da nova tramitação deve ser igual ao ' @@ -173,7 +173,7 @@ def test_create_tramitacao(admin_client): 'unidade_tramitacao_destino': unidade_tramitacao_destino_2.pk, 'documento': documento_adm.pk, 'status': status.pk, - 'data_tramitacao': datetime.date(2016, 8, 20)}, + 'data_tramitacao': date(2016, 8, 20)}, follow=True) msg = _('A data da nova tramitação deve ser ' + @@ -191,7 +191,7 @@ def test_create_tramitacao(admin_client): 'unidade_tramitacao_destino': unidade_tramitacao_destino_2.pk, 'documento': documento_adm.pk, 'status': status.pk, - 'data_tramitacao': datetime.date.today() + datetime.timedelta( + 'data_tramitacao': date.today() + timedelta( days=1)}, follow=True) @@ -210,8 +210,8 @@ def test_create_tramitacao(admin_client): 'unidade_tramitacao_destino': unidade_tramitacao_destino_2.pk, 'documento': documento_adm.pk, 'status': status.pk, - 'data_tramitacao': datetime.date(2016, 8, 21), - 'data_encaminhamento': datetime.date(2016, 8, 20)}, + 'data_tramitacao': date(2016, 8, 21), + 'data_encaminhamento': date(2016, 8, 20)}, follow=True) msg = force_text(_('A data de encaminhamento deve ser ' + @@ -229,8 +229,8 @@ def test_create_tramitacao(admin_client): 'unidade_tramitacao_destino': unidade_tramitacao_destino_2.pk, 'documento': documento_adm.pk, 'status': status.pk, - 'data_tramitacao': datetime.date(2016, 8, 21), - 'data_fim_prazo': datetime.date(2016, 8, 20)}, + 'data_tramitacao': date(2016, 8, 21), + 'data_fim_prazo': date(2016, 8, 20)}, follow=True) msg = _('A data fim de prazo deve ser ' + @@ -248,12 +248,12 @@ def test_create_tramitacao(admin_client): 'unidade_tramitacao_destino': unidade_tramitacao_destino_2.pk, 'documento': documento_adm.pk, 'status': status.pk, - 'data_tramitacao': datetime.date(2016, 8, 21)}, + 'data_tramitacao': date(2016, 8, 21)}, follow=True) tramitacao = TramitacaoAdministrativo.objects.last() # Verifica se a tramitacao que obedece as regras de negócios é criada - assert tramitacao.data_tramitacao == datetime.date(2016, 8, 21) + assert tramitacao.data_tramitacao == date(2016, 8, 21) @pytest.mark.django_db(transaction=False) diff --git a/sapl/protocoloadm/views.py b/sapl/protocoloadm/views.py index c4558801b..348f79229 100644 --- a/sapl/protocoloadm/views.py +++ b/sapl/protocoloadm/views.py @@ -1,4 +1,3 @@ -from datetime import date, datetime from braces.views import FormValidMessageMixin from django.contrib import messages @@ -10,6 +9,7 @@ from django.db.models import Max, Q from django.http import Http404, HttpResponse, JsonResponse from django.http.response import HttpResponseRedirect from django.shortcuts import redirect +from django.utils import timezone from django.utils.translation import ugettext_lazy as _ from django.views.generic import CreateView, ListView from django.views.generic.base import RedirectView, TemplateView @@ -296,7 +296,7 @@ class ProtocoloDocumentoView(PermissionRequiredMixin, if numeracao == 'A': numero = Protocolo.objects.filter( - ano=date.today().year).aggregate(Max('numero')) + ano=timezone.now().year).aggregate(Max('numero')) elif numeracao == 'L': legislatura = Legislatura.objects.last() data_inicio = legislatura.data_inicio @@ -310,10 +310,10 @@ class ProtocoloDocumentoView(PermissionRequiredMixin, f.tipo_processo = '0' # TODO validar o significado f.anulado = False f.numero = (numero['numero__max'] + 1) if numero['numero__max'] else 1 - f.ano = datetime.now().year - f.data = datetime.now().date() - f.hora = datetime.now().time() - f.timestamp = datetime.now() + f.ano = timezone.now().year + f.data = timezone.now() + f.hora = timezone.now().time() + f.timestamp = timezone.now() f.assunto_ementa = self.request.POST['assunto'] f.save() @@ -335,7 +335,7 @@ class CriarDocumentoProtocolo(PermissionRequiredMixin, CreateView): kwargs={'pk': self.kwargs['pk']}) def criar_documento(self, protocolo): - curr_year = datetime.now().date().year + curr_year = timezone.now().year numero_max = DocumentoAdministrativo.objects.filter( tipo=protocolo.tipo_documento, ano=curr_year @@ -344,7 +344,7 @@ class CriarDocumentoProtocolo(PermissionRequiredMixin, CreateView): doc = {} doc['tipo'] = protocolo.tipo_documento doc['ano'] = curr_year - doc['data'] = datetime.today() + doc['data'] = timezone.now() doc['numero_protocolo'] = protocolo.numero doc['ano_protocolo'] = protocolo.ano doc['protocolo'] = protocolo.id @@ -431,7 +431,7 @@ class ProtocoloMateriaView(PermissionRequiredMixin, CreateView): if numeracao == 'A': numero = Protocolo.objects.filter( - ano=date.today().year).aggregate(Max('numero')) + ano=timezone.now().year).aggregate(Max('numero')) elif numeracao == 'U': numero = Protocolo.objects.all().aggregate(Max('numero')) @@ -442,10 +442,10 @@ class ProtocoloMateriaView(PermissionRequiredMixin, CreateView): protocolo.numero = ( numero['numero__max'] + 1) if numero['numero__max'] else 1 - protocolo.ano = datetime.now().year - protocolo.data = datetime.now().date() - protocolo.hora = datetime.now().time() - protocolo.timestamp = datetime.now() + protocolo.ano = timezone.now().year + protocolo.data = timezone.now().date() + protocolo.hora = timezone.now().time() + protocolo.timestamp = timezone.now() protocolo.tipo_protocolo = 0 protocolo.tipo_processo = '1' # TODO validar o significado @@ -483,7 +483,7 @@ class ProtocoloMateriaView(PermissionRequiredMixin, CreateView): lista_comissoes = Comissao.objects.filter(Q( data_extincao__isnull=True) | Q( - data_extincao__gt=date.today())).values_list('id', flat=True) + data_extincao__gt=timezone.now())).values_list('id', flat=True) model_comissao = ContentType.objects.get_for_model(Comissao) autor_comissoes = Autor.objects.filter( content_type=model_comissao, object_id__in=lista_comissoes) @@ -597,7 +597,7 @@ class TramitacaoAdmCrud(MasterDetailCrud): ] = local.unidade_tramitacao_destino.pk else: self.initial['unidade_tramitacao_local'] = '' - self.initial['data_tramitacao'] = datetime.now() + self.initial['data_tramitacao'] = timezone.now().date() return self.initial def get_context_data(self, **kwargs): diff --git a/sapl/relatorios/views.py b/sapl/relatorios/views.py index 87510089d..01a3b06b2 100644 --- a/sapl/relatorios/views.py +++ b/sapl/relatorios/views.py @@ -1,9 +1,10 @@ import html import re -from datetime import datetime +from datetime import datetime as dt from django.core.exceptions import ObjectDoesNotExist from django.http import Http404, HttpResponse +from django.utils import timezone from django.utils.translation import ugettext_lazy as _ from sapl.base.models import Autor, CasaLegislativa @@ -88,7 +89,7 @@ def get_rodape(casa): linha2 = linha2 + " - " linha2 = linha2 + str(_("E-mail: ")) + casa.email - data_emissao = datetime.today().strftime("%d/%m/%Y") + data_emissao = dt.strftime(timezone.now(), "%d/%m/%Y") return [linha1, linha2, data_emissao] @@ -932,8 +933,11 @@ def get_etiqueta_protocolos(prots): dic = {} dic['titulo'] = str(p.numero) + '/' + str(p.ano) + + tz_hora = timezone.localtime(p.timestamp) + dic['data'] = 'Data: ' + p.data.strftime( - "%d/%m/%Y") + ' - Horário: ' + p.hora.strftime("%H:%M") + "%d/%m/%Y") + ' - Horário: ' + tz_hora.strftime("%H:%M") dic['txt_assunto'] = p.assunto_ementa dic['txt_interessado'] = p.interessado diff --git a/sapl/sessao/forms.py b/sapl/sessao/forms.py index 5f2e8303c..ee7b2f9de 100644 --- a/sapl/sessao/forms.py +++ b/sapl/sessao/forms.py @@ -15,7 +15,7 @@ from sapl.materia.models import (MateriaLegislativa, StatusTramitacao, from sapl.parlamentares.models import Parlamentar from sapl.utils import (RANGE_DIAS_MES, RANGE_MESES, MateriaPesquisaOrderingFilter, autor_label, - autor_modal) + autor_modal, timezone) from .models import (Bancada, ExpedienteMateria, Orador, OradorExpediente, OrdemDia, SessaoPlenaria, SessaoPlenariaPresenca) @@ -132,7 +132,7 @@ class ExpedienteMateriaForm(ModelForm): data_ordem = forms.CharField( label='Data Sessão', - initial=datetime.now().strftime('%d/%m/%Y'), + initial=datetime.strftime(timezone.now(), '%d/%m/%Y'), widget=forms.TextInput(attrs={'readonly': 'readonly'})) class Meta: diff --git a/sapl/sessao/views.py b/sapl/sessao/views.py index 018e42791..6fe3087f1 100644 --- a/sapl/sessao/views.py +++ b/sapl/sessao/views.py @@ -1,4 +1,3 @@ -from datetime import datetime from re import sub from django.contrib import messages @@ -10,6 +9,7 @@ from django.db.models import Max, Q from django.forms.utils import ErrorList from django.http import JsonResponse from django.http.response import Http404, HttpResponseRedirect +from django.utils import timezone from django.utils.datastructures import MultiValueDictKeyError from django.utils.decorators import method_decorator from django.utils.html import strip_tags @@ -2576,7 +2576,7 @@ class AdicionarVariasMateriasExpediente(PermissionRequiredForAppCrudMixin, expediente.numero_ordem = posicao else: expediente.numero_ordem = 1 - expediente.data_ordem = datetime.now() + expediente.data_ordem = timezone.now() expediente.tipo_votacao = request.POST['tipo_votacao_%s' % m] expediente.save() @@ -2645,7 +2645,7 @@ class AdicionarVariasMateriasOrdemDia(AdicionarVariasMateriasExpediente): ordem_dia.numero_ordem = posicao else: ordem_dia.numero_ordem = 1 - ordem_dia.data_ordem = datetime.now() + ordem_dia.data_ordem = timezone.now() ordem_dia.tipo_votacao = tipo_votacao ordem_dia.save() diff --git a/sapl/settings.py b/sapl/settings.py index 274e2ed0a..4598023bd 100644 --- a/sapl/settings.py +++ b/sapl/settings.py @@ -209,7 +209,7 @@ LANGUAGES = ( TIME_ZONE = 'America/Sao_Paulo' USE_I18N = True USE_L10N = True -USE_TZ = False +USE_TZ = True # DATE_FORMAT = 'N j, Y' DATE_FORMAT = 'd/m/Y' SHORT_DATE_FORMAT = 'd/m/Y' diff --git a/sapl/templates/materia/prop_devolvidas_list.html b/sapl/templates/materia/prop_devolvidas_list.html index 79c9bd531..8ec29f177 100644 --- a/sapl/templates/materia/prop_devolvidas_list.html +++ b/sapl/templates/materia/prop_devolvidas_list.html @@ -1,6 +1,6 @@ {% extends "base.html" %} {% load i18n %} - +{% load tz %} {% block base_content %}
Proposições Não Incorporadas @@ -20,7 +20,7 @@ {% for prop in object_list %} - {{ prop.data_devolucao|date:"d/m/Y H:i:s" }} + {{ prop.data_devolucao|localtime|date:"d/m/Y H:i:s" }} {{ prop.tipo.descricao }} {{ prop.descricao }} {{ prop.autor }} diff --git a/sapl/templates/materia/prop_pendentes_list.html b/sapl/templates/materia/prop_pendentes_list.html index e07ba0ee7..cff6c10b0 100644 --- a/sapl/templates/materia/prop_pendentes_list.html +++ b/sapl/templates/materia/prop_pendentes_list.html @@ -1,5 +1,6 @@ {% extends "base.html" %} {% load i18n %} +{% load tz %} {% block base_content %}
Proposições Não Recebidas @@ -18,7 +19,7 @@ {% for prop in object_list %} - {{ prop.data_envio|date:"d/m/Y H:i:s" }} + {{ prop.data_envio|localtime|date:"d/m/Y H:i:s" }} {{ prop.tipo.descricao }} {{ prop.descricao }} {{ prop.autor }} diff --git a/sapl/templates/materia/prop_recebidas_list.html b/sapl/templates/materia/prop_recebidas_list.html index 4d4ff5ddb..4c437d6b9 100644 --- a/sapl/templates/materia/prop_recebidas_list.html +++ b/sapl/templates/materia/prop_recebidas_list.html @@ -1,5 +1,6 @@ {% extends "base.html" %} {% load i18n %} +{% load tz %} {% block base_content %}
Proposições Incorporadas @@ -19,7 +20,7 @@ {% for prop in object_list %} - {{ prop.data_recebimento|date:"d/m/Y H:i:s" }} + {{ prop.data_recebimento|localtime|date:"d/m/Y H:i:s" }} {{ prop.tipo.descricao }} {{ prop.descricao }} {{ prop.autor }} diff --git a/sapl/templates/materia/proposicao_detail.html b/sapl/templates/materia/proposicao_detail.html index ab1939aa9..ee42b7ace 100644 --- a/sapl/templates/materia/proposicao_detail.html +++ b/sapl/templates/materia/proposicao_detail.html @@ -1,6 +1,6 @@ {% extends "crud/detail.html" %} {% load i18n common_tags %} - +{% load tz %} {% block sub_actions %}{{block.super}}
{% if object.texto_articulado.exists %} @@ -62,7 +62,7 @@
diff --git a/sapl/templates/materia/recibo_proposicao.html b/sapl/templates/materia/recibo_proposicao.html index a8b15d2b7..a2ec81039 100644 --- a/sapl/templates/materia/recibo_proposicao.html +++ b/sapl/templates/materia/recibo_proposicao.html @@ -1,4 +1,5 @@ {% load i18n %} +{% load tz %} {% load crispy_forms_tags %} {% load static %} @@ -49,7 +50,7 @@ Autor: {{proposicao.autor}} - Data de Envio: {{proposicao.data_envio|date:"d/m/Y H:i:s"}} + Data de Envio: {{proposicao.data_envio|localtime|date:"d/m/Y H:i:s"}} Descrição: {{proposicao.descricao}} diff --git a/sapl/templates/protocoloadm/protocolo_filter.html b/sapl/templates/protocoloadm/protocolo_filter.html index 42a9cb840..d50439ae8 100644 --- a/sapl/templates/protocoloadm/protocolo_filter.html +++ b/sapl/templates/protocoloadm/protocolo_filter.html @@ -1,5 +1,6 @@ {% extends "protocoloadm/protocoloadm_detail.html" %} {% load i18n %} +{% load tz %} {% load crispy_forms_tags %} {% load static %} @@ -44,6 +45,7 @@
Assunto: {{ p.assunto_ementa|default_if_none:"Não informado"}}
Data Protocolo: {{ p.data|date:"d/m/Y"|default_if_none:"Não informado" }} - Horário: {{ p.hora|date:"G:i:s" }}
+ Data Protocolo: {{ p.data|date:"d/m/Y"|default_if_none:"Não informado" }} - Horário: {{ p.timestamp|localtime|date:"G:i:s" }}
{% if p.tipo_processo == 0 %} Interessado: {{ p.interessado|default_if_none:"Não informado" }}
diff --git a/sapl/templates/protocoloadm/protocolo_list.html b/sapl/templates/protocoloadm/protocolo_list.html index 8abcb0d7c..f525745c5 100644 --- a/sapl/templates/protocoloadm/protocolo_list.html +++ b/sapl/templates/protocoloadm/protocolo_list.html @@ -1,8 +1,8 @@ {% extends "protocoloadm/protocoloadm_detail.html" %} {% load i18n %} +{% load tz %} {% load crispy_forms_tags %} {% load static %} - {% block detail_content %} {% if protocolos %} @@ -20,7 +20,7 @@ Etiqueta Individual
Assunto: {{ p.assunto_ementa }}
- Data Protocolo: {{ p.data|date:"d/m/Y" }} - Horário: {{ p.hora|date:"H:m:s" }}
+ Data Protocolo: {{ p.data|date:"d/m/Y" }} - Horário: {{ p.timestamp|localtime|date:"H:m:s" }}
Natureza do Processo: {% if p.tipo_processo == 0 %} Administrativo
diff --git a/sapl/templates/protocoloadm/protocolo_mostrar.html b/sapl/templates/protocoloadm/protocolo_mostrar.html index bc8340b69..43d6e30c4 100644 --- a/sapl/templates/protocoloadm/protocolo_mostrar.html +++ b/sapl/templates/protocoloadm/protocolo_mostrar.html @@ -1,11 +1,12 @@ {% extends "protocoloadm/protocoloadm_detail.html" %} {% load i18n %} +{% load tz %} {% load crispy_forms_tags %} {% block detail_content %} Protocolo: {{ protocolo.numero|stringformat:'06d' }}/{{ protocolo.ano }}
Assunto: {{ protocolo.assunto_ementa|default:"Não informado" }}
- Data Protocolo: {{ protocolo.data|date:"d/m/Y" }} - Horário: {{ protocolo.hora|date:"H:i" }}
+ Data Protocolo: {{ protocolo.data|date:"d/m/Y" }} - Horário: {{ protocolo.timestamp|localtime|date:"H:i" }}
{% if protocolo.tipo_processo == 0 %} Interessado: {{ protocolo.interessado|default_if_none:"Não informado" }}
diff --git a/sapl/utils.py b/sapl/utils.py index d30d71625..7afa00d1a 100644 --- a/sapl/utils.py +++ b/sapl/utils.py @@ -2,7 +2,6 @@ import hashlib import logging import os import re -from datetime import date from functools import wraps from unicodedata import normalize as unicodedata_normalize @@ -18,7 +17,7 @@ from django.contrib.contenttypes.fields import (GenericForeignKey, GenericRel, GenericRelation) from django.core.exceptions import ValidationError from django.db.models import Q -from django.utils import six +from django.utils import six, timezone from django.utils.translation import ugettext_lazy as _ from django_filters.filterset import STRICTNESS from floppyforms import ClearableFileInput @@ -303,7 +302,8 @@ UF = [ ('EX', 'Exterior'), ] -RANGE_ANOS = [(year, year) for year in range(date.today().year, 1889, -1)] +RANGE_ANOS = [(year, year) for year in range(timezone.now().year, + 1889, -1)] RANGE_MESES = [ (1, 'Janeiro'),