annotate Implab.Fx/PromiseHelpers.cs @ 33:b255e4aeef17

removed the reference to the parent from the promise object this allows resolved promises to release parents and results they are holding. Added complete set of operations to IPromiseBase interface Subscribing to the cancellation event of the promise should not affect it's IsExclusive property More tests.
author cin
date Thu, 10 Apr 2014 02:39:29 +0400
parents 381095ad0a69
children d67b95eddaf4 0fdaf280c797
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
4
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
1 using System;
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
2 using System.Collections.Generic;
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
3 using System.Linq;
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
4 using System.Text;
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
5 using System.Windows.Forms;
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
6 using System.Threading;
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
7
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
8 namespace Implab.Fx
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
9 {
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
10 public static class PromiseHelpers
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
11 {
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
12 /// <summary>
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
13 /// Перенаправляет обработку обещания в поток указанного элемента управления.
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
14 /// </summary>
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
15 /// <typeparam name="T">Тип результата обещания</typeparam>
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
16 /// <param name="that">Исходное обещание</param>
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
17 /// <param name="ctl">Элемент управления</param>
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
18 /// <returns>Новое обещание, обработчики которого будут выполнены в потоке элемента управления.</returns>
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
19 /// <exception cref="ArgumentNullException">Параметр не может быть <c>null</c>.</exception>
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
20 /// <example>
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
21 /// client
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
22 /// .Get("description.txt") // returns a promise
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
23 /// .DirectToControl(m_ctl) // handle the promise in the thread of the control
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
24 /// .Then(
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
25 /// description => m_ctl.Text = description // now it's safe
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
26 /// )
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
27 /// </example>
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
28 public static Promise<T> DispatchToControl<T>(this Promise<T> that, Control ctl)
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
29 {
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
30 if (that == null)
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
31 throw new ArgumentNullException("that");
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
32 if (ctl == null)
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
33 throw new ArgumentNullException("ctl");
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
34
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
35 var directed = new Promise<T>();
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
36
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
37 that.Then(
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
38 res =>
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
39 {
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
40 if (ctl.InvokeRequired)
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
41 ctl.Invoke(new Action<T>(directed.Resolve), res);
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
42 else
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
43 directed.Resolve(res);
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
44 },
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
45 err =>
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
46 {
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
47 if (ctl.InvokeRequired)
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
48 ctl.Invoke(new Action<Exception>(directed.Reject), err);
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
49 else
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
50 directed.Reject(err);
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
51 }
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
52 );
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
53
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
54 return directed;
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
55 }
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
56
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
57 /// <summary>
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
58 /// Направляет обработку обещания в текущий поток, если у него существует контекст синхронизации.
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
59 /// </summary>
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
60 /// <typeparam name="T">Тип результата обещания.</typeparam>
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
61 /// <param name="that">Обещание которое нужно обработать в текущем потоке.</param>
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
62 /// <returns>Перенаправленное обещание.</returns>
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
63 public static Promise<T> DispatchToCurrentThread<T>(this Promise<T> that)
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
64 {
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
65 var sync = SynchronizationContext.Current;
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
66 if (sync == null)
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
67 throw new InvalidOperationException("The current thread doesn't have a syncronization context");
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
68 return DispatchToSyncContext(that, sync);
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
69 }
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
70
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
71 /// <summary>
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
72 /// Направляет обработку обещания в указанный контекст синхронизации.
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
73 /// </summary>
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
74 /// <typeparam name="T">Тип результата обещания.</typeparam>
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
75 /// <param name="that">Обещание, которое требуется обработать в указанном контексте синхронизации.</param>
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
76 /// <param name="sync">Контекст синхронизации в который будет направлено обещание.</param>
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
77 /// <returns>Новое обещание, которое будет обрабатываться в указанном контексте.</returns>
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
78 public static Promise<T> DispatchToSyncContext<T>(this Promise<T> that, SynchronizationContext sync)
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
79 {
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
80 if (that == null)
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
81 throw new ArgumentNullException("that");
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
82 if (sync == null)
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
83 throw new ArgumentNullException("sync");
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
84
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
85 var d = new Promise<T>();
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
86
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
87 that.Then(
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
88 res => sync.Post(state => d.Resolve(res), null),
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
89 err => sync.Post(state => d.Reject(err), null)
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
90 );
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
91
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
92 return d;
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
93 }
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
94 }
381095ad0a69 Implab.Fx: implemented animation object
cin
parents:
diff changeset
95 }