Make MimeMap final and introduce MimeMap.Builder.

This CL topic introduces a new @CorePlatformApi MimeMap.Builder
and uses it to make MimeMap a concrete, final, immutable type.

This has the following advantages:

 - Consistency of behavior of MimeMap implementations with regards
   to lower-casing and treatment of null is trivial to guarantee
   because there is only one implementation.
 - The @CorePlatformApi surface now makes more sense. The responsibility
   for lower-casing and treatment of null was previously split between
   MimeMap in libcore and  MimeMapImpl in frameworks/base, which is why
   MimeMap.toLowerCase() and MimeMap.isNullOrEmpty() were in the
   @CorePlatformApi.
 - Most of the logic now lives in libcore / ART module.
   frameworks/base now has minimal logic. This makes it easier to write
   (in a follow-up CL) a CTS test that asserts all the default mappings,
   because that test can now duplicate that small amount of logic in
   order to read from a copy of the same data files.

Note: The semantics of the @CorePlatformApi Builder.put(String, List<String>)
are fairly complex, which isn't great. This was done because:
 - By following the semantics of the *mime.types file format, it allows
   us to minimize the logic in frameworks/base.
 - It's simpler than having multiple overloads of put() for
   mimeType -> file extension mapping and vice versa,
   and for whether or not any existing mapping should be overwritten.
   If we had named classes for MimeType and FileExtension with
   appropriate case-insensitive equals and hashCode semantics, then
   we could instead have API such as
      builder.asMimeToExtensionMap().put(...)
   but existing API (e.g. Intent.getType(), android.webkit.MimeTypeMap)
   has set precedent for treating these as Strings.

Bug: 136256059
Test: atest CtsLibcoreTestCases
Test: atest CtsMimeMapTestCases

Change-Id: I9a185a689745726dd79b15117892001461fa4a0d
1 file changed