Sending emails with attachment in django
Asked Answered
U

2

29

I'm trying to send email with some images attached in django. Code used is this snippet : http://www.djangosnippets.org/snippets/1063/. I don't know, why the attachment part returns me a core error.

The code. forms.py

from django import forms
from common import slugify_unique
from django.conf import settings
from django.core.cache import cache
from django.contrib.admin import widgets    
from django.shortcuts import get_object_or_404                                   

class WorkForm(forms.Form):
    name = forms.CharField(label='Name and surname', max_length=64, required = True )
    nick = forms.CharField(label='nickname', max_length=40, required = True )
    email = forms.EmailField(label='e-mail', required = True )
    image1 = forms.Field(label='sample photo', widget = forms.FileInput,    required = True )
    image2 = forms.Field(label='sample photo', widget = forms.FileInput, required = True )
    image3 = forms.Field(label='sample photo', widget = forms.FileInput, required = True )
    text = forms.CharField(label='Few words about you', widget=forms.Textarea, required = False )

views.py

from forms import WorkForm
from django.core.mail import send_mail, EmailMessage


def work(request):
    template = 'other/work.html'                             
    
    if request.method == 'POST':
        form = WorkForm(request.POST, request.FILES)
        if form.is_valid():
            name = form.cleaned_data['name']
            nick = form.cleaned_data['nick']
            email = form.cleaned_data['email']
            subject = 'Work'
            text = form.cleaned_data['text']
            image1 = request.FILES['image1']
            image2 = request.FILES['image2']
            image3 = request.FILES['image3']
            try:
                mail = EmailMessage(subject, text, ['EMAIL_ADDRESS'], [email])
                mail.attach(image1.name, attach.read(), attach.content_type)
                mail.attach(image2.name, attach.read(), attach.content_type)
                mail.attach(image3.name, attach.read(), attach.content_type)
                mail.send()
                template = 'other/mail_sent.html'
            except:
                return "Attachment error"
            return render_to_response(template, {'form':form},
                              context_instance=RequestContext(request))   
    else:
        form = WorkForm()                              
    return render_to_response(template, {'form':form},
                  context_instance=RequestContext(request))

And here's error site image : http://img201.imageshack.us/img201/6027/coreerror.png What am I doing wrong ?

Unprincipled answered 16/3, 2010 at 20:33 Comment(0)
K
34

The error traceback you've posted doesn't seem to have anything to do with the actual code - it seems to be some sort of problem with middleware (presumably when rendering the 500 error page).

However, your error is probably caused by your use of the undefined variable name attach in the calls to mail.attach. You don't have an attach variable - you've called the posted files image1 etc, so you should use those names.

mail.attach(image1.name, image1.read(), image1.content_type)
mail.attach(image2.name, image2.read(), image2.content_type)
mail.attach(image3.name, image3.read(), image3.content_type)
Karajan answered 16/3, 2010 at 20:57 Comment(3)
can I use Django's send_email() method to attach files or I have to work with EmailMessage class in this case.Frasco
@chiragsoni It's better you use the EmailMessage class directly. See docs.djangoproject.com/en/dev/_modules/django/core/mail/…Bloodhound
I would say a cleaner answer to @chiragsoni's question is that it's not possible to use send_mail(). From documentation - "Not all features of the EmailMessage class are available through the send_mail() and related wrapper functions. If you wish to use advanced features, such as BCC’ed recipients, file attachments, or multi-part email, you’ll need to create EmailMessage instances directly"Petasus
F
2

Send Mail with attachment in Django

forms.py

from django import forms


class SendMailForm(forms.Form):
    email_id = forms.EmailField()
    email_cc = forms.EmailField()
    email_bcc = forms.EmailField()
    subject = forms.CharField(max_length=200)
    msg = forms.CharField(widget=forms.Textarea)
    attachment = forms.FileField()

views.py

from django.core.mail import EmailMessage
from django.shortcuts import render, HttpResponse, HttpResponseRedirect

from .forms import SendMailForm


# Create your views here.
def simple_send_mail(request):
    if request.method == 'POST':
        fm = SendMailForm(request.POST or None, request.FILES or None)
        if fm.is_valid():
            subject = fm.cleaned_data['subject']
            message = fm.cleaned_data['msg']
            from_mail = request.user.email
            print(from_mail)
            to_mail = fm.cleaned_data['email_id']
            to_cc = fm.cleaned_data['email_cc']
            to_bcc = fm.cleaned_data['email_bcc']
            print(fm.cleaned_data)
            attach = fm.cleaned_data['attachment']
            if from_mail and to_mail:
                try:
                    mail = EmailMessage(subject=subject, body=message, from_email=from_mail, to=[to_mail], bcc=[to_bcc],
                                        cc=[to_cc]
                                        )
                    mail.attach(attach.name, attach.read(), attach.content_type)
                    mail.send()
                # except Exception as ex:
                except ArithmeticError as aex:
                    print(aex.args)
                    return HttpResponse('Invalid header found')
                return HttpResponseRedirect('/mail/thanks/')
            else:
                return HttpResponse('Make sure all fields are entered and valid.')
    else:
        fm = SendMailForm()
    return render(request, 'mail/send_mail.html', {'fm': fm})

settings.py

# Email Configurations

# DEFAULT_FROM_EMAIL = ''
EMAIL_BACKEND = 'django.core.mail.backends.smtp.EmailBackend'
EMAIL_HOST = 'smtp.gmail.com'
EMAIL_HOST_USER = '[email protected]'
EMAIL_HOST_PASSWORD = '************'
EMAIL_PORT = 587
EMAIL_USE_TLS = True

send_mail.html

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Mail</title>
</head>
<body>
    <form method="POST" action="" enctype="multipart/form-data">
        {% csrf_token %}
        <center><h1>Mail send from "{{request.user.email}}"</h1></center>
        {{fm.as_p}}
        <input type="submit" value="Send">
    </form>
</body>
</html>
Floorer answered 6/10, 2021 at 11:43 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.