当前位置: 首页 > 知识库问答 >
问题:

Java ServerSocket在接受客户端后如何获得绑定到同一个本地端口的新套接字?

邵弘义
2023-03-14

我对Socket和ServerSocket端口用法感到困惑。Oracle关于套接字的Java教程是这样说的:

插座是什么?

通常,服务器运行在特定的计算机上,并具有绑定到特定端口号的套接字。服务器只是等待,监听套接字让客户机发出连接请求。在客户端:客户端知道服务器运行的机器的主机名和服务器侦听的端口号。要发出连接请求,客户端尝试在服务器的机器和端口上与服务器会合。客户端还需要向服务器标识自己,以便绑定到在此连接期间将使用的本地端口号。这通常是由系统分配的。

如果一切顺利,服务器接受连接。接受后,服务器将获得绑定到相同本地端口的新套接字,并将其远程endpoint设置为客户端的地址和端口。它需要一个新的套接字,这样它就可以继续监听用于连接请求的原始套接字,同时倾向于连接的客户端的需求。

在客户端,如果连接被接受,则成功创建了一个套接字,并且客户端可以使用该套接字与服务器通信。客户端和服务器现在可以通过写入或读取它们的套接字进行通信。

我尝试了下面的代码进行测试。但会引发异常。

try {
    ServerSocket serverSocket = new ServerSocket(8080);

    Socket socket = serverSocket.accept();

    // This prints 8080
    System.out.println("Local port of accepted socket : " + socket.getLocalPort());  

    // But this throws java.net.BindException: Address already in use: JVM_Bind 
    Socket myClientSocket = new Socket("www.google.com", 80, null, 8080);

} catch (Exception e) {
    e.printStackTrace();
}

我的问题很明显。虽然从ServerSocket.Accept()返回的套接字可以使用相同的本地端口(8080),为什么我创建的套接字不能使用它?

共有2个答案

宋宏毅
2023-03-14

您的服务器和客户端正在使用同一个本地端口进行通信。当您创建服务器套接字时,您“说”它必须监听8080端口。没问题。任何一个想要与您的服务器套接字通信的都必须使用这样的端口。

但是,在下面您正在创建一个客户端套接字,该套接字使用端口80连接到google站点(google正在监听该端口),在最后一个参数中,您说这个套接字还必须使用本地端口8080来建立连接。一次只能有一个连接使用一个端口,这就是为什么您得到java.net.bindexception,服务器和客户机连接都使用8080。

我的建议...从您的套接字客户端构造函数中获取最后两个参数,或者更改您的本地客户端端口(总是获得一个高的数字,以避免其他进程出现同样的问题):

Socket myClientSocket = new Socket("www.google.com", 80);

Socket myClientSocket = new Socket("www.google.com", 80, null, 58080);
汪典
2023-03-14

为了简单起见,侦听TCP套接字已经显式绑定到端口,因此您不能将第二个TCP套接字显式绑定到同一端口(除非两个套接字也显式绑定到不同的IP地址,不包括INADDR_ANY)。

接受的套接字不经过显式的“绑定”过程。它们自动获取本地IP地址和端口,如果您不绑定地连接出站套接字,它也会自动获取本地IP地址和端口。

 类似资料:
  • 问题内容: 我正在学习Java套接字编程。我使用以下语句连接到网站: 当我调试应用程序并查看s的内容时,我看到: 1)我想知道此本地端口7846的来源以及确切的含义。 2)如果网站的IP地址是2.21.246.97,为什么我不能仅在浏览器的地址栏中输入2.21.246.97来连接到该网站? 谢谢 问题答案: 这是本地套接字端口号。通常由系统分配。 请参阅什么是套接字?。 在客户端:客户端知道运行服

  • 我正在服务器端使用Apache Mina。我有一个客户是用传统的IO写的。下面是将数据发送到服务器的客户端代码。 上面的线程运行了20次。因此创建了20个套接字。在一个套接字中,发送许多消息。通过使用IO套接字类编写的服务器,我能够完美地检索数据。 问题出现在使用缓冲区的基于Apache Mina的服务器中!我无法获得单个消息。 我如何获得单个消息(如果我不能在客户端更改任何内容,并且单个消息的长

  • 问题内容: 当使用Socket类时,它正在某个端口上建立与服务器的TCP连接,但是ServerSocket能够在服务器上为每个接受请求处理多个客户端连接,并将其委托给线程来处理该请求。但是ServerSocket类如何在同一个端口上接受多个tcp连接。 这是否意味着要由操作系统来决定它允许多少个连接,或者允许的最大积压量是多少,并且可以由OS之上的应用程序控制(我的意思是Java受OS支持的最大积

  • 我对套接字协议非常陌生,我肯定问题来自于我对此几乎一无所知。但是基本上我在服务器端口5000上有一个套接字,我需要一个angularjs代码来监听这个套接字。服务器上的套接字可以读取我从另一台计算机(客户端)发送的任何内容。但是由于某种原因,angular代码不能监听/连接到插座。以下是我现在所拥有的: index.html 下面是angularjs代码: 在Firefox中: Firefox无法

  • 我刚刚开始使用Sockets,对于我当前的项目,我需要能够从客户端控制我的程序,但是如果我的项目合作伙伴想同时使用他的客户端,服务器不会向他发送“您已连接”消息,如连接类所示。所以我假设服务器不同时接受多个客户端。我尝试过使用类Connection的Thread,但这也不会向第二个客户端发送消息“您已连接”。我在这里做错了什么? 这是我用来同时连接多个用户的线程: 编辑:附加信息 在第一个客户端连

  • 问题内容: 我想知道我们如何知道套接字(java)中服务器端客户端的IP地址。假设有一个服务器“ S”和两个客户端“ A”和“ B”。客户端A向我(服务器)发送一些信息,客户端B向我(服务器)发送一些其他信息。我必须将来自A和B的信息存储在不同表中的数据库中。如何区分客户端A和客户端B的请求? 问题答案: 每个套接字都有一个方法来返回与其连接的客户端的IP地址。