docs: @Override
      public void handle() throws FacesException
      {
          if (unhandled != null && !unhandled.isEmpty())
          {
              if (handled == null)
              {
                  handled = new LinkedList<ExceptionQueuedEvent>();
              }
              
              FacesException toThrow = null;
              
              do
              {
                  // For each ExceptionEvent in the list
                  
                  // get the event to handle
                  ExceptionQueuedEvent event = unhandled.peek();
                  try
                  {
                      // call its getContext() method
                      ExceptionQueuedEventContext context = event.getContext();
                      
                      // and call getException() on the returned result
                      Throwable exception = context.getException();
                      
                      // Upon encountering the first such Exception that is not an instance of
                      // javax.faces.event.AbortProcessingException
                      if (!shouldSkip(exception))
                      {
                          // set handledAndThrown so that getHandledExceptionQueuedEvent() returns this event
                          handledAndThrown = event;
                          
                          // Re-wrap toThrow in a ServletException or (PortletException, if in a portlet environment) 
                          // and throw it
                          // FIXME: The spec says to NOT use a FacesException to propagate the exception, but I see
                          //        no other way as ServletException is not a RuntimeException
                          toThrow = wrap(getRethrownException(exception));
                          break;
                      }
                      else
                      {
                          // Testing mojarra it logs a message and the exception
                          // however, this behaviour is not mentioned in the spec
                          log.log(Level.SEVERE, exception.getClass().getName() + " occured while processing " +
                                  (context.inBeforePhase() ? "beforePhase() of " : 
                                          (context.inAfterPhase() ? "afterPhase() of " : "")) + 
                                  "phase " + context.getPhaseId() + ": " +
                                  "UIComponent-ClientId=" + 
                                  (context.getComponent() != null ? 
                                          context.getComponent().getClientId(context.getContext()) : "") + ", " +
                                  "Message=" + exception.getMessage());
                          
                          log.log(Level.SEVERE, exception.getMessage(), exception);
                          
                      }
                  }
                  catch (Throwable t)
                  {
                      // A FacesException must be thrown if a problem occurs while performing
                      // the algorithm to handle the exception
                      throw new FacesException("Could not perform the algorithm to handle the Exception", t);
                  }
                  finally
                  {
                      // if we will throw the Exception or if we just logged it,
                      // we handled it in either way --> add to handled
                      handled.add(event);
                      unhandled.remove(event);
                  }
              } while (!unhandled.isEmpty());
              
              // do we have to throw an Exception?
              if (toThrow != null)
              {
                  throw toThrow;
              }
          }
      }