We use GitHub Issues for bugs.
If you have a non-bug question, please ask on Stack Overflow: http://stackoverflow.com/questions/tagged/fresco
--- Please use this template, and delete everything above this line before submitting your issue ---
Im trying to run a unit test using Robolectric ( testImplementation "org.robolectric:robolectric:3.7.1") and a NPE appears when executing Fresco.initialize(this) in the main Application.
This is the code of the test:
@RunWith(RobolectricTestRunner.class)
public class MainActivityTest {
@Test
public void testRecyclerData() {
final MainActivity activity = Robolectric.setupActivity(MainActivity.class);
final RecyclerView recyclerView = activity.findViewById(R.id.recycler_view_main_activity);
final List<Show> list = new ArrayList<Show>();
list.add(new Show());
activity.addDataToView(list);
Assert.assertEquals(1, recyclerView.getAdapter().getItemCount());
}
}
Here is the stack:
java.lang.NullPointerException
at java.io.File.<init>(File.java:277)
at com.facebook.soloader.SoLoader.initImpl(SoLoader.java:198)
at com.facebook.soloader.SoLoader.init(SoLoader.java:120)
at com.facebook.soloader.SoLoader.init(SoLoader.java:104)
at com.facebook.drawee.backends.pipeline.Fresco.initialize(Fresco.java:63)
at com.facebook.drawee.backends.pipeline.Fresco.initialize(Fresco.java:39)
at com.sebas.sysfishapp.videofeed.MainApplication.onCreate(MainApplication.java:16)
at org.robolectric.android.internal.ParallelUniverse.lambda$setUpApplicationState$0(ParallelUniverse.java:204)
at org.robolectric.util.PerfStatsCollector.measure(PerfStatsCollector.java:72)
at org.robolectric.android.internal.ParallelUniverse.setUpApplicationState(ParallelUniverse.java:203)
at org.robolectric.RobolectricTestRunner.beforeTest(RobolectricTestRunner.java:333)
at org.robolectric.internal.SandboxTestRunner$2.evaluate(SandboxTestRunner.java:245)
at org.robolectric.internal.SandboxTestRunner.runChild(SandboxTestRunner.java:130)
at org.robolectric.internal.SandboxTestRunner.runChild(SandboxTestRunner.java:42)
at org.junit.runners.ParentRunner$3.run(ParentRunner.java:290)
at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:71)
at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:288)
at org.junit.runners.ParentRunner.access$000(ParentRunner.java:58)
at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:268)
at org.robolectric.internal.SandboxTestRunner$1.evaluate(SandboxTestRunner.java:84)
at org.junit.runners.ParentRunner.run(ParentRunner.java:363)
at org.gradle.api.internal.tasks.testing.junit.JUnitTestClassExecuter.runTestClass(JUnitTestClassExecuter.java:114)
at org.gradle.api.internal.tasks.testing.junit.JUnitTestClassExecuter.execute(JUnitTestClassExecuter.java:57)
at org.gradle.api.internal.tasks.testing.junit.JUnitTestClassProcessor.processTestClass(JUnitTestClassProcessor.java:66)
at org.gradle.api.internal.tasks.testing.SuiteTestClassProcessor.processTestClass(SuiteTestClassProcessor.java:51)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:498)
at org.gradle.internal.dispatch.ReflectionDispatch.dispatch(ReflectionDispatch.java:35)
at org.gradle.internal.dispatch.ReflectionDispatch.dispatch(ReflectionDispatch.java:24)
at org.gradle.internal.dispatch.ContextClassLoaderDispatch.dispatch(ContextClassLoaderDispatch.java:32)
at org.gradle.internal.dispatch.ProxyDispatchAdapter$DispatchingInvocationHandler.invoke(ProxyDispatchAdapter.java:93)
at com.sun.proxy.$Proxy3.processTestClass(Unknown Source)
at org.gradle.api.internal.tasks.testing.worker.TestWorker.processTestClass(TestWorker.java:109)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:498)
at org.gradle.internal.dispatch.ReflectionDispatch.dispatch(ReflectionDispatch.java:35)
at org.gradle.internal.dispatch.ReflectionDispatch.dispatch(ReflectionDispatch.java:24)
at org.gradle.internal.remote.internal.hub.MessageHubBackedObjectConnection$DispatchWrapper.dispatch(MessageHubBackedObjectConnection.java:146)
at org.gradle.internal.remote.internal.hub.MessageHubBackedObjectConnection$DispatchWrapper.dispatch(MessageHubBackedObjectConnection.java:128)
at org.gradle.internal.remote.internal.hub.MessageHub$Handler.run(MessageHub.java:404)
at org.gradle.internal.concurrent.ExecutorPolicy$CatchAndRecordFailures.onExecute(ExecutorPolicy.java:63)
at org.gradle.internal.concurrent.ManagedExecutorImpl$1.run(ManagedExecutorImpl.java:46)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624)
at org.gradle.internal.concurrent.ThreadFactoryImpl$ManagedThreadRunnable.run(ThreadFactoryImpl.java:55)
at java.lang.Thread.run(Thread.java:748)
100%
[OPTIONAL: Do you know what needs to be done to address this issue? Ideally, provide a pull request which fixes this issue.]
Try calling SoLoader.setInTestMode() in your test setup (@Before method). We do this in a bunch of our tests as well, see:
https://github.com/facebook/fresco/search?q=setintestmode
Let me know if this fixes the issue. We should probably document this somewhere.
Nop, same error.
@foghina the problem is that the MainApplication extends Application is called before the setUp (@Before) so the SoLoader.setInTestMode() is never been called. Now, I remove the Fresco.Initialize(this) from the MainApplication and set it in the activity and Its working :) but I dont want to call Fresco.initialize(this) in all the activities on my app. Is there any workarround for this situation? Thanks
Hmm, MainApplication#onCreate() shouldn't be called before setUp. Perhaps you can try using @BeforeClass instead?
Hi @sdeira
Could you replace your default Application class with one used only for the tests?
it should be possible using Robolectric: https://stackoverflow.com/questions/21725309/robolectric-not-using-test-application
@sdeira I know its tricky but I solved it with try-catch.
```
try {
Fresco.initialize(this, config);
} catch (Throwable th) {
Log.d("fresco", "error");
}
@foghina @BeforeClass is working thanks.
and the method should be static in the TestClass
```
@BeforeClass
public static void before() throws Exception{
SoLoader.setInTestMode();
}
@BansookNam thanks for the update!
@BansookNam SoLoader is a runtime dependency for Fresco 1.13.0. When using Gradle 5, this is now not included in compilation classpath by default (see migration guide). I had to declare it explicitly:
testImplementation 'com.facebook.soloader:soloader:0.6.0'
@BansookNam @BeforeClass
public static void before() throws Exception{
SoLoader.setInTestMode();
}
this code did not solve the problem for me. try catch did. Is there a way to solve this without using try catch?
@vkotovv Thank you for notice!
@harshmittal29 Did you try implement
testImplementation 'com.facebook.soloader:soloader:0.6.0'
this on your build.gradle? Check vkotovv's comment.
If not working. I have no Idea how to solve 馃槩you may use try catch.
Confirmed that
@BeforeClass
public static void setup() {
SoLoader.setInTestMode();
}
works for me.
Is there any reason why TestNativeLoader isn't in the 2.0.0 release of Fresco?
This forces consumers to explicitly include the soloader library, which doesn't seem reasonable since Fresco already consumes it so should provide test utilities around it.
TestNativeLoader was added with version 2.1.0 and should be available starting with that version.
Most helpful comment
@foghina @BeforeClass is working thanks.
and the method should be static in the TestClass
```
@BeforeClass
public static void before() throws Exception{
SoLoader.setInTestMode();
}