【问题标题】:How to get the remote IP adress in Java, TCP/IP Server/Client model with sockets?如何在 Java、TCP/IP 服务器/客户端模型中使用套接字获取远程 IP 地址?
【发布时间】:2012-05-10 18:31:37
【问题描述】:

所以我有一个在桌面应用程序中使用 Socket 和 ServerSocket 的 TCP/IP 服务器/客户端模型(应该在网络中玩的游戏)。

我需要获取服务器远程 IP 地址,以便客户端应用程序可以在打开的特定端口上打开的服务器应用程序连接到它。

public class ServerConnection {

private int PORT = 8100;
private ServerSocket serverSocket = null;

public void create() throws IOException {
    serverSocket = new ServerSocket();
    serverSocket.bind(new InetSocketAddress("localhost", PORT));
}

public void close() throws IOException {
    serverSocket.close();
}

public ClientConnection acceptRequest() throws IOException {
    Socket socket = serverSocket.accept();
    return new ClientConnection(socket);
}

public ServerConnection() throws IOException {
}
}
public class ClientConnection {

    private String adress = "127.0.0.1";
    private int PORT = 8100;
    private Socket socket = null;
    private PrintWriter out = null;
    private BufferedReader in = null;

    public ClientConnection() {

    }

    public ClientConnection(Socket socket) throws IOException {
        this.socket = socket;
        out = new PrintWriter(socket.getOutputStream(), true);
        in = new BufferedReader(new InputStreamReader(
                socket.getInputStream()));
    }

    public void connect() throws UnknownHostException, IOException {
        socket = new Socket(adress, PORT);
        out = new PrintWriter(socket.getOutputStream(), true);
        in = new BufferedReader(new InputStreamReader(
                socket.getInputStream()));
    }


    public void close() throws IOException {
        if (out != null) {
            out.close();
        }
        if (in != null) {
            in.close();
        }
        if (socket != null) {
            socket.close();
            socket = null;
        }
    }

    public void send(String request) {
        if (socket != null) {
            out.println(request);
        }            
    }

    public String receive() throws IOException {
        if (socket != null) {
            return in.readLine();
        }
        return null;
    }
}

它在 localhost 上运行良好,但我希望它能够在任何地方(服务器和客户端)运行。所以我需要一种方法让服务器找出它当前的远程 IP,用户将通过一些通信线路(IM、电子邮件等)发送它,然后客户端将输入地址并连接到服务器。因此,一个应用程序既可以作为服务器也可以作为客户端,因此不需要一个稳定的服务器应用程序来持续运行并为客户端提供服务

【问题讨论】:

  • 硬编码吗?如果没有,硬编码一个域来指向它?
  • 我希望能够在我想要的任何地方运行我的服务器应用程序,我怎样才能硬编码一个域来指向它?
  • 它实际上并不需要硬编码到您的代码中。客户端只需要能够以某种方式查找 IP 地址(或域)。 Ii 可能位于用户可配置的属性文件或类似文件中。
  • 请提供一些示例代码,以便我们为您提供帮助。
  • 您是否正在寻找可以处理 NAT 穿越的东西?例如:code.google.com/p/ice4j

标签: java networking client-server ip


【解决方案1】:

如果您的客户端和服务器位于同一网段,Zeroconf 是一个非常有吸引力的零配置(嗯...)解决方案。你会发现一个Java实现with JmDNS

此外,从头开始实施稳定的协议并非易事。如果不是出于教育目的,我建议您使用类似

  • 阿帕奇米娜
  • 灰熊
  • Netty 3
  • 快速服务器
  • xSocket

这些库为您提供了许多在这里很重要的功能,例如错误处理和并发(非阻塞调用)。

如果你想从外部访问你的服务器,你不能绑定到“localhost”。请参阅 ServerSocket.bind。您可以通过ServerSocket.getInetAddress绑定到“null”并请求默认使用的网络适配器。

【讨论】:

  • 你不明白,我有一个既可以用作服务器又可以用作客户端的应用程序,除了当前运行该应用程序的计算机的远程地址之外,我不需要其他任何东西(类似于 whatismyipaddress.com )
【解决方案2】:

你需要做两个调整:

  • 服务器套接字必须绑定到 localhost 以外的其他东西。通常,您使用new ServerSocket(port) 创建服务器套接字,而不指定主机名。这样,服务器套接字将在给定端口上侦听机器上所有可用地址。如果将套接字绑定到“localhost”,则只能通过 localhost 访问它。那不是你想要的。创建服务器套接字后,您可以尝试使用serverSocket.getLocalSocketAddress()找出它的SocketAddress

  • 客户端需要连接到您在创建/绑定服务器套接字时指定的地址。如果您创建了服务器套接字而没有指定地址(即绑定到所有可用地址),那么客户端可以连接到其中任何一个(通常是 localhost + 外部 IP 地址)。

服务器通常不需要知道他们的地址。它们只是绑定到<any address>:port,客户端必须知道要连接的地址。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2012-12-24
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-02-16
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多