@@ -613,6 +613,22 @@ def setUpClass(cls):
613613 op1 .result (SPANNER_OPERATION_TIMEOUT_IN_SECONDS ) # raises on failure / timeout.
614614 op2 .result (SPANNER_OPERATION_TIMEOUT_IN_SECONDS ) # raises on failure / timeout.
615615
616+ # Add retention period for backups
617+ retention_period = "7d"
618+ ddl_statements = DDL_STATEMENTS + [
619+ "ALTER DATABASE {}"
620+ " SET OPTIONS (version_retention_period = '{}')" .format (
621+ cls .DATABASE_NAME , retention_period
622+ )
623+ ]
624+ db = Config .INSTANCE .database (
625+ cls .DATABASE_NAME , pool = pool , ddl_statements = ddl_statements
626+ )
627+ operation = db .update_ddl (ddl_statements )
628+ # We want to make sure the operation completes.
629+ operation .result (240 ) # raises on failure / timeout.
630+ db .reload ()
631+
616632 current_config = Config .INSTANCE .configuration_name
617633 same_config_instance_id = "same-config" + unique_resource_id ("-" )
618634 create_time = str (int (time .time ()))
@@ -685,9 +701,16 @@ def test_backup_workflow(self):
685701 backup_id = "backup_id" + unique_resource_id ("_" )
686702 expire_time = datetime .utcnow () + timedelta (days = 3 )
687703 expire_time = expire_time .replace (tzinfo = UTC )
704+ version_time = datetime .utcnow () - timedelta (seconds = 5 )
705+ version_time = version_time .replace (tzinfo = UTC )
688706
689707 # Create backup.
690- backup = instance .backup (backup_id , database = self ._db , expire_time = expire_time )
708+ backup = instance .backup (
709+ backup_id ,
710+ database = self ._db ,
711+ expire_time = expire_time ,
712+ version_time = version_time ,
713+ )
691714 operation = backup .create ()
692715 self .to_delete .append (backup )
693716
@@ -702,6 +725,7 @@ def test_backup_workflow(self):
702725 self .assertEqual (self ._db .name , backup ._database )
703726 self .assertEqual (expire_time , backup .expire_time )
704727 self .assertIsNotNone (backup .create_time )
728+ self .assertEqual (version_time , backup .version_time )
705729 self .assertIsNotNone (backup .size_bytes )
706730 self .assertIsNotNone (backup .state )
707731
@@ -722,6 +746,80 @@ def test_backup_workflow(self):
722746 backup .delete ()
723747 self .assertFalse (backup .exists ())
724748
749+ def test_backup_version_time_defaults_to_create_time (self ):
750+ from datetime import datetime
751+ from datetime import timedelta
752+ from pytz import UTC
753+
754+ instance = Config .INSTANCE
755+ backup_id = "backup_id" + unique_resource_id ("_" )
756+ expire_time = datetime .utcnow () + timedelta (days = 3 )
757+ expire_time = expire_time .replace (tzinfo = UTC )
758+
759+ # Create backup.
760+ backup = instance .backup (backup_id , database = self ._db , expire_time = expire_time ,)
761+ operation = backup .create ()
762+ self .to_delete .append (backup )
763+
764+ # Check metadata.
765+ metadata = operation .metadata
766+ self .assertEqual (backup .name , metadata .name )
767+ self .assertEqual (self ._db .name , metadata .database )
768+ operation .result ()
769+
770+ # Check backup object.
771+ backup .reload ()
772+ self .assertEqual (self ._db .name , backup ._database )
773+ self .assertIsNotNone (backup .create_time )
774+ self .assertEqual (backup .create_time , backup .version_time )
775+
776+ backup .delete ()
777+ self .assertFalse (backup .exists ())
778+
779+ def test_create_backup_invalid_version_time_past (self ):
780+ from datetime import datetime
781+ from datetime import timedelta
782+ from pytz import UTC
783+
784+ backup_id = "backup_id" + unique_resource_id ("_" )
785+ expire_time = datetime .utcnow () + timedelta (days = 3 )
786+ expire_time = expire_time .replace (tzinfo = UTC )
787+ version_time = datetime .utcnow () - timedelta (days = 10 )
788+ version_time = version_time .replace (tzinfo = UTC )
789+
790+ backup = Config .INSTANCE .backup (
791+ backup_id ,
792+ database = self ._db ,
793+ expire_time = expire_time ,
794+ version_time = version_time ,
795+ )
796+
797+ with self .assertRaises (exceptions .InvalidArgument ):
798+ op = backup .create ()
799+ op .result ()
800+
801+ def test_create_backup_invalid_version_time_future (self ):
802+ from datetime import datetime
803+ from datetime import timedelta
804+ from pytz import UTC
805+
806+ backup_id = "backup_id" + unique_resource_id ("_" )
807+ expire_time = datetime .utcnow () + timedelta (days = 3 )
808+ expire_time = expire_time .replace (tzinfo = UTC )
809+ version_time = datetime .utcnow () + timedelta (days = 2 )
810+ version_time = version_time .replace (tzinfo = UTC )
811+
812+ backup = Config .INSTANCE .backup (
813+ backup_id ,
814+ database = self ._db ,
815+ expire_time = expire_time ,
816+ version_time = version_time ,
817+ )
818+
819+ with self .assertRaises (exceptions .InvalidArgument ):
820+ op = backup .create ()
821+ op .result ()
822+
725823 def test_restore_to_diff_instance (self ):
726824 from datetime import datetime
727825 from datetime import timedelta
@@ -818,9 +916,14 @@ def test_list_backups(self):
818916 instance = Config .INSTANCE
819917 expire_time_1 = datetime .utcnow () + timedelta (days = 21 )
820918 expire_time_1 = expire_time_1 .replace (tzinfo = UTC )
919+ version_time_1 = datetime .utcnow () - timedelta (minutes = 5 )
920+ version_time_1 = version_time_1 .replace (tzinfo = UTC )
821921
822922 backup1 = Config .INSTANCE .backup (
823- backup_id_1 , database = self ._dbs [0 ], expire_time = expire_time_1
923+ backup_id_1 ,
924+ database = self ._dbs [0 ],
925+ expire_time = expire_time_1 ,
926+ version_time = version_time_1 ,
824927 )
825928
826929 expire_time_2 = datetime .utcnow () + timedelta (days = 1 )
@@ -860,6 +963,13 @@ def test_list_backups(self):
860963 for backup in instance .list_backups (filter_ = filter_ ):
861964 self .assertEqual (backup .name , backup2 .name )
862965
966+ # List backups filtered by version time.
967+ filter_ = 'version_time > "{0}"' .format (
968+ create_time_compare .strftime ("%Y-%m-%dT%H:%M:%S.%fZ" )
969+ )
970+ for backup in instance .list_backups (filter_ = filter_ ):
971+ self .assertEqual (backup .name , backup2 .name )
972+
863973 # List backups filtered by expire time.
864974 filter_ = 'expire_time > "{0}"' .format (
865975 expire_time_1 .strftime ("%Y-%m-%dT%H:%M:%S.%fZ" )
0 commit comments