Java IO 服务器客户端读取并处理用户输入
Java IO Server Client read and process users input
我有一个简单的文件服务器和客户端(来自网络的代码),可以让我将文件发送到我家庭局域网内的另一台笔记本电脑。现在,从服务器发送到客户端的文件是硬编码的,但我想提示客户端的用户输入文件名,将其发送到服务器并发回指定的文件。我的代码如下所示:
服务器
import java.net.*;
import java.io.*;
public class Server {
public static void main(String[] args) {
BufferedOutputStream outputStream;
BufferedInputStream inputStream;
FileInputStream fileInput;
String file = "C:/java/file.mp4";
try {
ServerSocket socket = new ServerSocket(12345);
while(true) {
Socket clientSocket = socket.accept();
outputStream = new BufferedOutputStream(clientSocket.getOutputStream());
fileInput = new FileInputStream(file);
inputStream = new BufferedInputStream(fileInput);
int packetToSend = -1;
byte[] buffer = new byte[8192];
while((packetToSend = inputStream.read(buffer)) > -1) {
outputStream.write(buffer, 0, packetToSend);
System.out.println("sending " + packetToSend + " bytes");
outputStream.flush();
}
}
}
catch(Exception e) {
e.printStackTrace();
}
}
}
这就是客户端代码(服务器的IP地址是参数s[0],保存文件的路径是main方法中的s[1]。
import java.net.*;
import java.io.*;
public class Client {
public static void main(String[] s) {
try {
String address = new String(s[0]);
String fileToSave = new String(s[1]);
Socket socket = new Socket(address,12345);
BufferedInputStream bis = new BufferedInputStream(socket.getInputStream());
BufferedOutputStream bos = new BufferedOutputStream(socket.getOutputStream());
FileOutputStream fos = new FileOutputStream(fileToSave);
int n;
byte[] buffer = new byte[8192];
System.out.println("Connected");
while ((n = bis.read(buffer)) > 0) {
System.out.println("received "+n+" bytes");
fos.write(buffer, 0, n);
fos.flush();
}
System.out.println("recieved");
}
catch(Exception e) {
e.printStackTrace();
}
}
}
我想在客户端连接后提示客户端用户输入文件名以发送到服务器,服务器应发送该文件。
我试图在 System.out.println("connected");
之后将它放在客户端
System.out.print("Insert filename to download: ");
BufferedReader reader = new BufferedReader(new InputStreamReader(System.in));
String input = null;
try {
input = reader.readLine();
} catch (IOException ioe) {
System.out.println("Eingabe konnte nicht verarbeitet werden!");
System.exit(1);
}
System.out.println("Eingabe: " + input);
在服务器端,我把它放在 outputStream = new BufferedOutputStream(clientSocket.getOutputStream());
之后,以覆盖服务器开头的硬编码文件名 class。
inputStream = new BufferedInputStream(clientSocket.getInputStream());
fileInputStream = new FileInputStream(inputStream);
fileInputStream = new BufferedInputStream(fileInput);
建立连接后,客户端处于空闲状态(无法输入内容),服务器端在写入控制台后什么也不做 "new connection"。
请问我该如何解决?
客户端向服务器发送文件名。所以首先你必须从套接字的输入流中提取文件名。为此,您需要建立一个关于如何发送信息的协议。这在处理不同于 UDP 数据报的 TCP 流时至关重要。通常使用两个换行符来传达消息的结尾。但是因为文件名中有换行符是不正常的,所以我们将使用一个换行符来表示消息的结束。
然后我们可以使用 Scanner 从客户端的套接字中提取文件名。
String fileName;
Scanner scanner = new Scanner (clientSocket.getInputStream());
while(scanner.hasNextLine())
{
fileName = scanner.nextLine();
break;
}
fileInputStream = new FileInputStream(fileName);
fileInputStream = new BufferedInputStream(fileInput);
在此示例中,文件名必须是该文件在服务器文件系统中的绝对路径。在未来的版本中,您可能希望使用服务器上存储文件的目录,客户端可以为您提供该目录中文件的相对路径。这是它的样子。
String fileName;
Scanner scanner = new Scanner (clientSocket.getInputStream());
while(scanner.hasNextLine())
{
fileName = scanner.nextLine();
break;
}
fileInputStream = new FileInputStream(FILE_DIR + fileName);
fileInputStream = new BufferedInputStream(fileInput);
变量 FILE_DIR 看起来像这样:
static String FILE_DIR = "C:/java/";
客户端发送的文件就是 file.mp4
编辑 1:
这是带有建议的客户端代码。请注意,此测试质量代码,而非生产代码。
import java.net.*;
import java.io.*;
public class Client {
static String FILE_DIR = "./";
public static void main(String[] s) throws IOException {
/**
* Establish socket using main args.
*/
String address = s[0];
while (true) {
/**
* Get the file name from the user.
*/
System.out.print("Insert filename to download: ");
BufferedReader reader = new BufferedReader(new InputStreamReader(System.in));
String fileName = null;
try {
fileName = reader.readLine();
} catch (IOException ioe) {
System.out.println("Eingabe konnte nicht verarbeitet werden!");
System.exit(1);
}
System.out.println("Eingabe: " + fileName);
/**
* Create the socket.
*/
Socket socket = new Socket(address, 12345);
/**
* With file name in hand, proceed to send the filename to the
* server.
*/
//...put in try-with-resources to close the outputstream.
try (BufferedOutputStream bos = new BufferedOutputStream(socket.getOutputStream())) {
System.out.println("Connected: Sending file name to server.");
//...send file name plus a newline.
bos.write((fileName + '\n').getBytes());
bos.flush();
/**
* Get the file contents and save to disk.
*/
//...wrap input stream in DataInpuStream for portability.
//...put in try-with-resource to close the input stream.
try (BufferedInputStream bis = new BufferedInputStream(new DataInputStream(socket.getInputStream()))) {
DataOutputStream fos = new DataOutputStream(new FileOutputStream(fileName));
int n;
byte[] buffer = new byte[8192];
System.out.println("Connected: Recieving file contents from server.");
while ((n = bis.read(buffer)) > 0) {
System.out.println("received " + n + " bytes");
fos.write(buffer, 0, n);
fos.flush();
}
System.out.println("recieved");
} catch (Exception e) {
e.printStackTrace();
}
}
}
}
}
这是服务器代码。请注意服务器正在从名为 ./files/ 的本地目录中检索文件,请将其更改为您想要的任何目录。
导入java.net.;
导入 java.io.;
导入 java.util.Scanner;
public class 服务器 {
static String FILE_DIR = "./files/";
public static void main(String[] args) {
BufferedInputStream inputStream;
FileInputStream fileInput;
try {
ServerSocket socket = new ServerSocket(12345);
while (true) {
Socket clientSocket = socket.accept();
/**
* Get the file name from the client. File name is one per line.
*/
//...put in trye-with-resources to close InputStream for us.
try (InputStream inputFromClient = clientSocket.getInputStream()) {
System.out.println("Connected: Getting file name from client.");
Scanner scanner = new Scanner(inputFromClient);
String fileName;
if (scanner.hasNextLine()) {
fileName = scanner.nextLine();
System.out.println("File name = " + fileName);
} else {
//...no line found, continue. consider logging an error or warning.
continue;
}
/**
* With fileName in hand, we can proceed to send the
* contents of the file to the client.
*/
fileInput = new FileInputStream(fileName);
//...use DataInputStream for more portable code
DataInputStream dataInput = new DataInputStream(fileInput);
inputStream = new BufferedInputStream(dataInput);
int packetToSend = -1;
byte[] buffer = new byte[8192];
//...consider closing the OutputStream to let the client know.
//...use try-with-resource to close the outputStream for us.
//...wrap your outputStream in DataOutputStream
try (BufferedOutputStream outputStream = new BufferedOutputStream(new DataOutputStream(clientSocket.getOutputStream()))) {
while ((packetToSend = inputStream.read(buffer)) > -1) {
outputStream.write(buffer, 0, packetToSend);
System.out.println("sending " + packetToSend + " bytes");
outputStream.flush();
}
}
}
}
} catch (Exception e) {
e.printStackTrace();
}
}
}
我有一个简单的文件服务器和客户端(来自网络的代码),可以让我将文件发送到我家庭局域网内的另一台笔记本电脑。现在,从服务器发送到客户端的文件是硬编码的,但我想提示客户端的用户输入文件名,将其发送到服务器并发回指定的文件。我的代码如下所示:
服务器
import java.net.*;
import java.io.*;
public class Server {
public static void main(String[] args) {
BufferedOutputStream outputStream;
BufferedInputStream inputStream;
FileInputStream fileInput;
String file = "C:/java/file.mp4";
try {
ServerSocket socket = new ServerSocket(12345);
while(true) {
Socket clientSocket = socket.accept();
outputStream = new BufferedOutputStream(clientSocket.getOutputStream());
fileInput = new FileInputStream(file);
inputStream = new BufferedInputStream(fileInput);
int packetToSend = -1;
byte[] buffer = new byte[8192];
while((packetToSend = inputStream.read(buffer)) > -1) {
outputStream.write(buffer, 0, packetToSend);
System.out.println("sending " + packetToSend + " bytes");
outputStream.flush();
}
}
}
catch(Exception e) {
e.printStackTrace();
}
}
}
这就是客户端代码(服务器的IP地址是参数s[0],保存文件的路径是main方法中的s[1]。
import java.net.*;
import java.io.*;
public class Client {
public static void main(String[] s) {
try {
String address = new String(s[0]);
String fileToSave = new String(s[1]);
Socket socket = new Socket(address,12345);
BufferedInputStream bis = new BufferedInputStream(socket.getInputStream());
BufferedOutputStream bos = new BufferedOutputStream(socket.getOutputStream());
FileOutputStream fos = new FileOutputStream(fileToSave);
int n;
byte[] buffer = new byte[8192];
System.out.println("Connected");
while ((n = bis.read(buffer)) > 0) {
System.out.println("received "+n+" bytes");
fos.write(buffer, 0, n);
fos.flush();
}
System.out.println("recieved");
}
catch(Exception e) {
e.printStackTrace();
}
}
}
我想在客户端连接后提示客户端用户输入文件名以发送到服务器,服务器应发送该文件。
我试图在 System.out.println("connected");
System.out.print("Insert filename to download: ");
BufferedReader reader = new BufferedReader(new InputStreamReader(System.in));
String input = null;
try {
input = reader.readLine();
} catch (IOException ioe) {
System.out.println("Eingabe konnte nicht verarbeitet werden!");
System.exit(1);
}
System.out.println("Eingabe: " + input);
在服务器端,我把它放在 outputStream = new BufferedOutputStream(clientSocket.getOutputStream());
之后,以覆盖服务器开头的硬编码文件名 class。
inputStream = new BufferedInputStream(clientSocket.getInputStream());
fileInputStream = new FileInputStream(inputStream);
fileInputStream = new BufferedInputStream(fileInput);
建立连接后,客户端处于空闲状态(无法输入内容),服务器端在写入控制台后什么也不做 "new connection"。
请问我该如何解决?
客户端向服务器发送文件名。所以首先你必须从套接字的输入流中提取文件名。为此,您需要建立一个关于如何发送信息的协议。这在处理不同于 UDP 数据报的 TCP 流时至关重要。通常使用两个换行符来传达消息的结尾。但是因为文件名中有换行符是不正常的,所以我们将使用一个换行符来表示消息的结束。
然后我们可以使用 Scanner 从客户端的套接字中提取文件名。
String fileName;
Scanner scanner = new Scanner (clientSocket.getInputStream());
while(scanner.hasNextLine())
{
fileName = scanner.nextLine();
break;
}
fileInputStream = new FileInputStream(fileName);
fileInputStream = new BufferedInputStream(fileInput);
在此示例中,文件名必须是该文件在服务器文件系统中的绝对路径。在未来的版本中,您可能希望使用服务器上存储文件的目录,客户端可以为您提供该目录中文件的相对路径。这是它的样子。
String fileName;
Scanner scanner = new Scanner (clientSocket.getInputStream());
while(scanner.hasNextLine())
{
fileName = scanner.nextLine();
break;
}
fileInputStream = new FileInputStream(FILE_DIR + fileName);
fileInputStream = new BufferedInputStream(fileInput);
变量 FILE_DIR 看起来像这样:
static String FILE_DIR = "C:/java/";
客户端发送的文件就是 file.mp4
编辑 1:
这是带有建议的客户端代码。请注意,此测试质量代码,而非生产代码。
import java.net.*;
import java.io.*;
public class Client {
static String FILE_DIR = "./";
public static void main(String[] s) throws IOException {
/**
* Establish socket using main args.
*/
String address = s[0];
while (true) {
/**
* Get the file name from the user.
*/
System.out.print("Insert filename to download: ");
BufferedReader reader = new BufferedReader(new InputStreamReader(System.in));
String fileName = null;
try {
fileName = reader.readLine();
} catch (IOException ioe) {
System.out.println("Eingabe konnte nicht verarbeitet werden!");
System.exit(1);
}
System.out.println("Eingabe: " + fileName);
/**
* Create the socket.
*/
Socket socket = new Socket(address, 12345);
/**
* With file name in hand, proceed to send the filename to the
* server.
*/
//...put in try-with-resources to close the outputstream.
try (BufferedOutputStream bos = new BufferedOutputStream(socket.getOutputStream())) {
System.out.println("Connected: Sending file name to server.");
//...send file name plus a newline.
bos.write((fileName + '\n').getBytes());
bos.flush();
/**
* Get the file contents and save to disk.
*/
//...wrap input stream in DataInpuStream for portability.
//...put in try-with-resource to close the input stream.
try (BufferedInputStream bis = new BufferedInputStream(new DataInputStream(socket.getInputStream()))) {
DataOutputStream fos = new DataOutputStream(new FileOutputStream(fileName));
int n;
byte[] buffer = new byte[8192];
System.out.println("Connected: Recieving file contents from server.");
while ((n = bis.read(buffer)) > 0) {
System.out.println("received " + n + " bytes");
fos.write(buffer, 0, n);
fos.flush();
}
System.out.println("recieved");
} catch (Exception e) {
e.printStackTrace();
}
}
}
}
}
这是服务器代码。请注意服务器正在从名为 ./files/ 的本地目录中检索文件,请将其更改为您想要的任何目录。
导入java.net.; 导入 java.io.; 导入 java.util.Scanner;
public class 服务器 {
static String FILE_DIR = "./files/";
public static void main(String[] args) {
BufferedInputStream inputStream;
FileInputStream fileInput;
try {
ServerSocket socket = new ServerSocket(12345);
while (true) {
Socket clientSocket = socket.accept();
/**
* Get the file name from the client. File name is one per line.
*/
//...put in trye-with-resources to close InputStream for us.
try (InputStream inputFromClient = clientSocket.getInputStream()) {
System.out.println("Connected: Getting file name from client.");
Scanner scanner = new Scanner(inputFromClient);
String fileName;
if (scanner.hasNextLine()) {
fileName = scanner.nextLine();
System.out.println("File name = " + fileName);
} else {
//...no line found, continue. consider logging an error or warning.
continue;
}
/**
* With fileName in hand, we can proceed to send the
* contents of the file to the client.
*/
fileInput = new FileInputStream(fileName);
//...use DataInputStream for more portable code
DataInputStream dataInput = new DataInputStream(fileInput);
inputStream = new BufferedInputStream(dataInput);
int packetToSend = -1;
byte[] buffer = new byte[8192];
//...consider closing the OutputStream to let the client know.
//...use try-with-resource to close the outputStream for us.
//...wrap your outputStream in DataOutputStream
try (BufferedOutputStream outputStream = new BufferedOutputStream(new DataOutputStream(clientSocket.getOutputStream()))) {
while ((packetToSend = inputStream.read(buffer)) > -1) {
outputStream.write(buffer, 0, packetToSend);
System.out.println("sending " + packetToSend + " bytes");
outputStream.flush();
}
}
}
}
} catch (Exception e) {
e.printStackTrace();
}
}
}