Example #1
0
        public void TransferMoney_NearPayInLimit()
        {
            Setup();
            TransferMoney transferMoney = new TransferMoney(accountRepository.Object, notifcationService.Object);

            accountRepository.Setup(m => m.GetAccountById(account1.Id)).Returns((account1));// => accounts.Dequeue());
            accountRepository.Setup(m => m.GetAccountById(account2.Id)).Returns((account2));
            transferMoney.Execute(account1.Id, account2.Id, 3600);
            notifcationService.Verify(m => m.NotifyApproachingPayInLimit(account2.User.Email));
        }
Example #2
0
        public void TestSufficentToTransfer()
        {
            decimal startToBalance = this.testToAccount.Balance;

            TransferMoney transferMoneyFeature = new TransferMoney(accountRepository.Object, notificationService.Object);

            transferMoneyFeature.Execute(this.testFromAccount.Id, this.testToAccount.Id, 10.0m);

            Assert.AreEqual(this.testToAccount.Balance, startToBalance + 10.0m);
        }
Example #3
0
        public void ShouldExecuteSuccessfully(decimal balance, decimal withdrawn, decimal paidIn, decimal amount)
        {
            // Arrange
            var sourceAccount = SourceAccountFake(balance, withdrawn);

            _accountRepository.Setup(x => x.GetAccountById(sourceAccount.Id))
            .Returns(sourceAccount);

            var targetAccount = TargetAccountFake(balance, paidIn);

            _accountRepository.Setup(x => x.GetAccountById(targetAccount.Id))
            .Returns(targetAccount);

            // Act
            _feature.Execute(sourceAccount.Id, targetAccount.Id, amount);

            // Assert
            _accountRepository.Verify(x => x.Update(It.IsAny <Account>()), Times.Exactly(2));
        }
        public void Execute_ApproachPayInLimit4000_SendNotification()
        {
            _fromAccount.Balance = 1m;
            _toAccount.PaidIn    = PayInLimit - ReachingPayInLimitNotificationThreshold;
            var sut = new TransferMoney(_accountRepository.Object, _notificationService.Object);

            sut.Execute(_fromAccountId, _toAccountId, 1m);

            _notificationService.Verify(n => n.NotifyApproachingPayInLimit(_toUser.Email));
        }
        public void Execute_BalanceAfterWithdrawLowerThan500_NotifyLowerFunds()
        {
            // Arrange
            var fromAccountGuid = Guid.NewGuid();
            var toAccountGuid   = Guid.NewGuid();
            var email           = "*****@*****.**";

            var fromAccount = new Account
            {
                Balance = 1000m,
                Id      = fromAccountGuid,
                User    = new User
                {
                    Email = email
                },
                Withdrawn = 50m,
                PaidIn    = 50m
            };

            var toAccount = new Account
            {
                Balance   = 1500m,
                Id        = toAccountGuid,
                User      = new User(),
                Withdrawn = 50m,
                PaidIn    = 50m
            };

            accountRepositoryMock
            .Setup(x => x.GetAccountById(fromAccountGuid))
            .Returns(fromAccount);

            accountRepositoryMock
            .Setup(x => x.GetAccountById(toAccountGuid))
            .Returns(toAccount);

            // Act
            transferMoneyFeature.Execute(fromAccountGuid, toAccountGuid, 600m);

            // Assert
            notificationServiceMock.Verify(x => x.NotifyFundsLow(email), Times.Once);
        }
Example #6
0
        static void Main(string[] args)
        {
            try
            {
                decimal amount = 0;
                Guid    fromAccountID;

                Console.WriteLine("Welcome to MoneyBox.");
                Console.WriteLine("Type 1 to transfer money");
                Console.WriteLine("Type 2 to withdraw money");

                string optionPicked = Console.ReadLine();

                IAccountRepository   accountRepository   = new AccountRepository();
                INotificationService notificationService = new NotificationService();

                if (optionPicked.Equals("1"))
                {
                    fromAccountID = GetFromAccount();

                    var toAccountID = GetToAccount();

                    amount = GetAmount();

                    var transferMoney = new TransferMoney(accountRepository, notificationService);

                    var updatedAccount = transferMoney.Execute(fromAccountID, toAccountID, amount);

                    DisplayBalance(updatedAccount);
                }
                else if (optionPicked.Equals("2"))
                {
                    fromAccountID = GetFromAccount();

                    amount = GetAmount();

                    var withdrawMoney = new WithdrawMoney(accountRepository, notificationService);

                    var updatedAccount = withdrawMoney.Execute(fromAccountID, amount);

                    DisplayBalance(updatedAccount);
                }
                else
                {
                    Console.WriteLine("Sorry we were unable to process your request. Please try again or contact your system administrator.");
                }
            }
            catch (Exception ex)
            {
                Console.WriteLine(ex.Message);
            }

            Console.Read();
        }
        public void ValidatedMaxPaidInAmountSuccess()
        {
            var amountToTransfer = 3800;

            _fromAccount.Balance = 500;

            _accountRepositoryMock.Setup(x => x.GetAccountById(_fromAccountId)).Returns(_fromAccount);
            var transferMoney = new TransferMoney(_accountRepositoryMock.Object);

            transferMoney.Execute(_fromAccountId, _toAccountId, amountToTransfer);
        }
