簡體   English   中英

如何從客戶端關閉套接字通道,以便服務器引發java.nio.channels.ClosedChannelException

[英]How to close a socket channel from client side so that the server throws java.nio.channels.ClosedChannelException

我遇到一個服務器(Apache Synapse)間歇性地拋出“ java.nio.channels.ClosedChannelException”的問題。

java.nio.channels.ClosedChannelException
at sun.nio.ch.SocketChannelImpl.ensureWriteOpen(SocketChannelImpl.java:135)
at sun.nio.ch.SocketChannelImpl.write(SocketChannelImpl.java:326)
at org.apache.http.impl.nio.reactor.SessionOutputBufferImpl.flush(SessionOutputBufferImpl.java:167)
at org.apache.http.impl.nio.DefaultNHttpServerConnection.produceOutput(DefaultNHttpServerConnection.java:323)
at org.apache.synapse.transport.http.conn.LoggingNHttpServerConnection.produceOutput(LoggingNHttpServerConnection.java:112)
at org.apache.synapse.transport.passthru.ServerIODispatch.onOutputReady(ServerIODispatch.java:87)
at org.apache.synapse.transport.passthru.ServerIODispatch.onOutputReady(ServerIODispatch.java:39)
at org.apache.http.impl.nio.reactor.AbstractIODispatch.outputReady(AbstractIODispatch.java:143)
at org.apache.http.impl.nio.reactor.BaseIOReactor.writable(BaseIOReactor.java:180)
at org.apache.http.impl.nio.reactor.AbstractIOReactor.processEvent(AbstractIOReactor.java:342)
at org.apache.http.impl.nio.reactor.AbstractIOReactor.processEvents(AbstractIOReactor.java:316)
at org.apache.http.impl.nio.reactor.AbstractIOReactor.execute(AbstractIOReactor.java:277)
at org.apache.http.impl.nio.reactor.BaseIOReactor.execute(BaseIOReactor.java:105)
at org.apache.http.impl.nio.reactor.AbstractMultiworkerIOReactor$Worker.run(AbstractMultiworkerIOReactor.java:584)
at java.lang.Thread.run(Thread.java:662)

顯然,服務器嘗試在已經關閉的通道上執行一些IO操作。 我想編寫一個客戶端程序以隨意重現該問題。 客戶端故意關閉通道,導致服務器拋出異常。 這是客戶端的代碼。

public class Client
{
    String hostIp;
    int hostPort;

    public Client(String hostIp, int hostPort) {
        this.hostIp = hostIp;
        this.hostPort = hostPort;
    }

    public void runClient() throws IOException {
        Socket clientSocket = null;
        PrintWriter out = null;
        BufferedReader in = null;

        try {
            clientSocket = new Socket(hostIp, hostPort);
            out = new PrintWriter(clientSocket.getOutputStream(), true);
            in = new BufferedReader(new InputStreamReader(clientSocket.getInputStream()));
        } catch (UnknownHostException e) {
            System.err.println("Unknown host: " + hostIp);
            System.exit(1);
        } catch (IOException e) {
            System.err.println("Couldn't connect to: " + hostIp);
            System.exit(1);
        }

        String getMessage = "GET /services/echo?wsdl2 HTTP/1.1\n" +
                "Host:localhost\n";

        System.out.println("Client connected to host : " + hostIp + " port: " + hostPort);

        out.println(getMessage);

        in.close();
        out.close();
        clientSocket.close();
    }

    public static void main(String[] args) throws IOException {

        Client client = new Client("localhost", 8280);
        client.runClient();
    }
}

運行客戶端時,服務器僅引發IOException,以通知管道已損壞。

java.io.IOException: Broken pipe
    at sun.nio.ch.FileDispatcher.write0(Native Method)
    at sun.nio.ch.SocketDispatcher.write(SocketDispatcher.java:29)
    at sun.nio.ch.IOUtil.writeFromNativeBuffer(IOUtil.java:69)
    at sun.nio.ch.IOUtil.write(IOUtil.java:40)
    at sun.nio.ch.SocketChannelImpl.write(SocketChannelImpl.java:336)
    at org.apache.http.impl.nio.reactor.SessionOutputBufferImpl.flush(SessionOutputBufferImpl.java:100)
    at org.apache.http.impl.nio.DefaultNHttpServerConnection.produceOutput(DefaultNHttpServerConnection.java:220)
    at org.apache.synapse.transport.http.conn.LoggingNHttpServerConnection.produceOutput(LoggingNHttpServerConnection.java:112)
    at org.apache.synapse.transport.passthru.ServerIODispatch.onOutputReady(ServerIODispatch.java:87)
    at org.apache.synapse.transport.passthru.ServerIODispatch.onOutputReady(ServerIODispatch.java:39)
    at org.apache.http.impl.nio.reactor.AbstractIODispatch.outputReady(AbstractIODispatch.java:141)
    at org.apache.http.impl.nio.reactor.BaseIOReactor.writable(BaseIOReactor.java:181)
    at org.apache.http.impl.nio.reactor.AbstractIOReactor.processEvent(AbstractIOReactor.java:346)
    at org.apache.http.impl.nio.reactor.AbstractIOReactor.processEvents(AbstractIOReactor.java:320)
    at org.apache.http.impl.nio.reactor.AbstractIOReactor.execute(AbstractIOReactor.java:280)
    at org.apache.http.impl.nio.reactor.BaseIOReactor.execute(BaseIOReactor.java:106)
    at org.apache.http.impl.nio.reactor.AbstractMultiworkerIOReactor$Worker.run(AbstractMultiworkerIOReactor.java:604)
    at java.lang.Thread.run(Thread.java:662)

我應如何從客戶端使服務器拋出“ ClosedChannelException”?

如何從客戶端關閉套接字通道,以便服務器引發java.nio.channels.ClosedChannelException

你不能

我應如何從客戶端使服務器拋出“ ClosedChannelException”?

沒有。

您對ClosedChannelException.有一個基本的誤解ClosedChannelException. 關閉本地頻道並繼續使用它時,會拋出該錯誤。 對等方關閉連接不可以。

如果您正在尋找流結束指示,請使用read()返回-1的情況。

如果要查找連接丟失或失敗的跡象,請使用write()拋出IOException: connection reset

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM