webentwicklung-frage-antwort-db.com.de

Unit Testing: DateTime.Now

Ich habe einige Unit-Tests, von denen erwartet wird, dass die aktuelle Uhrzeit von DateTime abweicht. Jetzt möchte ich natürlich nicht die Uhrzeit des Computers ändern. 

Was ist die beste Strategie, um dies zu erreichen?

124
Pedro

Die best - Strategie besteht darin, die aktuelle Zeit in eine Abstraktion einzuwickeln und diese Abstraktion in den Verbraucher einzufügen .


Alternativ Sie können eine Zeitabstraktion auch als Ambient Context definieren:

public abstract class TimeProvider
{
    private static TimeProvider current =
        DefaultTimeProvider.Instance;

    public static TimeProvider Current
    {
       get { return TimeProvider.current; }
       set 
       {
           if (value == null)
           {
               throw new ArgumentNullException("value");
           }
           TimeProvider.current = value; 
       }
   }

   public abstract DateTime UtcNow { get; }

   public static void ResetToDefault()
   {    
       TimeProvider.current = DefaultTimeProvider.Instance;
   }            
}

Dies ermöglicht es Ihnen, es so zu konsumieren:

var now = TimeProvider.Current.UtcNow;

In einem Komponententest können Sie TimeProvider.Current durch ein Test Double/Mock-Objekt ersetzen. Beispiel mit Moq:

var timeMock = new Mock<TimeProvider>();
timeMock.SetupGet(tp => tp.UtcNow).Returns(new DateTime(2010, 3, 11));
TimeProvider.Current = timeMock.Object;

Denken Sie beim Komponententest mit statischem Status jedoch immer daran, Ihr Fixture herunterzuziehen, indem Sie TimeProvider.ResetToDefault() aufrufen.

181
Mark Seemann

Das sind alles gute Antworten, das habe ich bei einem anderen Projekt gemacht:

Verwendungszweck:

Holen Sie sich das heutige REAL Datum Zeit

var today = SystemTime.Now().Date;

Anstatt DateTime.Now zu verwenden, müssen Sie SystemTime.Now()... verwenden. Es ist nicht schwer zu ändern, aber diese Lösung ist möglicherweise nicht für alle Projekte geeignet.

Zeitreisen (Lets go 5 Jahre in der Zukunft)

SystemTime.SetDateTime(today.AddYears(5));

Get Our Fake "today" (wird 5 Jahre von "today" sein)

var fakeToday = SystemTime.Now().Date;

Datum zurücksetzen

SystemTime.ResetDateTime();

/// <summary>
/// Used for getting DateTime.Now(), time is changeable for unit testing
/// </summary>
public static class SystemTime
{
    /// <summary> Normally this is a pass-through to DateTime.Now, but it can be overridden with SetDateTime( .. ) for testing or debugging.
    /// </summary>
    public static Func<DateTime> Now = () => DateTime.Now;

    /// <summary> Set time to return when SystemTime.Now() is called.
    /// </summary>
    public static void SetDateTime(DateTime dateTimeNow)
    {
        Now = () =>  dateTimeNow;
    }

    /// <summary> Resets SystemTime.Now() to return DateTime.Now.
    /// </summary>
    public static void ResetDateTime()
    {
        Now = () => DateTime.Now;
    }
}

Maulwürfe:

[Test]  
public void TestOfDateTime()  
{  
      var firstValue = DateTime.Now;
      MDateTime.NowGet = () => new DateTime(2000,1,1);
      var secondValue = DateTime.Now;
      Assert(firstValue > secondValue); // would be false if 'moleing' failed
}

Disclaimer - Ich arbeite an Maulwürfen

23
Peli

Sie haben dazu einige Möglichkeiten:

  1. Verwenden Sie ein Mocking-Framework und verwenden Sie ein DateTimeService (Implementieren Sie eine kleine Wrapper-Klasse und fügen Sie sie in den Produktionscode ein). Die Wrapper-Implementierung greift auf DateTime zu. In den Tests können Sie die Wrapper-Klasse simulieren.

  2. Verwenden Sie Typemock Isolator , es kann DateTime.Now fälschen und Sie müssen den zu testenden Code nicht ändern.

  3. Verwenden Sie Moles , es kann auch DateTime.Now fälschen, und es ist keine Änderung des Produktionscodes erforderlich.

Einige Beispiele:

Wrapper-Klasse mit Moq:

