Документация Python неофициальный перевод

email.contentmanager.md

192 строк · 32.4 КБ · обычная страница · сырой текст · скачать

1> **Источник:** https://python-all.ru/3.4/library/email.contentmanager.html2>3> «Документация Python на русском» – неофициальный перевод официальной документации Python: версии от 2.6 до 3.16, полнотекстовый поиск, английский оригинал рядом с переводом. Эта Markdown-версия страницы предназначена для работы с LLM: вставьте её в ChatGPT, Claude или Cursor.45---67# 19.1.6. [`email.contentmanager`](https://python-all.ru/3.4/library/email.contentmanager.html#module-email.contentmanager): Управление MIME-содержимым89> **Примечание**10>11> Модуль contentmanager был включен в стандартную библиотеку на [*временной основе*](https://python-all.ru/3.4/glossary.html#term-provisional-package). Обратно несовместимые изменения (вплоть до удаления модуля) могут быть внесены, если основные разработчики сочтут это необходимым.1213Новое в версии 3.4: как [*временный модуль*](https://python-all.ru/3.4/glossary.html#term-provisional-package).1415Модуль [`message`](https://python-all.ru/3.4/library/email.message.html#module-email.message) предоставляет класс, который может представлять произвольное email-сообщение. Эта базовая модель сообщения имеет полезный и гибкий API, но предоставляет только низкоуровневый API для взаимодействия с общими частями сообщения (заголовки, общие параметры заголовков и полезная нагрузка, которая может быть списком подчастей). Данный модуль предоставляет классы и инструменты, которые обеспечивают улучшенный и расширяемый API для работы с различными конкретными типами содержимого, включая возможность извлекать содержимое сообщения в виде специализированного объекта, а не простого объекта bytes. Модуль автоматически обрабатывает указанные в RFC детали MIME (обязательные заголовки и параметры и т.д.) для определённых распространённых типов содержимого, а поддержка дополнительных типов может быть добавлена приложением с помощью механизмов расширения.1617Этот модуль определяет одноимённые классы «Content Manager». Базовый класс [`ContentManager`](https://python-all.ru/3.4/library/email.contentmanager.html#email.contentmanager.ContentManager) определяет API для регистрации функций управления содержимым, которые извлекают данные из объектов `Message` или вставляют данные и заголовки в объекты `Message`, предоставляя тем самым способ преобразования между объектами `Message`, содержащими данные, и другими представлениями этих данных (типы данных Python, специализированные объекты Python, внешние файлы и т.д.). Модуль также определяет один конкретный менеджер содержимого: [`raw_data_manager`](https://python-all.ru/3.4/library/email.contentmanager.html#email.contentmanager.raw_data_manager) преобразует между типами MIME-содержимого и данными `str` или `bytes`. Он также предоставляет удобный API для управления параметрами MIME при вставке содержимого в объекты `Message`. Он также обрабатывает вставку и извлечение объектов `Message` при работе с типом содержимого `message/rfc822`.1819Ещё одна часть улучшенного интерфейса – подклассы [`Message`](https://python-all.ru/3.4/library/email.message.html#email.message.Message), предоставляющие новые удобные функции API, включая удобные методы для вызова Content Managers, производных от этого модуля.2021> **Примечание**22>23> Хотя [`EmailMessage`](https://python-all.ru/3.4/library/email.contentmanager.html#email.message.EmailMessage) и [`MIMEPart`](https://python-all.ru/3.4/library/email.contentmanager.html#email.message.MIMEPart) в настоящее время документированы в этом модуле из-за предварительного характера кода, реализация находится в модуле [`email.message`](https://python-all.ru/3.4/library/email.message.html#module-email.message).2425#### `class email.message.EmailMessage(policy=default)`2627Если указан *policy* (он должен быть экземпляром класса [`policy`](https://python-all.ru/3.4/library/email.policy.html#module-email.policy)), используйте заданные им правила для обновления и сериализации представления сообщения. Если *policy* не задан, используется политика [`default`](https://python-all.ru/3.4/library/email.policy.html#email.policy.default), которая следует правилам RFC для email, за исключением окончаний строк (вместо предписанного RFC `\r\n` используются стандартные для Python окончания строк `\n`). Дополнительную информацию см. в документации [`policy`](https://python-all.ru/3.4/library/email.policy.html#module-email.policy).2829Этот класс является подклассом [`Message`](https://python-all.ru/3.4/library/email.message.html#email.message.Message). Он добавляет следующие методы:3031#### `is_attachment()`3233Возвращает `True`, если присутствует заголовок *Content-Disposition* и его значение (без учёта регистра) равно `attachment`, иначе `False`.3435Изменено в версии 3.4.2: is\_attachment теперь является методом, а не свойством, для согласованности с [`is_multipart()`](https://python-all.ru/3.4/library/email.message.html#email.message.Message.is_multipart).3637#### `get_body(preferencelist=('related', 'html', 'plain'))`3839Возвращает MIME-часть, которая наилучшим образом подходит на роль «тела» сообщения.4041*preferencelist* должен быть последовательностью строк из набора `related`, `html` и `plain`, и указывает порядок предпочтения типа содержимого возвращаемой части.4243Начинает поиск подходящих кандидатов с объекта, на котором вызывается метод `get_body`.4445Если `related` не включён в *preferencelist*, то рассматривать корневую часть (или подчасть корневой части) любого встреченного related как кандидата, если (под)часть соответствует предпочтению.4647При обнаружении `multipart/related` проверьте параметр `start`, и если найдена часть с соответствующим *Content-ID*, при поиске подходящих кандидатов рассматривайте только её. В противном случае рассматривайте только первую (корневую по умолчанию) часть `multipart/related`.4849Если часть имеет заголовок *Content-Disposition*, считайте её подходящим кандидатом, только если значение заголовка равно `inline`.5051Если ни один из кандидатов не соответствует ни одному из предпочтений в *preferneclist*, возвращается `None`.5253Примечания: (1) Для большинства приложений единственными комбинациями *preferencelist*, которые действительно имеют смысл, являются `('plain',)`, `('html', 'plain')` и значение по умолчанию `('related', 'html', 'plain')`. (2) Поскольку поиск начинается с объекта, на котором вызывается `get_body`, вызов `get_body` на `multipart/related` вернёт сам объект, если только *preferencelist* не имеет нестандартного значения. (3) Сообщения (или части сообщений), не указывающие *Content-Type* или имеющие недопустимый заголовок *Content-Type*, будут обрабатываться как тип `text/plain`, что иногда может привести к неожиданным результатам `get_body`.5455#### `iter_attachments()`5657Возвращает итератор по всем частям сообщения, которые не являются подходящими «теловыми» частями. То есть пропускает первое вхождение каждого из `text/plain`, `text/html`, `multipart/related` или `multipart/alternative` (если только они явно не помечены как вложения через *Content-Disposition: attachment*) и возвращает все остальные части. При применении непосредственно к `multipart/related` возвращает итератор по всем связанным частям, кроме корневой части (т.е. части, на которую указывает параметр `start`, или первой части, если параметр `start` отсутствует, или параметр `start` не соответствует *Content-ID* ни одной из частей). При применении непосредственно к `multipart/alternative` или не-`multipart` возвращает пустой итератор.5859#### `iter_parts()`6061Возвращает итератор по всем непосредственным подчастям сообщения, который будет пуст для не-`multipart`. (См. также `walk()`.)6263#### `get_content(*args, content_manager=None, **kw)`6465Вызывает метод `get_content` объекта *content\_manager*, передавая self в качестве объекта сообщения, а также любые другие аргументы или ключевые слова в качестве дополнительных аргументов. Если *content\_manager* не указан, используется `content_manager`, заданный текущим [`policy`](https://python-all.ru/3.4/library/email.policy.html#module-email.policy).6667#### `set_content(*args, content_manager=None, **kw)`6869Вызывает метод `set_content` объекта *content\_manager*, передавая self в качестве объекта сообщения, а также любые другие аргументы или ключевые слова в качестве дополнительных аргументов. Если *content\_manager* не указан, используется `content_manager`, заданный текущим [`policy`](https://python-all.ru/3.4/library/email.policy.html#module-email.policy).7071#### `make_related(boundary=None)`7273Преобразует не-`multipart` сообщение в сообщение `multipart/related`, перемещая все существующие заголовки *Content-* и полезную нагрузку в (новую) первую часть `multipart`. Если указан *boundary*, используйте его как строку границы в multipart, в противном случае оставьте границу, чтобы она была создана автоматически, когда потребуется (например, при сериализации сообщения).7475#### `make_alternative(boundary=None)`7677Преобразует не-`multipart` или `multipart/related` в `multipart/alternative`, перенося все существующие заголовки *Content-* и полезную нагрузку в (новую) первую часть `multipart`. Если указан *boundary*, использовать его как строку границы в multipart, в противном случае оставить границу для автоматического создания, когда она понадобится (например, при сериализации сообщения).7879#### `make_mixed(boundary=None)`8081Преобразует не-`multipart`, `multipart/related` или `multipart-alternative` в `multipart/mixed`, перенося все существующие заголовки *Content-* и полезную нагрузку в (новую) первую часть `multipart`. Если указан *boundary*, использовать его как строку границы в multipart, в противном случае оставить границу для автоматического создания, когда она понадобится (например, при сериализации сообщения).8283#### `add_related(*args, content_manager=None, **kw)`8485Если сообщение является `multipart/related`, создаёт новый объект сообщения, передаёт все аргументы его методу [`set_content()`](https://python-all.ru/3.4/library/email.contentmanager.html#email.message.EmailMessage.set_content) и [`присоединяет`](https://python-all.ru/3.4/library/email.message.html#email.message.Message.attach) его к `multipart`. Если сообщение является не-`multipart`, вызывает [`make_related()`](https://python-all.ru/3.4/library/email.contentmanager.html#email.message.EmailMessage.make_related) и затем действует как описано выше. Если сообщение относится к любому другому типу `multipart`, возбуждает [`TypeError`](https://python-all.ru/3.4/library/exceptions.html#TypeError). Если *content\_manager* не указан, используется `content_manager`, заданный текущей [`политикой`](https://python-all.ru/3.4/library/email.policy.html#module-email.policy). Если добавленная часть не имеет заголовка *Content-Disposition*, добавляется заголовок со значением `inline`.8687#### `add_alternative(*args, content_manager=None, **kw)`8889Если сообщение является `multipart/alternative`, создаёт новый объект сообщения, передаёт все аргументы его методу [`set_content()`](https://python-all.ru/3.4/library/email.contentmanager.html#email.message.EmailMessage.set_content) и [`присоединяет`](https://python-all.ru/3.4/library/email.message.html#email.message.Message.attach) его к `multipart`. Если сообщение является не-`multipart` или `multipart/related`, вызывает [`make_alternative()`](https://python-all.ru/3.4/library/email.contentmanager.html#email.message.EmailMessage.make_alternative) и затем действует как описано выше. Если сообщение относится к любому другому типу `multipart`, возбуждает [`TypeError`](https://python-all.ru/3.4/library/exceptions.html#TypeError). Если *content\_manager* не указан, используется `content_manager`, заданный текущей [`политикой`](https://python-all.ru/3.4/library/email.policy.html#module-email.policy).9091#### `add_attachment(*args, content_manager=None, **kw)`9293Если сообщение является `multipart/mixed`, создаёт новый объект сообщения, передаёт все аргументы его методу [`set_content()`](https://python-all.ru/3.4/library/email.contentmanager.html#email.message.EmailMessage.set_content) и [`присоединяет`](https://python-all.ru/3.4/library/email.message.html#email.message.Message.attach) его к `multipart`. Если сообщение является не-`multipart`, `multipart/related` или `multipart/alternative`, вызывает [`make_mixed()`](https://python-all.ru/3.4/library/email.contentmanager.html#email.message.EmailMessage.make_mixed) и затем действует как описано выше. Если *content\_manager* не указан, используется `content_manager`, заданный текущей [`политикой`](https://python-all.ru/3.4/library/email.policy.html#module-email.policy). Если добавленная часть не имеет заголовка *Content-Disposition*, добавляет заголовок со значением `attachment`. Этот метод можно использовать как для явных вложений (*Content-Disposition: attachment*), так и для `inline` вложений (*Content-Disposition: inline*), передавая соответствующие параметры в `content_manager`.9495#### `clear()`9697Удаляет полезную нагрузку и все заголовки.9899#### `clear_content()`100101Удаляет полезную нагрузку и все заголовки `Content-`, оставляя все остальные заголовки нетронутыми и в их исходном порядке.102103#### `class email.message.MIMEPart(policy=default)`104105Этот класс представляет подчасть MIME-сообщения. Он идентичен [`EmailMessage`](https://python-all.ru/3.4/library/email.contentmanager.html#email.message.EmailMessage), за исключением того, что заголовки *MIME-Version* не добавляются при вызове [`set_content()`](https://python-all.ru/3.4/library/email.contentmanager.html#email.message.EmailMessage.set_content), поскольку подчасти не нуждаются в собственных заголовках *MIME-Version*.106107#### `class email.contentmanager.ContentManager`108109Базовый класс для менеджеров содержимого. Предоставляет стандартные механизмы реестра для регистрации преобразователей между MIME-содержимым и другими представлениями, а также диспетчерские методы `get_content` и `set_content`.110111#### `get_content(msg, *args, **kw)`112113Ищет функцию-обработчик на основе `mimetype` сообщения *msg* (см. следующий абзац), вызывает её, передавая все аргументы, и возвращает результат вызова. Ожидается, что обработчик извлечёт полезную нагрузку из *msg* и вернёт объект, кодирующий информацию об извлечённых данных.114115Для поиска обработчика ищутся следующие ключи в реестре; поиск прекращается при первом найденном:116117> - строка, представляющая полный MIME-тип (`maintype/subtype`)118> - строка, представляющая `maintype`119> - пустая строка120121Если ни один из этих ключей не даёт обработчика, возбуждает [`KeyError`](https://python-all.ru/3.4/library/exceptions.html#KeyError) для полного MIME-типа.122123#### `set_content(msg, obj, *args, **kw)`124125Если `maintype` является `multipart`, возбуждает [`TypeError`](https://python-all.ru/3.4/library/exceptions.html#TypeError); в противном случае ищет функцию-обработчик на основе типа *obj* (см. следующий абзац), вызывает [`clear_content()`](https://python-all.ru/3.4/library/email.contentmanager.html#email.message.EmailMessage.clear_content) на *msg* и вызывает функцию-обработчик, передавая все аргументы. Ожидается, что обработчик преобразует и сохранит *obj* в *msg*, возможно также внося другие изменения в *msg*, такие как добавление различных MIME-заголовков для кодирования информации, необходимой для интерпретации сохранённых данных.126127Чтобы найти обработчик, необходимо получить тип *obj* (`typ = type(obj)`) и искать следующие ключи в реестре, останавливаясь на первом найденном:128129> - сам тип (`typ`)130> - полное квалифицированное имя типа (`typ.__module__ + '.' + typ.__qualname__`).131> - qualname типа (`typ.__qualname__`)132> - имя типа (`typ.__name__`).133134Если ни одно из вышеперечисленных не совпадает, повторить все проверки выше для каждого из типов в [*MRO*](https://python-all.ru/3.4/glossary.html#term-mro) (`typ.__mro__`). Наконец, если ни один другой ключ не даёт обработчика, проверить наличие обработчика для ключа `None`. Если обработчика для `None` нет, возбуждает [`KeyError`](https://python-all.ru/3.4/library/exceptions.html#KeyError) для полного квалифицированного имени типа.135136Также добавляет заголовок *MIME-Version*, если он отсутствует (см. также [`MIMEPart`](https://python-all.ru/3.4/library/email.contentmanager.html#email.message.MIMEPart)).137138#### `add_get_handler(key, handler)`139140Записывает функцию *handler* как обработчик для *key*. Возможные значения *key* см. в [`get_content()`](https://python-all.ru/3.4/library/email.contentmanager.html#email.contentmanager.get_content).141142#### `add_set_handler(typekey, handler)`143144Записывает *handler* как функцию, которая будет вызываться, когда объект типа, соответствующего *typekey*, передаётся в [`set_content()`](https://python-all.ru/3.4/library/email.contentmanager.html#email.contentmanager.set_content). Возможные значения *typekey* см. в [`set_content()`](https://python-all.ru/3.4/library/email.contentmanager.html#email.contentmanager.set_content).145146## 19.1.6.1. Экземпляры Content Manager147148В настоящее время пакет email предоставляет только один конкретный менеджер содержимого – [`raw_data_manager`](https://python-all.ru/3.4/library/email.contentmanager.html#email.contentmanager.raw_data_manager), хотя в будущем могут быть добавлены другие. [`raw_data_manager`](https://python-all.ru/3.4/library/email.contentmanager.html#email.contentmanager.raw_data_manager) – это [`content_manager`](https://python-all.ru/3.4/library/email.policy.html#email.policy.EmailPolicy.content_manager), предоставляемый [`EmailPolicy`](https://python-all.ru/3.4/library/email.policy.html#email.policy.EmailPolicy) и его производными.149150#### `email.contentmanager.raw_data_manager`151152Этот менеджер содержимого предоставляет лишь минимальный интерфейс в дополнение к тому, что предоставляет сам [`Message`](https://python-all.ru/3.4/library/email.message.html#email.message.Message): он работает только с текстом, необработанными байтовыми строками и объектами [`Message`](https://python-all.ru/3.4/library/email.message.html#email.message.Message). Тем не менее он даёт значительные преимущества по сравнению с базовым API: `get_content` на текстовой части возвращает строку Unicode без необходимости вручную декодировать её, `set_content` предоставляет богатый набор опций для управления заголовками, добавляемыми в часть, и управления кодировкой передачи содержимого, а также позволяет использовать различные методы `add_`, упрощая тем самым создание multipart-сообщений.153154#### `email.contentmanager.get_content(msg, errors='replace')`155156Возвращает полезную нагрузку части как строку (для частей `text`), как объект [`EmailMessage`](https://python-all.ru/3.4/library/email.contentmanager.html#email.message.EmailMessage) (для частей `message/rfc822`) или как объект `bytes` (для всех других не-multipart типов). Вызывает [`KeyError`](https://python-all.ru/3.4/library/exceptions.html#KeyError) при вызове на `multipart`. Если часть является текстовой (`text`) и указан параметр *errors*, используйте его как обработчик ошибок при декодировании полезной нагрузки в Unicode. Обработчик ошибок по умолчанию – `replace`.157158#### `email.contentmanager.set_content(msg, <'str'>, subtype="plain", charset='utf-8' cte=None, disposition=None, filename=None, cid=None, params=None, headers=None)`159160#### `email.contentmanager.set_content(msg, <'bytes'>, maintype, subtype, cte="base64", disposition=None, filename=None, cid=None, params=None, headers=None)`161162#### `email.contentmanager.set_content(msg, <'Message'>, cte=None, disposition=None, filename=None, cid=None, params=None, headers=None)`163164#### `email.contentmanager.set_content(msg, <'list'>, subtype='mixed', disposition=None, filename=None, cid=None, params=None, headers=None)`165166Добавляет заголовки и содержимое в *msg*:167168Добавляет заголовок *Content-Type* со значением `maintype/subtype`.169170> - Для `str` устанавливает MIME-тип `maintype` в `text`, а подтип – в *subtype*, если он указан, или в `plain`, если нет.171> - Для `bytes` использует указанные *maintype* и *subtype* или вызывает [`TypeError`](https://python-all.ru/3.4/library/exceptions.html#TypeError), если они не указаны.172> - Для объектов [`Message`](https://python-all.ru/3.4/library/email.message.html#email.message.Message) устанавливает maintype в `message`, а subtype – в *subtype*, если он указан, или в `rfc822`, если нет. Если *subtype* равен `partial`, вызывает ошибку (объекты `bytes` должны использоваться для создания частей `message/partial`).173> - Для *\<’list’\>*, который должен быть списком объектов [`Message`](https://python-all.ru/3.4/library/email.message.html#email.message.Message), устанавливает `maintype` в `multipart`, а `subtype` – в *subtype*, если он указан, и в `mixed`, если нет. Если части сообщения в *\<’list’\>* содержат заголовки *MIME-Version*, удаляет их.174175Если указан *charset* (это допустимо только для `str`), кодирует строку в байты с использованием указанной кодировки. По умолчанию – `utf-8`. Если указанный *charset* является известным псевдонимом стандартного имени MIME-кодировки, используется стандартная кодировка.176177Если установлен *cte*, кодирует полезную нагрузку с использованием указанной кодировки передачи содержимого и устанавливает заголовок *Content-Transfer-Endcoding* в это значение. Для объектов `str`, если он не установлен, использует эвристику для определения наиболее компактной кодировки. Возможные значения *cte*: `quoted-printable`, `base64`, `7bit`, `8bit` и `binary`. Если входные данные не могут быть закодированы в указанной кодировке (например, `7bit`), вызывает [`ValueError`](https://python-all.ru/3.4/library/exceptions.html#ValueError). Для [`Message`](https://python-all.ru/3.4/library/email.message.html#email.message.Message), в соответствии с [**RFC 2046**](https://python-all.ru/3.4/library/email.contentmanager.html), вызывает ошибку, если для *subtype* `rfc822` запрашивается *cte* `quoted-printable` или `base64`, и для любого *cte*, отличного от `7bit`, для *subtype* `external-body`. Для `message/rfc822` использует `8bit`, если *cte* не указан. Для всех остальных значений *subtype* использует `7bit`.178179> **Примечание**180>181> Значение *cte* `binary` пока что работает некорректно. Объект `Message`, изменённый с помощью `set_content`, корректен, но [`BytesGenerator`](https://python-all.ru/3.4/library/email.generator.html#email.generator.BytesGenerator) не сериализует его правильно.182183If *disposition* is set, use it as the value of the *Content-Disposition* header. If not specified, and *filename* is specified, add the header with the value `attachment`. If it is not specified and *filename* is also not specified, do not add the header. The only valid values for *disposition* are `attachment` and `inline`.184185Если указан *filename*, используется как значение параметра `filename` заголовка *Content-Disposition*. Значения по умолчанию нет.186187Если указан *cid*, добавляет заголовок *Content-ID* со значением *cid*.188189Если указан *params*, перебирает его метод `items` и использует полученные пары `(key, value)` для установки дополнительных параметров в заголовке *Content-Type*.190191Если указан *headers* и это список строк вида `headername: headervalue` или список объектов `header` (отличаются от строк наличием атрибута `name`), добавляет заголовки в *msg*.192