我必须使用一台服务器将文件块传输到不同的客户端。 当我运行服务器文件并提供文件的名称时,它成功地创建了块。当我第一次运行第一个客户端它工作但当我再次为客户端运行它(我的意思是当我作为第二个客户端连接时)它无法将块传输到第二个客户端。完整的服务器和客户端代码如下所示。 错误是第二个客户端它开始读取文件的内容作为文件名和程序终止。 提供一个大文本文件(1MB)文件作为服务器的输入
服务器代码:
import java.io.*;
import java.net.ServerSocket;
import java.net.Socket;
import java.util.*;
public class server {
private static final int sPort = 8000; //The server will be listening on this port number
public static String str;
public static int c;
public static void main(String[] args) throws Exception {
System.out.println("The server is running.");
ServerSocket listener = new ServerSocket(sPort);
int clientNum = 1;
System.out.println("Enter the name of the file: ");
Scanner in = new Scanner(System.in);
str = in.nextLine();
String path = System.getProperty("user.dir");
String filepath = path +"/"+ str;
in.close();
try {
c=splitFile(new File(filepath));
} catch (IOException e1) {
e1.printStackTrace();
}
try {
while(true) {
new Handler(listener.accept(),clientNum,c).start();
System.out.println("Client " + clientNum + " is connected!");
clientNum++;
}
} finally {
listener.close();
}
}
/**
* A handler thread class. Handlers are spawned from the listening
* loop and are responsible for dealing with a single client's requests.
*/
private static class Handler extends Thread {
private Socket connection;
private int chunkcount;
private ObjectInputStream in; //stream read from the socket
private ObjectOutputStream out; //stream write to the socket
private int no; //The index number of the client
public Handler(Socket connection, int no,int c) {
this.connection = connection;
this.no = no;
this.chunkcount=c;
}
public void run() {
try{
//initialize Input and Output streams
out = new ObjectOutputStream(connection.getOutputStream());
out.flush();
in = new ObjectInputStream(connection.getInputStream());
try{
String path = System.getProperty("user.dir");
path=path+"/"+"chunks"+ "/";
System.out.println(path);
System.out.println("Total chunks: "+chunkcount);
int i=no;
int j=i;
int k=0;
OutputStream op=connection.getOutputStream();
DataOutputStream d = new DataOutputStream(op);
d.writeInt(no);
d.flush();
System.out.println("value of j or clientnum: "+j);
while(j<chunkcount)
{
k++;
j=j+5;
}
System.out.println(k);
d.writeInt(k);
d.flush();
//d.close();
while(i<chunkcount)
{
String pathname= path+Integer.toString(i)+str;
System.out.println(i+str);
sendFile(connection,pathname);
i=i+5;
}
}
catch(Exception e){
e.printStackTrace();
}
}
catch(IOException ioException){
System.out.println("Disconnect with Client " + no);
}
finally{
//Close connections
try{
in.close();
out.close();
connection.close();
}
catch(IOException ioException){
System.out.println("Disconnect with Client " + no);
}
}
}
}
public static int splitFile(File f) throws IOException {
int partCounter = 1;//I like to name parts from 001, 002, 003, ...
//you can change it to 0 if you want 000, 001, ...
int sizeOfFiles = 102400;// 1MB
byte[] buffer = new byte[sizeOfFiles];
try (BufferedInputStream bis = new BufferedInputStream(
new FileInputStream(f))) {//try-with-resources to ensure closing stream
String name = f.getName();
String path = f.getParent();
long sizefile = f.getTotalSpace();
String newpath = path + "/" + "chunks";
File dir = new File(newpath);
dir.mkdir();
int tmp = 0;
while ((tmp = bis.read(buffer)) > 0) {
//write each chunk of data into separate file with different number in name
File newFile = new File(dir, String.format("%d", partCounter++) + name );
//System.out.println(f.getParent());
try (FileOutputStream out = new FileOutputStream(newFile)) {
out.write(buffer, 0, tmp);//tmp is chunk size
}
}
System.out.println("File details are : "+name+" "+sizefile);
System.out.println("Number of chunks: "+ (partCounter-1));
}
return (partCounter-1);
}
public static void sendFile(Socket conn,String fileName) throws IOException
{
File myFile = new File(fileName);
byte[] mybytearray = new byte[(int) myFile.length()];
FileInputStream fis = new FileInputStream(myFile);
BufferedInputStream bis = new BufferedInputStream(fis);
DataInputStream dis = new DataInputStream(bis);
dis.readFully(mybytearray, 0, mybytearray.length);
OutputStream os = conn.getOutputStream();
DataOutputStream dos = new DataOutputStream(os);
dos.writeUTF(myFile.getName());
dos.writeLong(mybytearray.length);
dos.write(mybytearray, 0, mybytearray.length);
dos.flush();
dis.close();
}
}
客户代码:
import java.net.*;
import java.io.*;
public class Client {
Socket requestSocket; //socket connect to the server
ObjectOutputStream out; //stream write to the socket
ObjectInputStream in; //stream read from the socket
public Client() {}
void run()
{
try{
//create a socket to connect to the server
requestSocket = new Socket("localhost", 8000);
System.out.println("Connected to localhost in port 8000");
//initialize inputStream and outputStream
out = new ObjectOutputStream(requestSocket.getOutputStream());
out.flush();
in = new ObjectInputStream(requestSocket.getInputStream());
System.out.println("Ready to receive files ( Enter QUIT to end):");
BufferedInputStream in1 = new BufferedInputStream(requestSocket.getInputStream());
DataInputStream d = new DataInputStream(in1);
int clientnum=d.readInt();
String path = System.getProperty("user.dir");
String oppath = path + "/" + "Client" + clientnum;
File dir = new File(oppath);
dir.mkdir();
int numchunk=d.readInt();
System.out.println(numchunk);
int jakarta=1;
while(jakarta<=numchunk ){
jakarta++;
String newpath=oppath+"/";
File f = new File(newpath);
f.createNewFile();
receiveFile(requestSocket,newpath);
System.out.println("File Received");
}
}
catch (ConnectException e) {
System.err.println("Connection refused. You need to initiate a server first.");
}
catch(UnknownHostException unknownHost){
System.err.println("You are trying to connect to an unknown host!");
}
catch(IOException ioException){
ioException.printStackTrace();
}
finally{
//Close connections
try{
in.close();
out.close();
requestSocket.close();
}
catch(IOException ioException){
ioException.printStackTrace();
}
}
}
//send a message to the output stream
public static void receiveFile(Socket s1,String oppath) throws IOException
{
String fileName;
try {
int bytesRead;
InputStream in = s1.getInputStream();
DataInputStream clientData = new DataInputStream(in);
fileName = clientData.readUTF();
OutputStream output = new FileOutputStream(oppath+fileName);
long size = clientData.readLong();
byte[] buffer = new byte[1024];
while (size > 0
&& (bytesRead = clientData.read(buffer, 0,
(int) Math.min(buffer.length, size))) != -1) {
output.write(buffer, 0, bytesRead);
size -= bytesRead;
}
output.flush();
output.close();
}
catch(Exception e)
{
e.printStackTrace();
}
}
//main method
public static void main(String args[])
{
Client client = new Client();
client.run();
}
}