-2

みなさんこんにちは、SKYPEのようにファイルを転送/送信するためのアプリケーションを開発しようとしています。そのため、あるコンピューター(クライアント)から別のコンピューター(クライアント)にファイルを転送するためにソケットを使用しています。あるクライアントからファイルを転送できますこれを使用してサーバーに. code.しかし、サーバーから2番目のクライアントに同じファイルを送信しようとすると、0バイトで転送され、ソケットクローズ例外も発生するため、クライアント側で新しいソケットオブジェクトを作成しようとします.だから、例外は来ませんが、ファイルは転送されませんデバッグ後、ファイルはサーバーによってクライアントに正常に送信されましたが、クライアント側のソケットでデータを読み取ることができず、データを待機していることがわかりました。これ以上の解決策が見つかりません。誰かがこれについて何か知っている場合は、教えてください。ファイル転送のための他の解決策があれば、教えてください。事前に感謝します 以下は私のコードです

 Server code:

public class ChatServer
{ 

 serversocket = new ServerSocket(1436);
 thread = new Thread(this);
 thread.start();

 /*************Thread Implementation***************/
public void run()
{
    /*********Accepting all the client connections and create a seperate thread******/
    while(thread != null)
    {
        try
        {
            /********Accepting the Server Connections***********/
            socket = serversocket.accept();             

  /******* Create a Seperate Thread for that each client**************/
            chatcommunication = new ChatCommunication(this,socket);

            thread.sleep(THREAD_SLEEP_TIME);    
        }
        catch(InterruptedException _INExc)  { ExitServer(); }
        catch(IOException _IOExc)           { ExitServer(); }   
    }   
}

protected void SendGroupFile(Socket ClientSocket, String FileName,String GroupName,String UserName) throws IOException
{
    try
    {
     // receive file from Client
      byte [] mybytearray  = new byte [filesize];
      InputStream is = socket.getInputStream();
      FileOutputStream fos = new FileOutputStream(Filepath);
      BufferedOutputStream bos = new BufferedOutputStream(fos);
      int bytesRead = is.read(mybytearray,0,mybytearray.length);
      current = bytesRead;

          do {
           bytesRead =is.read(mybytearray, current, (mybytearray.length-current));
           System.out.println("Reading Bytes server"+bytesRead); 
           if(bytesRead >= 0) 
               current += bytesRead;
         } while(bytesRead > -1);

      bos.write(mybytearray,0,current);
      bos.flush();
      bos.close();



    } catch (IOException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }
}

