@@ -3198,6 +3198,7 @@ def compose(
31983198 timeout = _DEFAULT_TIMEOUT ,
31993199 if_generation_match = None ,
32003200 if_metageneration_match = None ,
3201+ if_source_generation_match = None ,
32013202 retry = DEFAULT_RETRY_IF_GENERATION_SPECIFIED ,
32023203 ):
32033204 """Concatenate source blobs into this one.
@@ -3218,73 +3219,98 @@ def compose(
32183219 (Optional) The amount of time, in seconds, to wait
32193220 for the server response. See: :ref:`configuring_timeouts`
32203221
3221- :type if_generation_match: list of long
3222+ :type if_generation_match: long
32223223 :param if_generation_match:
3223- (Optional) Make the operation conditional on whether the blob's
3224- current generation matches the given value. Setting to 0 makes the
3225- operation succeed only if there are no live versions of the blob.
3226- The list must match ``sources`` item-to-item.
3224+ (Optional) Makes the operation conditional on whether the
3225+ destination object's current generation matches the given value.
3226+ Setting to 0 makes the operation succeed only if there are no live
3227+ versions of the object.
3228+
3229+ Note: In a previous version, this argument worked identically to the
3230+ ``if_source_generation_match`` argument. For backwards-compatibility reasons,
3231+ if a list is passed in, this argument will behave like ``if_source_generation_match``
3232+ and also issue a DeprecationWarning.
32273233
3228- :type if_metageneration_match: list of long
3234+ :type if_metageneration_match: long
32293235 :param if_metageneration_match:
3230- (Optional) Make the operation conditional on whether the blob's
3231- current metageneration matches the given value. The list must match
3232- ``sources`` item-to-item.
3236+ (Optional) Makes the operation conditional on whether the
3237+ destination object's current metageneration matches the given
3238+ value.
3239+
3240+ If a list of long is passed in, no match operation will be performed.
3241+ (Deprecated: type(list of long) is supported for backwards-compatability reasons only.)
3242+
3243+ :type if_source_generation_match: list of long
3244+ :param if_source_generation_match:
3245+ (Optional) Makes the operation conditional on whether the current generation
3246+ of each source blob matches the corresponding generation.
3247+ The list must match ``sources`` item-to-item.
32333248
32343249 :type retry: google.api_core.retry.Retry or google.cloud.storage.retry.ConditionalRetryPolicy
32353250 :param retry:
32363251 (Optional) How to retry the RPC. See: :ref:`configuring_retries`
32373252
32383253 Example:
3239- Compose blobs using generation match preconditions.
3254+ Compose blobs using source generation match preconditions.
32403255
32413256 >>> from google.cloud import storage
32423257 >>> client = storage.Client()
32433258 >>> bucket = client.bucket("bucket-name")
32443259
32453260 >>> blobs = [bucket.blob("blob-name-1"), bucket.blob("blob-name-2")]
3246- >>> if_generation_match = [None] * len(blobs)
3247- >>> if_generation_match [0] = "123" # precondition for "blob-name-1"
3261+ >>> if_source_generation_match = [None] * len(blobs)
3262+ >>> if_source_generation_match [0] = "123" # precondition for "blob-name-1"
32483263
32493264 >>> composed_blob = bucket.blob("composed-name")
3250- >>> composed_blob.compose(blobs, if_generation_match )
3265+ >>> composed_blob.compose(blobs, if_source_generation_match=if_source_generation_match )
32513266 """
32523267 sources_len = len (sources )
3253- if if_generation_match is not None and len (if_generation_match ) != sources_len :
3254- raise ValueError (
3255- "'if_generation_match' length must be the same as 'sources' length"
3268+ client = self ._require_client (client )
3269+ query_params = {}
3270+
3271+ if isinstance (if_generation_match , list ):
3272+ warnings .warn (
3273+ "if_generation_match: type list is deprecated and supported for backwards-compatability reasons only."
3274+ "Use if_source_generation_match instead to match source objects generations." ,
3275+ DeprecationWarning ,
3276+ stacklevel = 2 ,
32563277 )
32573278
3258- if (
3259- if_metageneration_match is not None
3260- and len (if_metageneration_match ) != sources_len
3261- ):
3262- raise ValueError (
3263- "'if_metageneration_match' length must be the same as 'sources' length"
3279+ if if_source_generation_match is not None :
3280+ raise ValueError (
3281+ "Use if_generation_match to match the generation of the destination object by passing in a generation number, instead of a list."
3282+ "Use if_source_generation_match to match source objects generations."
3283+ )
3284+
3285+ # if_generation_match: type list is deprecated. Instead use if_source_generation_match.
3286+ if_source_generation_match = if_generation_match
3287+ if_generation_match = None
3288+
3289+ if isinstance (if_metageneration_match , list ):
3290+ warnings .warn (
3291+ "if_metageneration_match: type list is deprecated and supported for backwards-compatability reasons only."
3292+ "Note that the metageneration to be matched is that of the destination blob."
3293+ "Please pass in a single value (type long)." ,
3294+ DeprecationWarning ,
3295+ stacklevel = 2 ,
32643296 )
32653297
3266- client = self ._require_client (client )
3267- query_params = {}
3298+ if_metageneration_match = None
32683299
3269- if self .user_project is not None :
3270- query_params ["userProject" ] = self .user_project
3300+ if if_source_generation_match is None :
3301+ if_source_generation_match = [None ] * sources_len
3302+ if len (if_source_generation_match ) != sources_len :
3303+ raise ValueError (
3304+ "'if_source_generation_match' length must be the same as 'sources' length"
3305+ )
32713306
32723307 source_objects = []
3273- for index , source in enumerate (sources ):
3274- source_object = {"name" : source .name }
3308+ for source , source_generation in zip (sources , if_source_generation_match ):
3309+ source_object = {"name" : source .name , "generation" : source . generation }
32753310
32763311 preconditions = {}
3277- if (
3278- if_generation_match is not None
3279- and if_generation_match [index ] is not None
3280- ):
3281- preconditions ["ifGenerationMatch" ] = if_generation_match [index ]
3282-
3283- if (
3284- if_metageneration_match is not None
3285- and if_metageneration_match [index ] is not None
3286- ):
3287- preconditions ["ifMetagenerationMatch" ] = if_metageneration_match [index ]
3312+ if source_generation is not None :
3313+ preconditions ["ifGenerationMatch" ] = source_generation
32883314
32893315 if preconditions :
32903316 source_object ["objectPreconditions" ] = preconditions
@@ -3295,6 +3321,16 @@ def compose(
32953321 "sourceObjects" : source_objects ,
32963322 "destination" : self ._properties .copy (),
32973323 }
3324+
3325+ if self .user_project is not None :
3326+ query_params ["userProject" ] = self .user_project
3327+
3328+ _add_generation_match_parameters (
3329+ query_params ,
3330+ if_generation_match = if_generation_match ,
3331+ if_metageneration_match = if_metageneration_match ,
3332+ )
3333+
32983334 api_response = client ._post_resource (
32993335 "{}/compose" .format (self .path ),
33003336 request ,
0 commit comments