AbstractPromiseT.cs
204 lines
| 6.6 KiB
| text/x-csharp
|
CSharpLexer
/ Implab / AbstractPromiseT.cs
|
|
r144 | using System; | ||
| using Implab.Parallels; | ||||
| namespace Implab { | ||||
| public abstract class AbstractPromise<T> : AbstractEvent<AbstractPromise<T>.HandlerDescriptor>, IPromise<T> { | ||||
| public struct HandlerDescriptor { | ||||
| readonly Action m_handler; | ||||
| readonly Action<T> m_success; | ||||
| readonly Action<Exception> m_error; | ||||
| readonly Action<Exception> m_cancel; | ||||
| readonly PromiseEventType m_mask; | ||||
| public HandlerDescriptor(Action<T> success, Action<Exception> error, Action<Exception> cancel) { | ||||
| m_success = success; | ||||
| m_error = error; | ||||
| m_cancel = cancel; | ||||
|
|
r145 | |||
| m_handler = null; | ||||
| m_mask = 0; | ||||
|
|
r144 | } | ||
| public HandlerDescriptor(Action success, Action<Exception> error, Action<Exception> cancel) { | ||||
| m_handler = success; | ||||
|
|
r145 | m_success = null; | ||
|
|
r144 | m_error = error; | ||
| m_cancel = cancel; | ||||
| m_mask = PromiseEventType.Success; | ||||
| } | ||||
| public HandlerDescriptor(Action handler, PromiseEventType mask) { | ||||
| m_handler = handler; | ||||
| m_mask = mask; | ||||
|
|
r145 | m_success = null; | ||
| m_error = null; | ||||
| m_cancel = null; | ||||
|
|
r144 | } | ||
| public void SignalSuccess(T result) { | ||||
| if (m_success != null) { | ||||
| try { | ||||
| m_success(result); | ||||
|
|
r197 | // Analysis disable once EmptyGeneralCatchClause | ||
| } catch { | ||||
|
|
r144 | } | ||
|
|
r145 | } else if ((m_mask & PromiseEventType.Success) != 0 && m_handler != null) { | ||
|
|
r144 | try { | ||
| m_handler(); | ||||
|
|
r197 | // Analysis disable once EmptyGeneralCatchClause | ||
| } catch { | ||||
|
|
r144 | } | ||
| } | ||||
| } | ||||
| public void SignalError(Exception err) { | ||||
| if (m_error != null) { | ||||
| try { | ||||
| m_error(err); | ||||
| // Analysis disable once EmptyGeneralCatchClause | ||||
| } catch { | ||||
| } | ||||
|
|
r145 | } else if ((m_mask & PromiseEventType.Error) != 0 && m_handler != null) { | ||
|
|
r144 | try { | ||
| m_handler(); | ||||
| // Analysis disable once EmptyGeneralCatchClause | ||||
| } catch { | ||||
| } | ||||
| } | ||||
| } | ||||
| public void SignalCancel(Exception reason) { | ||||
| if (m_cancel != null) { | ||||
| try { | ||||
| m_cancel(reason); | ||||
|
|
r197 | // Analysis disable once EmptyGeneralCatchClause | ||
| } catch { | ||||
|
|
r144 | } | ||
|
|
r145 | } else if ((m_mask & PromiseEventType.Cancelled) != 0 && m_handler != null) { | ||
|
|
r144 | try { | ||
| m_handler(); | ||||
| // Analysis disable once EmptyGeneralCatchClause | ||||
| } catch { | ||||
| } | ||||
| } | ||||
| } | ||||
| } | ||||
|
|
r242 | public Type ResultType { | ||
|
|
r144 | get { | ||
| return typeof(T); | ||||
| } | ||||
| } | ||||
|
|
r145 | public T Join() { | ||
|
|
r144 | WaitResult(-1); | ||
| return m_result; | ||||
| } | ||||
|
|
r145 | public T Join(int timeout) { | ||
|
|
r144 | WaitResult(timeout); | ||
| return m_result; | ||||
| } | ||||
|
|
r145 | void IPromise.Join() { | ||
| WaitResult(-1); | ||||
| } | ||||
| void IPromise.Join(int timeout) { | ||||
| WaitResult(timeout); | ||||
| } | ||||
|
|
r144 | public IPromise<T> On(Action<T> success, Action<Exception> error, Action<Exception> cancel) { | ||
| AddHandler(new HandlerDescriptor(success, error, cancel)); | ||||
| return this; | ||||
| } | ||||
| public IPromise<T> On(Action<T> success, Action<Exception> error) { | ||||
| AddHandler(new HandlerDescriptor(success, error, null)); | ||||
| return this; | ||||
| } | ||||
| public IPromise<T> On(Action<T> success) { | ||||
| AddHandler(new HandlerDescriptor(success, null, null)); | ||||
| return this; | ||||
| } | ||||
| public IPromise<T> On(Action handler, PromiseEventType events) { | ||||
| AddHandler(new HandlerDescriptor(handler, events)); | ||||
| return this; | ||||
| } | ||||
| public IPromise<T> On(Action success, Action<Exception> error, Action<Exception> cancel) { | ||||
| AddHandler(new HandlerDescriptor(success, error, cancel)); | ||||
| return this; | ||||
| } | ||||
| public IPromise<T> On(Action success, Action<Exception> error) { | ||||
| AddHandler(new HandlerDescriptor(success, error, null)); | ||||
| return this; | ||||
| } | ||||
| public IPromise<T> On(Action success) { | ||||
| AddHandler(new HandlerDescriptor(success, null, null)); | ||||
| return this; | ||||
| } | ||||
| IPromise IPromise.On(Action success, Action<Exception> error, Action<Exception> cancel) { | ||||
| AddHandler(new HandlerDescriptor(success, error, cancel)); | ||||
| return this; | ||||
| } | ||||
| IPromise IPromise.On(Action success, Action<Exception> error) { | ||||
| AddHandler(new HandlerDescriptor(success, error, null)); | ||||
| return this; | ||||
| } | ||||
| IPromise IPromise.On(Action success) { | ||||
| AddHandler(new HandlerDescriptor(success, null, null)); | ||||
| return this; | ||||
| } | ||||
|
|
r145 | IPromise IPromise.On(Action handler, PromiseEventType events) { | ||
| AddHandler(new HandlerDescriptor(handler, events)); | ||||
| return this; | ||||
| } | ||||
|
|
r144 | public IPromise<T2> Cast<T2>() { | ||
| return (IPromise<T2>)this; | ||||
| } | ||||
| #region implemented abstract members of AbstractPromise | ||||
|
|
r242 | protected override Signal GetFulfillSignal() { | ||
|
|
r144 | var signal = new Signal(); | ||
| AddHandler(new HandlerDescriptor(signal.Set, PromiseEventType.All)); | ||||
| return signal; | ||||
| } | ||||
|
|
r156 | protected override void SignalHandler(HandlerDescriptor handler, int signal) { | ||
| switch (signal) { | ||||
| case SUCCEEDED_STATE: | ||||
| handler.SignalSuccess(m_result); | ||||
| break; | ||||
| case REJECTED_STATE: | ||||
|
|
r242 | handler.SignalError(RejectReason); | ||
|
|
r156 | break; | ||
| case CANCELLED_STATE: | ||||
| handler.SignalCancel(CancellationReason); | ||||
| break; | ||||
| default: | ||||
| throw new InvalidOperationException(String.Format("Invalid promise signal: {0}", signal)); | ||||
| } | ||||
|
|
r144 | } | ||
| #endregion | ||||
| T m_result; | ||||
| protected void SetResult(T value) { | ||||
| if (BeginSetResult()) { | ||||
| m_result = value; | ||||
| EndSetResult(); | ||||
| } | ||||
| } | ||||
| } | ||||
| } | ||||
