java.net.SocketException:套接字失败:EPERM(不允许操作)

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/56266801/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-11 01:16:01  来源:igfitidea点击:

java.net.SocketException: socket failed: EPERM (Operation not permitted)

javaandroidjsonservlets

提问by Aaron Villalobos

I am working on an Android Studio project with several activities. I am currently trying to read the output from a Java Servlet on localhost but it seems to be crashing due to a socket permission.

我正在处理一个包含多项活动的 Android Studio 项目。我目前正在尝试从本地主机上的 Java Servlet 读取输出,但由于套接字权限,它似乎崩溃了。

I've made a new project, used the exact same code and worked perfectly. So I dont understand why is not willing to work on my project.

我做了一个新项目,使用了完全相同的代码并且运行良好。所以我不明白为什么不愿意在我的项目上工作。

public class LoginActivity extends AppCompatActivity {


String apiUrl = "http://10.0.2.2:8080/ProyectService/Servlet?action=login";
EditText username;
EditText password;
AlertDialog dialog;
Usuario session;

@Override
public void onCreate(Bundle savedInstanceState) {
    // Inicializacion de ventana
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_login);
    getSupportActionBar().hide();

    // Inicializacion de componentes
    username = findViewById(R.id.username);
    password = findViewById(R.id.password);

    // Inicializacion de funcionalidad de botones
    Button button= (Button) findViewById(R.id.login);
    button.setOnClickListener(new View.OnClickListener() {
        public void onClick(View v) {
            UserLoginTask mAuthTask = new UserLoginTask();
            mAuthTask.execute();
        }
    });

    password = findViewById(R.id.password);
    createAlertDialog("Usuario o Contrase?a Incorrectos");
    }

    private void createAlertDialog(String message){
    AlertDialog.Builder builder = new AlertDialog.Builder(this);
    builder.setMessage(message)
            .setTitle("Error");
    dialog = builder.create();
    }



    // ASYNCRONUS NETWORK PROCESS

    public class UserLoginTask extends AsyncTask<String, String, String> {

    @Override
    protected void onPreExecute() {
    }


    @Override
    protected String doInBackground(String... params) {

        // implement API in background and store the response in current variable
        String current = "";
        try {
            URL url;
            HttpURLConnection urlConnection = null;
            try {
                url = new URL(apiUrl);
                System.out.println(apiUrl);
                urlConnection = (HttpURLConnection) url
                        .openConnection();

                InputStream in = urlConnection.getInputStream();

                InputStreamReader isw = new InputStreamReader(in);

                int data = isw.read();
                while (data != -1) {
                    current += (char) data;
                    data = isw.read();
                    //System.out.print(current);

                }
                System.out.print(current);
                // return the data to onPostExecute method
                return current;

            } catch (Exception e) {
                e.printStackTrace();
            } finally {
                if (urlConnection != null) {
                    urlConnection.disconnect();
                }
            }

        } catch (Exception e) {
            e.printStackTrace();
            return "Exception: " + e.getMessage();
        }
        return current;
        }
    }

    protected void onPostExecute(String success) {
        Log.i(success, "");
       //attemptLogin();
    }
}

I Expect it to read the data but it crashes at this line:

我希望它读取数据,但它在这一行崩溃:

InputStream in = urlConnection.getInputStream();

This is the error output:

这是错误输出:

