/// <summary>
        /// <see cref="M:Microsoft.Samples.NLayerApp.Application.MainBoundedContext.ERPModule.Services.ICustomerManagement.AddNewCustomer"/>
        /// </summary>
        /// <param name="customerDTO"><see cref="M:Microsoft.Samples.NLayerApp.Application.MainBoundedContext.ERPModule.Services.ICustomerManagement.AddNewCustomer"/></param>
        /// <returns><see cref="M:Microsoft.Samples.NLayerApp.Application.MainBoundedContext.ERPModule.Services.ICustomerManagement.AddNewCustomer"/></returns>
        public CustomerDTO AddNewCustomer(CustomerDTO customerDTO)
        {
            //check preconditions
            if (customerDTO == null || customerDTO.CountryId == Guid.Empty)
                throw new ArgumentException(Messages.warning_CannotAddCustomerWithEmptyInformation);

            var country = _countryRepository.Get(customerDTO.CountryId);

            if (country != null)
            {
                //Create the entity and the required associated data
                var address = new Address(customerDTO.AddressCity, customerDTO.AddressZipCode, customerDTO.AddressAddressLine1, customerDTO.AddressAddressLine2);

                var customer = CustomerFactory.CreateCustomer(customerDTO.FirstName,
                                                              customerDTO.LastName,
                                                              customerDTO.Telephone,
                                                              customerDTO.Company,
                                                              country,
                                                              address);

                //save entity
                SaveCustomer(customer);

                //return the data with id and assigned default values
                return customer.ProjectedAs<CustomerDTO>();
            }
            else
                return null;
        }
        public void AddNewCustomerThrowArgumentExceptionIfCustomerCountryInformationIsEmpty()
        {
            //Arrange
            var countryRepository = new SICountryRepository();
            var customerRepository = new SICustomerRepository();

            var customerManagementService = new CustomerAppService(countryRepository, customerRepository);

            var customerDTO = new CustomerDTO()
            {
                CountryId = Guid.Empty
            };

            //act
            var result = customerManagementService.AddNewCustomer(customerDTO);
        }
 /// <summary>
 /// <see cref="Microsoft.Samples.NLayerApp.Application.MainBoundedContext.BankingModule.Services.IMainBoundedContextService"/>
 /// </summary>
 /// <param name="customer"><see cref="Microsoft.Samples.NLayerApp.Application.MainBoundedContext.BankingModule.Services.IMainBoundedContextService"/></param>
 public void UpdateCustomer(CustomerDTO customer)
 {
     _customerAppService.UpdateCustomer(customer);
 }
 /// <summary>
 /// <see cref="Microsoft.Samples.NLayerApp.Application.MainBoundedContext.BankingModule.Services.IMainBoundedContextService"/>
 /// </summary>
 /// <param name="customer"><see cref="Microsoft.Samples.NLayerApp.Application.MainBoundedContext.BankingModule.Services.IMainBoundedContextService"/></param>
 /// <returns><see cref="Microsoft.Samples.NLayerApp.Application.MainBoundedContext.BankingModule.Services.IMainBoundedContextService"/></returns>
 public CustomerDTO AddNewCustomer(CustomerDTO customer)
 {
     return _customerAppService.AddNewCustomer(customer);
 }
        public void AddNewCustomerReturnAdaptedDTO()
        {
            //Arrange
             
            var countryRepository = new SICountryRepository();
            countryRepository.GetGuid = (guid) =>
            {
                var country = new Country("Spain", "es-ES"); ;
                country.ChangeCurrentIdentity(guid);

                return country;
            };
            var customerRepository = new SICustomerRepository();
            customerRepository.AddCustomer = (customer) => { };
            customerRepository.UnitOfWorkGet = () =>
            {
                var uow = new SIUnitOfWork();
                uow.Commit = () => { };

                return uow;
            };

            var customerManagementService = new CustomerAppService(countryRepository, customerRepository);

            var customerDTO = new CustomerDTO()
            {
                CountryId = Guid.NewGuid(),
                FirstName = "Jhon",
                LastName = "El rojo"
            };

            //act
            var result = customerManagementService.AddNewCustomer(customerDTO);

            //Assert
            Assert.IsNotNull(result);
            Assert.IsTrue(result.Id != Guid.Empty);
            Assert.AreEqual(result.FirstName, customerDTO.FirstName);
            Assert.AreEqual(result.LastName, customerDTO.LastName);
        }
        public void UpdateCustomerMergePersistentAndCurrent()
        {
            //Arrange
            var country = new Country("spain", "es-ES");
            country.GenerateNewIdentity();

            Guid customerId = Guid.NewGuid();
            
            var countryRepository = new SICountryRepository();
            var customerRepository = new SICustomerRepository();

            customerRepository.UnitOfWorkGet = () =>
            {
                var uow = new SIUnitOfWork();
                uow.Commit = () => { };

                return uow;
            };

            customerRepository.GetGuid = (guid) =>
            {
                var customer = CustomerFactory.CreateCustomer("Jhon",
                                                               "El rojo",
                                                               "+3434",
                                                               "company",
                                                               country,
                                                               new Address("city", "zipCode", "address line", "address line"));
                customer.ChangeCurrentIdentity(customerId);

                return customer;
            };

            customerRepository.MergeCustomerCustomer = (persistent, current) =>
            {
                Assert.AreEqual(persistent, current);
                Assert.IsTrue(persistent != null);
                Assert.IsTrue(current != null);
            };

            var customerManagementService = new CustomerAppService(countryRepository, customerRepository);

            var customerDTO = new CustomerDTO() //missing lastname
            {
                Id = customerId,
                CountryId = country.Id,
                FirstName = "Jhon",
                LastName = "El rojo",
            };

            //act
            customerManagementService.UpdateCustomer(customerDTO);
        }
        public void AddNewCustomerThrowApplicationErrorsWhenEntityIsNotValid()
        {
            //Arrange
            var countryId = Guid.NewGuid();

            var countryRepository = new SICountryRepository();
            countryRepository.GetGuid = (guid)=>
            {
                var country = new Country("spain", "es-ES");
                country.GenerateNewIdentity();

                return country;
            };
            var customerRepository = new SICustomerRepository();
            customerRepository.AddCustomer = (customer) => { };
            customerRepository.UnitOfWorkGet = () =>
            {
                var uow = new SIUnitOfWork();
                uow.Commit = () => { };

                return uow;
            };

            var customerManagementService = new CustomerAppService(countryRepository, customerRepository);

            var customerDTO = new CustomerDTO() //missing lastname
            {
                CountryId = Guid.NewGuid(),
                FirstName = "Jhon"
            };

            //act
            var result = customerManagementService.AddNewCustomer(customerDTO);
        }
        Customer MaterializeCustomerFromDto(CustomerDTO customerDTO)
        {
            //create the current instance with changes from customerDTO
            var address = new Address(customerDTO.AddressCity, customerDTO.AddressZipCode, customerDTO.AddressAddressLine1, customerDTO.AddressAddressLine2);

            var current = CustomerFactory.CreateCustomer(customerDTO.FirstName,
                                                         customerDTO.LastName,
                                                         customerDTO.Telephone,
                                                         customerDTO.Company,
                                                         customerDTO.CountryId,
                                                         address);

            //set credit
            current.ChangeTheCurrentCredit(customerDTO.CreditLimit);

            //set picture
            var picture = new Picture { RawPhoto = customerDTO.PictureRawPhoto };
            picture.ChangeCurrentIdentity(current.Id);

            current.ChangePicture(picture);

            //set identity
            current.ChangeCurrentIdentity(customerDTO.Id);


            return current;
        }
        /// <summary>
        /// <see cref="M:Microsoft.Samples.NLayerApp.Application.MainBoundedContext.ERPModule.Services.ICustomerManagement.UpdateCustomer"/>
        /// </summary>
        /// <param name="customerDTO"><see cref="M:Microsoft.Samples.NLayerApp.Application.MainBoundedContext.ERPModule.Services.ICustomerManagement.UpdateCustomer"/></param>
        /// <returns><see cref="M:Microsoft.Samples.NLayerApp.Application.MainBoundedContext.ERPModule.Services.ICustomerManagement.UpdateCustomer"/></returns>
        public void UpdateCustomer(CustomerDTO customerDTO)
        {
            if (customerDTO == null || customerDTO.Id == Guid.Empty)
                throw new ArgumentException(Messages.warning_CannotUpdateCustomerWithEmptyInformation);

            //get persisted item
            var persisted = _customerRepository.Get(customerDTO.Id);

            if (persisted != null) //if customer exist
            {
                //materialize from customer dto
                var current = MaterializeCustomerFromDto(customerDTO);

                //Merge changes
                _customerRepository.Merge(persisted, current);

                //commit unit of work
                _customerRepository.UnitOfWork.Commit();
            }
            else
                LoggerFactory.CreateLog().LogWarning(Messages.warning_CannotUpdateNonExistingCustomer);
        }