public async Task Should_Be_Able_To_Mark_Pokemon_As_Seen()
        {
            // Arrange
            var rnd = new Random();
            var id  = rnd.Next(1, 152);

            var fakePokemon = BogusDomain.PokemonFaker();

            pokemonRepository.Setup(x => x.ExistsById(id)).ReturnsAsync(true);
            pokemonRepository.Setup(x => x.FindById(id)).ReturnsAsync(fakePokemon);
            pokemonRepository.Setup(x => x.SaveChangesToDatabase());
            mapper.Setup(x => x.Map <PokemonViewModel>(fakePokemon))
            .Returns(() => new PokemonViewModel()
            {
                Id             = fakePokemon.Id,
                Name           = fakePokemon.Name,
                EvolutionLevel = fakePokemon.EvolutionLevel,
                LevelingRate   = fakePokemon.LevelingRate,
                CatchRate      = fakePokemon.CatchRate,
                HatchTime      = fakePokemon.HatchTime,
                Seen           = fakePokemon.Seen,
                Captured       = fakePokemon.Captured,
            });

            // Act
            var response = await pokemonServices.MarkPokemonAsSeen(id);

            // Assert
            Assert.NotNull(response);
            Assert.True(response.Seen);
        }
        public async Task Should_Not_Create_Pokemon_If_Any_Abilities_Not_Exist(
            bool abilityPresent, bool hiddenAbilityPresent
            )
        {
            // Arrange
            var pokemon = BogusDomain.PokemonFaker();

            var stats = BogusDomain.StatsFaker();

            var abilities = BogusDomain.AbilitiesFaker();

            var data = BogusViewModel.PokemonViewModelFaker(pokemon, stats, abilities);

            mapper.Setup(x => x.Map <Pokemon>(data)).Returns(pokemon);
            mapper.Setup(x => x.Map <Stats>(data.Stats)).Returns(stats);
            pokemonRepository.Setup(x => x.ExistsById(pokemon.Id)).ReturnsAsync(false);
            pokemonRepository.Setup(x => x.ExistsByName(pokemon.Name))
            .ReturnsAsync(false);
            pokemonRepository.Setup(x => x.CreatePokemon(pokemon))
            .ReturnsAsync(pokemon);
            statsRepository.Setup(x => x.CreateStats(stats))
            .ReturnsAsync(stats);
            abilitiesRepository.Setup(x => x.ExistsById(abilities[0].Id))
            .ReturnsAsync(abilityPresent);
            abilitiesRepository.Setup(x => x.ExistsById(abilities[1].Id))
            .ReturnsAsync(hiddenAbilityPresent);

            // Act

            // Assert
            await Assert.ThrowsAsync <AbilityException>(
                () => pokemonServices.CreatePokemon(data)
                );
        }
        public async Task Should_Not_Be_Able_To_Add_Pre_Evolution_If_Base_Pokemon_Already_Has_Pre_Evolution()
        {
            // Arrange
            var rnd           = new Random();
            var data          = BogusViewModel.EvolutionViewModelFaker();
            var mappedPokemon = BogusViewModel.PokemonViewModelFaker();

            mappedPokemon.Abilities = null;
            mappedPokemon.Stats     = null;

            var pokemon             = BogusDomain.PokemonFaker();
            var preEvolutionPokemon = BogusDomain.PokemonFaker();

            pokemon.Id             = data.pokemonId;
            pokemon.PreEvolutionId = rnd.Next(1, 152);
            preEvolutionPokemon.Id = data.pokemonEvolutionId - 2;

            pokemonRepository.Setup(x => x.ExistsById(data.pokemonId)).ReturnsAsync(true);
            pokemonRepository.Setup(x => x.ExistsById(data.pokemonEvolutionId)).ReturnsAsync(true);
            pokemonRepository.Setup(x => x.FindById(data.pokemonId)).ReturnsAsync(pokemon);
            pokemonRepository.Setup(x => x.FindById(data.pokemonEvolutionId)).ReturnsAsync(
                preEvolutionPokemon
                );

            // Act

            // Assert
            await Assert.ThrowsAsync <PokemonException>(
                () => pokemonServices.AddPokemonPreEvolution(data)
                );
        }
        public async Task Should_Not_Be_Able_To_Add_Pre_Evolution_If_Pre_Evolution_Pokemon_Not_Exist()
        {
            // Arrange
            var data = BogusViewModel.EvolutionViewModelFaker();

            var pokemon = BogusDomain.PokemonFaker();

            pokemonRepository.Setup(x => x.ExistsById(data.pokemonId)).ReturnsAsync(true);
            pokemonRepository.Setup(x => x.ExistsById(data.pokemonEvolutionId)).ReturnsAsync(false);
            pokemonRepository.Setup(x => x.FindById(data.pokemonId)).ReturnsAsync(pokemon);

            // Act

            // Asert
            await Assert.ThrowsAsync <PokemonException>(
                () => pokemonServices.AddPokemonPreEvolution(data)
                );
        }
        public async Task Should_Not_Be_Able_To_Mark_Pokemon_As_Seen_If_Already_Marked()
        {
            // Arrange
            var rnd = new Random();
            var id  = rnd.Next(1, 152);

            var fakePokemon = BogusDomain.PokemonFaker();

            fakePokemon.Seen = true;

            pokemonRepository.Setup(x => x.ExistsById(id)).ReturnsAsync(false);
            pokemonRepository.Setup(x => x.FindById(id)).ReturnsAsync(fakePokemon);

            // Act

            // Assert
            await Assert.ThrowsAsync <PokemonException>(
                () => pokemonServices.MarkPokemonAsSeen(id)
                );
        }
        public async Task Should_Not_Create_Pokemon_If_Number_Not_Unique()
        {
            // Arrange
            var pokemon = BogusDomain.PokemonFaker();

            var stats = BogusDomain.StatsFaker();

            var abilities = BogusDomain.AbilitiesFaker();

            var data = BogusViewModel.PokemonViewModelFaker(pokemon, stats, abilities);

            mapper.Setup(x => x.Map <Pokemon>(data)).Returns(pokemon);
            pokemonRepository.Setup(x => x.ExistsById(pokemon.Id)).ReturnsAsync(true);

            // Act

            // Assert
            await Assert.ThrowsAsync <PokemonException>(
                () => pokemonServices.CreatePokemon(data)
                );
        }
        public async Task Should_Be_Able_To_Add_Pre_Evolution_Pokemon_To_Pokemon()
        {
            // Arrange
            var data          = BogusViewModel.EvolutionViewModelFaker();
            var mappedPokemon = BogusViewModel.PokemonViewModelFaker();

            mappedPokemon.Abilities = null;
            mappedPokemon.Stats     = null;

            var pokemon             = BogusDomain.PokemonFaker();
            var preEvolutionPokemon = BogusDomain.PokemonFaker();

            pokemon.Id             = data.pokemonId;
            preEvolutionPokemon.Id = data.pokemonEvolutionId - 2;

            pokemonRepository.Setup(x => x.ExistsById(data.pokemonId)).ReturnsAsync(true);
            pokemonRepository.Setup(x => x.ExistsById(data.pokemonEvolutionId)).ReturnsAsync(true);
            pokemonRepository.Setup(x => x.FindById(data.pokemonId)).ReturnsAsync(pokemon);
            pokemonRepository.Setup(x => x.FindById(data.pokemonEvolutionId)).ReturnsAsync(
                preEvolutionPokemon
                );
            pokemonRepository.Setup(x => x.SaveChangesToDatabase());

            mapper.Setup(x => x.Map <PokemonViewModel>(pokemon)).Returns(() => {
                mappedPokemon.Id             = data.pokemonId;
                mappedPokemon.PreEvolutionId = data.pokemonEvolutionId;

                return(mappedPokemon);
            });

            // Act
            var response = await pokemonServices.AddPokemonPreEvolution(data);

            // Assert
            Assert.Equal(data.pokemonId, response.Id);
            Assert.Equal(data.pokemonEvolutionId, response.PreEvolutionId);
        }
        public async Task Should_Be_Able_To_Create_New_Pokemon()
        {
            // Arrange
            var pokemon = BogusDomain.PokemonFaker();

            var stats = BogusDomain.StatsFaker();

            var abilities = BogusDomain.AbilitiesFaker();

            var data  = BogusViewModel.PokemonViewModelFaker(pokemon, stats, abilities);
            var photo = LoadPokemonPhoto();

            data.PokemonPhoto = photo;

            var response = new PokemonViewModel()
            {
                Id             = pokemon.Id,
                Name           = pokemon.Name,
                EvolutionLevel = pokemon.EvolutionLevel,
                LevelingRate   = pokemon.LevelingRate,
                CatchRate      = pokemon.CatchRate,
                HatchTime      = pokemon.HatchTime,
                CreatedAt      = pokemon.CreatedAt,
            };

            var statsViewModel = data.Stats;

            var abilityViewModel = new AbilityViewModel()
            {
                Id     = abilities[0].Id,
                Name   = abilities[0].Name,
                Effect = abilities[0].Effect,
            };

            var hiddenAbilityViewModel = new AbilityViewModel()
            {
                Id     = abilities[1].Id,
                Name   = abilities[1].Name,
                Effect = abilities[1].Effect,
            };

            mapper.Setup(x => x.Map <Pokemon>(data)).Returns(pokemon);
            mapper.Setup(x => x.Map <Stats>(data.Stats)).Returns(stats);
            pokemonRepository.Setup(x => x.ExistsById(pokemon.Id)).ReturnsAsync(false);
            pokemonRepository.Setup(x => x.ExistsByName(pokemon.Name))
            .ReturnsAsync(false);
            abilitiesRepository.Setup(x => x.ExistsById(
                                          abilities[0].Id
                                          )).ReturnsAsync(true);
            abilitiesRepository.Setup(x => x.ExistsById(
                                          abilities[1].Id
                                          )).ReturnsAsync(true);
            storageProvider.Setup(x => x.SaveFile(photo)).Returns(Guid.NewGuid().ToString());
            pokemonRepository.Setup(x => x.CreatePokemon(pokemon))
            .ReturnsAsync(pokemon);
            statsRepository.Setup(x => x.CreateStats(stats))
            .ReturnsAsync(stats);
            pokemonRepository.Setup(x => x.CreatePokemonAbility(
                                        data.Id, data.Abilities[0].Id
                                        )).ReturnsAsync(new PokemonAbility()
            {
                PokemonId = data.Id,
                AbilityId = data.Abilities[0].Id
            });
            pokemonRepository.Setup(x => x.CreatePokemonAbility(
                                        data.Id, data.Abilities[1].Id
                                        )).ReturnsAsync(new PokemonAbility()
            {
                PokemonId = data.Id,
                AbilityId = data.Abilities[1].Id
            });
            abilitiesRepository.Setup(x => x.FindByPokemonId(data.Id))
            .ReturnsAsync(new List <Ability>()
            {
                abilities[0],
                abilities[1]
            });
            mapper.Setup(x => x.Map <PokemonViewModel>(pokemon)).Returns(
                response
                );
            mapper.Setup(x => x.Map <StatsViewModel>(stats)).Returns(
                statsViewModel
                );
            mapper.Setup(x => x.Map <List <AbilityViewModel> >(abilities)).Returns(
                new List <AbilityViewModel>()
            {
                abilityViewModel,
                hiddenAbilityViewModel
            }
                );

            // Act
            var result = await pokemonServices.CreatePokemon(data);

            // Assert
            Assert.IsType <PokemonViewModel>(result);
            Assert.IsType <StatsViewModel>(result.Stats);
            Assert.IsType <List <AbilityViewModel> >(result.Abilities);
            Assert.Equal(pokemon.Id, result.Id);
            Assert.Equal(stats.Total, result.Stats.Total);
            Assert.Equal(2, result.Abilities.Count);
            Assert.Equal(
                DateTime.Today.ToLocalTime().Date,
                result.CreatedAt.ToLocalTime().Date
                );
        }