This commit is contained in:
fjrodriguez
2022-12-08 16:01:53 -06:00
parent 356653ed86
commit 3e2374508e
4 changed files with 291 additions and 105 deletions

View File

@@ -99,7 +99,7 @@ ACCOUNT_LOGOUT_REDIRECT_URL = '/accounts/login/'
ACCOUNT_SIGNUP_REDIRECT_URL =LOGIN_REDIRECT_URL ACCOUNT_SIGNUP_REDIRECT_URL =LOGIN_REDIRECT_URL
ACCOUNT_LOGOUT_ON_PASSWORD_CHANGE = True ACCOUNT_LOGOUT_ON_PASSWORD_CHANGE = True
EMAIL_TIMEOUT = 5 EMAIL_TIMEOUT = 10
#EMAIL_USE_TLS = True #EMAIL_USE_TLS = True
EMAIL_BACKEND = 'django.core.mail.backends.smtp.EmailBackend' EMAIL_BACKEND = 'django.core.mail.backends.smtp.EmailBackend'
EMAIL_HOST = 'secure.emailsrvr.com' EMAIL_HOST = 'secure.emailsrvr.com'

View File

@@ -2,6 +2,24 @@ from django import forms
from .models import Clientes from .models import Clientes
from datetime import datetime from datetime import datetime
class EmailForm(forms.Form):
RFC = forms.CharField(max_length=13, required=True)
mes = forms.CharField( max_length=4, required=True)
email = forms.EmailField(required=False)
subject = forms.CharField(max_length=100, required=False)
adjunto = forms.FileField(widget=forms.ClearableFileInput(
attrs={
'multiple': True,
'accept':'application/pdf,application/vnd.ms-excel',
}
), required=False)
message = forms.CharField(widget=forms.Textarea, required=True)
class Meta:
fields = '__all__'
class ClienteForm(forms.ModelForm): class ClienteForm(forms.ModelForm):
fecha_baja = forms.DateField( fecha_baja = forms.DateField(

View File

@@ -4,11 +4,12 @@ from django.http import HttpResponse
from django.http import JsonResponse from django.http import JsonResponse
from django.contrib.auth.decorators import login_required from django.contrib.auth.decorators import login_required
from .models import Clientes,Timbres,saldoModel,ErroresTimbres from .models import Clientes,Timbres,saldoModel,ErroresTimbres
from django.core.paginator import Paginator, EmptyPage, PageNotAnInteger from django.core.paginator import Paginator, EmptyPage, PageNotAnInteger
from django.db.models import Q from django.db.models import Q
import datetime import datetime
from django.views.generic.edit import UpdateView from django.views.generic.edit import UpdateView
from .forms import ClienteForm from .forms import ClienteForm,EmailForm
from django.contrib.auth.mixins import LoginRequiredMixin from django.contrib.auth.mixins import LoginRequiredMixin
from django.contrib.auth.mixins import UserPassesTestMixin from django.contrib.auth.mixins import UserPassesTestMixin
from asgiref.sync import sync_to_async from asgiref.sync import sync_to_async
@@ -26,17 +27,35 @@ import requests
import os import os
import re import re
from io import BytesIO from io import BytesIO
@login_required import functools
def send_timbres_Email(request):
RFC = request.GET.get('RFC', None)
mes = request.GET.get('mes', None)
@sync_to_async(thread_sensitive=False)
def send_timbres_Email(request):
req = request.method
if req == "POST":
form = EmailForm(request.POST, request.FILES)
if not form.is_valid():
messages.add_message(request, messages.ERROR, f'{form.errors}')
return redirect('index')
today = datetime.date.today() today = datetime.date.today()
year = today.year year = today.year
if mes is None or mes =='None':
RFC = request.GET.get('RFC', None) if req=='GET' else form.cleaned_data["RFC"]
mes = request.GET.get('mes', None) if req=='GET' else form.cleaned_data["mes"]
if mes is None or mes =='None':
mes = today.month mes = today.month
Cli = Clientes.objects.get(RFC=RFC)
subject = f'Timbres del Mes:{mes} RFC:{RFC}' if req=='GET' else ( form.cleaned_data["subject"] if 'subject' in form.cleaned_data.keys() else '' )
message = 'Envio de timbres por AS_Admin' if req=='GET' else ( form.cleaned_data["message"] if 'message' in form.cleaned_data.keys() else '' )
email = form.cleaned_data["email"] if 'email' in form.cleaned_data.keys() else ''
emails = [Cli.email] if req=='GET' else [ Cli.email, email ]
if len(emails) ==0 :
messages.add_message(request, messages.ERROR, f'La lista de correos esta vacia, favor de agregar un correo.')
return redirect('index')
dat =datetime.datetime(int(year), int(mes),1) dat =datetime.datetime(int(year), int(mes),1)
if dat.month in(1,3,5,7,8,10,12): if dat.month in(1,3,5,7,8,10,12):
@@ -83,20 +102,34 @@ def send_timbres_Email(request):
files = BytesIO(response.content) files = BytesIO(response.content)
#print('files: ',response.content)
Cli = Clientes.objects.get(RFC=RFC)
subject = f'Timbres del Mes:{mes} RFC:{RFC}'
message = 'Envio de timbres por AS_Admin'
email = Cli.email
try: try:
mail = EmailMessage(subject,message,settings.EMAIL_HOST_USER,[email]) mail = EmailMessage(subject,message,settings.EMAIL_HOST_USER,emails)
mail.attach(filename='Timbres.xls',content=files.getbuffer(),mimetype='application/vnd.ms-excel') mail.attach(filename='Timbres.xls',content=files.getbuffer(),mimetype='application/vnd.ms-excel')
adjunto = request.FILES.getlist('adjunto')
if req=='POST' and len(adjunto) >0:
total = functools.reduce(lambda a, b: a+b,[adj.size for adj in adjunto])
total += files.getbuffer().nbytes
if total > 2.5e+7:
messages.add_message(request, messages.ERROR, f'Se excedio el limite de 25 MegaBytes para los adjuntos')
return redirect('index')
try:
for adj in adjunto:
mail.attach(filename=adj.name,content=adj.read(),mimetype=adj.content_type)
except Exception as E:
messages.add_message(request, messages.ERROR, f'Error Adjuntos {E}')
return redirect('index')
mail.send() mail.send()
messages.success(request, 'Email Enviado correctamente.') messages.success(request, 'Email Enviado correctamente.')
except Exception as E: except Exception as E:
messages.error(request, f'Email no se envio correctamente.{E}') messages.error(request, f'Email no se envio correctamente.{E}')
return redirect('index') return redirect('index')
# def send_timbres_Email(request): # def send_timbres_Email(request):
# RFC = request.GET.get('RFC', None) # RFC = request.GET.get('RFC', None)
# mes = request.GET.get('mes', None) # mes = request.GET.get('mes', None)
@@ -167,7 +200,8 @@ def index(request):
context = { context = {
'lista':clientes_list, 'lista':clientes_list,
'mes':mes, 'mes':mes,
'filters':filters 'filters':filters,
'emailForm':EmailForm(),
} }
return render(request,'Clientes/index.html',context) return render(request,'Clientes/index.html',context)
@@ -249,11 +283,7 @@ def timbres_cliente(request, RFC):
conteo = lista.count() conteo = lista.count()
if conteo !=0 : lista =pageFunc(page,lista,50)
perPage = conteo // 2
else:
perPage = 1
lista =pageFunc(page,lista,perPage)
context ={ context ={
'lista':lista, 'lista':lista,

View File

@@ -1,6 +1,5 @@
{% extends "base.html" %} {% extends "base.html" %}
{% load widget_tweaks %}
{% block title %}Timbres{% endblock title %} {% block title %}Timbres{% endblock title %}
@@ -10,6 +9,7 @@ Timbres disponibles Comercio Digital: {{saldo.saldo}}
{% block content %} {% block content %}
<table class="table"> <table class="table">
<thead> <thead>
<tr> <tr>
@@ -54,10 +54,10 @@ Timbres disponibles Comercio Digital: {{saldo.saldo}}
</th> </th>
<th>Estado</th> <th>Estado</th>
<th scope="col">actions</th> <th scope="col">
<th>
<a target="_blank" rel="noopener noreferrer" href="{% url 'export_Excel' %}?mes={{mes}}">Excel Todos los clientes X Mes </a> <a target="_blank" rel="noopener noreferrer" href="{% url 'export_Excel' %}?mes={{mes}}">Excel Todos los clientes X Mes </a>
</th> </th>
</tr> </tr>
</thead> </thead>
<tbody> <tbody>
@@ -81,22 +81,117 @@ Timbres disponibles Comercio Digital: {{saldo.saldo}}
<td> <td>
{% if request.user.is_staff %} {% if request.user.is_staff %}
<a href="{% url 'timbres_cliente' obj.RFC %}" class="btn btn-info">Ver Timbres</a> <div class="btn-group">
<button type="button" class="btn btn-info dropdown-toggle" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
Acciones
</button>
<div class="dropdown-menu">
<a class="btn btn-outline-info w-100" href="{% url 'timbres_cliente' obj.RFC %}" >
<svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" fill="currentColor" class="bi bi-eye" viewBox="0 0 16 16">
<path d="M16 8s-3-5.5-8-5.5S0 8 0 8s3 5.5 8 5.5S16 8 16 8zM1.173 8a13.133 13.133 0 0 1 1.66-2.043C4.12 4.668 5.88 3.5 8 3.5c2.12 0 3.879 1.168 5.168 2.457A13.133 13.133 0 0 1 14.828 8c-.058.087-.122.183-.195.288-.335.48-.83 1.12-1.465 1.755C11.879 11.332 10.119 12.5 8 12.5c-2.12 0-3.879-1.168-5.168-2.457A13.134 13.134 0 0 1 1.172 8z"/>
<path d="M8 5.5a2.5 2.5 0 1 0 0 5 2.5 2.5 0 0 0 0-5zM4.5 8a3.5 3.5 0 1 1 7 0 3.5 3.5 0 0 1-7 0z"/>
</svg>
Ver Timbres
</a>
<div class="dropdown-divider"></div>
<button class="btn btn-outline-secondary w-100" id ="id_b_{{obj.RFC}}" onclick="aclick(event, '{{obj.RFC}}','{{obj.conteo_mes}}')">
<svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" fill="currentColor" class="bi bi-cloud-download" viewBox="0 0 16 16">
<path d="M4.406 1.342A5.53 5.53 0 0 1 8 0c2.69 0 4.923 2 5.166 4.579C14.758 4.804 16 6.137 16 7.773 16 9.569 14.502 11 12.687 11H10a.5.5 0 0 1 0-1h2.688C13.979 10 15 8.988 15 7.773c0-1.216-1.02-2.228-2.313-2.228h-.5v-.5C12.188 2.825 10.328 1 8 1a4.53 4.53 0 0 0-2.941 1.1c-.757.652-1.153 1.438-1.153 2.055v.448l-.445.049C2.064 4.805 1 5.952 1 7.318 1 8.785 2.23 10 3.781 10H6a.5.5 0 0 1 0 1H3.781C1.708 11 0 9.366 0 7.318c0-1.763 1.266-3.223 2.942-3.593.143-.863.698-1.723 1.464-2.383z"></path>
<path d="M7.646 15.854a.5.5 0 0 0 .708 0l3-3a.5.5 0 0 0-.708-.708L8.5 14.293V5.5a.5.5 0 0 0-1 0v8.793l-2.146-2.147a.5.5 0 0 0-.708.708l3 3z"></path>
</svg>
Excel
</button>
<a style="display: none;" id="id_a_{{obj.RFC}}" target="_blank" rel="noopener noreferrer" href="{% url 'export_Excel' %}?RFC={{obj.RFC}}&mes={{mes}}">
Excel
</a>
<div class="dropdown-divider"></div>
<a class="btn btn-info w-100" href="{% url 'send_timbres_Email' %}?RFC={{obj.RFC}}&mes={{mes}}" >
<div>
<svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" fill="currentColor" class="bi bi-envelope-at" viewBox="0 0 16 16">
<path d="M2 2a2 2 0 0 0-2 2v8.01A2 2 0 0 0 2 14h5.5a.5.5 0 0 0 0-1H2a1 1 0 0 1-.966-.741l5.64-3.471L8 9.583l7-4.2V8.5a.5.5 0 0 0 1 0V4a2 2 0 0 0-2-2H2Zm3.708 6.208L1 11.105V5.383l4.708 2.825ZM1 4.217V4a1 1 0 0 1 1-1h12a1 1 0 0 1 1 1v.217l-7 4.2-7-4.2Z"/>
<path d="M14.247 14.269c1.01 0 1.587-.857 1.587-2.025v-.21C15.834 10.43 14.64 9 12.52 9h-.035C10.42 9 9 10.36 9 12.432v.214C9 14.82 10.438 16 12.358 16h.044c.594 0 1.018-.074 1.237-.175v-.73c-.245.11-.673.18-1.18.18h-.044c-1.334 0-2.571-.788-2.571-2.655v-.157c0-1.657 1.058-2.724 2.64-2.724h.04c1.535 0 2.484 1.05 2.484 2.326v.118c0 .975-.324 1.39-.639 1.39-.232 0-.41-.148-.41-.42v-2.19h-.906v.569h-.03c-.084-.298-.368-.63-.954-.63-.778 0-1.259.555-1.259 1.4v.528c0 .892.49 1.434 1.26 1.434.471 0 .896-.227 1.014-.643h.043c.118.42.617.648 1.12.648Zm-2.453-1.588v-.227c0-.546.227-.791.573-.791.297 0 .572.192.572.708v.367c0 .573-.253.744-.564.744-.354 0-.581-.215-.581-.8Z"/>
</svg>
<svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" fill="currentColor" class="bi bi-send" viewBox="0 0 16 16">
<path d="M15.854.146a.5.5 0 0 1 .11.54l-5.819 14.547a.75.75 0 0 1-1.329.124l-3.178-4.995L.643 7.184a.75.75 0 0 1 .124-1.33L15.314.037a.5.5 0 0 1 .54.11ZM6.636 10.07l2.761 4.338L14.13 2.576 6.636 10.07Zm6.787-8.201L1.591 6.602l4.339 2.76 7.494-7.493Z"/>
</svg>
</div>
Email Timbres
</a>
<div class="dropdown-divider"></div>
<!-- Button trigger modal -->
<button class="btn btn-primary w-100" onclick="addValues('{{obj.RFC}}')" type="button" data-toggle="modal" data-target="#exampleModalCenter">
<svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" fill="currentColor" class="bi bi-envelope-plus" viewBox="0 0 16 16">
<path d="M2 2a2 2 0 0 0-2 2v8.01A2 2 0 0 0 2 14h5.5a.5.5 0 0 0 0-1H2a1 1 0 0 1-.966-.741l5.64-3.471L8 9.583l7-4.2V8.5a.5.5 0 0 0 1 0V4a2 2 0 0 0-2-2H2Zm3.708 6.208L1 11.105V5.383l4.708 2.825ZM1 4.217V4a1 1 0 0 1 1-1h12a1 1 0 0 1 1 1v.217l-7 4.2-7-4.2Z"/>
<path d="M16 12.5a3.5 3.5 0 1 1-7 0 3.5 3.5 0 0 1 7 0Zm-3.5-2a.5.5 0 0 0-.5.5v1h-1a.5.5 0 0 0 0 1h1v1a.5.5 0 0 0 1 0v-1h1a.5.5 0 0 0 0-1h-1v-1a.5.5 0 0 0-.5-.5Z"/>
</svg>
Enviar Email
</button>
</div>
</div>
{% endif %} {% endif %}
</td> </td>
<td>
<button class="btn btn-outline-info" id ="id_b_{{obj.RFC}}" onclick="aclick(event, '{{obj.RFC}}','{{obj.conteo_mes}}')">Excel</button>
<a style="display: none;" id="id_a_{{obj.RFC}}" target="_blank" rel="noopener noreferrer" href="{% url 'export_Excel' %}?RFC={{obj.RFC}}&mes={{mes}}">Excel</a>
<a href="{% url 'send_timbres_Email' %}?RFC={{obj.RFC}}&mes={{mes}}" >Email Timbres</a>
</td>
</tr> </tr>
{% endfor %} {% endfor %}
</tbody> </tbody>
</table> </table>
<div id='id_filters' style="display: none;">{% for i,v in filters.items %}&{{i}}={{v}}{% endfor%}</div> <div id='id_filters' style="display: none;">{% for i,v in filters.items %}&{{i}}={{v}}{% endfor%}</div>
<!-- Modal -->
<div class="modal fade" data-backdrop="static" id="exampleModalCenter" tabindex="-1" role="dialog" aria-labelledby="exampleModalCenterTitle" aria-hidden="true">
<form enctype="multipart/form-data" id="id_form" action="{% url 'send_timbres_Email' %}" method="post">
{% csrf_token %}
<div class="modal-dialog modal-dialog-centered" role="document">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="exampleModalCenterTitle">Enviar Email</h5>
<button id="cerrar2" type="button" class="close" data-dismiss="modal" aria-label="Close">
<span aria-hidden="true">&times;</span>
</button>
</div>
<div class="modal-body">
<div class="form-group">
<label for="email"><strong> Email </strong></label>
<input type="email" name="email" id="email_add" autocomplete="off" class="form-control" placeholder="Email">
</div>
<div class="form-group">
<label for="subject"><strong> Subject </strong></label>
<input type="text" name="subject" maxlength="100" id="subject_add" autocomplete="off" class="form-control" placeholder="Subject">
</div>
<div class="form-group">
<label for="adjunto"><strong> Adjunto</strong></label>
<!--input type="file" name="adjunto" multiple="" id="adjunto_add" autocomplete="off" class="form-control" placeholder="Adjunto"-->
{{emailForm.adjunto}}
</div>
<div class="form-group">
<label for="message"><strong> Message </strong></label>
<textarea name="message" cols="40" rows="10" id="message_add" autocomplete="off" class="form-control" placeholder="Message" ></textarea>
</div>
<div hidden class="form-group">
<label for="RFC"><strong> Rfc </strong></label>
<input type="text" name="RFC" maxlength="13" id="RFC_add" autocomplete="off" class="form-control" placeholder="RFC" required>
</div>
<div hidden class="form-group">
<label for="mes"><strong> Mes </strong></label>
<input type="text" name="mes" maxlength="2" value="{{mes}}" id="mes_add" autocomplete="off" class="form-control" placeholder="Mes" required>
</div>
</div>
<div class="modal-footer">
<button id="cerrar1" type="button" class="btn btn-secondary" data-dismiss="modal">Cerrar</button>
<button id="enviar_btn" type="submit" class="btn btn-primary">
<span id="spinner_enviar" style="display:none;" class="spinner-grow spinner-grow-sm" role="status" aria-hidden="false"></span>
Enviar
</button>
</div>
</div>
</div>
</form>
</div>
{% endblock content %} {% endblock content %}
{% block scripts %} {% block scripts %}
@@ -138,6 +233,49 @@ Timbres disponibles Comercio Digital: {{saldo.saldo}}
anc.click() anc.click()
}) })
enviar_btn.addEventListener('click',(e)=>{
if(id_form.checkValidity()){
//
spinner_enviar.removeAttribute('style');
/*
id_form.getElementsByTagName('*');
for (var node of childNodes) {
node.disabled = true;
}
*/
}
})
id_adjunto.addEventListener('change',(e)=>{
if(id_adjunto.files.length){
let fsize;
for (var i =0; i<= id_adjunto.files.length-1; i++){
fsize = id_adjunto.files.item(i).size
fsize +=fsize;
console.log(((fsize/1024)/1024))
if( 25 <= ((fsize/1024)/1024) ){
alert('Limite excedido de 25 MegaBytes adjuntos');
id_adjunto.value=''
return false;
}
}
}
})
cerrar1.addEventListener('click', (event)=>{
id_form.reset()
})
cerrar2.addEventListener('click', (event)=>{
id_form.reset()
})
function addValues(RFC){
RFC_add.value = RFC
console.log('RFC', RFC)
}
</script> </script>
{% endblock scripts %} {% endblock scripts %}