Как Moq защищен собственности в C#

public class Business {  
    protected List<BusinessRulesDto> BusinessRules { get; set; }  
}

Я старался:

  1. businessMockObject.Protected().SetupSet<List<BusinessRulesDto>>("BusinessRules", ItExpr.IsAny<List<BusinessRulesDto>>()).Verifiable();
    
  2. var businessRulesDtoList = Builder<BusinessRulesDto>.CreateListOfSize(2).Build().ToList();  
    businessMockObject.Protected().SetupGet<List<BusinessRulesDto>>("BusinessRules").Returns(businessRulesDtoList);
    businessMockObject.Protected().SetupSet<List<BusinessRulesDto>>("BusinessRules", ItExpr.IsAny<List<BusinessRulesDto>>()).Verifiable();
    

Я много чего перепробовал, но ничего не получилось. Я умею издеваться над защищенным методом, но не над защищенными свойствами.

Как я могу издеваться над защищенными свойствами?

2 ответа

Согласно документации

Moq 4.8 и более поздние версии позволяют настраивать защищенные элементы с помощью совершенно не связанного типа, который имеет те же элементы и, таким образом, предоставляет информацию о типе, необходимую для работы IntelliSense. Вы также можете использовать этот интерфейс для настройки защищенных обобщенных методов и методов, имеющих параметры by-ref:

Создайте интерфейс в тестовом проекте, чтобы инкапсулировать защищенный элемент, который нужно смоделировать

public interface IBusinessProtectedMembers {  
    List<BusinessRulesDto> BusinessRules { get; set; }  
}

Затем используйте это с макетом, чтобы также воспользоваться IntelliSense

var businessRulesDtoList = Builder<BusinessRulesDto>.CreateListOfSize(2).Build().ToList();
businessMockObject.Protected().As<IBusinessProtectedMembers>()
    .Setup(_ => _.BusinessRules)
    .Returns(businessRulesDtoList);

Наконец, все это зависит от требования Moq о том, что члены, которые должны быть имитированы / заглушены, должны быть виртуальными, чтобы структура могла переопределять элемент.

Что значит Business должен выглядеть так

public class Business {  
    protected virtual List<BusinessRulesDto> BusinessRules { get; set; }  
}

для вышеупомянутого предложения, чтобы работать.

Макет под капотом создает подкласс цели. Всякий раз, когда целью является конкретный класс (не интерфейс), методы, которые вы хотите смоделировать, должны быть виртуальными, в противном случае подкласс не может переопределить его и предоставить Setupped функциональность.

Другие вопросы по тегам