@@ -429,6 +429,90 @@ async def test_datetime_auto_now_naive_with_use_tz_false(db):
429429 timezone ._reset_timezone_cache ()
430430
431431
432+ @pytest .mark .asyncio
433+ async def test_datetime_auto_now_add_matches_db_on_create (db ):
434+ """Test auto_now_add value on instance after create() matches what DB returns."""
435+ model = testmodels .DatetimeFields
436+ old_use_tz = os .environ .get ("USE_TZ" )
437+ old_tz = os .environ .get ("TIMEZONE" , "UTC" )
438+ os .environ ["USE_TZ" ] = "True"
439+ os .environ ["TIMEZONE" ] = "Asia/Shanghai"
440+ timezone ._reset_timezone_cache ()
441+
442+ obj = await model .create (datetime = datetime (2021 , 1 , 1 , tzinfo = get_default_timezone ()))
443+ obj_get = await model .get (pk = obj .pk )
444+
445+ # Instance from create() should match instance from get() — no refresh needed
446+ assert obj .datetime_add == obj_get .datetime_add
447+ assert obj .datetime_add .tzinfo is not None
448+ assert obj .datetime_add .tzinfo .key == "Asia/Shanghai"
449+
450+ os .environ ["TIMEZONE" ] = old_tz
451+ if old_use_tz is not None :
452+ os .environ ["USE_TZ" ] = old_use_tz
453+ else :
454+ os .environ .pop ("USE_TZ" , None )
455+ timezone ._reset_timezone_cache ()
456+
457+
458+ @pytest .mark .asyncio
459+ async def test_datetime_auto_now_matches_db_on_save (db ):
460+ """Test auto_now value on instance after save() matches what DB returns."""
461+ model = testmodels .DatetimeFields
462+ old_use_tz = os .environ .get ("USE_TZ" )
463+ old_tz = os .environ .get ("TIMEZONE" , "UTC" )
464+ os .environ ["USE_TZ" ] = "True"
465+ os .environ ["TIMEZONE" ] = "Asia/Shanghai"
466+ timezone ._reset_timezone_cache ()
467+
468+ obj = await model .create (datetime = datetime (2021 , 1 , 1 , tzinfo = get_default_timezone ()))
469+ sleep (0.01 )
470+ obj .datetime = datetime (2021 , 2 , 2 , tzinfo = get_default_timezone ())
471+ await obj .save ()
472+ obj_get = await model .get (pk = obj .pk )
473+
474+ # Instance from save() should match instance from get() — no refresh needed
475+ assert obj .datetime_auto == obj_get .datetime_auto
476+ assert obj .datetime_auto .tzinfo is not None
477+ assert obj .datetime_auto .tzinfo .key == "Asia/Shanghai"
478+
479+ os .environ ["TIMEZONE" ] = old_tz
480+ if old_use_tz is not None :
481+ os .environ ["USE_TZ" ] = old_use_tz
482+ else :
483+ os .environ .pop ("USE_TZ" , None )
484+ timezone ._reset_timezone_cache ()
485+
486+
487+ @pytest .mark .asyncio
488+ async def test_datetime_auto_fields_match_db_with_use_tz_false (db ):
489+ """Test auto_now/auto_now_add on instance match DB when use_tz=False."""
490+ model = testmodels .DatetimeFields
491+ old_use_tz = os .environ .get ("USE_TZ" )
492+ os .environ ["USE_TZ" ] = "False"
493+ timezone ._reset_timezone_cache ()
494+
495+ obj = await model .create (datetime = datetime (2021 , 1 , 1 ))
496+ obj_get = await model .get (pk = obj .pk )
497+
498+ assert obj .datetime_add == obj_get .datetime_add
499+ assert timezone .is_naive (obj .datetime_add )
500+
501+ sleep (0.01 )
502+ obj .datetime = datetime (2021 , 2 , 2 )
503+ await obj .save ()
504+ obj_get = await model .get (pk = obj .pk )
505+
506+ assert obj .datetime_auto == obj_get .datetime_auto
507+ assert timezone .is_naive (obj .datetime_auto )
508+
509+ if old_use_tz is not None :
510+ os .environ ["USE_TZ" ] = old_use_tz
511+ else :
512+ os .environ .pop ("USE_TZ" , None )
513+ timezone ._reset_timezone_cache ()
514+
515+
432516@pytest .mark .asyncio
433517@test .requireCapability (dialect = NotIn ("sqlite" , "mssql" ))
434518async def test_datetime_filter_by_year_month_day (db ):
0 commit comments