简体   繁体   English

Java套接字服务器客户端到客户端文件传输

[英]Java socket server client to client file transfer

I'm not sure if what I'm trying to do is possible. 我不确定我要做什么。 I want a socket server to run, multiple clients can connect to it. 我希望套接字服务器运行,多个客户端可以连接到它。 Client A drags and drops a file onto his GUI and client B gets a popup asking if he wants to receive the file. 客户端A将文件拖放到其GUI上,客户端B弹出对话框询问他是否要接收该文件。 If agreed client A starts uploading the file and client B starts downloading the file directly. 如果达成协议,则客户端A开始上传文件,而客户端B开始直接下载文件。 Is this possible? 这可能吗? should the file first be transferred to the server? 应该先将文件传输到服务器吗? If I send a file to the server it works, but when I try to send a file to client BI get the following: 如果我将文件发送到服务器,则可以正常工作,但是当我尝试将文件发送到客户端BI时,将获得以下信息:

java.net.ConnectException: Connection timed out: connect
    at java.net.DualStackPlainSocketImpl.connect0(Native Method)
    at java.net.DualStackPlainSocketImpl.socketConnect(DualStackPlainSocketImpl.java:79)
    at java.net.AbstractPlainSocketImpl.doConnect(AbstractPlainSocketImpl.java:339)
    at java.net.AbstractPlainSocketImpl.connectToAddress(AbstractPlainSocketImpl.java:200)
    at java.net.AbstractPlainSocketImpl.connect(AbstractPlainSocketImpl.java:182)
    at java.net.PlainSocketImpl.connect(PlainSocketImpl.java:172)
    at java.net.SocksSocketImpl.connect(SocksSocketImpl.java:392)
    at java.net.Socket.connect(Socket.java:579)
    at java.net.Socket.connect(Socket.java:528)
    at java.net.Socket.<init>(Socket.java:425)
    at java.net.Socket.<init>(Socket.java:241)

here is the upload class: 这是上传类:

public Upload(String addr, int port, File filepath, OpenChatFrame frame) {
        super();
        try {
            file = filepath;
            ui = frame;
            socket = new Socket(InetAddress.getByName(addr), port);
            Out = socket.getOutputStream();
            In = new FileInputStream(filepath);
            length = file.length();
        } catch (Exception ex) {
            ex.printStackTrace();
        }
    }

    @Override
    public void run() {
        try {
            byte[] buffer = new byte[1024];

            int count;

            ui.jProgressBar1.setMaximum((int) length);

            while ((count = In.read(buffer)) >= 0) {
                Out.write(buffer, 0, count);
                bytes += count;
                ui.jProgressBar1.setValue(bytes);

            }
            Out.flush();


            if (In != null) {
                In.close();
            }
            if (Out != null) {
                Out.close();
            }
            if (socket != null) {
                socket.close();
            }
        } catch (Exception ex) {
            ex.printStackTrace();
        }
    }

and here is the download class: 这是下载类:

public Download(String saveTo, OpenChatFrame ui) {
    try {
        server = new ServerSocket(0);
        port = server.getLocalPort();
        this.saveTo = saveTo;
        this.ui = ui;
    } catch (IOException ex) {
        //TODO: catch
    }
}

@Override
public void run() {
    try {
        socket = server.accept();
        System.out.println("Download : " + socket.getRemoteSocketAddress());

        In = socket.getInputStream();
        Out = new FileOutputStream(saveTo);

        byte[] buffer = new byte[1024];
        int count;

        while ((count = In.read(buffer)) >= 0) {
            Out.write(buffer, 0, count);
        }

        Out.flush();

        File physicalFile = new File(saveTo);
        System.out.println("FILE FILENAME: " + physicalFile.getName());
        System.out.println("saveTo: " + saveTo);


        if (Out != null) {
            Out.close();
        }
        if (In != null) {
            In.close();
        }
        if (socket != null) {
            socket.close();
        }
    } catch (Exception ex) {
        //TODO: catch
    }
}

I want a socket server to run, multiple clients can connect to it. 我希望套接字服务器运行,多个客户端可以连接到它。 Client A drags and drops a file onto his GUI and client B gets a popup asking if he wants to receive the file. 客户端A将文件拖放到其GUI上,客户端B弹出对话框询问他是否要接收该文件。 If agreed client A starts uploading the file and client B starts downloading the file directly. 如果达成协议,则客户端A开始上传文件,而客户端B开始直接下载文件。 Is this possible? 这可能吗? should the file first be transferred to the server? 应该先将文件传输到服务器吗?

Yes it is possible, if the circumstances allow it. 是的,如果情况允许,这是可能的。

Assuming that the client A initiates the Socket connection, then client B's IP address must be addressable by client A. If client B has a public IP address, or a private IP address that client A's network has a route to, then you are OK. 假定客户端A启动了Socket连接,则客户端B必须可以对客户端B的IP地址进行寻址。如果客户端B具有公用IP地址,或者客户端A的网络可以路由到的专用IP地址,则可以。 However, client B has a private IP address and client A cannot route to it, then it cannot work, and you would need a public server (accessible to both) to relay the data. 但是,客户端B有一个专用IP地址,客户端A无法路由到它,然后它不能工作,并且您将需要一个公共服务器(两个服务器都可以访问)来中继数据。

The other thing that is required is that there are no firewalls blocking connections from client A to client B on the port that they are trying to use. 需要做的另一件事是,没有防火墙阻止它们试图使用的端口上的客户端A到客户端B的连接。


Your partial stacktrace seems to be from the initiating client (client A), and indicates that the connection attempt is not getting through. 您的部分堆栈跟踪似乎来自于发起客户端(客户端A),并指示连接尝试未通过。 Given the nature of the exception, I think that most likely explanation is that there is a firewall blocking the connection. 考虑到异常的性质,我认为最可能的解释是有防火墙阻止了连接。

(If this was a routing problem, or if the server wasn't listening on the designated port, you would see different exceptions ... ) (如果这是路由问题,或者服务器未在指定的端口上侦听,则会看到不同的异常...)


Asides: 旁白:

  1. It is bad style to start variable names with an uppercase letter; 用大写字母开头的变量名是不好的风格。 eg In and Out . 例如, InOut The style rules say that In and Out ought to be class names. 样式规则说InOut应该是类名。

  2. The terms "upload" and "download" are not normally used to describe a "peer-to-peer" transfer; 术语“上载”和“下载”通常不用于描述“对等”传输; eg between two clients. 例如两个客户之间。

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

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