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.
 
 
 
 
 
 

233 lines
11 KiB

import os
from datetime import datetime, date, timedelta
from PIL import Image
from PIL import ImageFont
from PIL import ImageDraw
from unidecode import unidecode
from django.contrib.auth import get_user_model
from django.contrib.contenttypes.models import ContentType
from django.contrib.staticfiles.storage import staticfiles_storage
from django.utils.timezone import now
from django.conf import settings
from django.utils.text import slugify
from apps.notification.models import UserNotification
from apps.notification.utils import send_email
from apps.payment.models import SchoolPayment, CoursePayment, Payment, UserGiftCertificate, UserBonus, DrawingCampPayment
from project.celery import app
from project.utils.db import format_sql, execute_sql
from project.sengrid import get_sendgrid_client
from apps.user.models import Child
User = get_user_model()
def draw_cert(path, email, first_name, last_name, x=None, y=900, color=(29, 115, 224), font_size=170, fn_prefix=''):
img = Image.open(path)
draw = ImageDraw.Draw(img)
font = ImageFont.truetype(os.path.join(settings.STATIC_ROOT, 'ProximaNova-Reg.otf'), font_size)
text = first_name.capitalize()
if last_name:
text += ' ' + last_name.capitalize()
w, h = draw.textsize(text, font=font)
_x = (img.width - w) // 2 if x is None else x
draw.text((_x, y), text, color, font=font)
fn = os.path.join(settings.MEDIA_ROOT, 'tmp')
try:
os.mkdir(fn)
except:
pass
if first_name:
name = '-'.join(filter(None, [first_name, last_name]))
fn = os.path.join(fn, '%scertificate-for-%s-%s.jpg' % (fn_prefix, email, slugify(unidecode(name))))
else:
fn = os.path.join(fn, '%scertificate-for-%s.jpg' % (fn_prefix, email))
img.save(fn)
img.close()
return fn
@app.task
def send_certificates(email=None, date_end=None, dry_run=False, users=None, subject='Грамота от Lil School',
template='notification/email/certificate.html'):
signed_path_pattern = 'signed-user-certificates/%d.jpg'
if email:
try:
send_email('Грамота от Lil School', email, 'notification/email/certificate.html',
childs=[], certificate_number=1, many_childs=False, child_filled=False)
except:
pass
else:
print('Email has been sent')
finally:
return
date_end = datetime.strptime(date_end, '%d-%m-%Y').date() if date_end else now().date()
today = now().date()
if users is None:
users = set(list(SchoolPayment.objects.paid().filter(date_end=date_end, add_days=False).values_list('user_id', flat=True)))
user_notifications_qs = UserNotification.objects.filter(user_id__in=users)
user_notifications = {un.user_id: un for un in user_notifications_qs}
notified_users = user_notifications_qs.filter(certificate_last_email__date=today).values_list(
'user_id', flat=True).distinct()
for user_id in users:
if user_id in notified_users:
print('skip', user_id)
continue
un = user_notifications.get(user_id, UserNotification(user_id=user_id))
print(un.user.email)
if dry_run:
continue
un.certificate_number = un.certificate_number + 1 \
if un.certificate_number and os.path.isfile(os.path.join(settings.RESOURCES_ROOT,
signed_path_pattern % (un.certificate_number + 1))) \
else 1
un.save()
try:
send_email(subject, un.user.email, template,
childs=un.user.childs.all(), certificate_number=un.certificate_number,
many_childs=un.user.childs.all().count() > 1, child_filled=un.user.child_filled)
except Exception as e:
print('Not OK')
print(e)
continue
un.certificate_last_email = now()
un.save()
@app.task
def sendgrid_update_recipients():
date_format = '%m/%d/%Y'
ct_course = ContentType.objects.get_for_model(CoursePayment).id
ct_school = ContentType.objects.get_for_model(SchoolPayment).id
course_payments_sql = '''
select {p.user}, max({p.created_at}) from {p} where {p}.polymorphic_ctype_id = {ct} group by {p.user}
'''
course_payments = {p[0]: p[1] for p in execute_sql(format_sql(course_payments_sql, p=Payment, ct=ct_course))}
school_payments_sql = '''
select {p.user}, max({p.created_at}) from {p} where {p}.polymorphic_ctype_id = {ct} group by {p.user}
'''
school_payments = {p[0]: p[1] for p in execute_sql(format_sql(school_payments_sql, p=Payment, ct=ct_school))}
users = list(User.objects.filter(role=User.USER_ROLE))
data = []
for user in users:
last_course_purchase = course_payments.get(user.id) and course_payments.get(user.id).strftime(date_format)
last_school_purchase = school_payments.get(user.id) and school_payments.get(user.id).strftime(date_format)
courses_purchased = CoursePayment.objects.filter(user=user,
status__in=CoursePayment.PW_PAID_STATUSES).values_list('course_id', flat=True)
data.append({
'first_name': user.first_name,
'last_name': user.last_name,
'email': user.email,
'last_login': user.last_login and user.last_login.strftime(date_format),
'last_course_purchase': last_course_purchase,
'last_school_purchase': last_school_purchase,
# 'gender': {User.NOT_DEFINED: '', User.MALE: 'Мужчина', User.FEMALE: 'Женщина'}[user.gender] if user.gender else '',
'birthday': user.birthday and user.birthday.strftime(date_format),
'date_joined': user.date_joined.strftime(date_format),
'courses_purchased': ','.join(map(str, courses_purchased)) + ',' if courses_purchased else '',
})
sg = get_sendgrid_client()
response = sg.client.contactdb.recipients.patch(request_body=data)
print(response.body)
@app.task
def send_gift_certificate(user_gift_certificate):
user_gift_certificate = UserGiftCertificate.objects.get(id=user_gift_certificate)
send_email('Подарочный сертификат от Lil School', user_gift_certificate.user.email, 'notification/email/gift_certificate.html',
inline_images=[('twitter_icon', 'img/twitter.png'), ('fb_icon', 'img/fb.png'), ('instagram_icon', 'img/instagram.png'),],
user_gift_certificate=user_gift_certificate, gift_certificate=user_gift_certificate.gift_certificate)
@app.task
def send_child_birthday_email_and_bonuses():
today = now().date()
for user_id, email in set(Child.objects.filter(birthday__day=today.day, birthday__month=today.month).select_related('user')
.values_list('user_id', 'user__email')):
print('user', email)
if not UserBonus.objects.filter(user_id=user_id, is_service=True, action_name=UserBonus.ACTION_CHILD_BIRTHDAY,
created_at__year=today.year).count():
UserBonus.objects.create(user_id=user_id, amount=UserBonus.AMOUNT_CHILD_BIRTHDAY, is_service=True,
action_name=UserBonus.ACTION_CHILD_BIRTHDAY)
try:
fn = staticfiles_storage.path('img/birthday_postcard.jpg')
file = open(fn, 'rb')
send_email('С Днем Рождения!', email, 'notification/email/birthday_postcard.html',
attachments=[(file.name, file.read(), 'image/jpeg')],)
print('email has been sent')
finally:
file.close()
@app.task
def send_camp_certificates(email=None, dry_run=False, certificate_number=None):
path_pattern = 'camp-certificates/%d.jpg'
signed_path_pattern = 'signed-camp-certificates/%d.jpg'
color = (0, 27, 94)
if certificate_number is None:
certificate_number = 1
if certificate_number == 2:
color = (106, 5, 163)
if certificate_number == 3:
color = (24, 57, 220)
if email:
fn = draw_cert(os.path.join(settings.RESOURCES_ROOT, signed_path_pattern % certificate_number), email, 'Имя', 'Фамилия',
font_size=120, y=1000, color=color)
file = open(fn, 'rb')
try:
send_email('Грамота от Lil School', email, 'notification/email/camp_certificate.html',
attachments=[(file.name, file.read(), 'image/jpeg')], certificate_number=certificate_number)
# send_email('Грамота от Lil School', email, 'notification/email/camp_certificate.html',
# attachments=[('file', '', 'image/jpeg')], certificate_number=certificate_number)
except Exception as e:
print(e)
else:
print('Email has been sent')
finally:
file.close()
return
date_end = date(now().year, 6 + certificate_number, 1) - timedelta(1)
users = set(list(DrawingCampPayment.objects.paid().filter(date_end=date_end).values_list('user_id', flat=True)))
user_notifications_qs = UserNotification.objects.filter(user_id__in=users)
user_notifications = {un.user_id: un for un in user_notifications_qs}
notified_users = user_notifications_qs.filter(camp_certificate_last_email__date=date_end).values_list(
'user_id', flat=True).distinct()
for user_id in users:
if user_id in notified_users:
print('skip', user_id)
continue
un = user_notifications.get(user_id, UserNotification(user_id=user_id))
print(un.user.email)
if dry_run:
continue
file_names = []
if un.user.child_filled:
fn = os.path.join(settings.RESOURCES_ROOT, signed_path_pattern % certificate_number)
for child in un.user.childs.all():
file_names.append(draw_cert(fn, un.user.email, child.first_name, child.last_name,
font_size=120, y=1000, color=color))
else:
file_names.append(os.path.join(settings.RESOURCES_ROOT, path_pattern % certificate_number))
files = [open(fn, 'rb') for fn in file_names]
try:
send_email('Грамота от Lil School', un.user.email, 'notification/email/camp_certificate.html',
attachments=[(f.name, f.read(), 'image/jpeg') for f in files], user_notification=un,
certificate_number=certificate_number, many_childs=un.user.childs.all().count() > 1)
except:
print('Not OK')
continue
finally:
un.camp_certificate_last_email = date_end
un.save()
for f in files:
f.close()
if un.user.child_filled:
for fn in file_names:
if os.path.isfile(fn):
os.remove(fn)