1 /* 2 * Copyright (C) 2017 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 com.googlecode.android_scripting.facade; 18 19 import com.google.common.collect.Maps; 20 import com.googlecode.android_scripting.Log; 21 import com.googlecode.android_scripting.facade.bluetooth.BluetoothA2dpFacade; 22 import com.googlecode.android_scripting.facade.bluetooth.BluetoothA2dpSinkFacade; 23 import com.googlecode.android_scripting.facade.bluetooth.BluetoothAvrcpFacade; 24 import com.googlecode.android_scripting.facade.bluetooth.BluetoothConnectionFacade; 25 import com.googlecode.android_scripting.facade.bluetooth.BluetoothFacade; 26 import com.googlecode.android_scripting.facade.bluetooth.BluetoothHfpClientFacade; 27 import com.googlecode.android_scripting.facade.bluetooth.BluetoothHidDeviceFacade; 28 import com.googlecode.android_scripting.facade.bluetooth.BluetoothHidFacade; 29 import com.googlecode.android_scripting.facade.bluetooth.BluetoothHspFacade; 30 import com.googlecode.android_scripting.facade.bluetooth.BluetoothLeAdvertiseFacade; 31 import com.googlecode.android_scripting.facade.bluetooth.BluetoothLeAdvertisingSetFacade; 32 import com.googlecode.android_scripting.facade.bluetooth.BluetoothLeScanFacade; 33 import com.googlecode.android_scripting.facade.bluetooth.BluetoothMapClientFacade; 34 import com.googlecode.android_scripting.facade.bluetooth.BluetoothMapFacade; 35 import com.googlecode.android_scripting.facade.bluetooth.BluetoothMediaFacade; 36 import com.googlecode.android_scripting.facade.bluetooth.BluetoothPanFacade; 37 import com.googlecode.android_scripting.facade.bluetooth.BluetoothPbapClientFacade; 38 import com.googlecode.android_scripting.facade.bluetooth.BluetoothRfcommFacade; 39 import com.googlecode.android_scripting.facade.bluetooth.GattClientFacade; 40 import com.googlecode.android_scripting.facade.bluetooth.GattServerFacade; 41 import com.googlecode.android_scripting.facade.media.AudioManagerFacade; 42 import com.googlecode.android_scripting.facade.media.MediaPlayerFacade; 43 import com.googlecode.android_scripting.facade.media.MediaRecorderFacade; 44 import com.googlecode.android_scripting.facade.media.MediaScannerFacade; 45 import com.googlecode.android_scripting.facade.media.MediaSessionFacade; 46 import com.googlecode.android_scripting.facade.net.IpSecManagerFacade; 47 import com.googlecode.android_scripting.facade.net.SocketFacade; 48 import com.googlecode.android_scripting.facade.net.SocketKeepaliveFacade; 49 import com.googlecode.android_scripting.facade.net.nsd.NsdManagerFacade; 50 import com.googlecode.android_scripting.facade.telephony.CarrierConfigFacade; 51 import com.googlecode.android_scripting.facade.telephony.CellBroadcastReceiverFacade; 52 import com.googlecode.android_scripting.facade.telephony.ImsManagerFacade; 53 import com.googlecode.android_scripting.facade.telephony.ImsMmTelManagerFacade; 54 import com.googlecode.android_scripting.facade.telephony.ProvisioningManagerFacade; 55 import com.googlecode.android_scripting.facade.telephony.RcsFacade; 56 import com.googlecode.android_scripting.facade.telephony.SmsFacade; 57 import com.googlecode.android_scripting.facade.telephony.SubscriptionManagerFacade; 58 import com.googlecode.android_scripting.facade.telephony.TelecomCallFacade; 59 import com.googlecode.android_scripting.facade.telephony.TelecomManagerFacade; 60 import com.googlecode.android_scripting.facade.telephony.TelephonyManagerFacade; 61 import com.googlecode.android_scripting.facade.ui.UiFacade; 62 import com.googlecode.android_scripting.facade.uwb.UwbManagerFacade; 63 import com.googlecode.android_scripting.facade.webcam.WebCamFacade; 64 import com.googlecode.android_scripting.facade.wifi.HttpFacade; 65 import com.googlecode.android_scripting.facade.wifi.WifiAwareManagerFacade; 66 import com.googlecode.android_scripting.facade.wifi.WifiManagerFacade; 67 import com.googlecode.android_scripting.facade.wifi.WifiP2pManagerFacade; 68 import com.googlecode.android_scripting.facade.wifi.WifiRtt2ManagerFacade; 69 import com.googlecode.android_scripting.facade.wifi.WifiRttManagerFacade; 70 import com.googlecode.android_scripting.facade.wifi.WifiScannerFacade; 71 import com.googlecode.android_scripting.jsonrpc.RpcReceiver; 72 import com.googlecode.android_scripting.rpc.MethodDescriptor; 73 import com.googlecode.android_scripting.rpc.RpcDeprecated; 74 import com.googlecode.android_scripting.rpc.RpcMinSdk; 75 import com.googlecode.android_scripting.rpc.RpcStartEvent; 76 import com.googlecode.android_scripting.rpc.RpcStopEvent; 77 78 import java.lang.reflect.Method; 79 import java.util.ArrayList; 80 import java.util.Collection; 81 import java.util.HashSet; 82 import java.util.List; 83 import java.util.Map; 84 import java.util.Set; 85 import java.util.SortedMap; 86 import java.util.TreeMap; 87 88 /** 89 * Encapsulates the list of supported facades and their construction. 90 */ 91 public class FacadeConfiguration { 92 private final static Set<Class<? extends RpcReceiver>> sFacadeClassList; 93 private final static SortedMap<String, MethodDescriptor> sRpcs = 94 new TreeMap<String, MethodDescriptor>(); 95 96 private static int sSdkLevel; 97 98 static { 99 sSdkLevel = android.os.Build.VERSION.SDK_INT; 100 101 sFacadeClassList = new HashSet<Class<? extends RpcReceiver>>(); 102 sFacadeClassList.add(ActivityResultFacade.class); 103 sFacadeClassList.add(AndroidFacade.class); 104 sFacadeClassList.add(ApplicationManagerFacade.class); 105 sFacadeClassList.add(AudioManagerFacade.class); 106 sFacadeClassList.add(BatteryManagerFacade.class); 107 sFacadeClassList.add(CallLogFacade.class); 108 sFacadeClassList.add(CameraFacade.class); 109 sFacadeClassList.add(CommonIntentsFacade.class); 110 sFacadeClassList.add(ContactsFacade.class); 111 sFacadeClassList.add(EventFacade.class); 112 sFacadeClassList.add(ImsManagerFacade.class); 113 sFacadeClassList.add(ImsMmTelManagerFacade.class); 114 sFacadeClassList.add(CellBroadcastReceiverFacade.class); 115 sFacadeClassList.add(LocationFacade.class); 116 sFacadeClassList.add(TelephonyManagerFacade.class); 117 sFacadeClassList.add(ProvisioningManagerFacade.class); 118 sFacadeClassList.add(PreferencesFacade.class); 119 sFacadeClassList.add(MediaPlayerFacade.class); 120 sFacadeClassList.add(MediaRecorderFacade.class); 121 sFacadeClassList.add(MediaScannerFacade.class); 122 sFacadeClassList.add(MediaSessionFacade.class); 123 sFacadeClassList.add(SensorManagerFacade.class); 124 sFacadeClassList.add(SettingsFacade.class); 125 sFacadeClassList.add(SmsFacade.class); 126 sFacadeClassList.add(SpeechRecognitionFacade.class); 127 sFacadeClassList.add(ToneGeneratorFacade.class); 128 sFacadeClassList.add(WakeLockFacade.class); 129 sFacadeClassList.add(HttpFacade.class); 130 sFacadeClassList.add(WifiManagerFacade.class); 131 sFacadeClassList.add(UiFacade.class); 132 sFacadeClassList.add(TextToSpeechFacade.class); 133 sFacadeClassList.add(BluetoothFacade.class); 134 sFacadeClassList.add(BluetoothA2dpFacade.class); 135 sFacadeClassList.add(BluetoothAvrcpFacade.class); 136 sFacadeClassList.add(BluetoothConnectionFacade.class); 137 sFacadeClassList.add(BluetoothHspFacade.class); 138 sFacadeClassList.add(BluetoothHidFacade.class); 139 sFacadeClassList.add(BluetoothHidDeviceFacade.class); 140 sFacadeClassList.add(BluetoothMapFacade.class); 141 sFacadeClassList.add(BluetoothPanFacade.class); 142 sFacadeClassList.add(BluetoothMediaFacade.class); 143 sFacadeClassList.add(BluetoothRfcommFacade.class); 144 sFacadeClassList.add(WebCamFacade.class); 145 sFacadeClassList.add(WifiP2pManagerFacade.class); 146 sFacadeClassList.add(BluetoothLeScanFacade.class); 147 sFacadeClassList.add(BluetoothLeAdvertiseFacade.class); 148 sFacadeClassList.add(GattClientFacade.class); 149 sFacadeClassList.add(GattServerFacade.class); 150 sFacadeClassList.add(ConnectivityManagerFacade.class); 151 sFacadeClassList.add(DisplayFacade.class); 152 sFacadeClassList.add(TelecomManagerFacade.class); 153 sFacadeClassList.add(WifiRttManagerFacade.class); 154 sFacadeClassList.add(WifiScannerFacade.class); 155 sFacadeClassList.add(SubscriptionManagerFacade.class); 156 sFacadeClassList.add(TelecomCallFacade.class); 157 sFacadeClassList.add(CarrierConfigFacade.class); 158 sFacadeClassList.add(NfcManagerFacade.class); 159 sFacadeClassList.add(VpnFacade.class); 160 161 /* Compatibility reset to >= Marshmallow */ 162 if (sSdkLevel >= 23) { 163 // add new facades here 164 sFacadeClassList.add(WifiAwareManagerFacade.class); 165 sFacadeClassList.add(BluetoothHfpClientFacade.class); 166 sFacadeClassList.add(BluetoothA2dpSinkFacade.class); 167 sFacadeClassList.add(BluetoothPbapClientFacade.class); 168 sFacadeClassList.add(NsdManagerFacade.class); 169 sFacadeClassList.add(BluetoothMapClientFacade.class); 170 sFacadeClassList.add(BluetoothLeAdvertisingSetFacade.class); 171 sFacadeClassList.add(IpSecManagerFacade.class); 172 sFacadeClassList.add(SocketFacade.class); 173 } 174 175 if (sSdkLevel >= 27) { 176 sFacadeClassList.add(WifiRtt2ManagerFacade.class); 177 } 178 179 if (sSdkLevel >= 29) { 180 sFacadeClassList.add(SocketKeepaliveFacade.class); 181 } 182 183 if (sSdkLevel >= 31) { 184 sFacadeClassList.add(UwbManagerFacade.class); 185 sFacadeClassList.add(RcsFacade.class); 186 } 187 188 for (Class<? extends RpcReceiver> recieverClass : sFacadeClassList) { 189 for (MethodDescriptor rpcMethod : MethodDescriptor.collectFrom(recieverClass)) { rpcMethod.getName()190 sRpcs.put(rpcMethod.getName(), rpcMethod); 191 } 192 } 193 } 194 FacadeConfiguration()195 private FacadeConfiguration() { 196 // Utility class. 197 } 198 getSdkLevel()199 public static int getSdkLevel() { 200 return sSdkLevel; 201 } 202 203 /** Returns a list of {@link MethodDescriptor} objects for all facades. */ collectMethodDescriptors()204 public static List<MethodDescriptor> collectMethodDescriptors() { 205 return new ArrayList<MethodDescriptor>(sRpcs.values()); 206 } 207 208 /** 209 * Returns a list of not deprecated {@link MethodDescriptor} objects for facades supported by 210 * the current SDK version. 211 */ collectSupportedMethodDescriptors()212 public static List<MethodDescriptor> collectSupportedMethodDescriptors() { 213 List<MethodDescriptor> list = new ArrayList<MethodDescriptor>(); 214 for (MethodDescriptor descriptor : sRpcs.values()) { 215 Method method = descriptor.getMethod(); 216 if (method.isAnnotationPresent(RpcDeprecated.class)) { 217 continue; 218 } else if (method.isAnnotationPresent(RpcMinSdk.class)) { 219 int requiredSdkLevel = method.getAnnotation(RpcMinSdk.class).value(); 220 if (sSdkLevel < requiredSdkLevel) { 221 continue; 222 } 223 } 224 list.add(descriptor); 225 } 226 return list; 227 } 228 collectStartEventMethodDescriptors()229 public static Map<String, MethodDescriptor> collectStartEventMethodDescriptors() { 230 Map<String, MethodDescriptor> map = Maps.newHashMap(); 231 for (MethodDescriptor descriptor : sRpcs.values()) { 232 Method method = descriptor.getMethod(); 233 if (method.isAnnotationPresent(RpcStartEvent.class)) { 234 String eventName = method.getAnnotation(RpcStartEvent.class).value(); 235 if (map.containsKey(eventName)) { 236 Log.d("Duplicate eventName " + eventName); 237 throw new RuntimeException("Duplicate start event method descriptor found."); 238 } 239 map.put(eventName, descriptor); 240 } 241 } 242 return map; 243 } 244 collectStopEventMethodDescriptors()245 public static Map<String, MethodDescriptor> collectStopEventMethodDescriptors() { 246 Map<String, MethodDescriptor> map = Maps.newHashMap(); 247 for (MethodDescriptor descriptor : sRpcs.values()) { 248 Method method = descriptor.getMethod(); 249 if (method.isAnnotationPresent(RpcStopEvent.class)) { 250 String eventName = method.getAnnotation(RpcStopEvent.class).value(); 251 if (map.containsKey(eventName)) { 252 throw new RuntimeException("Duplicate stop event method descriptor found."); 253 } 254 map.put(eventName, descriptor); 255 } 256 } 257 return map; 258 } 259 260 /** Returns a method by name. */ getMethodDescriptor(String name)261 public static MethodDescriptor getMethodDescriptor(String name) { 262 return sRpcs.get(name); 263 } 264 getFacadeClasses()265 public static Collection<Class<? extends RpcReceiver>> getFacadeClasses() { 266 return sFacadeClassList; 267 } 268 } 269