java.net.SocketException: socket failed: EPERM (Operation not permitted)
at java.net.Socket.createImpl(Socket.java:492)
at java.net.Socket.getImpl(Socket.java:552)
at java.net.Socket.setSoTimeout(Socket.java:1180)
at com.android.okhttp.internal.io.RealConnection.connectSocket(RealConnection.java:143)
at com.android.okhttp.internal.io.RealConnection.connect(RealConnection.java:116)
at com.android.okhttp.internal.http.StreamAllocation.findConnection(StreamAllocation.java:186)
at com.android.okhttp.internal.http.StreamAllocation.findHealthyConnection(StreamAllocation.java:128)
at com.android.okhttp.internal.http.StreamAllocation.newStream(StreamAllocation.java:97)
at com.android.okhttp.internal.http.HttpEngine.connect(HttpEngine.java:289)
at com.android.okhttp.internal.http.HttpEngine.sendRequest(HttpEngine.java:232)
at com.android.okhttp.internal.huc.HttpURLConnectionImpl.execute(HttpURLConnectionImpl.java:465)
at com.android.okhttp.internal.huc.HttpURLConnectionImpl.getResponse(HttpURLConnectionImpl.java:411)
at com.android.okhttp.internal.huc.HttpURLConnectionImpl.getInputStream(HttpURLConnectionImpl.java:248)
at com.example.controller.LoginActivity$UserLoginTask.doInBackground(LoginActivity.java:114)
at com.example.controller.LoginActivity$UserLoginTask.doInBackground(LoginActivity.java:93)
at android.os.AsyncTask.call(AsyncTask.java:378)
at java.util.concurrent.FutureTask.run(FutureTask.java:266)
at android.os.AsyncTask$SerialExecutor.run(AsyncTask.java:289)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1167)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:641)
at java.lang.Thread.run(Thread.java:919)

回答by Aaron Villalobos

Solved: All I needed to do was to uninstall the app from the emulator and run it again.

已解决:我需要做的就是从模拟器中卸载应用程序并再次运行它。

回答by Archil Labadze

First of all you need change your android manifest .xml But after this action you must uninstall application and run it again. https://developer.android.com/training/basics/network-ops/connecting

首先,您需要更改您的 android manifest .xml 但在此操作之后,您必须卸载应用程序并再次运行它。 https://developer.android.com/training/basics/network-ops/connecting

and code here:

和代码在这里:

<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />

in AndroidManifest.xml

AndroidManifest.xml 中

回答by Juan Cabello

I had to uninstall the app from the emulator and then everything started to work. I just needed the folowing permission on the AndroidManifest.xml

我不得不从模拟器中卸载该应用程序,然后一切都开始工作了。我只需要 AndroidManifest.xml 上的以下权限

<uses-permission android:name="android.permission.INTERNET" />

回答by John Alexander

just uninstall the app from the emulator then run again and it'll work i had the same issue

只需从模拟器卸载应用程序然后再次运行它就会工作我遇到了同样的问题

to unistall the app run your project when "the application had stopped" message appear click "app info" then unistall

要卸载应用程序,请在出现“应用程序已停止”消息时运行您的项目,单击“应用程序信息”,然后卸载

回答by ovidiur

If anyone still has this issue I encountered it when I used VPN and tried to connect to wifi while cellular was on. I was using Anyconnect VPN client. Solution is to enable the allow bypass that will let you bind a socket to a specific network if this is what you are looking for.

如果有人仍然遇到这个问题,我在使用 VPN 并尝试在蜂窝网络打开时连接到 wifi 时遇到了这个问题。我正在使用 Anyconnect VPN 客户端。解决方案是启用允许绕过,如果这是您正在寻找的,它将允许您将套接字绑定到特定网络。

AnyConnect only uses allowBypass if it's configured in its managed restrictions (by EMM), via this key: vpn_connection_allow_bypass.

AnyConnect 仅使用 allowBypass,如果它在其托管限制中配置(通过 EMM),通过此密钥:vpn_connection_allow_bypass。

回答by Habib Adnan

  1. Add ACCESS_NETWORK_STATE permission in manifest
  2. Reinstallation emulator
  1. 在清单中添加 ACCESS_NETWORK_STATE 权限
  2. 重装模拟器

回答by Ssenyonjo

Set android:usesCleartextTraffic="true"in the manifest file. Add the permission INTERNET. Uninstall app and then install again.

android:usesCleartextTraffic="true"在清单文件中设置 。添加权限INTERNET。卸载应用程序,然后重新安装。