public void ActionDispatcherSyncContext_AfterConstruction_RegistersStandardPropertiesExceptSpecificAssociatedThread()
        {
            // Just calling "typeof" isn't sufficient to invoke the static constructor, so we create one
            // Ordinarily, this isn't necessary, since Verify is normally only called on types of initialized objects
            using (ActionDispatcher dispatcher = new ActionDispatcher())
            {
                new ActionDispatcherSynchronizationContext(dispatcher);
            }

            // This will throw an exception if the type doesn't support all Standard properties except SpecificAssociatedThread
            SynchronizationContextRegister.Verify(typeof(ActionDispatcherSynchronizationContext), SynchronizationContextProperties.NonReentrantPost | SynchronizationContextProperties.NonReentrantSend | SynchronizationContextProperties.Sequential | SynchronizationContextProperties.Synchronized);
        }
        public void Current_FromOutsideAction_IsNull()
        {
            using (ActionDispatcher dispatcher = new ActionDispatcher())
            {
                Thread thread = new Thread(() => dispatcher.Run());
                thread.Start();

                Assert.IsNull(ActionDispatcher.Current, "ActionDispatcher.Current is not null outside Run()");

                dispatcher.QueueExit();
                thread.Join();
            }
        }
        public void Current_FromInsideAction_IsActionDispatcherForThatAction()
        {
            ActionDispatcher innerDispatcher = null;

            using (ActionDispatcher dispatcher = new ActionDispatcher())
            {
                Thread thread = new Thread(() => dispatcher.Run());
                thread.Start();
                dispatcher.QueueAction(() => { innerDispatcher = ActionDispatcher.Current; });
                dispatcher.QueueExit();
                thread.Join();

                Assert.AreSame(dispatcher, innerDispatcher, "ActionDispatcher did not set Current correctly for action");
            }
        }
        public void CurrentSynchronizationContext_FromInsideAction_IsActionDispatcherSynchronizationContext()
        {
            SynchronizationContext innerContext = null;

            using (ActionDispatcher dispatcher = new ActionDispatcher())
            {
                Thread thread = new Thread(() => dispatcher.Run());
                thread.Start();
                dispatcher.QueueAction(() => { innerContext = SynchronizationContext.Current; });
                dispatcher.QueueExit();
                thread.Join();

                Assert.IsInstanceOfType(innerContext, typeof(ActionDispatcherSynchronizationContext), "ActionDispatcher did not set SynchronizationContext.Current correctly for action");
            }
        }
        public void Action_QueuedToActionDispatcher_IsExecutedByRun()
        {
            bool sawAction = false;

            using (ActionDispatcher dispatcher = new ActionDispatcher())
            {
                Thread thread = new Thread(() => dispatcher.Run());
                thread.Start();
                dispatcher.QueueAction(() => { sawAction = true; });
                dispatcher.QueueExit();
                thread.Join();

                Assert.IsTrue(sawAction, "ActionDispatcher did not execute action");
            }
        }
        public void Action_QueuedAfterExitAction_IsNotExecutedByRun()
        {
            bool sawAction = false;

            using (ActionDispatcher dispatcher = new ActionDispatcher())
            {
                Thread thread = new Thread(() => dispatcher.Run());
                dispatcher.QueueExit();
                dispatcher.QueueAction(() => { sawAction = true; });
                thread.Start();
                thread.Join();

                Assert.IsFalse(sawAction, "ActionDispatcher did execute the action");
            }
        }
        public void ExitAction_OnEmptyQueueAfterThreadStarted_CausesRunToReturn()
        {
            using (ActionDispatcher dispatcher = new ActionDispatcher())
            {
                Thread thread = new Thread(() => dispatcher.Run());
                thread.Start();
                dispatcher.QueueExit();

                bool threadExited = thread.Join(TimeSpan.FromMilliseconds(100));
                Assert.IsTrue(threadExited, "Thread did not exit after ActionDispatcher.QueueExit");
            }
        }
        public void Run_WithoutExitAction_DoesNotReturn()
        {
            using (ActionDispatcher dispatcher = new ActionDispatcher())
            {
                Thread thread = new Thread(() => dispatcher.Run());
                thread.Start();

                bool threadExited = thread.Join(TimeSpan.FromMilliseconds(100));
                Assert.IsFalse(threadExited, "Thread exited before ActionDispatcher.QueueExit");

                dispatcher.QueueExit();
                thread.Join();
            }
        }
        public void MultipleActions_QueuedBeforeThreadStart_AreExecutedByRun()
        {
            bool sawAction1 = false;
            bool sawAction2 = false;

            using (ActionDispatcher dispatcher = new ActionDispatcher())
            {
                Thread thread = new Thread(() => dispatcher.Run());
                dispatcher.QueueAction(() => { sawAction1 = true; });
                dispatcher.QueueAction(() => { sawAction2 = true; });
                thread.Start();
                dispatcher.QueueExit();
                thread.Join();

                Assert.IsTrue(sawAction1, "ActionDispatcher did not execute the first action");
                Assert.IsTrue(sawAction2, "ActionDispatcher did not execute the second action");
            }
        }
 /// <summary>
 /// Initializes a new instance of the <see cref="ActionDispatcherSynchronizationContext"/> class by using the specified <see cref="Nito.Async.ActionDispatcher"/>.
 /// </summary>
 /// <param name="actionDispatcher">The action queue to associate with this <see cref="ActionDispatcherSynchronizationContext"/>.</param>
 public ActionDispatcherSynchronizationContext(ActionDispatcher actionDispatcher)
 {
     ActionDispatcher = actionDispatcher;
 }
Example #11
0
 /// <summary>
 /// Initializes a new instance of the <see cref="ActionThread"/> class, creating a child thread waiting for commands.
 /// </summary>
 /// <example>The following code sample demonstrates how to create an ActionThread, start it, and then join with it:
 /// <code source="..\..\Source\Examples\DocumentationExamples\ActionThread\ConstructStartJoin.cs"/>
 /// </example>
 public ActionThread()
 {
     this.dispatcher = new ActionDispatcher();
     this.thread     = new Thread(() => this.dispatcher.Run());
 }
Example #12
0
 /// <summary>
 /// Initializes a new instance of the <see cref="ActionDispatcherSynchronizationContext"/> class by using the specified <see cref="Nito.Async.ActionDispatcher"/>.
 /// </summary>
 /// <param name="actionDispatcher">The action queue to associate with this <see cref="ActionDispatcherSynchronizationContext"/>.</param>
 public ActionDispatcherSynchronizationContext(ActionDispatcher actionDispatcher)
 {
     this.ActionDispatcher = actionDispatcher;
 }
Example #13
0
 /// <summary>
 /// Initializes a new instance of the <see cref="ActionDispatcherSynchronizationContext"/> class by using the specified <see cref="Nito.Async.ActionDispatcher"/>.
 /// </summary>
 /// <param name="actionDispatcher">The action queue to associate with this <see cref="ActionDispatcherSynchronizationContext"/>. May not be <c>null</c>.</param>
 public ActionDispatcherSynchronizationContext(ActionDispatcher actionDispatcher)
 {
     Contract.Requires(actionDispatcher != null);
     this.actionDispatcher = actionDispatcher;
 }