Animowana ikona w temacie wiadomości e-mail

103

Wiem o identyfikatorach URI danych, w których base64zakodowane dane mogą być używane w tekście, na przykład obrazy. Dzisiaj otrzymałem e-mail, właściwie spam, w którym w temacie była ikona animacji (gif):

wprowadź opis obrazu tutaj

Oto sama ikona:

wprowadź opis obrazu tutaj

Więc jedyne, co przyszło mi do głowy, dotyczyło identyfikatorów URI danych i tego, czy Gmail umożliwia wstawianie w temacie emotikonów. Zobaczyłem pełną szczegółową wersję wiadomości e-mail i wskazałem wiersz tematu na poniższym obrazku:

wprowadź opis obrazu tutaj

Więc GIF pochodzi z =?UTF-8?B?876Urg==?=zakodowanego ciągu, który jest podobny do schematu URI danych, ale nie mogłem wyciągnąć z niego ikony. Oto źródło HTML elementu:

wprowadź opis obrazu tutaj

Krótko mówiąc, istnieje wiele emotikonów, z https://mail.google.com/mail/e/XXXktórych XXXpochodzą liczby szesnastkowe. Nigdzie nie są udokumentowane lub nie mogłem ich znaleźć. Jeśli chodzi o identyfikator URI danych, to jak można je uwzględnić w temacie wiadomości e-mail Gmaila? (Przekazałem ten e-mail na konto e-mail Yahoo, widząc [?]zamiast ikony), a jeśli nie, to w jaki sposób ten zakodowany ciąg jest analizowany?

revo
źródło
25
Prawdziwe pytanie brzmi: jak je blokujesz ?!
bambams
@bambams Co masz na myśli?
revo
13
Są niesamowicie irytujące i jak powiedziałeś, są używane tylko przez spamerów. Wolałbym, żeby Gmail nie wyświetlał ich (wydaje się, że już 99% wykrywa spam).
bambams
1
oto jak je zablokować
jamesmstone
link jamesmstone'a pokazuje, jak blokować wiadomości; jeśli chcesz zablokować same emotikony i pozostawić wiadomości, użyj skryptu użytkownika Gmail Subject Line Emoji Roach Motel .
Louis Semprini

Odpowiedzi:

175

Krótki opis:

Są one określane wewnętrznie jako goomojii wydają się być niestandardowym rozszerzeniem UTF-8. Gdy Gmail napotyka jeden z tych znaków, jest on zastępowany odpowiednią ikoną. Nie mogłem znaleźć na nich żadnej dokumentacji, ale udało mi się odtworzyć format.


Co to za ikony?

Te ikony to w rzeczywistości ikony wyświetlane w panelu „Wstaw emotikony”.

Gmail Wstaw emotikony

Chociaż nie widzę 52Eikony na liście, jest kilka innych, które stosują tę samą konwencję.

Zwróć uwagę, że istnieją również ikony, których nazwy są poprzedzone, na przykład . Nie byłem w stanie określić, czy i jak te ikony można wykorzystać w ten sposób.gtalk.03C gtalk.03C


Co to za identyfikator URI danych?

W rzeczywistości nie jest to identyfikator URI danych , chociaż ma pewne podobieństwa. W rzeczywistości jest to specjalna składnia do kodowania znaków spoza ASCII w tematach wiadomości e-mail, zdefiniowana w dokumencie RFC 2047 . Zasadniczo działa to w ten sposób.

=?charset?encoding?data?=

Tak więc w naszym przykładowym ciągu mamy następujące dane.

=?UTF-8?B?876Urg==?=
  • charset = UTF-8
  • encoding= B(oznacza base64)
  • data = 876Urg==


Więc jak to działa?

Jakoś to wiemy, 876Urg==oznacza ikonę 52E, ale jak?

Jeśli zdekodujemy base64 876Urg==, otrzymamy 0xf3be94ae. W formacie binarnym wygląda to następująco:

11110011 10111110 10010100 10101110

