2016-09-01 7 views
3

я пытался издеватьсяКак издеваются Class.forName и class.Constructor.newInstance()

clazz = Class.forName("Complete Class path") 
Object obj = clazz.Constructor().getInstance(); 

Я гугле, и нашел ссылки, которые информированные как издеваются статический метод с использованием powermock. Я попытался с помощью тех логики издеваться над

Class.forName("Complete Class path")

и

Object obj = clazz.Constructor().getInstance(), но были, с которыми сталкиваются ошибки.

at sun.reflect.GeneratedSerializationConstructorAccessor16.newInstance(Unknown Source) [junit] 
at java.lang.reflect.Constructor.newInstance(Constructor.java:423) [junit] 
at org.objenesis.instantiator.sun.SunReflectionFactoryInstantiator.newInstance(SunReflectionFactoryInstantiator.java:45) [junit] 
at org.powermock.reflect.internal.WhiteboxImpl.newInstance(WhiteboxImpl.java:223) [junit] 
at org.powermock.reflect.Whitebox.newInstance(Whitebox.java:139) [junit] 
at org.powermock.api.mockito.internal.mockcreation.MockCreator.mock(MockCreator.java:64) [junit] 
at org.powermock.api.mockito.PowerMockito.mock(PowerMockito.java:203) [junit] 
at org.powermock.api.extension.listener.AnnotationEnabler.standardInject(AnnotationEnabler.java:106) [junit] 
at org.powermock.api.extension.listener.AnnotationEnabler.beforeTestMethod(AnnotationEnabler.java:54) [junit] 
at org.powermock.tests.utils.impl.PowerMockTestNotifierImpl.notifyBeforeTestMethod(PowerMockTestNotifierImpl.java:90) [junit] 
at org.powermock.modules.junit4.internal.impl.PowerMockJUnit44RunnerDelegateImpl$PowerMockJUnit44MethodRunner.executeTest(PowerMockJUnit44RunnerDelegateImpl.java:292) [junit] 
at org.powermock.modules.junit4.internal.impl.PowerMockJUnit47RunnerDelegateImpl$PowerMockJUnit47MethodRunner.executeTestInSuper(PowerMockJUnit47RunnerDelegateImpl.java:127) [junit] 
at org.powermock.modules.junit4.internal.impl.PowerMockJUnit47RunnerDelegateImpl$PowerMockJUnit47MethodRunner.executeTest(PowerMockJUnit47RunnerDelegateImpl.java:82) [junit] 
at org.powermock.modules.junit4.internal.impl.PowerMockJUnit44RunnerDelegateImpl$PowerMockJUnit44MethodRunner.runBeforesThenTestThenAfters(PowerMockJUnit44RunnerDelegateImpl.java:282) [junit] 
at org.junit.internal.runners.MethodRoadie.runTest(MethodRoadie.java:87) [junit] 
at org.junit.internal.runners.MethodRoadie.run(MethodRoadie.java:50) [junit] 
at org.powermock.modules.junit4.internal.impl.PowerMockJUnit44RunnerDelegateImpl.invokeTestMethod(PowerMockJUnit44RunnerDelegateImpl.java:207) [junit] 
at org.powermock.modules.junit4.internal.impl.PowerMockJUnit44RunnerDelegateImpl.runMethods(PowerMockJUnit44RunnerDelegateImpl.java:146) [junit] 
at org.powermock.modules.junit4.internal.impl.PowerMockJUnit44RunnerDelegateImpl$1.run(PowerMockJUnit44RunnerDelegateImpl.java:120) [junit] 
at org.junit.internal.runners.ClassRoadie.runUnprotected(ClassRoadie.java:34) [junit] 
at org.junit.internal.runners.ClassRoadie.runProtected(ClassRoadie.java:44) [junit] 
at org.powermock.modules.junit4.internal.impl.PowerMockJUnit44RunnerDelegateImpl.run(PowerMockJUnit44RunnerDelegateImpl.java:122) [junit] 
at org.powermock.modules.junit4.common.internal.impl.JUnit4TestSuiteChunkerImpl.run(JUnit4TestSuiteChunkerImpl.java:106) [junit] 
at org.powermock.modules.junit4.common.internal.impl.AbstractCommonPowerMockRunner.run(AbstractCommonPowerMockRunner.java:53) 
+6

Позвольте мне спросить: почему вы хотите сделать это? – GhostCat

+0

Кроме того: ошибки «облицовки» не являются хорошей отправной точкой. Дайте нам подробности; иначе вы не увидите никакой полезной обратной связи! – GhostCat

+0

Не надо. Реорганизуйте код, чтобы вы не могли его издеваться. Перейдите на завод. –

ответ

1

Я думаю, вы не будете иметь успех насмешливо статический метод forName в связи с тем раннего Class нагрузки. Я не знаю фальшивые рамки, которые могли бы это сделать.

Но если вы проверяете свой код, то я предлагаю вам двигаться Class.forName логики этого strategy

interface ClassLoadingStrategy { 
    ClassLoadingStrategy DEFAULT = Class::forName; 

    Class<?> forName(final String name) throws Exception; 
} 

Перепишите код, чтобы использовать его там, где вам нужно Class.forName и заменить его макет в ваших тестах ,

+0

Mocking aint это легко. java.lang.Class является окончательным. Поэтому я думаю, он все еще нуждается в PowerMock для издевательства над экземплярами класса. – GhostCat

+0

@GhostCat Мне нужно перепроверить это, но afaik, издевающийся над финальными классами, загружаемыми загрузчиком bootstrap, невозможно, не переходя слишком низкоуровневым (например, с использованием javaagents). – vsminkov

1

Я не считаю, что насмешка Class - хорошая идея, вы должны переписать свой код, чтобы сделать его более проверяемым. Вы должны делегировать создание своего компонента на завод, тогда его будет легко издеваться над ним.

Вот как ваш завод может выглядеть следующим образом:

public interface MyObjectFactory { 
    MyObject create(); 
} 

Тогда в классе, где вам нужно создать этот объект, добавьте фабрику в поле

public class MyClass { 
    // The factory that will create my objects 
    private MyObjectFactory factory; 

    public void someMethod() { 
     // Calls the factory to create my object 
     MyObject object = factory.create(); 
     ... 
    } 
} 

После этого, вы можете используйте Mockito, чтобы высмеять ваш MyObjectFactory, чтобы предоставить экземпляр MyObject по вашему выбору.

Тестовый пример будет затем:

@RunWith(MockitoJUnitRunner.class) 
public class MyClassTest { 

    @Mock 
    MyObjectFactory factory; 
    @InjectMocks 
    MyClass myClass = new MyClass(); 

    @Test 
    public void testSomeMethod() { 
     ... 
     Mockito.when(factory.create()).thenReturn(myObject); 
     // Call the method 
     myClass.someMethod(); 
    } 
} 
+0

Согласен, это ** только ** разумный ответ здесь. Если кто-то положил неподвижный объект на ваш путь; то вы не тратите свое время на перемещение этой вещи. Вы ходите. И ваш подход - лучший способ «ходьбы» вокруг! – GhostCat

+0

Что делать, если вы тестируете завод? : -/ – Yuval

+0

@ Юваль, тогда будет другой вопрос/вопрос –

Смежные вопросы