Example #8
0
        public void TransferMoney_FundsLow()
        {
            Setup();
            account1.Balance = 900;
            TransferMoney transferMoney = new TransferMoney(accountRepository.Object, notifcationService.Object);

            accountRepository.Setup(m => m.GetAccountById(account1.Id)).Returns((account1));// => accounts.Dequeue());
            accountRepository.Setup(m => m.GetAccountById(account2.Id)).Returns((account2));
            transferMoney.Execute(account1.Id, account2.Id, 500);
            notifcationService.Verify(m => m.NotifyFundsLow(account1.User.Email));
        }
Example #9
0
        public void TransferMoney_PayInLimit()
        {
            Setup();
            TransferMoney transferMoney = new TransferMoney(accountRepository.Object, notifcationService.Object);

            accountRepository.Setup(m => m.GetAccountById(account1.Id)).Returns((account1));// => accounts.Dequeue());
            accountRepository.Setup(m => m.GetAccountById(account2.Id)).Returns((account2));
            Exception ex = Assert.Throws <InvalidOperationException>(() => transferMoney.Execute(account1.Id, account2.Id, 5000));

            Assert.Equal("Account pay in limit reached", ex.Message);
        }
Example #10
0
        public void TransferMoney_InsufficientFunds()
        {
            Setup();
            TransferMoney transferMoney = new TransferMoney(accountRepository.Object, notifcationService.Object);

            accountRepository.Setup(m => m.GetAccountById(account1.Id)).Returns((account1));// => accounts.Dequeue());
            accountRepository.Setup(m => m.GetAccountById(account2.Id)).Returns((account2));
            Exception ex = Assert.Throws <InvalidOperationException>(() => transferMoney.Execute(account1.Id, account2.Id, 7000));

            Assert.Equal("Insufficient funds to make transfer", ex.Message);
        }
Example #11
0
        public void TransferMoney()
        {
            Setup();
            TransferMoney transferMoney = new TransferMoney(accountRepository.Object, notifcationService.Object);

            accountRepository.Setup(m => m.GetAccountById(account1.Id)).Returns((account1));// => accounts.Dequeue());
            accountRepository.Setup(m => m.GetAccountById(account2.Id)).Returns((account2));
            transferMoney.Execute(account1.Id, account2.Id, 500);
            Assert.Equal(5500, account1.Balance);
            Assert.Equal(4500, account2.Balance);
        }
Example #12
0
        public void Execute_WhenCalled_UpdateAccountRepository()
        {
            _fromAccount.Balance = 1m;
            _accountRepository.Setup(a => a.Update(_fromAccount));
            _accountRepository.Setup(a => a.Update(_toAccount));
            var sut = new TransferMoney(_accountRepository.Object, _notificationService.Object);

            sut.Execute(_fromAccountId, _toAccountId, 1m);

            _accountRepository.Verify(a => a.Update(_fromAccount));
            _accountRepository.Verify(a => a.Update(_toAccount));
        }
        public void NotifyUserUponLowBalanceSuccess()
        {
            var amountToTransfer = 800;

            var transferMoney = new TransferMoney(_accountRepositoryMock.Object);

            transferMoney.Execute(_fromAccountId, _toAccountId, amountToTransfer);

            _notificationServiceMock.Verify(x => x.NotifyFundsLow(_fromAccount.User.Email));
            _accountRepositoryMock.Verify(x => x.Update(_fromAccount));
            _accountRepositoryMock.Verify(x => x.Update(_toAccount));
        }
Example #14
0
 public void TransferThrowsError_InsufficientFundsToMakeTransfer()
 {
     Assert.Throws <InvalidOperationException>(() =>
     {
         _transferMoney.Execute(fromAccountId, toAccountId, 6500);
     });
 }
