1 /* 2 * Copyright (C) 2016 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 package android.telephony.mbms; 18 19 import android.annotation.NonNull; 20 import android.annotation.Nullable; 21 import android.os.Parcel; 22 import android.os.Parcelable; 23 import android.text.TextUtils; 24 25 import java.util.ArrayList; 26 import java.util.Collections; 27 import java.util.Date; 28 import java.util.HashMap; 29 import java.util.List; 30 import java.util.Locale; 31 import java.util.Map; 32 import java.util.NoSuchElementException; 33 import java.util.Objects; 34 import java.util.Set; 35 36 /** 37 * Describes a cell-broadcast service. This class should not be instantiated directly -- use 38 * {@link StreamingServiceInfo} or {@link FileServiceInfo} 39 * @hide 40 */ 41 public class ServiceInfo { 42 // arbitrary limit on the number of locale -> name pairs we support 43 final static int MAP_LIMIT = 1000; 44 45 private final Map<Locale, String> names; 46 private final String className; 47 private final List<Locale> locales; 48 private final String serviceId; 49 private final Date sessionStartTime; 50 private final Date sessionEndTime; 51 52 /** @hide */ 53 public ServiceInfo(Map<Locale, String> newNames, String newClassName, List<Locale> newLocales, 54 String newServiceId, Date start, Date end) { 55 if (newNames == null || newNames.isEmpty() || TextUtils.isEmpty(newClassName) 56 || newLocales == null || newLocales.isEmpty() || TextUtils.isEmpty(newServiceId) 57 || start == null || end == null) { 58 throw new IllegalArgumentException("Bad ServiceInfo construction"); 59 } 60 if (newNames.size() > MAP_LIMIT) { 61 throw new RuntimeException("bad map length " + newNames.size()); 62 } 63 if (newLocales.size() > MAP_LIMIT) { 64 throw new RuntimeException("bad locales length " + newLocales.size()); 65 } 66 67 names = new HashMap(newNames.size()); 68 names.putAll(newNames); 69 className = newClassName; 70 locales = new ArrayList(newLocales); 71 serviceId = newServiceId; 72 sessionStartTime = (Date)start.clone(); 73 sessionEndTime = (Date)end.clone(); 74 } 75 76 /** @hide */ 77 protected ServiceInfo(Parcel in) { 78 int mapCount = in.readInt(); 79 if (mapCount > MAP_LIMIT || mapCount < 0) { 80 throw new RuntimeException("bad map length" + mapCount); 81 } 82 names = new HashMap(mapCount); 83 while (mapCount-- > 0) { 84 Locale locale = (java.util.Locale) in.readSerializable(); 85 String name = in.readString(); 86 names.put(locale, name); 87 } 88 className = in.readString(); 89 int localesCount = in.readInt(); 90 if (localesCount > MAP_LIMIT || localesCount < 0) { 91 throw new RuntimeException("bad locale length " + localesCount); 92 } 93 locales = new ArrayList<Locale>(localesCount); 94 while (localesCount-- > 0) { 95 Locale l = (java.util.Locale) in.readSerializable(); 96 locales.add(l); 97 } 98 serviceId = in.readString(); 99 sessionStartTime = (java.util.Date) in.readSerializable(); 100 sessionEndTime = (java.util.Date) in.readSerializable(); 101 } 102 103 /** @hide */ 104 public void writeToParcel(Parcel dest, int flags) { 105 Set<Locale> keySet = names.keySet(); 106 dest.writeInt(keySet.size()); 107 for (Locale l : keySet) { 108 dest.writeSerializable(l); 109 dest.writeString(names.get(l)); 110 } 111 dest.writeString(className); 112 int localesCount = locales.size(); 113 dest.writeInt(localesCount); 114 for (Locale l : locales) { 115 dest.writeSerializable(l); 116 } 117 dest.writeString(serviceId); 118 dest.writeSerializable(sessionStartTime); 119 dest.writeSerializable(sessionEndTime); 120 } 121 122 /** 123 * Get the user-displayable name for this cell-broadcast service corresponding to the 124 * provided {@link Locale}. 125 * @param locale The {@link Locale} in which you want the name of the service. This must be a 126 * value from the set returned by {@link #getNamedContentLocales()} -- an 127 * {@link java.util.NoSuchElementException} may be thrown otherwise. 128 * @return The {@link CharSequence} providing the name of the service in the given 129 * {@link Locale} 130 */ 131 public @NonNull CharSequence getNameForLocale(@NonNull Locale locale) { 132 if (!names.containsKey(locale)) { 133 throw new NoSuchElementException("Locale not supported"); 134 } 135 return names.get(locale); 136 } 137 138 /** 139 * Return an unmodifiable set of the current {@link Locale}s that have a user-displayable name 140 * associated with them. The user-displayable name associated with any {@link Locale} in this 141 * set can be retrieved with {@link #getNameForLocale(Locale)}. 142 * @return An unmodifiable set of {@link Locale} objects corresponding to a user-displayable 143 * content name in that locale. 144 */ 145 public @NonNull Set<Locale> getNamedContentLocales() { 146 return Collections.unmodifiableSet(names.keySet()); 147 } 148 149 /** 150 * The class name for this service - used to categorize and filter 151 */ 152 public String getServiceClassName() { 153 return className; 154 } 155 156 /** 157 * The languages available for this service content 158 */ 159 public List<Locale> getLocales() { 160 return locales; 161 } 162 163 /** 164 * The carrier's identifier for the service. 165 */ 166 public String getServiceId() { 167 return serviceId; 168 } 169 170 /** 171 * The start time indicating when this service will be available. 172 */ 173 public Date getSessionStartTime() { 174 return sessionStartTime; 175 } 176 177 /** 178 * The end time indicating when this session stops being available. 179 */ 180 public Date getSessionEndTime() { 181 return sessionEndTime; 182 } 183 184 @Override 185 public boolean equals(Object o) { 186 if (this == o) return true; 187 if (o == null) { 188 return false; 189 } 190 if (!(o instanceof ServiceInfo)) { 191 return false; 192 } 193 ServiceInfo that = (ServiceInfo) o; 194 return Objects.equals(names, that.names) && 195 Objects.equals(className, that.className) && 196 Objects.equals(locales, that.locales) && 197 Objects.equals(serviceId, that.serviceId) && 198 Objects.equals(sessionStartTime, that.sessionStartTime) && 199 Objects.equals(sessionEndTime, that.sessionEndTime); 200 } 201 202 @Override 203 public int hashCode() { 204 return Objects.hash(names, className, locales, serviceId, sessionStartTime, sessionEndTime); 205 } 206 } 207