Te bity są zgodne z 4-bajtowym znakiem zakodowanym w UTF-8.

11110xxx 10xxxxxx 10xxxxxx 10xxxxxx

Zatem odpowiednie bity są następujące .:

     011   111110   010100   101110

Lub po wyrównaniu:

00001111 11100101 00101110

Szesnastkowo te bajty są następujące:

FE52E

Jak widać, z wyjątkiem FEprzedrostka, który przypuszczalnie ma odróżniać goomojiikony od innych znaków UTF-8, pasuje on 52Edo adresu URL ikony. Niektóre testy dowodzą, że dotyczy to innych ikon.


Brzmi jak dużo pracy, czy jest konwerter ?:

Można to oczywiście napisać. Stworzyłem następujący kod Pythona do moich testów. Te funkcje mogą konwertować ciąg zakodowany algorytmem base64 na iz krótkiego ciągu szesnastkowego znalezionego w adresie URL. Uwaga, ten kod jest napisany dla Pythona 3 i nie jest zgodny z Pythonem 2.

Funkcje konwersji:

import base64

def goomoji_decode(code):
    #Base64 decode.
    binary = base64.b64decode(code)
    #UTF-8 decode.
    decoded = binary.decode('utf8')
    #Get the UTF-8 value.
    value = ord(decoded)
    #Hex encode, trim the 'FE' prefix, and uppercase.
    return format(value, 'x')[2:].upper()

def goomoji_encode(code):
    #Add the 'FE' prefix and decode.
    value = int('FE' + code, 16)
    #Convert to UTF-8 character.
    encoded = chr(value)
    #Encode UTF-8 to binary.
    binary = bytearray(encoded, 'utf8')
    #Base64 encode return end return a UTF-8 string. 
    return base64.b64encode(binary).decode('utf-8')

Przykłady:

print(goomoji_decode('876Urg=='))
print(goomoji_encode('52E'))

Wynik:

52E
876Urg==

I oczywiście znalezienie adresu URL ikony wymaga po prostu utworzenia nowej wersji roboczej w Gmailu, wstawienia żądanej ikony i użycia inspektora DOM przeglądarki.

Inspektor DOM

Alexander O'Mara
źródło
14
To niesamowita, pełna odpowiedź. Nie mam nic do powiedzenia, ale po prostu zastanawiam się, jak wykonałeś na tym inżynierię wsteczną !! Dziękuję Alexander.
revo
2
Stwierdzenie, że Bw specjalnej składni sugeruje, że Base64 mógł być zgadywaniem (ciąg na końcu wygląda jak łańcuch zakodowany w Base64, jeśli widziałeś je wcześniej); po czym nietrudno zauważyć, że cztery bajty są zgodne z jednym ze wzorców UTF-8 dla znaków Unicode, zwłaszcza dlatego, że szuka Unicode. To całkiem fajna praca detektywa, mimo wszystko :)
sameers
3
@sameers Nie ma potrzeby zgadywać B- jest to zdefiniowane w # 4
Byłoby dobrze wspomnieć o RFC w powyższej odpowiedzi, jako odniesienie.
sameers
@JeremyMiller Dziękujemy za znalezienie odpowiedniego dokumentu RFC! Nie byłem w stanie go zlokalizować, kiedy pisałem tę odpowiedź.
Alexander O'Mara
19

Jeśli użyjesz poprawnego punktu w kodzie szesnastkowym (np. Fe4f4 dla 'stos poo' ) i jeśli jest on poprawnie zakodowany w nagłówku tematu, niech będzie to base64 (patrz @AlexanderOMara) lub quoted-printable ( =?utf-8?Q?=F3=BE=93=B4?=), wtedy Gmail automatycznie przeanalizuj i zastąp go odpowiednim emoji.

Oto lista emoji Gmaila do kopiowania i wklejania w tematach - lub treści wiadomości e-mail. Animowane emotikony, które przyciągną jeszcze więcej uwagi w skrzynce odbiorczej, są umieszczone na żółtym tle:

