FreezeGun Documentation

repository·master·Indexed 26 days ago

https://github.com/spulec/freezegun

A Python library that allows tests to travel through time by mocking the datetime and time modules. It provides the freeze_time decorator and context manager to mock functions such as datetime.datetime.now(), time.time(), and time.monotonic(). Features include timezone offset support via tz_offset, time progression control with tick and auto_tick_seconds, manual time manipulation using tick() and move_to(), and asyncio compatibility with real_asyncio.

Tokens
2.1K
Snippets
8
Records
9
Agent score
39%

What's inside FreezeGun

  1. Use freeze_time as a decorator

    master

    The freeze_time decorator can be used to freeze time for various scopes:

    • Pytest style functions: Decorate the test function directly.
    • unittest.TestCase classes: Decorate the entire class to freeze time for every test, including setup and teardown.
    • Other classes: Decorate a class to freeze time around each callable (behavior may vary).
    • Methods: Decorate specific methods. You can pass the frozen time object into the method using as_kwarg.

    Note: freeze_time mocks datetime.datetime.now(), datetime.datetime.utcnow(), datetime.date.today(), time.time(), time.localtime(), time.gmtime(), and time.strftime(). It also freezes time.monotonic() and time.perf_counter(), though only their relative changes are guaranteed.

    from freezegun import freeze_time
    import datetime
    import unittest
    
    # Pytest style
    @freeze_time("2012-01-14")
    def test():
        assert datetime.datetime.now() == datetime.datetime(2012, 1, 14)
    
    # unittest TestCase
    @freeze_time("1955-11-12")
    class MyTests(unittest.TestCase):
        def test_the_class(self):
            assert datetime.datetime.now() == datetime.datetime(1955, 11, 12)
    
    # Method decorator with kwarg injection
    class TestUnitTestMethodDecorator(unittest.TestCase):
        @freeze_time('2013-04-09', as_kwarg='frozen_time')
        def test_method_decorator_works_on_unittest(self, frozen_time):
            self.assertEqual(datetime.date(2013, 4, 9), datetime.date.today())
            self.assertEqual(datetime.date(2013, 4, 9), frozen_time.time_to_freeze.date())
  2. Ignore specific packages from freezing

    master

    You can prevent FreezeGun from mocking certain packages to avoid side effects in specific libraries.

    For a single invocation: Pass a list of package names to the ignore argument.

    Globally: Use freezegun.configure() to set a default ignore list.

    • Use default_ignore_list to replace the entire list.
    • Use extend_ignore_list to add to the existing default list.
    from freezegun import freeze_time
    
    # Single invocation
    with freeze_time('2020-10-06', ignore=['threading']):
        pass
    
    # Global configuration
    import freezegun
    freezegun.configure(default_ignore_list=['threading', 'tensorflow'])
    freezegun.configure(extend_ignore_list=['tensorflow'])
  3. Use freeze_time as a context manager

    master

    Use freeze_time as a context manager to freeze time only within a specific block of code.

    from freezegun import freeze_time
    import datetime
    
    def test():
        assert datetime.datetime.now() != datetime.datetime(2012, 1, 14)
        with freeze_time("2012-01-14"):
            assert datetime.datetime.now() == datetime.datetime(2012, 1, 14)
        assert datetime.datetime.now() != datetime.datetime(2012, 1, 14)
  4. Use freeze_time with timezones

    master

    You can specify a timezone offset using the tz_offset parameter. This accepts an int (representing offset in hours) or a datetime.timedelta object.

    from freezegun import freeze_time
    import datetime
    
    @freeze_time("2012-01-14 03:21:34", tz_offset=-4)
    def test():
        assert datetime.datetime.utcnow() == datetime.datetime(2012, 1, 14, 3, 21, 34)
        assert datetime.datetime.now() == datetime.datetime(2012, 1, 13, 23, 21, 34)
    
    @freeze_time("2012-01-14 03:21:34", tz_offset=-datetime.timedelta(hours=3, minutes=30))
    def test_timedelta_offset():
        assert datetime.datetime.now() == datetime.datetime(2012, 1, 13, 23, 51, 34)
  5. Manually manipulate time with tick() and move_to()

    master

    When using freeze_time as a context manager or via raw use, you can manually advance or jump time using the returned object:

    • tick(delta): Advances time by a datetime.timedelta or a float (seconds). Defaults to 1 second.
    • move_to(target_datetime): Jumps time to a specific datetime, date, or string representation.
  6. Enable real monotonic time for asyncio with real_asyncio

    master

    If you are testing asyncio code, use the real_asyncio=True parameter. This allows asyncio event loops to see real monotonic time even though time.monotonic() is frozen, preventing issues with asyncio.sleep() and other functions that rely on monotonic time.

    @freeze_time("2012-01-14", real_asyncio=True)
    async def test_asyncio():
        await asyncio.sleep(1)
        assert datetime.datetime.now() == datetime.datetime(2012, 1, 14)
  7. Configure time progression with tick and auto_tick_seconds

    master

    By default, freeze_time keeps time stopped. You can change this behavior using:

    • tick=True: Restarts time at the given value, but time will continue to move forward normally.
    • auto_tick_seconds: Automatically increments the time by the specified number of seconds every time a time-related function is called. Note that if auto_tick_seconds is provided, the tick parameter is ignored.
    @freeze_time("Jan 14th, 2020", tick=True)
    def test_nice_datetime():
        assert datetime.datetime.now() > datetime.datetime(2020, 1, 14)
    
    @freeze_time("Jan 14th, 2020", auto_tick_seconds=15)
    def test_auto_increment():
        first_time = datetime.datetime.now()
        auto_incremented_time = datetime.datetime.now()
        assert first_time + datetime.timedelta(seconds=15) == auto_incremented_time
  8. Reference: freeze_time API signature

    master

    The primary entry point for FreezeGun is the freeze_time function.

    freeze_time(
        time_to_freeze: Optional[_Freezable]=None, 
        tz_offset: Union[int, datetime.timedelta]=0, 
        ignore: Optional[List[str]]=None, 
        tick: bool=False, 
        as_arg: bool=False, 
        as_kwarg: str='', 
        auto_tick_seconds: float=0, 
        real_asyncio: bool=False
    ) -> _freeze_time