Top.Mail.Ru
Ответы

Модуль email на языке Python

Имеется программа с графическим интерфейсом на tkinter'e, программа получает на входе один xlsx-файл с почтовыми адресами, также вводится тема и текст письма и вкладывается несколько файлов в формате xlsx и после этого происходит рассылка по адресам.
Так вот, в чем проблема. Все файлы имеют своё обязательное название и получатель должен получать файлы именно с такими названиями, но так как файлы на русском, а smtp поддерживает только английские названия файлов, то все прикрепленные вложения имеют название untitled.
Конечно мало верится, но может кто-то сталкивался с этим и поможет решить эту проблему.

По дате
По Рейтингу
Аватар пользователя
Новичок

Проблема с кодировкой файлов в электронных письмах может возникнуть, если не указать правильную кодировку при создании сообщений. В модуле email на языке Python есть несколько способов решения этой проблемы.

Первый способ - использовать параметр charset для указания кодировки файла при его вложении в письмо. Например, если вы хотите вложить файл "Файл.xlsx" в письмо и установить кодировку Windows-1251, то вы можете использовать следующий код:

from email.mime.multipart import MIMEMultipart
from email.mime.base import MIMEBase
from email import encoders

# Создание сообщения
msg = MIMEMultipart()
msg['Subject'] = 'Тема письма'
msg['From'] = 'youremail mail.com'
msg['To'] = 'recipient mail.com'

# Создание вложения
filename = 'Файл.xlsx'
attachment = open(filename, 'rb')
p = MIMEBase('application', 'octet-stream')
p.set_payload((attachment).read())
encoders.encode_base64(p)
p.add_header('Content-Disposition', "attachment; filename= %s" % filename.encode('cp1251').decode('utf-8'))
msg.attach(p)

# Отправка письма


Обратите внимание на строку кода, где мы устанавливаем заголовок Content-Disposition с помощью метода add_header. Мы используем кодировку cp1251, чтобы преобразовать название файла в набор байтов, а затем декодируем его обратно в Unicode, используя кодировку utf-8. Это позволяет отправлять файлы с русскими названиями в сообщениях электронной почты.

Если вы хотите автоматизировать процесс получения имен файлов на английском языке, вы можете использовать модуль transliterate для транслитерации русских символов в английские. Например, если вы хотите создать имя файла "Файл.xlsx", вы можете использовать следующий код:

from transliterate import translit

filename = 'Файл.xlsx'
filename_eng = translit(filename, 'ru', reversed=True)
print(filename_eng) # 'Fail.xlsx'

Здесь мы используем метод translit из модуля transliterate, чтобы преобразовать русские символы в соответствующие английские символы. Мы указываем параметр reversed=True, чтобы перевернуть порядок преобразования (т. е. заменить русские символы на соответствующие английские символы). Далее вы можете использовать это имя файла при создании вложений в письме.
Надеюсь, это поможет решить вашу проблему с вложениями в электронных письмах.

Аватар пользователя
Профи

Да, проблема с кодировкой имен файлов при использовании SMTP и русского языка в названиях файлов вполне возможна. Одним из способов решения этой проблемы является переименование файлов на английский язык перед их прикреплением к письму.

Для реализации этого вам понадобится модуль email и его методы. Вот пример кода, который может помочь вам решить проблему:

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051
 import smtplib 
from email.mime.multipart import MIMEMultipart 
from email.mime.text import MIMEText 
from email.mime.base import MIMEBase 
from email import encoders 
 
def send_email(subject, message, from_email, password, to_emails, attachments): 
    # Создаем сообщение 
    msg = MIMEMultipart() 
    msg['From'] = from_email 
    msg['To'] = ', '.join(to_emails) 
    msg['Subject'] = subject 
 
    # Добавляем текст письма 
    msg.attach(MIMEText(message, 'plain')) 
 
    # Прикрепляем файлы 
    for filename in attachments: 
        # Переименовываем файл на английский 
        english_filename = get_english_filename(filename) 
 
        # Открываем файл в режиме бинарного чтения 
        with open(filename, 'rb') as attachment: 
            part = MIMEBase('application', 'octet-stream') 
            part.set_payload(attachment.read()) 
            encoders.encode_base64(part) 
            part.add_header('Content-Disposition', f"attachment; filename= {english_filename}") 
            msg.attach(part) 
 
    # Отправляем письмо 
    with smtplib.SMTP('smtp.gmail.com', 587) as server: 
        server.starttls() 
        server.login(from_email, password) 
        server.send_message(msg) 
 
def get_english_filename(filename): 
    # Здесь можно написать функцию для перевода русского названия файла в английский 
    # Например, можно использовать модуль transliterate для транслитерации названия файла на английский 
    # Возвращаем переведенное имя файла 
    return translated_filename 
 
# Пример использования 
subject = "Тема письма" 
message = "Текст письма" 
from_email = "от_кого@example.com" 
password = "пароль" 
to_emails = ["получатель1@example.com", "получатель2@example.com"] 
attachments = ["файл1.xlsx", "файл2.xlsx", "файл3.xlsx"] 
 
send_email(subject, message, from_email, password, to_emails, attachments) 
 

В данном примере используется функция get_english_filename, которая может быть реализована с использованием модуля transliterate для транслитерации русского названия файла на английский. Вы можете выбрать подходящий способ транслитерации в зависимости от ваших потребностей.

Перед вызовом функции send_email вы можете вызвать функцию get_english_filename для каждого имени файла, чтобы получить английское имя файла перед прикреплением его к письму.