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 package android.app; 17 18 import android.annotation.NonNull; 19 import android.annotation.Nullable; 20 import android.content.BroadcastReceiver; 21 import android.content.ContentProvider; 22 import android.content.Intent; 23 import android.content.pm.ApplicationInfo; 24 25 /** 26 * Interface used to control the instantiation of manifest elements. 27 * 28 * @see #instantiateApplication 29 * @see #instantiateActivity 30 * @see #instantiateClassLoader 31 * @see #instantiateService 32 * @see #instantiateReceiver 33 * @see #instantiateProvider 34 */ 35 public class AppComponentFactory { 36 37 /** 38 * Selects the class loader which will be used by the platform to instantiate app components. 39 * <p> 40 * The default implementation of this method returns the {@code cl} parameter unchanged. 41 * Applications can override this method to set up a custom class loader or a custom class 42 * loader hierarchy and return it to the platform. 43 * <p> 44 * The method is a hook invoked before any application components are instantiated or the 45 * application Context is initialized. It is intended to allow the application's classes to 46 * be loaded from a different source than the base/split APK(s). 47 * <p> 48 * The default class loader {@code cl} is created by the platform and used to load the 49 * application's base or split APK(s). Its parent is typically the boot class loader, unless 50 * running under instrumentation. Its classname is configurable using the 51 * {@link android.R.attr#classLoader} manifest attribute. 52 * 53 * @param cl The default class loader created by the platform. 54 * @param aInfo Information about the application being loaded. 55 */ instantiateClassLoader(@onNull ClassLoader cl, @NonNull ApplicationInfo aInfo)56 public @NonNull ClassLoader instantiateClassLoader(@NonNull ClassLoader cl, 57 @NonNull ApplicationInfo aInfo) { 58 return cl; 59 } 60 61 /** 62 * Allows application to override the creation of the application object. This can be used to 63 * perform things such as dependency injection or class loader changes to these 64 * classes. 65 * <p> 66 * This method is only intended to provide a hook for instantiation. It does not provide 67 * earlier access to the Application object. The returned object will not be initialized 68 * as a Context yet and should not be used to interact with other android APIs. 69 * 70 * @param cl The default classloader to use for instantiation. 71 * @param className The class to be instantiated. 72 */ instantiateApplication(@onNull ClassLoader cl, @NonNull String className)73 public @NonNull Application instantiateApplication(@NonNull ClassLoader cl, 74 @NonNull String className) 75 throws InstantiationException, IllegalAccessException, ClassNotFoundException { 76 return (Application) cl.loadClass(className).newInstance(); 77 } 78 79 /** 80 * Allows application to override the creation of activities. This can be used to 81 * perform things such as dependency injection or class loader changes to these 82 * classes. 83 * <p> 84 * This method is only intended to provide a hook for instantiation. It does not provide 85 * earlier access to the Activity object. The returned object will not be initialized 86 * as a Context yet and should not be used to interact with other android APIs. 87 * 88 * @param cl The default classloader to use for instantiation. 89 * @param className The class to be instantiated. 90 * @param intent Intent creating the class. 91 */ instantiateActivity(@onNull ClassLoader cl, @NonNull String className, @Nullable Intent intent)92 public @NonNull Activity instantiateActivity(@NonNull ClassLoader cl, @NonNull String className, 93 @Nullable Intent intent) 94 throws InstantiationException, IllegalAccessException, ClassNotFoundException { 95 return (Activity) cl.loadClass(className).newInstance(); 96 } 97 98 /** 99 * Allows application to override the creation of receivers. This can be used to 100 * perform things such as dependency injection or class loader changes to these 101 * classes. 102 * 103 * @param cl The default classloader to use for instantiation. 104 * @param className The class to be instantiated. 105 * @param intent Intent creating the class. 106 */ instantiateReceiver(@onNull ClassLoader cl, @NonNull String className, @Nullable Intent intent)107 public @NonNull BroadcastReceiver instantiateReceiver(@NonNull ClassLoader cl, 108 @NonNull String className, @Nullable Intent intent) 109 throws InstantiationException, IllegalAccessException, ClassNotFoundException { 110 return (BroadcastReceiver) cl.loadClass(className).newInstance(); 111 } 112 113 /** 114 * Allows application to override the creation of services. This can be used to 115 * perform things such as dependency injection or class loader changes to these 116 * classes. 117 * <p> 118 * This method is only intended to provide a hook for instantiation. It does not provide 119 * earlier access to the Service object. The returned object will not be initialized 120 * as a Context yet and should not be used to interact with other android APIs. 121 * 122 * @param cl The default classloader to use for instantiation. 123 * @param className The class to be instantiated. 124 * @param intent Intent creating the class. 125 */ instantiateService(@onNull ClassLoader cl, @NonNull String className, @Nullable Intent intent)126 public @NonNull Service instantiateService(@NonNull ClassLoader cl, 127 @NonNull String className, @Nullable Intent intent) 128 throws InstantiationException, IllegalAccessException, ClassNotFoundException { 129 return (Service) cl.loadClass(className).newInstance(); 130 } 131 132 /** 133 * Allows application to override the creation of providers. This can be used to 134 * perform things such as dependency injection or class loader changes to these 135 * classes. 136 * <p> 137 * This method is only intended to provide a hook for instantiation. It does not provide 138 * earlier access to the ContentProvider object. The returned object will not be initialized 139 * with a Context yet and should not be used to interact with other android APIs. 140 * 141 * @param cl The default classloader to use for instantiation. 142 * @param className The class to be instantiated. 143 */ instantiateProvider(@onNull ClassLoader cl, @NonNull String className)144 public @NonNull ContentProvider instantiateProvider(@NonNull ClassLoader cl, 145 @NonNull String className) 146 throws InstantiationException, IllegalAccessException, ClassNotFoundException { 147 return (ContentProvider) cl.loadClass(className).newInstance(); 148 } 149 150 /** 151 * @hide 152 */ 153 public static final AppComponentFactory DEFAULT = new AppComponentFactory(); 154 } 155