MIME: jak tekst, HTML i załączniki mieszczą się w jednej wiadomości

« Blog · Autor:

Wiadomość pocztowa w pierwotnym założeniu jest zwykłym plikiem tekstowym: nagłówki, pusty wiersz, tekst. Siedem bitów na znak, bez polskich liter, bez załączników, bez formatowania. To, że dziś w jednej wiadomości mieści się faktura w PDF, logo w treści i dwie wersje tego samego pisma, zawdzięczamy dobudowanemu rozszerzeniu: MIME.

MIME nie zmienia zasady podstawowej. Wiadomość nadal jest plikiem tekstowym. Wszystko inne zostaje przepisane na tekst i wstawione w strukturę drzewa opisaną w nagłówkach.

Drzewo zwykłej wiadomości firmowej

Wiadomość z treścią HTML, osadzonym logotypem i załącznikiem PDF wygląda w środku tak:

multipart/mixed ├ multipart/related │  ├ multipart/alternative │  │  ├ text/plain │  │  └ text/html │  └ image/png └ application/pdf rama: treść plus załączniki treść plus osadzone obrazy wersja czysto tekstowa wersja HTML logo, przywoływane jako cid:logo właściwy załącznik dwie wersje tego samego tekstu Odbiorca widzi z tego tekst, obraz i jeden załącznik.
Trzy ramy zagnieżdżone jedna w drugiej. Każda ma własne zadanie — a kolejność zagnieżdżenia nie jest kwestią gustu.

Trzy ramy i po co są

TypZnaczenieCo robi z tym program
multipart/mixedKilka części, równorzędnychpokazuje je jedna po drugiej
multipart/alternativeTa sama treść w kilku postaciachpokazuje jedną z nich — ostatnią, którą umie wyświetlić
multipart/relatedCzęść główna plus pliki do niej należącepokazuje część główną i dociąga resztę w miarę potrzeby

Środkowy wiersz jest tym, w którym rozstrzyga kolejność. Przy alternative obowiązuje zasada: pierwszeństwo ma część wymieniona jako ostatnia. Dlatego wersja tekstowa stoi zawsze przed wersją HTML, nigdy po niej. Kto zamieni kolejność, w programach umiejących jedno i drugie zobaczy czysty tekst.

Jak części są od siebie oddzielane

Skoro wszystko jest tekstem, potrzebny jest znacznik rozdzielający. Stoi on w nagłówku ramy:

Content-Type: multipart/alternative; boundary="=_a7f31c9b4e2d"

--=_a7f31c9b4e2d
Content-Type: text/plain; charset=UTF-8

Dzien dobry, faktura w zalaczeniu.

--=_a7f31c9b4e2d
Content-Type: text/html; charset=UTF-8

<p>Dzien dobry, faktura w zalaczeniu.</p>

--=_a7f31c9b4e2d--

Znacznik musi być na tyle losowy, żeby nie wystąpił w treści — inaczej wiadomość rozpadnie się w złym miejscu. Znacznik zamykający nosi na końcu dwa dodatkowe łączniki; gdy ich brakuje, część programów uznaje wiadomość za uciętą.

Dlaczego załączniki rosną ponad swój rozmiar

PDF składa się z dowolnych bajtów, a treść wiadomości może zawierać wyłącznie tekst. Następuje więc przekodowanie, zwykle metodą Base64: co trzy bajty stają się czterema znakami.

Daje to narzut niemal dokładnie jednej trzeciej, plus łamania wierszy. Plik o rozmiarze 15 MB zajmuje w wiadomości około 20 MB.

Stąd bierze się częste zaskoczenie: skrzynka z limitem 25 MB nie przyjmie pliku 25 MB, tylko około 18 MB. Limit dotyczy gotowej wiadomości, nie pliku w środku.

Dla tekstu stosuje się zwykle oszczędniejsze quoted-printable: zostawia znaki zwykłe bez zmian i przepisuje wyłącznie pozostałe. Stamtąd biorą się ciągi w rodzaju =C5=BC, widoczne w surowej postaci — to polska litera, nie błąd.

Obraz osadzony czy załącznik?

Technicznie to jedno i to samo: plik w jednej z części wiadomości. Różnica leży w dwóch nagłówkach.

Obraz osadzony nosi identyfikator i jest przywoływany z HTML-a powyżej:

Content-Type: image/png
Content-ID: <logo>
Content-Disposition: inline

… w części HTML: <img src="cid:logo">

Załącznik nosi zamiast tego Content-Disposition: attachment i nazwę pliku. Tyle że to pole jest życzeniem, nie poleceniem. Część programów pokazuje na pasku załączników każdy plik, również ten osadzony. Dlatego odbiorcy wiadomości z logotypem w nagłówku widują niekiedy „2 załączniki", choć chodziło o jeden.

Co z tego wynika w praktyce

  • Zawsze dołączaj prawdziwą wersję tekstową. Nie dla formalności: to ta wersja dociera, gdy HTML nie może zostać wyświetlony — a część tekstowa pusta albo wypełniona zdaniem „ta wiadomość wymaga HTML" rzuca się w oczy przy ocenie.
  • Pilnuj kolejności w alternative. Najpierw tekst, potem HTML.
  • Dużych plików nie załączaj, tylko podlinkuj. Narzut jednej trzeciej dotyka każdej stacji pośredniej, a każda ma własny limit.
  • Ustawiaj zestaw znaków w każdej części. Nie stoi globalnie, tylko w każdym Content-Type — brakująca albo błędna wartość to najczęstsza przyczyna nieczytelnych znaków.

Zajrzeć samodzielnie

Każdy program pocztowy potrafi pokazać źródło wiadomości. Całe drzewo stoi w nim otworem: znaczniki rozdzielające, typy, kodowania. Kto raz sprawdził, dlaczego dany załącznik nazywa się u odbiorcy inaczej albo dlaczego obraz się nie pojawia, znajduje odpowiedź z reguły w kilku wierszach — to plik tekstowy i zbudowano go tak, żeby człowiek mógł go przeczytać.