Example #15
0
        public void Transfer_100_From_Acount1_To_Account2()
        {
            // Arrange
            var accountRepository             = CreateAccountRepository(fromAccount, toAccount);
            var notificationServiceRepository = CreateNotificationService();

            // Act
            var transferMoney = new TransferMoney(accountRepository.Object, notificationServiceRepository.Object);

            transferMoney.Execute(fromAccount.Id, toAccount.Id, 100m);

            // Assert
            accountRepository.VerifyAll();
        }
Example #16
0
        public void Execute_SuccessfulTransfer_UpdatesAccounts()
        {
            //Arrange
            var amount = 150m;

            var fromAccount = new Account
            {
                Balance   = 900m,
                Withdrawn = 250m,
                PaidIn    = 0m,
                User      = new User
                {
                    Email = "*****@*****.**"
                }
            };

            var toAccount = new Account
            {
                Balance   = 750m,
                Withdrawn = 250m,
                PaidIn    = 0m,
                User      = new User
                {
                    Email = "*****@*****.**"
                }
            };

            _mockAccountRepository.Setup(x => x.GetAccountById(_fromAccountId)).Returns(fromAccount);
            _mockAccountRepository.Setup(x => x.GetAccountById(_toAccountId)).Returns(toAccount);

            //Act
            _sut.Execute(_fromAccountId, _toAccountId, amount);

            //Assert
            Assert.AreEqual(750m, fromAccount.Balance);
            Assert.AreEqual(900m, toAccount.Balance);
        }
        public void Execute_InvalidFromAccountId_InvalidOperationException()
        {
            // Arrange
            Guid from = new Guid("11223344-5566-7788-99AA-BBCCDDEEFF03");
            Guid to   = new Guid("11223344-5566-7788-99AA-BBCCDDEEFF00");

            _iAccountRepository.Setup(x => x.GetAccountById(from)).Returns(() => null);
            _iAccountRepository.Setup(x => x.GetAccountById(to)).Returns(new App.Account {
                Id = new Guid("11223344-5566-7788-99AA-BBCCDDEEFF00"), User = new App.User()
                {
                    Id = new Guid("12223344-5566-7788-99AA-BBCCDDEEFF00"), Name = "Test1", Email = "*****@*****.**"
                }, Balance = 100, Withdrawn = 50, PaidIn = 50
            });

            // Act
            Assert.Throws <InvalidOperationException>(() => _transferMoney.Execute(from, to, 500));

            // Assert
            _iAccountRepository.Verify(service => service.Update(null), Times.Never);
        }
Example #18
0
        public void TestNegativeTransfer()
        {
            TransferMoney transferMoneyFeature = new TransferMoney(accountRepository.Object, notificationService.Object);

            try
            {
                transferMoneyFeature.Execute(this.testFromAccount.Id, this.testToAccount.Id, -10.0m);
            }
            catch (InvalidOperationException e)
            {
                StringAssert.Contains(e.Message, "Cannot complete action with a negative amount");
                return;
            }
            Assert.Fail("No exception was thrown.");
        }
        public void WhenSenderInsufficentFunds_Throw()
        {
            var fakeAccountRepo         = new Mock <IAccountRepository>();
            var fakeNotificationService = new Mock <INotificationService>();

            fakeAccountRepo.Setup(x => x.GetAccountById(It.IsAny <Guid>())).Returns(new Account {
                Balance = 10
            });

            var transferMoney = new TransferMoney(fakeAccountRepo.Object, fakeNotificationService.Object);
            var fromGuid      = new Guid("3605a4f9-96a4-439e-9155-064a94736e9c");
            var toGuid        = new Guid("7c8cb0f1-a101-4563-8a22-0f4cfdf56e80");

            Assert.Throws <InvalidOperationException>(() => transferMoney.Execute(fromGuid, toGuid, 100));
        }
Example #20
0
        public void Test_TransferMoney_Execute_Account_Pay_In_Limit_Reached()
        {
            TransferMoney transferMoney = new TransferMoney(new TestAccountRepository(), new TestNotificationService());

            var exception = Assert.Throws <InvalidOperationException>(() =>
                                                                      transferMoney.Execute
                                                                      (
                                                                          new Guid("99662f03-2d84-44c1-9282-7363ee9d9776"),
                                                                          new Guid("8e15fd8d-6dc2-4415-a5fa-93de494322bf"),
                                                                          4001m
                                                                      )
                                                                      );

            Assert.Equal($"Account pay in limit reached", exception.Message);
        }
