71
71
import java .util .logging .Logger ;
72
72
import edu .umd .cs .findbugs .annotations .CheckForNull ;
73
73
import edu .umd .cs .findbugs .annotations .NonNull ;
74
+ import hudson .remoting .ChannelClosedException ;
75
+ import java .io .EOFException ;
76
+ import java .nio .channels .ClosedChannelException ;
77
+ import java .util .stream .Stream ;
74
78
import jenkins .MasterToSlaveFileCallable ;
75
79
import jenkins .model .Jenkins ;
76
80
import jenkins .security .MasterToSlaveCallable ;
@@ -541,8 +545,8 @@ public FilePath getOutputFile(FilePath workspace) throws IOException, Interrupte
541
545
}
542
546
543
547
@ Override public void watch (FilePath workspace , Handler handler , TaskListener listener ) throws IOException , InterruptedException , ClassCastException {
544
- workspace .act (new StartWatching (this , handler , listener ));
545
- LOGGER .log (Level .FINE , "started asynchronous watch in {0}" , controlDir );
548
+ workspace .actAsync (new StartWatching (this , handler , listener ));
549
+ LOGGER .log (Level .FINE , "started asynchronous watch in " + controlDir , new Throwable () );
546
550
}
547
551
548
552
/**
@@ -576,6 +580,21 @@ private static class StartWatching extends MasterToSlaveFileCallable<Void> {
576
580
577
581
}
578
582
583
+ // TODO https://github.com/jenkinsci/remoting/pull/657
584
+ private static boolean isClosedChannelException (Throwable t ) {
585
+ if (t instanceof ClosedChannelException ) {
586
+ return true ;
587
+ } else if (t instanceof ChannelClosedException ) {
588
+ return true ;
589
+ } else if (t instanceof EOFException ) {
590
+ return true ;
591
+ } else if (t == null ) {
592
+ return false ;
593
+ } else {
594
+ return isClosedChannelException (t .getCause ()) || Stream .of (t .getSuppressed ()).anyMatch (FileMonitoringTask ::isClosedChannelException );
595
+ }
596
+ }
597
+
579
598
private static class Watcher implements Runnable {
580
599
581
600
private final FileMonitoringController controller ;
@@ -585,6 +604,7 @@ private static class Watcher implements Runnable {
585
604
private final @ CheckForNull Charset cs ;
586
605
587
606
Watcher (FileMonitoringController controller , FilePath workspace , Handler handler , TaskListener listener ) {
607
+ LOGGER .log (Level .FINE , "starting " + this , new Throwable ());
588
608
this .controller = controller ;
589
609
this .workspace = workspace ;
590
610
this .handler = handler ;
@@ -611,7 +631,8 @@ private static class Watcher implements Runnable {
611
631
handler .output (utf8EncodedStream );
612
632
long newLocation = ch .position ();
613
633
lastLocationFile .write (Long .toString (newLocation ), null );
614
- LOGGER .log (Level .FINER , "copied {0} bytes from {1}" , new Object [] {newLocation - lastLocation , logFile });
634
+ long delta = newLocation - lastLocation ;
635
+ LOGGER .finer (() -> this + " copied " + delta + " bytes from " + logFile );
615
636
}
616
637
}
617
638
if (exitStatus != null ) {
@@ -621,7 +642,7 @@ private static class Watcher implements Runnable {
621
642
} else {
622
643
output = null ;
623
644
}
624
- LOGGER .log ( Level . FINE , " exiting with code {0}" , exitStatus );
645
+ LOGGER .fine (() -> this + " exiting with code " + exitStatus );
625
646
handler .exited (exitStatus , output );
626
647
controller .cleanup (workspace );
627
648
} else {
@@ -636,7 +657,11 @@ private static class Watcher implements Runnable {
636
657
}
637
658
} catch (Exception x ) {
638
659
// note that LOGGER here is going to the agent log, not master log
639
- LOGGER .log (Level .WARNING , "giving up on watching " + controller .controlDir , x );
660
+ if (isClosedChannelException (x )) {
661
+ LOGGER .warning (() -> this + " giving up on watching " + controller .controlDir );
662
+ } else {
663
+ LOGGER .log (Level .WARNING , this + " giving up on watching " + controller .controlDir , x );
664
+ }
640
665
// Typically this will have been inside Handler.output, e.g.:
641
666
// hudson.remoting.ChannelClosedException: channel is already closed
642
667
// at hudson.remoting.Channel.send(Channel.java:667)
0 commit comments