2011-08-21 21 views

Odpowiedz

3

Ogólnie rzecz biorąc, jest to zła droga do zejścia, aby polegać na rejestrowaniu testów i. Wynik pozytywny/negatywny powinien być wynikiem testów. I po prostu nie powinni wchodzić na scenę, na której jest wystarczająco dużo rzeczy, które będą wymagały patrzenia na ślad.

Na xunit.gui.exe widać komunikat Konsola i dane śledzenia, xunit.console.exe. Jeśli jest to ważne, możesz podłączyć TraceListener, który przekierowuje do pliku, tworząc odpowiednie standardowe wpisy .NET config (Theres 'a FileWriterTraceListener, które powinieneś być w stanie podłączyć, jeśli google to).


UPDATE: Jak omówiono his blog post Damian Hickey ma dobry przykład możliwego substytut - rejestrowanie okablowania do xUnit 2 ITestOutputHelper jak wykazano w https://github.com/damianh/CapturingLogOutputWithXunit2AndParallelTests/blob/master/src/Lib.Tests/Tests.cs

UPDATE 2: W niektórych przypadkach, można dodać rejestrowanie i karmić go do ITestOutputHelper bez angażowania LogContext za pomocą prostego adaptera następująco (i tylko mieć go w F #, przepraszam):

// Requirement: Make SUT depend on Serilog NuGet 
// Requirement: Make Tests depend on Serilog.Sinks.Observable 

type TestOutputAdapter(testOutput : Xunit.Abstractions.ITestOutputHelper) = 
    let formatter = Serilog.Formatting.Display.MessageTemplateTextFormatter(
     "{Timestamp:yyyy-MM-dd HH:mm:ss.fff zzz} [{Level}] {Message}{NewLine}{Exception}", null); 
    let write logEvent = 
     use writer = new System.IO.StringWriter() 
     formatter.Format(logEvent, writer); 
     writer |> string |> testOutput.WriteLine 
    member __.Subscribe(source: IObservable<Serilog.Events.LogEvent>) = 
     source.Subscribe write 

let createLogger hookObservers = 
    LoggerConfiguration() 
     .WriteTo.Observers(Action<_> hookObservers) 
     .CreateLogger() 
let createTestOutputLogger (output: ITestOutputHelper) = 
    let adapter = TestOutputAdapter testOutputHelper 
    createLogger (adapter.Subscribe >> ignore) 

type Tests(testOutputHelper) = 
    let log = createTestOutputLogger testOutputHelper 

    [<Fact>] let feedToSut() = 
     // TODO pass log to System Under Test either as a ctor arg or a method arg 

Różnica w Takie podejście w porównaniu z kontekstem logu polega na tym, że logowanie do globalnego [kontekstualizowanego] Seriloga Logger nie zostanie odebrane.

+1

Dziękuję za odpowiedź. Używałem xunit.console.exe. Mam świadomość, że to nie jest dobre rozwiązanie, a tak naprawdę nie było to zamierzone użycie. Powodem, dla którego go potrzebowałem, było debugowanie operacji łańcuchowych podczas tworzenia nowej klasy przy użyciu TDD. – kfuglsang

+0

Osobiście ustawiłbym w tym przypadku xunit.console.exe jako projekt startowy w debugerze. BTW TeamCity i inne środowiska działające w podobnym środowisku przechwytują wyniki testów, gdy szukasz –

+0

@downvoter Dlaczego? (Przy okazji w V2 zaplanowano prace mające na celu powstrzymanie połknięcia danych ...) –

2

Istnieje rozwiązanie, jak znaleźć tutaj: https://xunit.codeplex.com/discussions/211566

Wystarczy dodać do tego konstruktora lub metody gdzie chcesz Wyjście diagnostyczne:

Debug.Listeners.Add(new DefaultTraceListener()); 
+1

W przypadku późniejszego strojenia, nie jest to już zalecana praktyka. Zobacz http://xunit.github.io/docs/capturing-output.html. –

+4

Oh man tych xunit guys, jeśli to nie jest wystarczająco skomplikowane to nie jest xunit -.- Ofc nie ma IMessageSink na .Net Core .... MsTestV2 na ratunek! – MushyPeas

24

Sytuacja zmieniła się trochę z xUnit.net 2. Wiem, że pytanie dotyczy wcześniejszej wersji, ale ponieważ ludzie wylądują tutaj po aktualizacji, pomyślałem, że warto to wskazać.

Aby zobaczyć jakieś wyjście na wyjściu testowym w wersji 2 trzeba będzie wziąć zależność w swojej klasie testowej (poprzez argument konstruktora) na wystąpienie ITestOutputHelper, a następnie użyć metody WriteLine na tym interfejsie . Np .:

public class MyTestSpec 
{ 
    private readonly ITestOutputHelper _testOutputHelper; 

    public MyTestSpec(ITestOutputHelper testOutputHelper) 
    { 
    _testOutputHelper = testOutputHelper; 
    } 

    [Fact] 
    public void MyFact() 
    { 
    _testOutputHelper.WriteLine("Hello world"); 
    } 
} 

Można wybrać, aby podłączyć swoje ramy rejestrowania do tego interfejsu, może przez wstrzykiwanie ILog realizację że przekazane wszystkie połączenia do ITestOutpuHelper.

Przyjmuję do wiadomości, że nie będziesz chciał tego robić domyślnie, ale od czasu do czasu może to być przydatne. Dotyczy to szczególnie sytuacji, w której testy zakończą się niepowodzeniem na serwerze testowym opartym na chmurze, &!

+1

Nawiasem mówiąc, ITestOutputHelper znajduje się w przestrzeni nazw Xunit.Abstractions. – Syndog

+0

[oficjalny przykładowy kod] (https://github.com/xunit/samples.xunit/blob/master/TestOutputExample/Example.cs). Nadal działa na podstawowych projektach .NET. – zwcloud

+0

Co się stanie, jeśli już masz niestandardową instancję obiektu (np. 'MyDatabaseFixture') przekazaną w tym konstruktorze MyTestSpec zamiast' ITestOutputHelper'? –

1

To może pomóc, jeśli Console.Write jest osadzony głęboko w dół jakąś klasę hierarchię że nie chcesz byłaby:

public MyTestClass(ITestOutputHelper output) 
    { 
     var converter = new Converter(output); 
     Console.SetOut(converter); 
    } 

    private class Converter : TextWriter 
    { 
     ITestOutputHelper _output; 
     public Converter(ITestOutputHelper output) 
     { 
      _output = output; 
     } 
     public override Encoding Encoding 
     { 
      get { return Encoding.Whatever; } 
     } 
     public override void WriteLine(string message) 
     { 
      _output.WriteLine(message); 
     } 
     public override void WriteLine(string format, params object[] args) 
     { 
      _output.WriteLine(format, args); 
     } 
    } 
Powiązane problemy