public void AddRevertAction_ShouldExecuteWhenDisposedAndNotCompleteted()
        {
            var  ct       = new AtomicComposition();
            bool executed = false;

            ct.AddRevertAction(() => executed = true);

            ct.Dispose();

            Assert.True(executed);
        }
        public void Dispose_AllMethodsShouldThrow()
        {
            var ct = new AtomicComposition();

            ct.Dispose();

            Assert.Throws <ObjectDisposedException>(() => ct.AddCompleteAction(() => ct = null));
            Assert.Throws <ObjectDisposedException>(() => ct.Complete());
            Assert.Throws <ObjectDisposedException>(() => ct.SetValue(ct, 10));
            object value;

            Assert.Throws <ObjectDisposedException>(() => ct.TryGetValue(ct, out value));
        }
        public void AddRevertAction_ShouldExecuteInReverseOrder()
        {
            var         ct    = new AtomicComposition();
            Stack <int> stack = new Stack <int>();

            stack.Push(1);
            stack.Push(2);
            stack.Push(3);

            ct.AddRevertAction(() => Assert.Equal(1, stack.Pop()));
            ct.AddRevertAction(() => Assert.Equal(2, stack.Pop()));
            ct.AddRevertAction(() => Assert.Equal(3, stack.Pop()));

            ct.Dispose();

            Assert.True(stack.Count == 0);
        }
        public void SetValue_ChangeOuterValuesWhileHaveInner_ShouldThrow()
        {
            var ct = new AtomicComposition();

            var ct2 = new AtomicComposition(ct);

            var key = new object();

            Assert.Throws <InvalidOperationException>(() => ct.SetValue(key, 1));

            object value;

            Assert.False(ct2.TryGetValue(key, out value));
            Assert.False(ct.TryGetValue(key, out value));

            // remove the inner atomicComposition so the outer one becomes unlocked.
            ct2.Dispose();

            ct.SetValue(key, 2);
            Assert.True(ct.TryGetValue(key, out value));
            Assert.Equal(2, value);
        }