[Test]
public void TestOfDateTime()
{
     var mock = new Mock<IDateTime>();
     mock.Setup(fake => fake.Now)
         .Returns(new DateTime(2000, 1, 1));

     var result = new UnderTest(mock.Object).CalculateSomethingBasedOnDate();
}

public class DateTimeWrapper : IDateTime
{
      public DateTime Now { get { return DateTime.Now; } }
}

DateTime direkt mit Isolator fälschen:

[Test]
public void TestOfDateTime()
{
     Isolate.WhenCalled(() => DateTime.Now).WillReturn(new DateTime(2000, 1, 1));

     var result = new UnderTest().CalculateSomethingBasedOnDate();
}

Disclaimer - Ich arbeite bei Typemock

16
Elisha

Fügen Sie eine gefälschte Assembly für System hinzu (klicken Sie mit der rechten Maustaste auf Systemreferenz => Fake Assembly hinzufügen).

Und schreibe in deine Testmethode:

using (ShimsContext.Create())
{
   System.Fakes.ShimDateTime.NowGet = () => new DateTime(2014, 3, 10);
   MethodThatUsesDateTimeNow();
}
9
dave

Ein Thread-sicherer SystemClock, der ThreadLocal<T> verwendet, funktioniert für mich.

ThreadLocal<T> ist in .NET Framework v4.0 und höher verfügbar.

/// <summary>
/// Provides access to system time while allowing it to be set to a fixed <see cref="DateTime"/> value.
/// </summary>
/// <remarks>
/// This class is thread safe.
/// </remarks>
public static class SystemClock
{
    private static readonly ThreadLocal<Func<DateTime>> _getTime =
        new ThreadLocal<Func<DateTime>>(() => () => DateTime.Now);

    /// <inheritdoc cref="DateTime.Today"/>
    public static DateTime Today
    {
        get { return _getTime.Value().Date; }
    }

    /// <inheritdoc cref="DateTime.Now"/>
    public static DateTime Now
    {
        get { return _getTime.Value(); }
    }

    /// <inheritdoc cref="DateTime.UtcNow"/>
    public static DateTime UtcNow
    {
        get { return _getTime.Value().ToUniversalTime(); }
    }

    /// <summary>
    /// Sets a fixed (deterministic) time for the current thread to return by <see cref="SystemClock"/>.
    /// </summary>
    public static void Set(DateTime time)
    {
        if (time.Kind != DateTimeKind.Local)
            time = time.ToLocalTime();

        _getTime.Value = () => time;
    }

    /// <summary>
    /// Resets <see cref="SystemClock"/> to return the current <see cref="DateTime.Now"/>.
    /// </summary>
    public static void Reset()
    {
        _getTime.Value = () => DateTime.Now;
    }
}

Anwendungsbeispiel:

[TestMethod]
public void Today()
{
    SystemClock.Set(new DateTime(2015, 4, 3));

    DateTime expectedDay = new DateTime(2015, 4, 2);
    DateTime yesterday = SystemClock.Today.AddDays(-1D);
    Assert.AreEqual(expectedDay, yesterday);

    SystemClock.Reset();
}
5

In Bezug auf die Antwort von @crabcrusherclamcollector gibt es Probleme, wenn dieser Ansatz in EF-Abfragen verwendet wird (System.NotSupportedException: Der LINQ-Ausdrucksknotentyp 'Invoke' wird in LINQ to Entities nicht unterstützt). Ich habe die Implementierung dahingehend geändert:

public static class SystemTime
    {
        private static Func<DateTime> UtcNowFunc = () => DateTime.UtcNow;

        public static void SetDateTime(DateTime dateTimeNow)
        {
            UtcNowFunc = () => dateTimeNow;
        }

        public static void ResetDateTime()
        {
            UtcNowFunc = () => DateTime.UtcNow;
        }

        public static DateTime UtcNow
        {
            get
            {
                DateTime now = UtcNowFunc.Invoke();
                return now;
            }
        }
    }
5
marcinn

Um einen Code zu testen, der von System.DateTime abhängt, muss der system.dll übergangen werden.

Es gibt zwei Rahmen, von denen ich weiß, dass sie dies tun. Microsoft fakes und Smocks .

Microsoft-Fälschungen erfordern Visual Studio 2012 Ultimatum und funktionieren direkt aus dem Computer.

Smocks ist eine Open Source und sehr einfach zu bedienen. Es kann mit NuGet heruntergeladen werden.

Das Folgende zeigt eine Darstellung von System.DateTime:

Smock.Run(context =>
{
  context.Setup(() => DateTime.Now).Returns(new DateTime(2000, 1, 1));

   // Outputs "2000"
   Console.WriteLine(DateTime.Now.Year);
});
3
persianLife

Ein besonderer Hinweis zum Spott DateTime.Now mit TypeMock ...

Der Wert von DateTime.Now muss in eine Variable eingefügt werden, damit dies korrekt dargestellt wird. Zum Beispiel:

Das funktioniert nicht:

if ((DateTime.Now - message.TimeOpened.Value) > new TimeSpan(1, 0, 0))

Dies tut jedoch:

var currentDateTime = DateTime.Now;
if ((currentDateTime - message.TimeOpened.Value) > new TimeSpan(1, 0, 0))
2
Dave Black

Ich bin auf dasselbe Problem gestoßen, habe aber ein Forschungsprojekt von Microsoft gefunden, das dieses Problem löst.

http://research.Microsoft.com/en-us/projects/moles/

Moles ist ein einfaches Framework für Teststubs und Umwege in .NET, das auf Delegierten basiert. Mole können verwendet werden, um jede .NET-Methode umzuleiten, einschließlich nicht virtueller/statischer Methoden in versiegelten Typen

// Let's detour DateTime.Now
MDateTime.NowGet = () => new DateTime(2000,1, 1);