      /*****    Function To Send a File to Client   **********/
protected void SendGroupFileClient(Socket ClientSocket, String FileName,String GroupName,String UserName)
{
        try {
            int m_userListSize = userarraylist.size();

                clientobject = GetClientObject(GroupName);

                 if(clientobject != null)
                for(G_ILoop = 0; G_ILoop < m_userListSize; G_ILoop++)
                {

                    clientobject = (ClientObject) userarraylist.get(G_ILoop);
                    if((clientobject.getGroupName().equals(GroupName)) && (!(clientobject.getUserName().equals(UserName))))
                    {   
                   {    

                     File myFile = new File (Filepath);
                     byte [] mybytearray  = new byte [(int)myFile.length()];
                     FileInputStream fis = new FileInputStream(myFile);
                     BufferedInputStream bis = new BufferedInputStream(fis);
                     bis.read(mybytearray,0,mybytearray.length);
                     os = socket.getOutputStream();
                     System.out.println("Sending...");
                     os.write(mybytearray,0,mybytearray.length);
                     os.flush();
                     os.close();
             }  

        }catch(IOException _IOExc) 
        {
            _IOExc.printStackTrace();   
        }
}
}

チャットコミュニケーション.java

public class ChatCommunication implements Runnable,CommonSettings
{
   Thread thread;
Socket socket;
DataInputStream inputstream;
String RFC;
ChatServer Parent;

     /********Initialize the Socket to the Client***********/
ChatCommunication(ChatServer chatserver,Socket clientsocket)
{               
  Parent = chatserver;
    socket = clientsocket;  
    try 
    {       
    inputstream = new DataInputStream(new  BufferedInputStream(socket.getInputStream()));       
    }catch(IOException _IOExc) { }
    thread = new Thread(this);
    thread.start(); 
}

public void run()
{
    while(thread != null)
    {
        try {               
            RFC = inputstream.readLine();

            if(RFC.startsWith("FILEGRUP"))
            {
                Parent.SendGroupFile(socket,RFC.substring(9,RFC.indexOf("!")),RFC.substring(RFC.indexOf("!")+1,RFC.indexOf("*")),RFC.substring(RFC.indexOf("*")+1));    
            }

            if(RFC.startsWith("FILEGET"))
            {
                Parent.SendGroupFileClient(socket,RFC.substring(8,RFC.indexOf("!")),RFC.substring(RFC.indexOf("!")+1,RFC.indexOf("*")),RFC.substring(RFC.indexOf("*")+1));  
            }


        }catch(Exception _Exc) 
         {
            Parent.RemoveUserWhenException(socket);QuitConnection();
         }  
    }
}

クライアントコード

  class Client extends JFrame
 {
  ServerName="192.168.1.103";
  ServerPort=1436;

Client()
 {
  socket = new Socket(ServerName,ServerPort);
  SendGroupFileToServer(Filepath,SelectedGroup);    
}

 /*******Function To Send File To Server and receiving the file ***********/
protected void SendGroupFileToServer(String FileName, String ToGroup)
{
try {

dataoutputstream.writeBytes(FileName.concat("!").concat(ToUser)+"\r\n");
//send file to sever
           File myFile = new File (FileName.substring(9));
           byte [] mybytearray  = new byte [(int)myFile.length()];
           FileInputStream fis = new FileInputStream(myFile);
           BufferedInputStream bis = new BufferedInputStream(fis);
           bis.read(mybytearray,0,mybytearray.length);
           OutputStream os = socket.getOutputStream();
           System.out.println("Sending...");
           os.write(mybytearray,0,mybytearray.length);
           os.flush();
           os.close();
           System.out.println("File successfully Sended  to server");
          }catch(IOException _IoExc) { QuitConnection(QUIT_TYPE_DEFAULT);}  


               try {
          socket1 = new Socket(ServerName,ServerPort); //Creating new Socket                                    
          dataoutputstream = new DataOutputStream(socket1.getOutputStream());
          dataoutputstream.writeBytes("FILEGET"+FileName.concat("!").concat(ToGroup+"*"+UserName)+"\r\n");  //sending string to server           

    } catch (IOException e1) {
        e1.printStackTrace();
    }

    // receive file sended by server
      byte [] mybytearray  = new byte [filesize];
      InputStream is;
    try {
        is = socket1.getInputStream();

      FileOutputStream fos = new FileOutputStream(Filepath);
      BufferedOutputStream bos = new BufferedOutputStream(fos);
      int bytesRead = is.read(mybytearray,0,mybytearray.length);
      current = bytesRead; //up to this working fine

      do {
           bytesRead =is.read(mybytearray, current, (mybytearray.length-current)); //not reading the file data sent by server just waiting and not go ahead 
           if(bytesRead >= 0) 
               current += bytesRead;
         } while(bytesRead > -1);

      bos.write(mybytearray,0,current);
      bos.flush();
      bos.close();
    } catch (IOException e) {
        e.printStackTrace();
    }
    } 

}

4

2 に答える 2

4

ここには非常に多くの問題があるため、どこから始めればよいかわかりません。

  1. ループ内は文字通り時間の無駄thread.sleep()です。accept()これは、クライアントが受け入れられる速度を調整する以外に、何の役にも立ちません。それがあなたの意図でないなら、それをしないでください。

  2. 例外をキャッチしたときに行っていることは、例外メッセージを出力することさえせずにサーバーを終了することだけです。したがって、何かがうまくいかない場合、ここにあるように、それが何であったかを知ることはできません. そうしないでください。

  3. readLine()は EOS で null を返します。EOS では、ソケットを閉じ、読み取りを停止し、スレッドを終了する必要があります。あなたはそれをテストしていないので、必要な 3 つの手順をすべて省略しています。そうしないでください。

  4. DataInputStreamコマンドを読み取るときに使用するために aを構築してBufferedInputStreamいますが、それらのコマンドを処理するメソッドに渡していません。ソケットを渡しているだけです。したがって、データが失われます。そうしないでください。プログラムのすべての部分で、ソケットに対して同じ入力ストリームまたはリーダーを使用する必要があります。

  5. ファイル全体をメモリに読み込んでいます。intこれは (a) ファイルサイズが;に収まることを前提としています。(b) 大きなファイルには対応していません。(c) スペースを浪費し、(d) レイテンシーを追加します。そうしないでください。

  6. そのバッファーへの read() の結果を無視し、それがいっぱいになったと想定しています。そんなことはできません。Java でストリームをコピーする正しい方法を以下に示します。これは、任意の長さの入力に対して任意のサイズ (8192 など) のバッファーで機能し、入力全体をメモリにバッファーする必要はありません。このループは、ファイルを送信するときのクライアントと、ファイルを受信するときのサーバーの両方で使用できます。

    while ((count = in.read(buffer)) > 0)
    {
      out.write(buffer, 0, count);
    }
    
  7. 上記の (4) と同様に、BufferedOutputStream の周りに DataOutputStream を使用するものもあれば、ソケット出力ストリームを直接使用するものもあります。そうしないでください。プログラムのすべての部分は、ソケットに対して同じ出力ストリームまたはライターである必要があります。

  8. flush()前にする必要はありませんclose()。それは自動的に起こります。

  9. 何らかの理由でファイルを送信した後、新しい接続を作成して別のコマンドを送信しています。その後、接続を閉じることさえありません。サーバーは、この接続とこのコマンドが上記のコードで送信されたばかりのファイルを参照していることを知る簡単な方法はありません。また、最終的な EOS を受信すると、ファイルが正常に送信されたことがサーバーに通知されるため、冗長です。これをしないでください。ファイルと一緒にさらに情報を送信する必要がある場合は、同じ接続で、ファイルの前に最初に送信してください。

  10. あなたが引用した参照は、上記の問題の多くを示しています。評判の良い出発点を見つけるように努力してください。

于 2012-10-27T05:30:16.240 に答える
-1

これが解決策です。このロジックをコードに適用してください。

サーバーからクライアント、クライアントからサーバーにファイルを送信できます。

次のコードを確認して、クライアントからサーバーにファイルを送信します。それはうまく機能しています。

問題がある場合はお知らせください。

サーバー側コード:

public class ServerRecieveFile {
public static void main(String[] args) throws IOException {// TODO Auto-enerated method stub int filesize=1022386; 
int bytesRead; int currentTot= ;
ServerSocket serverSocket=new ServerSocket(15123); 
Socket socket=rverSocket.accept();
byte [] bytearray  = new byte [filesize];
InputStream is=socket.getInputStream();
File copyFileName=new File("c:/Files Sockets/2.txt");
FileOutputStream fos = new FileOutputStream(copyFileName);
BufferedOutputStream bos = new BufferedOutputStream(fos);
bytesRead = is.read(bytearray,0,bytearray.length);
currentTot = bytesRead;
do {
bytesRead =is.read(bytearray, currentTot, (bytearray.length-currentTot)); if(bytesRead >= 0)
 currentTot += bytesRead;
} while(bytesRead > -1);
bos.write(bytearray, 0 , currentTot);
bos.flush();
 bos.close();
socket.close();
 }
}

クライアント側のコード:

public class ClientSendFile {
public static void main(String[] args) throws UnknownHostException, IOException {// TODO Auto-generated method stub
Client client=new Client();
Socket socket = new Socket(InetAddress.getLocalHost(),15123);
System.out.println("Accepted connection : " + socket);
File transferFile = new File ("c:/Files Sockets/1.txt");
byte [] bytearray  = new byte (int)transferFile.length()];
FileInputStream fin = new FileInputStream(transferFile);
BufferedInputStream bin = new BufferedInputStream(fin);
bin.read(bytearray,0,bytearray.length);
OutputStream os = socket.getOutputStream();
System.out.println("Sending Files...");
os.write(bytearray,0,bytearray.length);
os.flush();
socket.close();
System.out.println("File transfer complete");
 }
}
于 2013-01-31T20:01:29.037 に答える