/// <summary> /// Push event to this stage. Work may run /// on callers thread, or a different one depending on /// the RunInCallerContext property /// </summary> /// <param name="callback">Callback</param> /// <param name="e">Event being queued</param> protected void PushEvent (StageWorkerCallback callback, StageEvent e) { if (Log.IsDebugEnabled) { Log.Debug("Pushing event, current Stage is [" + this + "], e is [" + e + "]"); } var swc = new StageWorkerContext(callback, e); if (StageThreadPool == null || RunInCallerContext || e.RunSynchronous) { // run in caller context try { callback.Invoke(e); } catch (Exception ex) { swc.Exception = ex; FireStageEvent(new StageExceptionEvent(swc)); } } else { // push context StageThreadPool.QueueWork(swc); } }
/// <summary> /// Stage event handler. This is what listening /// stages register to, e.g. in the /// Spring Application Context /// </summary> /// <param name="source">Source of event</param> /// <param name="e">The event being fired</param> public virtual void StageEventHandler (IStage source, StageEvent e) { if (Log.IsDebugEnabled) { Log.Debug("StageEventHandler source is [" + source + "], Current Stage is [" + this + "], e is [" + e + "]"); } PushEvent(e); }
/// <summary> /// Send an event to all registered listeners /// </summary> /// <param name="e">The event to fire</param> public virtual void FireStageEvent(StageEvent e) { if (ObserverComparer != null) { FireStageEvent(e, ObserverComparer); } else // better not to reflect if we do not have to { _stageEventHandler(this, e); } }
/// <summary> /// Send event to registered listeners. This /// overload allows you to sort the Invocation /// list of the event delegate. This is useful /// when you want to apply non-default order to the /// listener call list. You should probably only /// use this with RunInCallerContext set to true. /// </summary> /// <param name="e">The event to fire</param> /// <param name="comparer">IComparer to sort list of /// registered Delegates</param> /// <see cref="IComparer{T}"/> public virtual void FireStageEvent (StageEvent e, IComparer <Delegate> comparer) { Log.Debug("Firing Stage Event with comparer " + comparer); if (_stageEventHandler == null) { return; } var dl = _stageEventHandler.GetInvocationList(); Array.Sort(dl, comparer); /* call each observer in our order */ foreach (var d in dl) { d.Method.Invoke(d.Target, new object[] { this, e }); } }
/// <summary> /// Ctor with init /// </summary> /// <param name="cb">The worker callback</param> /// <param name="e">The state used by worker</param> public StageWorkerContext (StageWorkerCallback cb, StageEvent e) { StageWorkerCallback = cb; StageWorkerEvent = e; }
/// <summary> /// Push event into stage /// </summary> /// <param name="e">The event</param> public void PushEvent(StageEvent e) { PushEvent(StageWorker, e); }
/// <summary> /// Stage implementations override this to do their work /// </summary> /// <param name="e">The event to handle</param> protected abstract void StageWorker(StageEvent e);