1616import edu .wpi .grip .core .sources .MultiImageFileSource ;
1717import edu .wpi .grip .core .util .ExceptionWitness ;
1818
19- import java .util . logging . Level ;
20- import java .util .logging .Logger ;
19+ import java .io . IOException ;
20+ import java .util .logging .* ;
2121
2222/**
2323 * A Guice {@link com.google.inject.Module} for GRIP's core package. This is where instances of {@link Pipeline},
@@ -29,6 +29,47 @@ public class GRIPCoreModule extends AbstractModule {
2929 private final EventBus eventBus = new EventBus (this ::onSubscriberException );
3030
3131 public GRIPCoreModule () {
32+ //Set up the global level logger. This handles IO for all loggers.
33+ final Logger globalLogger = LogManager .getLogManager ().getLogger ("" );//This is our global logger
34+
35+ try {
36+ // Remove the default handlers that stream to System.err
37+ for (Handler handler : globalLogger .getHandlers ()) {
38+ globalLogger .removeHandler (handler );
39+ }
40+
41+ final Handler fileHandler = new FileHandler ("%h/GRIP.log" );//Log to the file "GRIPlogger.log"
42+
43+ //Set level to handler and logger
44+ fileHandler .setLevel (Level .FINE );
45+ globalLogger .setLevel (Level .FINE );
46+
47+ // We need to stream to System.out instead of System.err
48+ final StreamHandler sh = new StreamHandler (System .out , new SimpleFormatter ()) {
49+
50+ @ Override
51+ public synchronized void publish (final LogRecord record ) {
52+ super .publish (record );
53+ // For some reason this doesn't happen automatically.
54+ // This will ensure we get all of the logs printed to the console immediately
55+ // when running on a remote device.
56+ flush ();
57+ }
58+ };
59+ sh .setLevel (Level .CONFIG );
60+
61+ globalLogger .addHandler (sh ); // Add stream handler
62+
63+ globalLogger .addHandler (fileHandler );//Add the handler to the global logger
64+
65+ fileHandler .setFormatter (new SimpleFormatter ());//log in text, not xml
66+
67+ globalLogger .config ("Configuration done." );//Log that we are done setting up the logger
68+
69+ } catch (IOException exception ) {//Something happened setting up file IO
70+ throw new IllegalStateException ("Failed to configure the Logger" , exception );
71+ }
72+
3273 Thread .setDefaultUncaughtExceptionHandler (this ::onThreadException );
3374 }
3475
@@ -68,6 +109,7 @@ private void onSubscriberException(Throwable exception, SubscriberExceptionConte
68109 logger .log (Level .FINE , "EventBus Subscriber threw InterruptedException" , exception );
69110 Thread .currentThread ().interrupt ();
70111 } else {
112+ logger .log (Level .SEVERE , "An event subscriber threw an exception" , exception );
71113 eventBus .post (new UnexpectedThrowableEvent (exception , "An event subscriber threw an exception" ));
72114 }
73115 }
@@ -77,6 +119,8 @@ private void onThreadException(Thread thread, Throwable exception) {
77119 logger .log (Level .FINE , "InterruptedException from thread " + thread , exception );
78120 Thread .currentThread ().interrupt ();
79121 } else {
122+ // This can potentially happen before the main class has even been loaded to handle these exceptions
123+ logger .log (Level .SEVERE , "Uncaught Exception on thread " + thread , exception );
80124 eventBus .post (new UnexpectedThrowableEvent (exception , thread + " threw an exception" ));
81125 }
82126 }
0 commit comments