Observação
O acesso a essa página exige autorização. Você pode tentar entrar ou alterar diretórios.
O acesso a essa página exige autorização. Você pode tentar alterar os diretórios.
Tipos de correção é uma das duas tecnologias que os usos de Framework de falsificação do Microsoft deixar facilmente isolar componentes no teste de ambiente.As correções desviam chamadas para métodos específicos para o código que você escreve como parte do seu teste.Muitos métodos retorna os resultados diferentes dependentes em condições externos, mas uma correção está sob o controle do seu teste e pode retornar resultados consistentes em cada chamada.Isso facilita escrever seus testes muito.
Use correções para isolar o código de assemblies que não são parte de sua solução.Para isolar componentes de sua solução de se, recomendamos que você usa modelos.
Para uma orientação da visão geral e de início rápido, consulte Isolando código em teste com falsificação da Microsoft
Requisitos
- Visual Studio Ultimate
Consulte Exibição (1h16): Testando o código Un- testavel com as falsificação no Visual Studio 2012
Neste tópico
Aqui é o que você aprenderá neste tópico:
Adicionar conjuntos de falsificação
Use ShimsContext
Escreva testando com correções
Correções para tipos diferentes de métodos
Alterar o comportamento padrão
Chamando o método original do método corretivo
Exemplo: O erro de Y2K
Vamos considerar um método que lança uma exceção º de janeiro de 2000:
// code under test
public static class Y2KChecker {
public static void Check() {
if (DateTime.Now == new DateTime(2000, 1, 1))
throw new ApplicationException("y2kbug!");
}
}
Testar esse método é particularmente problemático porque o programa depende de DateTime.Now, um método que depende do relógio do computador, um ambiente- dependente, método não determinística.Além disso, DateTime.Now é uma propriedade estática para que um tipo de stub não pode ser usado aqui.Esse problema é sintomático do problema de isolamento em testes de unidade: os programas que chamam diretamente nas APIs de banco de dados, se comunicam com os serviços da Web, são e assim por diante difícil para o teste de unidade porque sua lógica depende de ambiente.
Isso é onde os tipos de correção devem ser usados.Os tipos de correção fornecem um mecanismo para detour qualquer método .NET a um delegado definido pelo usuário.Os tipos de correção são gerados pelo gerador de falsificação, e usam os representantes, nós que chamamos tipos corretivos, para especificar as novas implementações de método.
O teste a seguir mostra como usar o tipo corretivo, ShimDateTime, para fornecer uma implementação personalizada de DateTime.Now:
//unit test code
// create a ShimsContext cleans up shims
using (ShimsContext.Create()
// hook delegate to the shim method to redirect DateTime.Now
// to return January 1st of 2000
ShimDateTime.NowGet = () => new DateTime(2000, 1, 1);
Y2KChecker.Check();
}
Como usar correções
Adicionar conjuntos de falsificação
No solution Explorer, expanda Referênciasdo seu projeto de teste de unidade.
- Se você estiver trabalhando em Visual Basic, você deve selecionar Mostrar todos os arquivos na barra de ferramentas do Gerenciador de soluções, para ver a lista de referências.
Selecione o assembly que contém as definições de classes que você deseja criar correções.Por exemplo, se você deseja calçar DateTime, selecione System.dll
No menu de atalho, escolha Adicione o conjunto de falsificação.
Use ShimsContext
Quando usar corretivo digite uma estrutura de testes de unidade, você deve encapsular código de teste em ShimsContext para controlar o tempo de vida das correções.Se nós não exigimos isso, as correções duraram até que o Appdomain é desligado.A maneira mais fácil de criar ShimsContext é usando o método estático Create() conforme mostrado no código o seguir:
//unit test code
[Test]
public void Y2kCheckerTest() {
using(ShimsContext.Create()) {
...
} // clear all shims
}
É importante adequadamente exibir cada contexto corretivo.Em geral, chame sempre ShimsContext.Create em uma instrução de using para garantir que o esclarecimento apropriado de correções registrados.Por exemplo, você pode registrar uma correção para um método de teste que substituísse o método de DateTime.Now com um delegado que sempre retorna o primeiro de janeiro de 2000.Se você esquece desmarque a correção registrada no método de teste, o resto de ensaio retornaria sempre o primeiro de janeiro de 2000 porque o valor de DateTime.Now.Isso pode ser surpreendente e confuso.
Escreva um teste com correções
No seu código de teste, insira um rodeio para o método que você deseja falsificar.Por exemplo:
[TestClass]
public class TestClass1
{
[TestMethod]
public void TestCurrentYear()
{
int fixedYear = 2000;
using (ShimsContext.Create())
{
// Arrange:
// Detour DateTime.Now to return a fixed date:
System.Fakes.ShimDateTime.NowGet =
() =>
{ return new DateTime(fixedYear, 1, 1); };
// Instantiate the component under test:
var componentUnderTest = new MyComponent();
// Act:
int year = componentUnderTest.GetTheCurrentYear();
// Assert:
// This will always be true if the component is working:
Assert.AreEqual(fixedYear, year);
}
}
}
<TestClass()> _
Public Class TestClass1
<TestMethod()> _
Public Sub TestCurrentYear()
Using s = Microsoft.QualityTools.Testing.Fakes.ShimsContext.Create()
Dim fixedYear As Integer = 2000
' Arrange:
' Detour DateTime.Now to return a fixed date:
System.Fakes.ShimDateTime.NowGet = _
Function() As DateTime
Return New DateTime(fixedYear, 1, 1)
End Function
' Instantiate the component under test:
Dim componentUnderTest = New MyComponent()
' Act:
Dim year As Integer = componentUnderTest.GetTheCurrentYear
' Assert:
' This will always be true if the component is working:
Assert.AreEqual(fixedYear, year)
End Using
End Sub
End Class
Os nomes de classe corretivos são compostos Fakes.Shim prefixando o nome do tipo original.
As correções funcionam inserindo rodeios no código do aplicativo no teste.Onde uma chamada para o método original ocorre, as falsificação que o sistema executa um rodeio, de modo que em vez de chamada do método real, seu código corretivo é chamado.
Observe que os rodeios são criados e excluídos em tempo de execução.Você sempre deve criar um rodeio dentro de vida de ShimsContext.Quando é descartada, algumas correções que você criou quando foi ativa é removida.A melhor maneira de fazer isso é dentro de uma instrução de using .
Você pode ver um erro de compilação que indica que o namespace de falsificação não existe.Este erro aparece as vezes quando existem outros erros de compilação.Corrigir os outros erros e desaparecerá.
Correções para tipos diferentes de métodos
Os tipos de correção permitem que você substitua todo o método .NET, incluindo métodos estáticos ou não métodos virtuais, com seus próprios representantes.
Métodos estáticos
As propriedades para anexar correções para métodos estáticos são colocadas em um tipo corretivo.Cada propriedade tem apenas um setter que pode ser usado para anexar um representante para o método de destino.Por exemplo, dado uma classe MyClass com um método estático MyMethod:
//code under test
public static class MyClass {
public static int MyMethod() {
...
}
}
Nós podemos anexar uma correção a MyMethod que sempre retorna 5:
// unit test code
ShimMyClass.MyMethod = () =>5;
Métodos de instância (para todas as instâncias)
Da mesma forma que os métodos estáticos, os métodos de instância podem ser calçados para todas as instâncias.As propriedades para anexar as correções são colocadas em um tipo aninhado chamado AllInstances para evitar confusão.Por exemplo, dado uma classe MyClass com um método de instância MyMethod:
// code under test
public class MyClass {
public int MyMethod() {
...
}
}
Você pode anexar uma correção a MyMethod que sempre retorna 5, independentemente da instância:
// unit test code
ShimMyClass.AllInstances.MyMethod = () => 5;
A estrutura gerado de tipo de aspectos de ShimMyClass como o seguinte código:
// Fakes generated code
public class ShimMyClass : ShimBase<MyClass> {
public static class AllInstances {
public static Func<MyClass, int>MyMethod {
set {
...
}
}
}
}
Observe que as falsificação passam a instância de tempo de execução como o primeiro argumento do delegado nesse caso.
Métodos como exemplo métodos (para uma instância de tempo de execução)
Os métodos de instância também podem ser calçados por destinos diferentes, com base no receptor de chamada.Isso permite que o mesmo método de instância para ter diferentes comportamentos por instância do tipo.As propriedades para configurar as correções são os métodos do tipo corretivo próprios de instância.Cada tipo corretivo instanciado também é associado com uma instância de um tipo " bruto " calçado.
Por exemplo, dado uma classe MyClass com um método de instância MyMethod:
// code under test
public class MyClass {
public int MyMethod() {
...
}
}
Nós podemos configurar dois tipos de corretivos MyMethod como a primeira sempre retorna 5 e o segundo sempre retorna 10:
// unit test code
var myClass1 = new ShimMyClass()
{
MyMethod = () => 5
};
var myClass2 = new ShimMyClass { MyMethod = () => 10 };
A estrutura gerado de tipo de aspectos de ShimMyClass como o seguinte código:
// Fakes generated code
public class ShimMyClass : ShimBase<MyClass> {
public Func<int> MyMethod {
set {
...
}
}
public MyClass Instance {
get {
...
}
}
}
A instância calçada real do tipo pode ser acessada através da propriedade da instância:
// unit test code
var shim = new ShimMyClass();
var instance = shim.Instance;
O tipo corretivo também tem uma conversão implícita para o tipo calçado portanto, você geralmente pode simplesmente usar o tipo corretivo como é:
// unit test code
var shim = new ShimMyClass();
MyClass instance = shim; // implicit cast retrieves the runtime
// instance
Construtores
Construtores podem também ser calçados para anexar tipos corretivos a objetos futuros.Cada construtor é exposta como um construtor estático do método no tipo corretivo.Por exemplo, dado uma classe MyClass com um construtor que aceita um inteiro:
// code under test
public class MyClass {
public MyClass(int value) {
this.Value = value;
}
...
}
Nós configuramos o tipo corretivo do construtor de modo que cada instância futura retorna -5 quando o getter do valor é chamado, independentemente do valor no construtor:
// unit test code
ShimMyClass.ConstructorInt32 = (@this, value) => {
var shim = new ShimMyClass(@this) {
ValueGet = () => -5
};
};
Observe que cada tipo corretivo expõe dois construtores.O construtor padrão deve ser usado quando uma instância atualizado é necessária, quando o construtor que utiliza uma instância calçada como o argumento deve ser usado em correções do construtor somente:
// unit test code
public ShimMyClass() { }
public ShimMyClass(MyClass instance) : base(instance) { }
A estrutura gerado de tipo de ShimMyClass lembra o código followoing:
// Fakes generated code
public class ShimMyClass : ShimBase<MyClass>
{
public static Action<MyClass, int> ConstructorInt32 {
set {
...
}
}
public ShimMyClass() { }
public ShimMyClass(MyClass instance) : base(instance) { }
...
}
Membros de base
As propriedades corretivos de membros de base podem ser acessadas criando uma correção para o tipo base e passando a instância filho como um parâmetro para o construtor da classe baseia corretivo.
Por exemplo, dado uma classe MyBase com um método de instância MyMethod e um subtipo MyChild:
public abstract class MyBase {
public int MyMethod() {
...
}
}
public class MyChild : MyBase {
}
Nós podemos configurar uma correção de MyBase criando uma nova correção de ShimMyBase :
// unit test code
var child = new ShimMyChild();
new ShimMyBase(child) { MyMethod = () => 5 };
Observe que o tipo corretivo filho é convertido implicitamente à instância filho quando passado como um parâmetro para o construtor corretivo base.
A estrutura gerado de tipo de ShimMyChild e de ShimMyBase é parecida com o seguinte código:
// Fakes generated code
public class ShimMyChild : ShimBase<MyChild> {
public ShimMyChild() { }
public ShimMyChild(Child child)
: base(child) { }
}
public class ShimMyBase : ShimBase<MyBase> {
public ShimMyBase(Base target) { }
public Func<int> MyMethod
{ set { ... } }
}
Construtores estáticos
Os tipos de correção expõe um método StaticConstructor estático para calçar o construtor estático de um tipo.Desde que os construtores estáticos são executadas somente uma vez, você precisará garantir que a correção está configurada antes que qualquer membro de tipo foi acessado.
Finalizers
Finalizers não é suportado em falsificação.
Métodos privados
O gerador de código de falsificação criará propriedades corretivos para os métodos particulares que possuem apenas visível na assinatura, os tipos de parâmetro.. de IE e o tipo de retorno visíveis.
Associando interfaces
Quando um tipo calçado implementa uma interface, o gerador de código emite-se um método que permite que associa todos os membros da interface imediatamente.
Por exemplo, dado MyClass uma classe que implementa IEnumerable<int>:
public class MyClass : IEnumerable<int> {
public IEnumerator<int> GetEnumerator() {
...
}
...
}
Nós podemos calçar as implementações de IEnumerable<int> em MyClass chamando o método bind:
// unit test code
var shimMyClass = new ShimMyClass();
shimMyClass.Bind(new List<int> { 1, 2, 3 });
A estrutura gerado de tipo de ShimMyClass é parecida com o seguinte código:
// Fakes generated code
public class ShimMyClass : ShimBase<MyClass> {
public ShimMyClass Bind(IEnumerable<int> target) {
...
}
}
Alterar o comportamento padrão
Cada tipo corretivo gerado contém uma instância da interface de IShimBehavior , através da propriedade de ShimBase<T>.InstanceBehavior .O comportamento é usado sempre que um cliente chama um membro de instância que não é calçado explicitamente.
Se o comportamento não foi definido explicitamente, usará a instância retornada pela propriedade estática de ShimsBehaviors.Current .Por padrão, essa propriedade retorna um comportamento que lança uma exceção de NotImplementedException .
Esse comportamento pode ser alterado a qualquer momento definindo a propriedade de InstanceBehavior em qualquer instância corretivo.Por exemplo, o seguinte trecho altera a correção a um comportamento que não faz nada ou retorna o valor padrão de retorno com que é, opção (T):
// unit test code
var shim = new ShimMyClass();
//return default(T) or do nothing
shim.InstanceBehavior = ShimsBehaviors.DefaultValue;
O comportamento também pode ser alterado global para todas as instâncias calçadas para a propriedade de InstanceBehavior não foi definida explicitamente definindo a propriedade estática de ShimsBehaviors.Current :
// unit test code
// change default shim for all shim instances
// where the behavior has not been set
ShimsBehaviors.Current =
ShimsBehaviors.DefaultValue;
Detectando acessa de ambiente
É possível anexar um comportamento para todos os membros, incluindo métodos estáticos, de um determinado tipo atribuindo o comportamento de ShimsBehaviors.NotImplemented a propriedade estática Behavior de tipo correspondente corretivo:
// unit test code
// assigning the not implemented behavior
ShimMyClass.Behavior = ShimsBehaviors.NotImplemented;
// shorthand
ShimMyClass.BehaveAsNotImplemented();
Concorrência
Os tipos de correção aplicam-se a todos os segmentos em Appdomain e não se têm afinidade de threads.Este é um importante fato se você planejar usar um corredor de teste que suporta concorrência: os testes que envolvem tipos corretivos não podem executar simultaneamente.Esta propriedade não enfored em tempo de execução de falsificação.
Chamando o método original do método corretivo
Imagine que queremos escrever realmente o texto para o sistema de arquivos após validar o nome de arquivo passado para o método.Nesse caso, é desejaríamos para chamar o método original no meio do método corretivo.
A primeira abordagem para resolver esse problema é envolver uma chamada para o método original usando um representante e ShimsContext.ExecuteWithoutShims() como no código a seguir:
// unit test code
ShimFile.WriteAllTextStringString = (fileName, content) => {
ShimsContext.ExecuteWithoutShims(() => {
Console.WriteLine("enter");
File.WriteAllText(fileName, content);
Console.WriteLine("leave");
});
};
Outra abordagem é definir a correção para nulo, chame o método original e restaurar a correção.
// unit test code
ShimsDelegates.Action<string, string> shim = null;
shim = (fileName, content) => {
try {
Console.WriteLine("enter”);
// remove shim in order to call original method
ShimFile.WriteAllTextStringString = null;
File.WriteAllText(fileName, content);
}
finally
{
// restore shim
ShimFile.WriteAllTextStringString = shim;
Console.WriteLine("leave");
}
};
// initialize the shim
ShimFile.WriteAllTextStringString = shim;
Restrições
As correções não podem ser usadas em todos os tipos de biblioteca mscorlib e Sistemada classe base .NET.
Recursos externos
Orientação
Consulte também
Conceitos
Isolando código em teste com falsificação da Microsoft
Outros recursos
Blog de reitor de Peter: O Visual Studio 2012 correções
Exibição (1h16): Testando o código Un- testavel com as falsificação no Visual Studio 2012