1 /* 2 * Copyright (c) 2017 Mockito contributors 3 * This program is made available under the terms of the MIT License. 4 */ 5 package org.mockito.internal.configuration.plugins; 6 7 import org.mockito.internal.creation.instance.InstantiatorProvider2Adapter; 8 import org.mockito.plugins.AnnotationEngine; 9 import org.mockito.plugins.InstantiatorProvider; 10 import org.mockito.plugins.InstantiatorProvider2; 11 import org.mockito.plugins.MockMaker; 12 import org.mockito.plugins.MockitoPlugins; 13 import org.mockito.plugins.PluginSwitch; 14 import org.mockito.plugins.StackTraceCleanerProvider; 15 16 import java.util.HashMap; 17 import java.util.Map; 18 19 class DefaultMockitoPlugins implements MockitoPlugins { 20 21 private final static Map<String, String> DEFAULT_PLUGINS = new HashMap<String, String>(); 22 static final String INLINE_ALIAS = "mock-maker-inline"; 23 24 static { 25 //Keep the mapping: plugin interface name -> plugin implementation class name 26 DEFAULT_PLUGINS.put(PluginSwitch.class.getName(), DefaultPluginSwitch.class.getName()); 27 DEFAULT_PLUGINS.put(MockMaker.class.getName(), "org.mockito.internal.creation.bytebuddy.ByteBuddyMockMaker"); 28 DEFAULT_PLUGINS.put(StackTraceCleanerProvider.class.getName(), "org.mockito.internal.exceptions.stacktrace.DefaultStackTraceCleanerProvider"); 29 DEFAULT_PLUGINS.put(InstantiatorProvider2.class.getName(), "org.mockito.internal.creation.instance.DefaultInstantiatorProvider"); 30 DEFAULT_PLUGINS.put(AnnotationEngine.class.getName(), "org.mockito.internal.configuration.InjectingAnnotationEngine"); 31 DEFAULT_PLUGINS.put(INLINE_ALIAS, "org.mockito.internal.creation.bytebuddy.InlineByteBuddyMockMaker"); 32 } 33 34 @Override 35 public <T> T getDefaultPlugin(Class<T> pluginType) { 36 if (pluginType == InstantiatorProvider.class) { 37 //the implementation class is not configured via map so that we can reduce duplication 38 //(ensure that we are adapting the currently configured default implementation for InstantiatorProvider2) 39 String className = DEFAULT_PLUGINS.get(InstantiatorProvider2.class.getName()); 40 return pluginType.cast(new InstantiatorProvider2Adapter(create(InstantiatorProvider2.class, className))); 41 } else { 42 String className = DEFAULT_PLUGINS.get(pluginType.getName()); 43 return create(pluginType, className); 44 } 45 } 46 47 String getDefaultPluginClass(String classOrAlias) { 48 return DEFAULT_PLUGINS.get(classOrAlias); 49 } 50 51 /** 52 * Creates an instance of given plugin type, using specific implementation class. 53 */ 54 private <T> T create(Class<T> pluginType, String className) { 55 if (className == null) { 56 throw new IllegalStateException( 57 "No default implementation for requested Mockito plugin type: " + pluginType.getName() + "\n" 58 + "Is this a valid Mockito plugin type? If yes, please report this problem to Mockito team.\n" 59 + "Otherwise, please check if you are passing valid plugin type.\n" 60 + "Examples of valid plugin types: MockMaker, StackTraceCleanerProvider."); 61 } 62 try { 63 // Default implementation. Use our own ClassLoader instead of the context 64 // ClassLoader, as the default implementation is assumed to be part of 65 // Mockito and may not be available via the context ClassLoader. 66 return pluginType.cast(Class.forName(className).newInstance()); 67 } catch (Exception e) { 68 throw new IllegalStateException("Internal problem occurred, please report it. " + 69 "Mockito is unable to load the default implementation of class that is a part of Mockito distribution. " + 70 "Failed to load " + pluginType, e); 71 } 72 } 73 74 @Override 75 public MockMaker getInlineMockMaker() { 76 return create(MockMaker.class, DEFAULT_PLUGINS.get(INLINE_ALIAS)); 77 } 78 } 79