diff --git a/mail/common/src/main/java/com/fsck/k9/mail/Address.java b/mail/common/src/main/java/com/fsck/k9/mail/Address.java index 33d8d8d0400..b0eee8528f5 100644 --- a/mail/common/src/main/java/com/fsck/k9/mail/Address.java +++ b/mail/common/src/main/java/com/fsck/k9/mail/Address.java @@ -74,7 +74,7 @@ private Address(String address, String personal, boolean parse) { Log.e("Invalid address: %s", address); } } else { - mAddress = address; + mAddress = Rfc822Token.withULabelDomain(address); mPersonal = personal; } } diff --git a/mail/common/src/main/java/com/fsck/k9/mail/helper/Rfc822Token.java b/mail/common/src/main/java/com/fsck/k9/mail/helper/Rfc822Token.java index bf0721f910b..f7ea61f4773 100644 --- a/mail/common/src/main/java/com/fsck/k9/mail/helper/Rfc822Token.java +++ b/mail/common/src/main/java/com/fsck/k9/mail/helper/Rfc822Token.java @@ -17,6 +17,7 @@ package com.fsck.k9.mail.helper; +import java.net.IDN; import org.jetbrains.annotations.Nullable; @@ -34,7 +35,7 @@ public class Rfc822Token { */ public Rfc822Token(@Nullable String name, @Nullable String address, @Nullable String comment) { mName = name; - mAddress = address; + mAddress = withULabelDomain(address); mComment = comment; } @@ -73,7 +74,7 @@ public void setName(@Nullable String name) { * Changes the address to the specified address. */ public void setAddress(@Nullable String address) { - mAddress = address; + mAddress = withULabelDomain(address); } /** @@ -202,4 +203,14 @@ public boolean equals(@Nullable Object o) { stringEquals(mAddress, other.mAddress) && stringEquals(mComment, other.mComment)); } + + @Nullable + public static String withULabelDomain(@Nullable final String address) { + if (address == null) return null; + int at = address.lastIndexOf('@'); + if (at < 0 || at == address.length()-1) + return address; + return address.substring(0, at+1) + + IDN.toUnicode(address.substring(at+1), IDN.ALLOW_UNASSIGNED); + } } diff --git a/mail/common/src/test/java/com/fsck/k9/mail/AddressTest.java b/mail/common/src/test/java/com/fsck/k9/mail/AddressTest.java index cfccf1fd9a8..2f4ed58053d 100644 --- a/mail/common/src/test/java/com/fsck/k9/mail/AddressTest.java +++ b/mail/common/src/test/java/com/fsck/k9/mail/AddressTest.java @@ -66,6 +66,7 @@ public void parse_withUnusualEmails_shouldSetAddress() { "example@s.solutions", "user@com", "user@localserver", + "user@orléans.example", "user@[IPv6:2001:db8::1]" }; @@ -87,6 +88,16 @@ public void parse_withEncodedPersonal_shouldDecode() { } + @Test + public void construction_withALabel_shouldDecode() { + // Mutt and Exchange do this, and maybe Plesk too. Best fix it + // at the earliest opportinity. + Address a = new Address("grå@xn--gr-zia.org", "Grå katt"); + + assertEquals("Grå katt", a.getPersonal()); + assertEquals("grå@grå.org", a.getAddress()); + } + @Test public void parse_withQuotedEncodedPersonal_shouldDecode() { Address[] addresses = Address.parse( @@ -94,7 +105,14 @@ public void parse_withQuotedEncodedPersonal_shouldDecode() { assertEquals("Yahoo!ダイレクトオファー ", addresses[0].getPersonal()); assertEquals("directoffer-master@mail.yahoo.co.jp", addresses[0].getAddress()); + } + + @Test + public void parse_withALabel_shouldDecode() { + Address[] addresses = Address.parse("info@xn--gr-zia.org"); + assertEquals(1, addresses.length); + assertEquals("info@grå.org", addresses[0].getAddress()); } /**