Example #21
0
        public void Test_TransferMoney_Execute_Insufficient_Funds()
        {
            TransferMoney transferMoney = new TransferMoney(new TestAccountRepository(), new TestNotificationService());

            var exception = Assert.Throws <InvalidOperationException>(() =>
                                                                      transferMoney.Execute
                                                                      (
                                                                          new Guid("ed817038-feff-4e09-a517-d70166c5c995"),
                                                                          new Guid("c7b7f0db-4a4f-4f56-ac65-c64e4fe08337"),
                                                                          2
                                                                      )
                                                                      );

            Assert.Equal($"Insufficient funds to make this transaction", exception.Message);
        }
        public void NotifyUserCaseMaxTransferLimitReachedSuccess()
        {
            var amountToTransfer = 3800;

            _fromAccount.Balance = 5000;

            _accountRepositoryMock.Setup(x => x.GetAccountById(_fromAccountId)).Returns(_fromAccount);
            var transferMoney = new TransferMoney(_accountRepositoryMock.Object);

            transferMoney.Execute(_fromAccountId, _toAccountId, amountToTransfer);

            _notificationServiceMock.Verify(x => x.NotifyApproachingPayInLimit(_toAccount.User.Email));
            _accountRepositoryMock.Verify(x => x.Update(_fromAccount));
            _accountRepositoryMock.Verify(x => x.Update(_toAccount));
        }
        public void TransferMoneyExecute_ExecutingTransfer_AccountPayLimit()
        {
            // Arrange

            var fromAccountId = Guid.NewGuid();
            var toAccountId   = Guid.NewGuid();

            var fromAccount = new Account();

            fromAccount.Balance   = 600;
            fromAccount.Withdrawn = 500m;
            fromAccount.User      = new User();
            fromAccount.Id        = fromAccountId;

            var toAccount = new Account();

            toAccount.Balance   = 20m;
            toAccount.Withdrawn = 20m;
            toAccount.User      = new User();
            toAccount.Id        = toAccountId;
            toAccount.PaidIn    = 5000m;

            var amount = 10;

            this.mockAccountRepository.Setup(x => x.GetAccountById(It.Is <Guid>(v => v.Equals(fromAccountId))))
            .Returns(fromAccount);

            this.mockAccountRepository.Setup(x => x.GetAccountById(It.Is <Guid>(v => v.Equals(toAccountId))))
            .Returns(toAccount);


            var myTransforMoney = new TransferMoney(this.mockAccountRepository.Object, this.mockNotificationService.Object);

            // Act

            myTransforMoney.Execute(fromAccountId, toAccountId, amount);

            // Assert

            this.mockAccountRepository.Verify(x => x.GetAccountById(fromAccountId), Times.Once);
            this.mockAccountRepository.Verify(x => x.GetAccountById(toAccountId), Times.Once);

            this.mockNotificationService.Verify(x => x.NotifyApproachingPayInLimit(It.IsAny <string>()), Times.Once);
            this.mockNotificationService.Verify(x => x.NotifyFundsLow(It.IsAny <string>()), Times.Never);

            this.mockAccountRepository.Verify(x => x.Update(fromAccount), Times.Never);
            this.mockAccountRepository.Verify(x => x.Update(toAccount), Times.Never);
        }
        public void Execute_ShouldUpdateAccountsSuccesfully()
        {
            // Arrange
            decimal amount = 500m;

            var sender   = new Account();
            var receiver = new Account();

            // As the tranfer takes place succesfully, both accounts are being updated.
            // However, if an exception is thrown, the Execute method will never reach
            // the update invocation.

            sender.Balance   = 500m;  // simply change the sender's balance to 499 or less to cause an insufficient funds exception and see this test failing.
            receiver.Balance = 2500m;
            receiver.PaidIn  = 3500m; // or change the receiver's paidIn balance to 3501 or more to cause an pay in limit reached exception and see this test failing.

            var mockAccountRepository   = new Mock <IAccountRepository>();
            var mockNotificationService = new Mock <INotificationService>();

            var senderID   = Guid.NewGuid();
            var receiverID = Guid.NewGuid();

            sender.User = new User {
                Email = "*****@*****.**", Id = senderID
            };
            receiver.User = new User {
                Email = "*****@*****.**", Id = senderID
            };

            var transferMoney = new TransferMoney(mockAccountRepository.Object, mockNotificationService.Object);

            mockAccountRepository.Setup(x => x.GetAccountById(It.Is <Guid>(y => y == senderID))).Returns(sender);
            mockAccountRepository.Setup(x => x.GetAccountById(It.Is <Guid>(y => y == receiverID))).Returns(receiver);

            mockNotificationService.Setup(x => x.NotifyFundsLow(sender.User.Email));
            mockNotificationService.Setup(y => y.NotifyApproachingPayInLimit(receiver.User.Email));

            mockAccountRepository.Setup(x => x.Update(sender));
            mockAccountRepository.Setup(y => y.Update(receiver));

            // Act
            transferMoney.Execute(senderID, receiverID, amount);

            // Assert
            mockAccountRepository.Verify(x => x.Update(sender));
            mockAccountRepository.Verify(y => y.Update(receiver));
        }
