17

当我抓住它时,我需要以不同的方式处理它SocketTimeoutException。我发现唯一的事情就是依赖getMessage(). 到目前为止,我发现了两个:

java.net.SocketTimeoutException: connect timed out
java.net.SocketTimeoutException: Read timed out

消息(连接超时、读取超时)是硬编码的吗?它们是在哪里生成的?至少这些消息的任何常数值?

4

4 回答 4

2

您可以检查 Socket.isConnected。但是由于异常是由不同的方法引发的,所以最好使用两个具有不同操作的 catch 块。

 try {
       socket.connect(address);
    } catch (SocketTimeoutException e) {
        throw new SocketConnectionException(e);
    }
    try {
       socket.getInputStream();
       ...
    } catch (SocketTimeoutException e) {
        throw new SocketReadException(e);
    } 
于 2013-03-01T20:23:18.747 回答
1

它们来自不同的方法。隐式或显式调用 connect() 时会发生“连接超时”;调用 read() 或其同源之一时会发生“读取超时”。所以你可以区分只有两个不同的 catch 块。但无论哪种情况,您都可能要关闭连接...

于 2013-03-01T22:16:30.307 回答
1

所以,这是我声名鹊起的地方。在这里,我们沿着 StackTrace 走,寻找异常的起源方法。

public class ExceptionOriginTracing {

    public static void main(String[] args){
        try {
            originOne();
            originTwo();
        } catch (Exception e){
            // Now for the magic:
            for (StackTraceElement element : e.getStackTrace()){
                if (element.getMethodName().equals("originOne")){
                    System.out.println("It's a read error!");
                    break;
                } else if (element.getMethodName().equals("originTwo")){
                    System.out.println("It's a write error!");
                    break;
                }
            }
        }
    }

    public static void originOne() throws Exception{
        throw new Exception("Read Failed...", null);
    }

    public static void originTwo() throws Exception{
        throw new Exception("Connect failed...", null);
    }
}

解析异常给出的消息的不同之处在于,一个简单的字符串比实际方法的名称更有可能发生变化。

除此之外,这不是最佳解决方案!但遗憾的是,这里没有最佳解决方案。

此外,使用这种方法,在使用源混淆时必须格外小心,这将改变方法名称,从而改变 的返回值getMethodName()


设计这样的东西时,正确的方法是将异常包装在一个新的异常中,它提供了通过使用标志或枚举来实际找出真正起源的方法。

解析消息/StackTrace 总是感觉很脏,并且在未来的版本中会被破坏!

于 2013-03-01T22:27:26.157 回答
0

回复有点晚。我只有一个布尔标志'isConnected'初始化为false。连接后,我将其设置为true。如果连接超时,您将永远无法到达那里。

在抛出异常后检查 Socket.isConnected 听起来是个坏主意。到那时,套接字可能会被关闭。

通过在 之前定义标志try,它可以在catch处理程序中读取。

于 2020-11-27T10:19:11.610 回答