if (DateTime.Now == new DateTime(2000, 1, 1);
{
    throw new Exception("Wahoo we did it!");
}

Der Beispielcode wurde gegenüber dem Original geändert.

Ich hatte getan, was die DateTime in einem anderen Anbieter vorgeschlagen und abstrahiert hatte. Es fühlte sich einfach falsch an und ich hatte das Gefühl, dass es zu viel war, um es zu testen. Ich werde das heute Abend in mein persönliches Projekt umsetzen.

2
Bobby Cannon

Scheinobjekte.

Eine scheinbare DateTime, die ein Now zurückgibt, das für Ihren Test geeignet ist.

2
S.Lott

Ich bin überrascht, dass niemand einen der naheliegendsten Wege vorgeschlagen hat:

public class TimeDependentClass
{
    public void TimeDependentMethod(DateTime someTime)
    {
        if (GetCurrentTime() > someTime) DoSomething();
    }

    protected virtual DateTime GetCurrentTime()
    {
        return DateTime.Now; // or UtcNow
    }
}

Dann können Sie diese Methode einfach in Ihrem Test-Double überschreiben.

Ich mag es auch, in einigen Fällen eine TimeProvider-Klasse zu injizieren, aber für andere ist das mehr als genug. Ich würde wahrscheinlich die Version TimeProvider bevorzugen, wenn Sie dies in mehreren Klassen wiederverwenden müssen.

BEARBEITEN: Für alle, die daran interessiert sind, wird dies als Hinzufügen einer "Naht" zu Ihrer Klasse bezeichnet. Dies ist ein Punkt, an dem Sie sich an das Verhalten anschließen können, um sie zu ändern (zu Testzwecken oder auf andere Weise), ohne den Code in der Klasse ändern zu müssen.

2
sara

Eine gute Praxis ist, wenn DateTimeProvider IDisposable implementiert.

public class DateTimeProvider : IDisposable 
{ 
    [ThreadStatic] 
    private static DateTime? _injectedDateTime; 

    private DateTimeProvider() 
    { 
    } 

    /// <summary> 
    /// Gets DateTime now. 
    /// </summary> 
    /// <value> 
    /// The DateTime now. 
    /// </value> 
    public static DateTime Now 
    { 
        get 
        { 
            return _injectedDateTime ?? DateTime.Now; 
        } 
    } 

    /// <summary> 
    /// Injects the actual date time. 
    /// </summary> 
    /// <param name="actualDateTime">The actual date time.</param> 
    public static IDisposable InjectActualDateTime(DateTime actualDateTime) 
    { 
        _injectedDateTime = actualDateTime; 

        return new DateTimeProvider(); 
    } 

    public void Dispose() 
    { 
        _injectedDateTime = null; 
    } 
} 

Als nächstes können Sie Ihre gefälschte DateTime für Komponententests injizieren

    using (var date = DateTimeProvider.InjectActualDateTime(expectedDateTime)) 
    { 
        var bankAccount = new BankAccount(); 

        bankAccount.DepositMoney(600); 

        var lastTransaction = bankAccount.Transactions.Last(); 

        Assert.IsTrue(expectedDateTime.Equals(bankAccount.Transactions[0].TransactionDate)); 
    } 

Siehe Beispiel Beispiel für DateTimeProvider

1
Mino

Eine alternative Option, die nicht erwähnt wird, besteht darin, die aktuelle Zeit in die abhängige Methode einzugeben:

public class DateTimeNowDependencyClass
{
    ...

    public void ImplicitTimeDependencyMethod(Obj arg0)
    {
        this.TimeDependencyMethod(DateTime.Now, arg0);
    }

    internal void TimeDependencyMethod(DateTime now, Obj arg1)
    {
        ...
    }

    ...
}

Die interne Variante ist für die Prüfung von Einheiten offen, parallel oder nicht.

Dies basiert auf dem Prinzip, dass ImplicitTimeDependencyMethod "zu einfach zu brechen" ist (siehe: http://junit.sourceforge.net/doc/faq/faq.htm#best_3 ) Gerätetestabdeckung. In Integrationstests sollte es trotzdem berührt werden.

Abhängig vom Zweck der Klasse kann es wünschenswert sein, diese beiden Methoden trotzdem öffentlich zu machen.

0
amcc

Ich hatte dasselbe Problem, aber ich dachte, wir sollten die gesetzten datetime-Dinge nicht für dieselbe Klasse verwenden. denn es könnte eines Tages zu Missbrauch führen. also ich habe den anbieter gerne benutzt

public class DateTimeProvider
{
    protected static DateTime? DateTimeNow;
    protected static DateTime? DateTimeUtcNow;

    public DateTime Now
    {
        get
        {
            return DateTimeNow ?? System.DateTime.Now;
        }
    }

    public DateTime UtcNow
    {
        get
        {
            return DateTimeUtcNow ?? System.DateTime.UtcNow;
        }
    }

    public static DateTimeProvider DateTime
    {
        get
        {
            return new DateTimeProvider();
        }
    }

    protected DateTimeProvider()
    {       
    }
}

Für Tests, bei Testprojekt einen Helfer gemacht, der sich mit eingestellten Dingen beschäftigen wird,

public class MockDateTimeProvider : DateTimeProvider
{
    public static void SetNow(DateTime now)
    {
        DateTimeNow = now;
    }

    public static void SetUtcNow(DateTime utc)
    {
        DateTimeUtcNow = utc;
    }

    public static void RestoreAsDefault()
    {
        DateTimeNow = null;
        DateTimeUtcNow = null;
    }
}

auf Code

var dateTimeNow = DateTimeProvider.DateTime.Now         //not DateTime.Now
var dateTimeUtcNow = DateTimeProvider.DateTime.UtcNow   //not DateTime.UtcNow

und auf Tests

[Test]
public void Mocked_Now()
{
    DateTime now = DateTime.Now;
    MockDateTimeProvider.SetNow(now);    //set to mock
    Assert.AreEqual(now, DateTimeProvider.DateTime.Now);
    Assert.AreNotEqual(now, DateTimeProvider.DateTime.UtcNow);
}

[Test]
public void Mocked_UtcNow()
{
    DateTime utcNow = DateTime.UtcNow;
    MockDateTimeProvider.SetUtcNow(utcNow);   //set to mock
    Assert.AreEqual(utcNow, DateTimeProvider.DateTime.UtcNow);
    Assert.AreNotEqual(utcNow, DateTimeProvider.DateTime.Now);
}

Aber man muss sich an eines erinnern, manchmal verhält sich die tatsächliche DateTime und die DateTime des Providers nicht gleich

[Test]
public void Now()
{
    Assert.AreEqual(DateTime.Now.Kind, DateTimeProvider.DateTime.Now.Kind);
    Assert.LessOrEqual(DateTime.Now, DateTimeProvider.DateTime.Now);
    Assert.LessOrEqual(DateTimeProvider.DateTime.Now - DateTime.Now, TimeSpan.FromMilliseconds(1));
}

Ich ging davon aus, dass die Rücksicht maximal TimeSpan.FromMilliseconds (0,00002) sein würde. Meistens ist es aber noch weniger

Das Muster finden Sie unter MockSamples

0
Dipon Roy

Mit ITimeProvider mussten wir es in ein special shared common -Projekt aufnehmen, das von den übrigen Projekten referenziert werden muss. Aber dies kompliziert die Kontrolle von Abhängigkeiten .

Wir haben im .NET-Framework nach ITimeProvider gesucht. Wir haben nach dem NuGet-Paket gesucht und one gefunden, das mit DateTimeOffset nicht funktioniert.

Wir haben also eine eigene Lösung entwickelt, die nur von den Typen der Standardbibliothek abhängt. Wir verwenden eine Instanz von Func<DateTimeOffset>.

Wie benutzt man

public class ThingThatNeedsTimeProvider
{
    private readonly Func<DateTimeOffset> now;
    private int nextId;

    public ThingThatNeedsTimeProvider(Func<DateTimeOffset> now)
    {
        this.now = now;
        this.nextId = 1;
    }

    public (int Id, DateTimeOffset CreatedAt) MakeIllustratingTuple()
    {
        return (nextId++, now());
    }
}

Wie man sich registriert

Autofac

builder.RegisterInstance<Func<DateTimeOffset>>(() => DateTimeOffset.Now);

(Für zukünftige Redakteure: Fügen Sie hier Ihre Fälle hinzu).

Wie wird der Komponententest durchgeführt?

public void MakeIllustratingTuple_WhenCalled_FillsCreatedAt()
{
    DateTimeOffset expected = CreateRandomDateTimeOffset();
    DateTimeOffset StubNow() => expected;
    var thing = new ThingThatNeedsTimeProvider(StubNow);

    var (_, actual) = thing.MakeIllustratingTuple();

    Assert.AreEqual(expected, actual);
}
0
Mark Shevchenko

Hier ist meine Antwort auf diese Frage. Ich kombiniere das 'Ambient Context'-Muster mit IDisposable. Sie können also DateTimeProvider.Current in Ihrem normalen Programmcode verwenden und im Test den Gültigkeitsbereich mit einer using-Anweisung überschreiben. 

using System;
using System.Collections.Immutable;


namespace ambientcontext {

public abstract class DateTimeProvider : IDisposable
{
    private static ImmutableStack<DateTimeProvider> stack = ImmutableStack<DateTimeProvider>.Empty.Push(new DefaultDateTimeProvider());

    protected DateTimeProvider()
    {
        if (this.GetType() != typeof(DefaultDateTimeProvider))
            stack = stack.Push(this);
    }

    public static DateTimeProvider Current => stack.Peek();
    public abstract DateTime Today { get; }
    public abstract DateTime Now {get; }

    public void Dispose()
    {
        if (this.GetType() != typeof(DefaultDateTimeProvider))
            stack = stack.Pop();
    }

    // Not visible Default Implementation 
    private class DefaultDateTimeProvider : DateTimeProvider {
        public override DateTime Today => DateTime.Today; 
        public override DateTime Now => DateTime.Now; 
    }
}
}

So verwenden Sie den obigen DateTimeProvider in einem Unit-Test 

using System;
using Xunit;

namespace ambientcontext
{
    public class TestDateTimeProvider
    {
        [Fact]
        public void TestDateTime()
        {
            var actual = DateTimeProvider.Current.Today;
            var expected = DateTime.Today;

            Assert.Equal<DateTime>(expected, actual);

            using (new MyDateTimeProvider(new DateTime(2012,12,21)))
            {
                Assert.Equal(2012, DateTimeProvider.Current.Today.Year);

                using (new MyDateTimeProvider(new DateTime(1984,4,4)))
                {
                    Assert.Equal(1984, DateTimeProvider.Current.Today.Year);    
                }

                Assert.Equal(2012, DateTimeProvider.Current.Today.Year);
            }

            // Fall-Back to Default DateTimeProvider 
            Assert.Equal<int>(expected.Year,  DateTimeProvider.Current.Today.Year);
        }

        private class MyDateTimeProvider : DateTimeProvider 
        {
            private readonly DateTime dateTime; 

            public MyDateTimeProvider(DateTime dateTime):base()
            {
                this.dateTime = dateTime; 
            }

            public override DateTime Today => this.dateTime.Date;

            public override DateTime Now => this.dateTime;
        }
    }
}
0
Stefc

Eine saubere Möglichkeit, dies zu tun, ist das Injizieren von VirtualTime. Damit können Sie die Zeit steuern. Installieren Sie zuerst VirtualTime

Install-Package VirtualTime

So können Sie beispielsweise bei allen Aufrufen von DateTime.Now oder UtcNow fünfmal schneller arbeiten

var DateTime = DateTime.Now.ToVirtualTime(5);

Um die Zeit langsamer zu machen, z. B. fünfmal langsamer

var DateTime = DateTime.Now.ToVirtualTime(0.5);

Um die Zeit still stehen zu lassen 

var DateTime = DateTime.Now.ToVirtualTime(0);

Sich in der Zeit rückwärts zu bewegen, ist noch nicht getestet

Hier ein Beispieltest:

[TestMethod]
public void it_should_make_time_move_faster()
{
    int speedOfTimePerMs = 1000;
    int timeToPassMs = 3000;
    int expectedElapsedVirtualTime = speedOfTimePerMs * timeToPassMs;
    DateTime whenTimeStarts = DateTime.Now;
    ITime time = whenTimeStarts.ToVirtualTime(speedOfTimePerMs);
    Thread.Sleep(timeToPassMs);
    DateTime expectedTime = DateTime.Now.AddMilliseconds(expectedElapsedVirtualTime - timeToPassMs);
    DateTime virtualTime = time.Now;

    Assert.IsTrue(TestHelper.AreEqualWithinMarginOfError(expectedTime, virtualTime, MarginOfErrorMs));
}

Sie können weitere Tests hier ausprobieren:

https://github.com/VirtualTime/VirtualTime/blob/master/VirtualTimeLib.Tests/when_virtual_time_is_used.cs

Die DateTime.Now.ToVirtualTime-Erweiterung gibt Ihnen eine Instanz von ITime, die Sie an eine von ITime abhängige Methode/Klasse übergeben. Einige DateTime.Now.ToVirtualTime ist in einem DI-Container Ihrer Wahl eingerichtet

Hier ist ein weiteres Beispiel, das in einen Klassengegner einspritzt

public class AlarmClock
{
    private ITime DateTime;
    public AlarmClock(ITime dateTime, int numberOfHours)
    {
        DateTime = dateTime;
        SetTime = DateTime.UtcNow.AddHours(numberOfHours);
        Task.Run(() =>
        {
            while (!IsAlarmOn)
            {
                IsAlarmOn = (SetTime - DateTime.UtcNow).TotalMilliseconds < 0;
            }
        });
    }
    public DateTime SetTime { get; set; }
    public bool IsAlarmOn { get; set; }
}

[TestMethod]
public void it_can_be_injected_as_a_dependency()
{
    //virtual time has to be 1000*3.75 faster to get to an hour 
    //in 1000 ms real time
    var dateTime = DateTime.Now.ToVirtualTime(1000 * 3.75);
    var numberOfHoursBeforeAlarmSounds = 1;
    var alarmClock = new AlarmClock(dateTime, numberOfHoursBeforeAlarmSounds);
    Assert.IsFalse(alarmClock.IsAlarmOn);
    System.Threading.Thread.Sleep(1000);
    Assert.IsTrue(alarmClock.IsAlarmOn);
}
0
Samuel

Wir verwendeten ein statisches SystemTime-Objekt, hatten jedoch Probleme beim Ausführen von parallelen Komponententests. Ich habe versucht, die Lösung von Henk van Boeijen zu verwenden, hatte jedoch Probleme mit asynchrone Threads und endete mit AsyncLocal auf ähnliche Weise:

public static class Clock
{
    private static Func<DateTime> _utcNow = () => DateTime.UtcNow;

    static AsyncLocal<Func<DateTime>> _override = new AsyncLocal<Func<DateTime>>();

    public static DateTime UtcNow => (_override.Value ?? _utcNow)();

    public static void Set(Func<DateTime> func)
    {
        _override.Value = func;
    }

    public static void Reset()
    {
        _override.Value = null;
    }
}

Von https://Gist.github.com/CraftyFella/42f459f7687b0b8b268fc311e6b4af08 bezogen

0
rrrr

Möglicherweise ist eine weniger professionelle, aber einfachere Lösung die Erstellung eines DateTime-Parameters bei der Consumer-Methode. Beispiel: Anstelle einer make-Methode wie SampleMethod machen Sie SampleMethod1 mit parameter. Das Testen von SampleMethod1 ist einfacher

public void SampleMethod()
    {
        DateTime anotherDateTime = DateTime.Today.AddDays(-10);
        if ((DateTime.Now-anotherDateTime).TotalDays>10)
        {

        }
    }
    public void SampleMethod1(DateTime dateTimeNow)
    {
        DateTime anotherDateTime = DateTime.Today.AddDays(-10);
        if ((dateTimeNow - anotherDateTime).TotalDays > 10)
        {

        }

    }
0
Mehmet