简体   繁体   English

如何在没有服务器的情况下通过套接字连接两个Android设备

[英]How can I connect two Android device by socket without server

I am trying to develop an android application that can exchange data on peer to peer connection with other devices without server. 我正在尝试开发一个Android应用程序,可以在没有服务器的情况下与其他设备进行对等连接的数据交换。 So please suggest how can I do this. 所以请建议我该怎么做。 Thank you in advance. 先感谢您。

This is a complete code for chat by SocketProgramming without server. 这是一个没有服务器的SocketProgramming聊天的完整代码。

In my Application, first you are a client and you search for a server. 在我的应用程序中,首先您是客户端并搜索服务器。 When you do not find any server, you become a server and wait for a client. 当您找不到任何服务器时,您将成为服务器并等待客户端。

public class MainActivity extends ActionBarActivity {

private Handler handler = new Handler();
private TextView text;
private EditText input;
private Button send;
private Socket socket;
private DataOutputStream outputStream;
private BufferedReader inputStream;
private String DeviceName = "Device";

private boolean searchNetwork() {
    log("Connecting");
    String range = "192.168.56.";
    for (int i = 1; i <= 255; i++) {
        String ip = range + i;
        try {
            socket = new Socket();
            socket.connect(new InetSocketAddress(ip, 9000), 50);
            outputStream = new DataOutputStream(socket.getOutputStream());
            inputStream = new BufferedReader(new InputStreamReader(
                    socket.getInputStream()));
            DeviceName += "1";
            Log.i("Server", DeviceName);
            log("Connected");
            return true;
        } catch (Exception e) {
        }
    }
    return false;

}

private void runNewChatServer() {
    ServerSocket serverSocket;
    try {
        serverSocket = new ServerSocket(9000);
        log("Waiting for client...");
        socket = serverSocket.accept();
        DeviceName += "2";
        log("a new client Connected");
    } catch (IOException e) {
    }

}

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);
    text = (TextView) findViewById(R.id.text);
    input = (EditText) findViewById(R.id.input);
    send = (Button) findViewById(R.id.send);
    Thread thread = new Thread(new Runnable() {

        @Override
        public void run() {
            try {
                if (!searchNetwork()) {
                    runNewChatServer();

                }

                outputStream = new DataOutputStream(
                        socket.getOutputStream());
                inputStream = new BufferedReader(new InputStreamReader(
                        socket.getInputStream()));
                while (true) {

                    String Message = inputStream.readLine();
                    if (Message != null) {
                        log(Message);
                    }
                }
            } catch (IOException e) {
                log("Error: IO Exception");
                e.printStackTrace();
            }
        }
    });
    send.setOnClickListener(new OnClickListener() {

        @Override
        public void onClick(View arg0) {
            if (outputStream == null) {
                return;
            }
            try {
                String Message = input.getText().toString() + "\n";
                outputStream.write(Message.getBytes());
                log2(input.getText().toString());
            } catch (IOException e) {
                e.printStackTrace();
            }
            input.setText("");
        }
    });
    thread.start();

}

private void log(final String message) {
    handler.post(new Runnable() {
        String DeviceName2="";
        @Override
        public void run() {
            if (DeviceName.equals("Device1")) {
                DeviceName2 = "Device2";
            }else if(DeviceName.equals("Device2")) {
                DeviceName2 = "Device1";
            }else{
                DeviceName2 = "UnknowDevice";
            }

            text.setText(text.getText() + "\n" + DeviceName2 + " :"
                    + message);

        }
    });
}
private void log2(final String message) {
    handler.post(new Runnable() {

        @Override
        public void run() {


            text.setText(text.getText() + "\n" + "you" + " :"
                    + message);

        }
    });
}

@Override
public boolean onKeyDown(int keyCode, KeyEvent event) {
    if (keyCode == KeyEvent.KEYCODE_BACK) {
        if (socket != null) {
            try {
                socket.close();
            } catch (IOException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }
        }
        System.exit(0);
        return true;
    }
    return super.onKeyDown(keyCode, event);
}

}

Java provides ServerSocket and Socket to communicate b/w devices. Java提供ServerSocketSocket来与b / w设备进行通信。 One of the device you can make as server and other device you can make as client and communicate b/w 'em without introducing server hosted on some machine. 您可以将其中一个设备作为服务器和其他设备,您可以作为客户端进行通信,而无需在某些计算机上引入托管服务器。

The Other and better option is Using Wi-Fi Peer-to-Peer . 其他更好的选择是使用Wi-Fi Peer-to-Peer WifiP2pManager help you to achieve your purpose. WifiP2pManager帮助您实现目标。 Here is an example. 是一个例子。

If you're looking for such P2P over a local network, there are two parts to it: 如果您正在通过本地网络寻找此类P2P,则有两个部分:

  1. Discovering peers 发现同行
  2. Communicating with peers 与同行沟通

Among Android APIs, you can either use Network Service Discovery APIs for this or Wifi P2P Service Discovery APIs . 在Android API中,您可以使用网络服务发现APIWifi P2P服务发现API

There's a wrapper library which which uses these internally and has comparatively better documentation - Salut, which can also be used. 有一个包装库,它在内部使用它们并具有相对更好的文档 - Salut,也可以使用。

I also created a library for P2P - Near , which uses sockets directly. 我还为P2P创建了一个库 - Near ,它直接使用套接字。 The problem I was facing with Android APIs was that discovery wasn't happening with certainty every time and the underlying issue was unknown. 我在Android API面临的问题是,每次发现都没有确定性,而且潜在的问题是未知的。

If you're looking for P2P across the internet, socket IO is a prevalent solution. 如果您正在寻找互联网上的P2P, 套接字IO是一种流行的解决方案。 Even Near should be able to facilitate the transfers if you provide the IP addresses and they're not behind NAT firewalls. 如果您提供IP地址并且它们不在NAT防火墙之后,即使近,也应该能够促进传输。

Your design has a big problem : ... 你的设计有一个大问题:......

If there is no central server some android devices should act as client and others as server but this will not work in some situations: 如果没有中央服务器,一些Android设备应该充当客户端而其他设备充当服务器但是在某些情况下这不起作用:

  • When the mobile telephony provider assigns private and non-public IP 当移动电话提供商分配私有和非公共IP时

  • When the device is connected to a Wi-Fi network but no NAT rule is defined on the router. 当设备连接到Wi-Fi网络但路由器上未定义NAT规则时。

In both cases the problem is that the listening port of the device that must act as server is unreachable. 在这两种情况下,问题是必须充当服务器的设备的侦听端口是不可达的。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM