Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

IOException: socket not created when running with Roboelectric Test #440

Closed
startthread opened this issue Sep 20, 2016 · 9 comments
Closed

Comments

@startthread
Copy link

Getting this error:

java.io.IOException: socket not created at android.net.LocalSocketImpl.bind(LocalSocketImpl.java:303) at android.net.LocalServerSocket.__constructor__(LocalServerSocket.java:48) at android.net.LocalServerSocket.<init>(LocalServerSocket.java) at com.facebook.stetho.server.LocalSocketServer.bindToSocket(LocalSocketServer.java:142) at com.facebook.stetho.server.LocalSocketServer.listenOnAddress(LocalSocketServer.java:78) at com.facebook.stetho.server.LocalSocketServer.run(LocalSocketServer.java:74) at com.facebook.stetho.server.ServerManager$1.run(ServerManager.java:40)

I have roboelectric test RobolectricTestRunner calls Application's onCreate, and it initialize stetho.

@RunWith(RobolectricTestRunner.class) @Config(constants = BuildConfig.class, sdk = 23)

@merri-dei
Copy link

Experiencing this, too. Were you able to solve this issue?

@joncottrell
Copy link

This is still allowing the tests to run, but I just want to suppress it! It's very annoying!

@ghost
Copy link

ghost commented Jan 28, 2017

Have the same issue, too.

@ghost
Copy link

ghost commented Mar 1, 2017

Same here, any fix for this?

@epetrenko
Copy link

epetrenko commented Mar 13, 2017

I have the same issue here and use custom RobolectricTestRunner (which defines test version of my application class) to avoid such errors, which seems a little bit hacky solution.

Extending Application class:

public class MyApplication extends Application {

    @Override
    public void onCreate() {
        super.onCreate();
        
        if (BuildConfig.DEBUG) {
            if (!isUnitTesting()) {
                Stetho.initializeWithDefaults(this);
            }
        }
    }

    protected boolean isUnitTesting() {
        return false;
    }
}

Then extending MyApplication and overriding isUnitTesting() method:

public class TestMyApplication extends MyApplication {

    @Override
    protected boolean isUnitTesting() {
        return true;
    }
}

And then extending RobolectricTestRunner:

public class MyRobolectricTestRunner extends RobolectricTestRunner {

    private static final int SDK_LEVEL = 25;

    public MyRobolectricTestRunner(Class<?> testClass) throws InitializationError {
        super(testClass);
    }

    @Override
    public Config getConfig(@NonNull Method method) {
        final Config defaultConfig = super.getConfig(method);
        return new Config.Implementation(
                new int[]{SDK_LEVEL},
                defaultConfig.minSdk(),
                defaultConfig.maxSdk(),
                defaultConfig.manifest(),
                defaultConfig.qualifiers(),
                defaultConfig.packageName(),
                defaultConfig.abiSplit(),
                defaultConfig.resourceDir(),
                defaultConfig.assetDir(),
                defaultConfig.buildDir(),
                defaultConfig.shadows(),
                defaultConfig.instrumentedPackages(),
                TestMyApplication.class,  // <-- overriding application class for testing here
                defaultConfig.libraries(),
                defaultConfig.constants() == Void.class ? BuildConfig.class : defaultConfig.constants()
        );
    }
}

Or you can just define it in Config section in test:

@RunWith(RobolectricTestRunner.class)
@Config(constants = BuildConfig.class, sdk = 25, application = TestMyApplication.class)
public class MyTest {
    [...]
}

@jasta
Copy link
Contributor

jasta commented Mar 13, 2017

This looks like it's actually a Robolectric issue. While the workarounds mentioned in this issue do seem like the right strategy short term, long term it would be beneficial to file this bug against Robolectric. Specifically the issue appears to be that LocalSocket simply doesn't work properly on Robolectric and needs to be emulated.

My best guess as to why this would be would be that LocalSocket is a Linux-specific concept that Robolectric would need to port to run on other types of systems (OS X, Windows, etc) and that even for Linux it's possible Robolectric lacks the underlying C/C++ implementation to make LocalSocket work properly. Stetho could probably detect this but it would be better and more consistent with Robolectric's long term vision to support this Android API properly so that tests can be written against it.

toyamah added a commit to toyamah/Likedit that referenced this issue Mar 27, 2017
If using Robolectric on local unit test, thrown IOException.
see facebook/stetho#440
@kakopappa
Copy link

this is the solution I came up with. Works with robolectric 3

if (!isRoboUnitTest()) {
Stetho.initializeWithDefaults(this);
}

public static boolean isRoboUnitTest() {
return "robolectric".equals(Build.FINGERPRINT);
}

@zyc945
Copy link

zyc945 commented May 26, 2017

if (!isRoboUnitTest()) {
Stetho.initializeWithDefaults(this);
}
public static boolean isRoboUnitTest() {
return "robolectric".equals(Build.FINGERPRINT);
}

it's works perfect

@kaershushu
Copy link

@kakopappa good works

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

8 participants