2

クライアントと通信するサーバーがあります。

サーバーはマルチスレッド化されており、ソケットから読み取られる最初の行が「request」の場合、このスレッドはソケットとソケットに接続された bufferedreader で作成されます。

public class scriptComm implements Runnable {

private Socket sock;
private Socket sock2;
private Connection connection;
private BufferedReader reader;

@Override
public void run() {
    try {

        String name = reader.readLine();
        String password = reader.readLine();

        String line;
        connection = methods.connectToDatabase();
        BufferedWriter bw = new BufferedWriter(new OutputStreamWriter(sock.getOutputStream()));
        if (connection != null && name != null && password != null) {
            try {
                ResultSet rs = connection.createStatement().executeQuery(
                        "SELECT name, password, doupdate FROM accounts "
                        + "WHERE name = '" + name + "' AND doupdate = 'yes'"
                        + " AND password = '" + password + "'");
                if (rs.next()) {
                    methods.log("worked");
                    bw.write("accept");
                    bw.flush();
                    bw.close();
                    reader = new BufferedReader(new InputStreamReader(sock2.getInputStream()));
                    if ((line = reader.readLine()) != null) {
                        mainFrame.jTextArea1.append("line \n");
                        connection.createStatement().executeUpdate(
                                "UPDATE accounts SET updatetext = '" + line + "' "
                                + "WHERE name = '" + name + "'");
                    }else{
                        mainFrame.jTextArea1.append("No text received \n");
                    }
                } else {
                    bw.write("decline");
                    bw.flush();
                }
                bw.close();
                rs.close();
            } catch (SQLException ex) {
                methods.log("Error when executing statement in scriptComm");
                ex.printStackTrace();
            } catch (IOException ex) {
                ex.printStackTrace();
            }
        } else {
            methods.log("missing values in scriptComm");

        }
    } catch (IOException ex) {
    }


}

public scriptComm(Socket sock, BufferedReader reader) {
    this.sock = sock;
    this.sock2 = sock;
    this.reader = reader;
}}

"accept" を書き込んだ後、bw ストリームを閉じることに気付くかもしれません。

これは、ストリームが閉じられていないときに、入力を受信しないかのように、クライアントが単にそこにぶら下がっているためです。

クライアント:

        try{
        String line;
        Socket sock = new Socket("myipaddresshere",portnumber); 
        PrintWriter writer = new PrintWriter(sock.getOutputStream());
        BufferedReader reader = new BufferedReader(new InputStreamReader(sock.getInputStream()));
        writer.println("script");
        writer.flush();
        writer.println(jTextField1.getText());
        writer.flush();
        writer.println(jTextField2.getText());
        writer.flush();
        if ((reader.readLine()).equals("accept")) {
            writer.write("testing123");
            writer.flush();
            writer.close();
        } else {
            jTextArea1.append("fail");

        }
        reader.close();
        writer.close();
    }catch(IOException e){
        jTextArea1.append("Server not available. Please try again later.");
    }

サーバーから「accept」を書き込んだ後にストリームが閉じられていない場合、クライアントが if(reader.readLine().equals("accept")) ブール値チェック (そして、はい、ストリームがフラッシュされたサーバー) に座っているかのようです。 -側)。

ただし、ストリームがサーバー側でも閉じられている場合、ブール値チェックに合格し、引き続き「testing123」という行をストリームに書き込みます。BufferedReader が閉じられたときにソケット ストリームが閉じられたため、サーバーは明らかにこの行を読み取ることができません。お気づきかもしれませんが、sock2 という別の変数を作成するだけでソケットを複製しようとしましたが、この接続も閉じているようです (理にかなっています)。

注: 間違ったユーザー/パスで接続する場合 (つまり、rs.next() が false を返す場合)、ストリームに「拒否」を書き込み、クライアントはこれを取得します。

これについては本当に混乱しています..

ありがとう、マイク。

4

2 に答える 2

3

書き込みは改行を書き込まず、行全体を読み取ろうとしていることに注意してください。フラッシュする前に改行文字を書く必要があります。

編集者は BufferedWriter を使用します。newLine()または"\n"書き込む文字列に追加します。

于 2011-07-25T10:55:16.870 に答える
2

アドバイスを添えて、これを撤回したままにします。

ストリームに文字を書き込む場合は、明示的な文字エンコーディングで常にOutputStreamWriterandを使用する必要があります。InputStreamReader「UTF-8」をお勧めします。

書かれているように、コードはプラットフォームのデフォルトのエンコーディングで書き込みと読み取りの両方を行います。これは、中国の誰かが Windows でクライアントを実行し、米国の誰かが Linux でサーバーを実行するまでは機能します (送信内容によっては、はるかに早く壊れる可能性があります)。

于 2011-07-25T10:56:59.017 に答える