Emoji Gmaila na emailmarketingtipps.de

Łukasz
źródło
0

Wielkie dzięki dla Alexandra O'Mary za tak dobrze zbadaną odpowiedź na temat obrazów HTML z tagami goomoji!

Chciałem tylko dodać trzy rzeczy:

  • Wciąż istnieje wiele emoji (i innych sekwencji Unicode generujących obrazy), których spamerzy i inni dawni marketerzy zaczynają używać w wierszach tematów wiadomości e-mail, a gmail nie konwertuje na obrazy HTML. W niektórych przeglądarkach są one pogrubione i kolorowe, co jest prawie tak złe jak animacja. Przeglądarki również mogą je animować, ale nie wiem, czy w ogóle to robią. Te sekwencje Unicode są wyświetlane przez przeglądarkę jako tekst Unicode, więc dokładny wygląd (kolor lub nie, animowany lub nie, ...) zależy od systemu renderowania tekstu używanego przez przeglądarkę. Wygląd danego emoji Unicode zależy również od dowolnych selektorów odmian Unicode i modyfikatorów emojiktóre pojawiają się obok niego w sekwencji punktów kodowych Unicode. W przeciwieństwie do spamu emoji opartego na obrazach, sekwencje te można kopiować i wklejać z przeglądarki i do innych aplikacji jako tekst Unicode.

  • Mam nadzieję, że wielu marketerów czytających to pytanie dotyczące StackOverflow powie nie. To okropny pomysł, aby umieścić te sekwencje w tematach wiadomości e-mail i natychmiast zniszczy Ciebie i Twoją markę jako marnych spamerów. Nie warto „zwracać uwagi” na Twój e-mail.

  • Oczywiście pierwsze pytanie, które przychodzi każdemu do głowy, brzmi: „jak pozbyć się tych rzeczy?” Na szczęście istnieje ten otwarty skrypt użytkownika Greasemonkey / Tampermonkey / Violentmonkey:

Temat Gmaila Emoji Roach Motel

Ten skrypt użytkownika eliminuje zarówno obraz HTML (dzięki niesamowitej pracy Alexandra O'Mary ), jak i czyste typy Unicode.

W przypadku drugiego typu skrypt użytkownika zawiera wyrażenie regularne przeznaczone do przechwytywania sekwencji Unicode, które mogą być nadużywane przez marketerów. Wyrażenie regularne wygląda następująco w skrypcie ES6 Javascript (skrypt użytkownika tłumaczy to na powszechnie obsługiwane wyrażenie regularne pre-ES6 przy użyciu niesamowitego transpilera regex ES6 ):

var re = /(\p{Emoji_Modifier_Base}\p{Emoji_Modifier}?|\p{Emoji_Presentation}|\p{Emoji}\uFE0F|[\u{2100}-\u{2BFF}\u{E000}-\u{F8FF}\u{1D000}-\u{1F5FF}\u{1F650}-\u{1FA6F}\u{F0000}-\u{FFFFF}\u{100000}-\u{10FFFF}])\s*/gu

// which includes the Unicode Emoji pattern from
//   https://github.com/tc39/proposal-regexp-unicode-property-escapes
// plus also these blocks frequently used for spammy emojis
// (see https://en.wikipedia.org/wiki/Unicode_block ):
//   U+2100..U+2BFF     Arrows, Dingbats, Box Drawing, ...
//   U+E000..U+F8FF     Private Use Area (gmail generates them for some emoji)
//   U+1D000..U+1F5FF   Musical Symbols, Playing Cards (sigh), Pictographs, ...
//   U+1F650..U+1FA6F   Ornamental Dingbats, Transport and Map symbols, ...
//   U+F0000..U+FFFFF   Supplementary Private Use Area-A
//   U+100000..U+10FFFF Supplementary Private Use Area-B
// plus any space AFTER the discovered emoji spam
Louis Semprini
źródło