xUnit testing using in-memory database for PUT method

Viewed 36

I have been trying to do an X unit test for the repository using an in-memory database. I am unable to perform the update function. my test case is throwing an exception.

The code which I have written namespace for testing the repository

using AmazonAPI.Models;
using AmazonAPI.Repository;
using FakeItEasy;
using FluentAssertions;
using Microsoft.AspNetCore.Identity;
using Microsoft.EntityFrameworkCore;
using System.ComponentModel.DataAnnotations;
using System.Threading.Tasks;

namespace AmazonAPITesting.Amazon_Repository
{
    public class Amazon_Merchant_Repository
    {
        
        private async Task<AmazonContext> GetDatabaseContext()
        {
            var options = new DbContextOptionsBuilder<AmazonContext>()
                            .UseInMemoryDatabase(databaseName: Guid.NewGuid().ToString())
                            .Options;
            var databaseContext = new AmazonContext(options);
            databaseContext.Database.EnsureCreated();
            int temp = 1000;
            if (await databaseContext.Merchants.CountAsync() <= 0)
            {
                for(int i = 0; i < 10; i++)
                {
                    databaseContext.Merchants.Add(
                        new Merchant()
                        {
                            MerchantId = temp++,
                            MerchantEmail = "akhil"+i+"@gmail.com",
                            MerchantName = "akhil"+i,
                            MerchantPassword = "12345",
                            ConfirmPassword = "12345",
                        }

                        );
                    
                    
                    await databaseContext.SaveChangesAsync();

                }
            }
            return databaseContext;


        }

        [Fact]
        public async Task UpdateMerchant_Merchant()
        {
            //Arrange

            var Id = 1001;
            Merchant merchant = new Merchant
            {
                MerchantId = Id,
                MerchantEmail = "akhil1@gmail.com",
                MerchantName = "updatedAkhil",
                MerchantPassword = "12345",
                ConfirmPassword = "12345",
            };
            var dbContext = await GetDatabaseContext();
            var merchantRepository = new MerchantRepository(dbContext);
            

            //Act
            var result = await merchantRepository.UpdateMerchant(Id,merchant);
            //Assert

            var name = result.MerchantName;
            "updatedAkhil".Should().BeEquivalentTo(name);

        }
        


    }
}

The real method in repository

public async Task<Merchant> UpdateMerchant(int MerchantId, Merchant Merchant)
{
    //Merchant _merchant = await _context.Merchants.FindAsync(MerchantId);
    _context.Update(Merchant);
    _context.SaveChanges();
    return Merchant;

}

the merchant model

public class Merchant
{
    [Key]
    public int MerchantId { get; set; }

    [Required(ErrorMessage = "Field can't be empty")]
    [DataType(DataType.EmailAddress, ErrorMessage = "E-mail is not valid")]
    public string? MerchantEmail { get; set; }

    public string? MerchantName { get; set; }

    [DataType(DataType.PhoneNumber)]
    [Display(Name = "Phone Number")]

    public string? MerchantPhoneNumber { get; set; }
    [Display(Name = "Please enter password"), MaxLength(20)]
    public string? MerchantPassword { get; set; }
    [NotMapped]

    [Display(Name = "ConfirmPassword")]
    [Compare("MerchantPassword", ErrorMessage = "Passwords do not match")]
    public string? ConfirmPassword { get; set; }
   

    
}

the exception which i got fron=m the test case Message:  System.InvalidOperationException : The instance of entity type 'Merchant' cannot be tracked because another instance with the same key value for {'MerchantId'} is already being tracked. When attaching existing entities, ensure that only one entity instance with a given key value is attached. Consider using 'DbContextOptionsBuilder.EnableSensitiveDataLogging' to see the conflicting key values.

Stack Trace:  IdentityMap1.ThrowIdentityConflict(InternalEntityEntry entry) IdentityMap1.Add(TKey key, InternalEntityEntry entry, Boolean updateDuplicate) IdentityMap1.Add(TKey key, InternalEntityEntry entry) IdentityMap1.Add(InternalEntityEntry entry) StateManager.StartTracking(InternalEntityEntry entry) InternalEntityEntry.SetEntityState(EntityState oldState, EntityState newState, Boolean acceptChanges, Boolean modifyProperties) InternalEntityEntry.SetEntityState(EntityState entityState, Boolean acceptChanges, Boolean modifyProperties, Nullable1 forceStateWhenUnknownKey) EntityGraphAttacher.PaintAction(EntityEntryGraphNode1 node) EntityEntryGraphIterator.TraverseGraph[TState](EntityEntryGraphNode1 node, Func2 handleNode) EntityGraphAttacher.AttachGraph(InternalEntityEntry rootEntry, EntityState targetState, EntityState storeGeneratedWithKeySetTargetState, Boolean forceStateWhenUnknownKey) DbContext.SetEntityState(InternalEntityEntry entry, EntityState entityState) DbContext.SetEntityState[TEntity](TEntity entity, EntityState entityState) DbContext.Update[TEntity](TEntity entity) MerchantRepository.UpdateMerchant(Int32 MerchantId, Merchant Merchant) line 90 Amazon_Merchant_Repository.UpdateMerchant_Merchant() line 109 --- End of stack trace from previous location ---

this is my repository [link]https://github.com/Akhil1812007/AmazonAPI-Test , can someone help me to resolve this problem ,by helping me how to do put actions in the Xunit test

0 Answers
Related