Example #25
0
 public void TransferMoney(Account from, Account to, double sum)
 {
     try
     {
         ITransaction transaction = new TransferMoney(from, to, sum);
         var          res         = transaction.Execute();
         if (!res && from.GetDoubtful())
         {
             throw new Exception("Ограниченный счет");
         }
         _history.Push(transaction);
     }
     catch (Exception e)
     {
         Console.WriteLine($"{e.Message}");
     }
 }
Example #26
0
        public void Test_TransferMoney_Execute_Success_Without_Notification()
        {
            TransferMoney transferMoney = new TransferMoney(new TestAccountRepository(), new TestNotificationService());

            var ex = Record.Exception
                     (
                () =>
                transferMoney.Execute
                (
                    new Guid("99662f03-2d84-44c1-9282-7363ee9d9776"),
                    new Guid("8e15fd8d-6dc2-4415-a5fa-93de494322bf"),
                    400m
                )
                     );

            Assert.Null(ex);
        }
        public void WhenRecieverPaymentLimit_Throw()
        {
            var fakeAccountRepo = new Mock <IAccountRepository>();
            var fromGuid        = new Guid("3605a4f9-96a4-439e-9155-064a94736e9c");
            var toGuid          = new Guid("7c8cb0f1-a101-4563-8a22-0f4cfdf56e80");

            fakeAccountRepo.Setup(x => x.GetAccountById(It.Is <Guid>(z => z == toGuid))).Returns(new Account {
                Balance = 5000, PaidIn = 3100
            });
            fakeAccountRepo.Setup(x => x.GetAccountById(It.Is <Guid>(z => z == fromGuid))).Returns(new Account {
                Balance = 2000, Withdrawn = 0
            });

            var fakeNotificationService = new Mock <INotificationService>();

            var transferMoney = new TransferMoney(fakeAccountRepo.Object, fakeNotificationService.Object);

            Assert.Throws <InvalidOperationException>(() => transferMoney.Execute(fromGuid, toGuid, 1000));
        }
Example #28
0
        public void ExceptionThrownOnInsufficientFunds()
        {
            var amount = TestAccountFactory.DefaultBalance + 1m;

            Action transferAction = () => transferMoney.Execute(
                TestAccountFactory.Ids.DefaultFrom,
                TestAccountFactory.Ids.DefaultTo,
                amount);

            transferAction.Should().Throw <InvalidOperationException>();

            // Ensure that no notifications were sent
            NotificationServiceMock.Verify(x => x.NotifyApproachingPayInLimit(It.IsAny <string>()), Times.Never);
            NotificationServiceMock.Verify(x => x.NotifyFundsLow(It.IsAny <string>()), Times.Never);

            // Ensure that neither account was updated
            AccountRepositoryMock.Verify(x => x.Update(It.IsAny <Account>()), Times.Never);
        }
Example #29
0
        public void TransferMoney_Execute_AmountToWithdrawExceedsBalance_ThrowsInvalidOperationException(decimal balance, decimal transferAmount)
        {
            // Arrange
            var accountRepository = new AccountRepository();

            var sourceAccount = new Account(_userA);

            sourceAccount.Deposit(balance);
            accountRepository.Update(sourceAccount);

            var destinationAccount = new Account(_userB);

            accountRepository.Update(destinationAccount);

            var notificationService  = new NotificationService();
            var transferMoneyFeature = new TransferMoney(accountRepository, notificationService);

            // Assert
            Assert.Throws <InvalidOperationException>(() => transferMoneyFeature.Execute(sourceAccount.Id, destinationAccount.Id, transferAmount));
        }
Example #30
0
        public void Execute_GivenInvalidAmount_ThrowException()
        {
            var fromAccount = new AccountBuilder().WithBalance(0).Build();
            var toAccount   = new AccountBuilder().Build();
            var amount      = 0.01m;

            var mockRepository = new Mock <IAccountRepository>();

            mockRepository
            .Setup(repo => repo.GetAccountById(fromAccount.Id))
            .Returns(fromAccount);

            mockRepository
            .Setup(repo => repo.GetAccountById(toAccount.Id))
            .Returns(toAccount);

            var sut = new TransferMoney(mockRepository.Object);

            Assert.Throws <InvalidOperationException>(() => sut.Execute(fromAccount.Id, toAccount.Id, amount));
        }