All Products
Search
Document Center

Object Storage Service:Multipart upload (Python SDK V1)

Last Updated:Aug 08, 2025

When you upload a large file (larger than 5 GB) to Object Storage Service (OSS), the upload may fail because of network interruptions or program crashes. In this case, you must use multipart upload. Multipart upload splits a large file into multiple smaller parts. You can upload these parts concurrently to make full use of network bandwidth and server resources and speed up the upload. After all parts are uploaded, call the CompleteMultipartUpload operation to combine these parts into a complete object.

Usage notes

  • In this topic, the public endpoint of the China (Hangzhou) region is used. If you want to access OSS from other Alibaba Cloud services in the same region as OSS, use an internal endpoint. For more information about OSS regions and endpoints, see Regions and endpoints.

  • In this topic, access credentials are obtained from environment variables. For more information about how to configure access credentials, see Configure access credentials.

  • In this topic, an OSSClient instance is created by using an OSS endpoint. If you want to create an OSSClient instance by using custom domain names or Security Token Service (STS), see Initialization.

  • To complete the multipart upload workflow, which includes InitiateMultipartUpload, UploadPart, and CompleteMultipartUpload, you must have the oss:PutObject permission. For more information, see Attach a custom policy to a RAM user.

Multipart upload process

Multipart upload consists of the following three steps:

  1. Initialize a multipart upload event.

    Call the bucket.init_multipart_upload method to return a globally unique uploadId that is created by OSS.

  2. Upload parts.

    Call the bucket.upload_part method to upload part data.

    Note
    • For the same uploadId, the part number (partNumber) identifies the relative position of the part in the complete file. If you upload new data using the same part number, the existing data of this part in OSS is overwritten.

    • OSS returns the MD5 hash of the received part in the ETag header.

    • OSS calculates the MD5 hash of the uploaded data and compares it with the MD5 hash that is calculated by the SDK. If the two MD5 hashes do not match, the InvalidDigest error code is returned.

  3. Complete the multipart upload.

    After all parts are uploaded, call the bucket.complete_multipart_upload method to combine all parts into a complete object.

Complete multipart upload examples

After all parts are uploaded, you can combine them into a complete object in one of the following two ways:

  • Combine all parts into a complete object by passing part information in the request body

    # -*- coding: utf-8 -*-
    import os
    from oss2 import SizedFileAdapter, determine_part_size
    from oss2.models import PartInfo
    import oss2
    from oss2.credentials import EnvironmentVariableCredentialsProvider
    
    # Obtain access credentials from environment variables. Before you run this code, make sure that the OSS_ACCESS_KEY_ID and OSS_ACCESS_KEY_SECRET environment variables are set.
    auth = oss2.ProviderAuthV4(EnvironmentVariableCredentialsProvider())
    
    # Specify the endpoint of the region where the bucket is located. For example, if the bucket is in the China (Hangzhou) region, set the endpoint to https://oss-cn-hangzhou.aliyuncs.com.
    endpoint = "https://oss-cn-hangzhou.aliyuncs.com"
    
    # Specify the region that corresponds to the endpoint, for example, cn-hangzhou. Note that this parameter is required for V4 signatures.
    region = "cn-hangzhou"
    
    # Replace yourBucketName with the name of your bucket.
    bucket = oss2.Bucket(auth, endpoint, "yourBucketName", region=region)
    
    # Specify the full path of the object. The path cannot contain the bucket name. Example: exampledir/exampleobject.txt.
    key = 'exampledir/exampleobject.txt'
    # Specify the full path of the local file. Example: D:\\localpath\\examplefile.txt.
    filename = 'D:\\localpath\\examplefile.txt'
    
    total_size = os.path.getsize(filename)
    # The determine_part_size method determines the part size. The minimum part size is 100 KB, and the maximum is 5 GB. The last part can be smaller than 100 KB. Set the part size to 1 MB.
    part_size = determine_part_size(total_size, preferred_size=1 * 1024 * 1024)
    
    # Initialize the multipart upload.
    # To set headers when you initialize the multipart upload, set the relevant headers in init_multipart_upload as follows.
    # headers = dict()
    # Specify the web page caching behavior for the object.
    # headers['Cache-Control'] = 'no-cache'
    # Specify the name of the object when it is downloaded.
    # headers['Content-Disposition'] = 'oss_MultipartUpload.txt'
    # Specify the expiration time in milliseconds.
    # headers['Expires'] = '1000'
    # Specify whether to overwrite an object that has the same name when you initialize the multipart upload. Set this to true to prevent overwriting.
    # headers['x-oss-forbid-overwrite'] = 'true'
    # Specify the server-side encryption method for each part of the object.
    # headers[OSS_SERVER_SIDE_ENCRYPTION] = SERVER_SIDE_ENCRYPTION_KMS
    # Specify the encryption algorithm for the object. If this option is not specified, the object is encrypted using AES256.
    # headers[OSS_SERVER_SIDE_DATA_ENCRYPTION] = SERVER_SIDE_ENCRYPTION_KMS
    # Specify the customer master key (CMK) managed by KMS.
    # headers[OSS_SERVER_SIDE_ENCRYPTION_KEY_ID] = '9468da86-3509-4f8d-a61e-6eab1eac****'
    # Specify the storage class of the object.
    # headers['x-oss-storage-class'] = oss2.BUCKET_STORAGE_CLASS_STANDARD
    # Specify object tags. You can specify multiple tags.
    # headers[OSS_OBJECT_TAGGING] = 'k1=v1&k2=v2&k3=v3'
    # upload_id = bucket.init_multipart_upload(key, headers=headers).upload_id
    upload_id = bucket.init_multipart_upload(key).upload_id
    # Cancel the multipart upload event or list uploaded parts based on the upload_id.
    # To cancel a multipart upload event based on the uploadId, obtain the uploadId after you call InitiateMultipartUpload to initialize the multipart upload.
    # To list uploaded parts based on the uploadId, obtain the uploadId after you call InitiateMultipartUpload and before you call CompleteMultipartUpload.
    # print("UploadID:", upload_id)
    parts = []
    
    # Upload parts one by one.
    with open(filename, 'rb') as fileobj:
        part_number = 1
        offset = 0
        while offset < total_size:
            num_to_upload = min(part_size, total_size - offset)
            # Calling the SizedFileAdapter(fileobj, size) method generates a new file object and recalculates the starting append position.
            result = bucket.upload_part(key, upload_id, part_number,
                                        SizedFileAdapter(fileobj, num_to_upload))
            parts.append(PartInfo(part_number, result.etag))
    
            offset += num_to_upload
            part_number += 1
    
    # Complete the multipart upload.
    # To set headers when you complete the multipart upload, see the following sample code.
    headers = dict()
    # Set the access control list (ACL) for the file. In this example, it is set to OBJECT_ACL_PRIVATE, which indicates private access.
    # headers["x-oss-object-acl"] = oss2.OBJECT_ACL_PRIVATE
    bucket.complete_multipart_upload(key, upload_id, parts, headers=headers)
    # bucket.complete_multipart_upload(key, upload_id, parts)
    Important

    If network conditions are good, increase the part size. Otherwise, decrease the part size.

  • Combine parts into a complete object by listing parts on the server

    Note

    If you want to use this method to combine parts into a complete object, make sure that multiple parts have been uploaded using the upload_id that is specified in the following sample code.

    # -*- coding: utf-8 -*-
    import oss2
    from oss2.credentials import EnvironmentVariableCredentialsProvider
    # Obtain access credentials from environment variables. Before you run this code, make sure that the OSS_ACCESS_KEY_ID and OSS_ACCESS_KEY_SECRET environment variables are set.
    auth = oss2.ProviderAuthV4(EnvironmentVariableCredentialsProvider())
    
    # Specify the endpoint of the region where the bucket is located. For example, if the bucket is in the China (Hangzhou) region, set the endpoint to https://oss-cn-hangzhou.aliyuncs.com.
    endpoint = "https://oss-cn-hangzhou.aliyuncs.com"
    
    # Specify the region that corresponds to the endpoint, for example, cn-hangzhou. Note that this parameter is required for V4 signatures.
    region = "cn-hangzhou"
    
    # Replace yourBucketName with the name of your bucket.
    bucket = oss2.Bucket(auth, endpoint, "yourBucketName", region=region)
    
    # Specify the full path of the object. The path cannot contain the bucket name. Example: exampledir/exampleobject.txt.
    key = 'exampledir/exampleobject.txt'
    # Specify the full path of the local file. Example: D:\\localpath\\examplefile.txt.
    filename = 'D:\\localpath\\examplefile.txt'
    # Specify the upload_id. You must obtain the upload_id after you call InitiateMultipartUpload and before you call CompleteMultipartUpload.
    upload_id = '0004B9894A22E5B1888A1E29F823****'
    
    # Complete the multipart upload.
    # To set the ACL of the file when you complete the multipart upload, set the relevant headers in the complete_multipart_upload function as follows.
    headers = dict()
    # headers["x-oss-object-acl"] = oss2.OBJECT_ACL_PRIVATE
    # If x-oss-complete-all:yes is specified, OSS lists all parts that are uploaded for the current uploadId, sorts them by part number, and then runs the CompleteMultipartUpload operation.
    # If x-oss-complete-all:yes is specified, you cannot specify a body. Otherwise, an error is reported.
    headers["x-oss-complete-all"] = 'yes'
    bucket.complete_multipart_upload(key, upload_id, None, headers=headers)

Cancel a multipart upload event

Call the bucket.abort_multipart_upload method to cancel a multipart upload event. After a multipart upload event is canceled, you can no longer use its uploadId for any operations. The parts that are already uploaded are deleted.

# -*- coding: utf-8 -*-
import os
import oss2
from oss2.credentials import EnvironmentVariableCredentialsProvider

# Obtain access credentials from environment variables. Before you run this code, make sure that the OSS_ACCESS_KEY_ID and OSS_ACCESS_KEY_SECRET environment variables are set.
auth = oss2.ProviderAuthV4(EnvironmentVariableCredentialsProvider())

# Specify the endpoint of the region where the bucket is located. For example, if the bucket is in the China (Hangzhou) region, set the endpoint to https://oss-cn-hangzhou.aliyuncs.com.
endpoint = "https://oss-cn-hangzhou.aliyuncs.com"

# Specify the region that corresponds to the endpoint, for example, cn-hangzhou. Note that this parameter is required for V4 signatures.
region = "cn-hangzhou"

# Replace yourBucketName with the name of your bucket.
bucket = oss2.Bucket(auth, endpoint, "yourBucketName", region=region)

# Specify the full path of the object. The path cannot contain the bucket name. Example: exampledir/exampleobject.txt.
key = 'exampledir/exampleobject.txt'
# Specify the upload_id. The upload_id is obtained from the response returned after you call InitiateMultipartUpload.
upload_id = 'yourUploadId'

# Cancel the multipart upload event with the specified upload_id. The uploaded parts are deleted.
bucket.abort_multipart_upload(key, upload_id)

List information about uploaded parts

The following sample code shows how to list uploaded parts:

# -*- coding: utf-8 -*-
import os
import oss2
from oss2.credentials import EnvironmentVariableCredentialsProvider

# Obtain access credentials from environment variables. Before you run this code, make sure that the OSS_ACCESS_KEY_ID and OSS_ACCESS_KEY_SECRET environment variables are set.
auth = oss2.ProviderAuthV4(EnvironmentVariableCredentialsProvider())

# Specify the endpoint of the region where the bucket is located. For example, if the bucket is in the China (Hangzhou) region, set the endpoint to https://oss-cn-hangzhou.aliyuncs.com.
endpoint = "https://oss-cn-hangzhou.aliyuncs.com"

# Specify the region that corresponds to the endpoint, for example, cn-hangzhou. Note that this parameter is required for V4 signatures.
region = "cn-hangzhou"

# Replace yourBucketName with the name of your bucket.
bucket = oss2.Bucket(auth, endpoint, "yourBucketName", region=region)

# Specify the full path of the object. The path cannot contain the bucket name. Example: exampledir/exampleobject.txt.
key = 'exampledir/exampleobject.txt'
# Specify the upload_id. The upload_id is obtained from the response returned after you call InitiateMultipartUpload and before you call CompleteMultipartUpload.
upload_id = 'yourUploadId'

# List information about the uploaded parts that correspond to the specified upload_id.
for part_info in oss2.PartIterator(bucket, key, upload_id):
    print('part_number:', part_info.part_number)
    print('etag:', part_info.etag)
    print('size:', part_info.size)

List multipart upload events

  • List the multipart upload events for a specific object

    The following sample code shows how to list the multipart upload events for a specific object:

    # -*- coding: utf-8 -*-
    import os
    import oss2
    from oss2.credentials import EnvironmentVariableCredentialsProvider
    
    # Obtain access credentials from environment variables. Before you run this code, make sure that the OSS_ACCESS_KEY_ID and OSS_ACCESS_KEY_SECRET environment variables are set.
    auth = oss2.ProviderAuthV4(EnvironmentVariableCredentialsProvider())
    
    # Specify the endpoint of the region where the bucket is located. For example, if the bucket is in the China (Hangzhou) region, set the endpoint to https://oss-cn-hangzhou.aliyuncs.com.
    endpoint = "https://oss-cn-hangzhou.aliyuncs.com"
    
    # Specify the region that corresponds to the endpoint, for example, cn-hangzhou. Note that this parameter is required for V4 signatures.
    region = "cn-hangzhou"
    
    # Replace yourBucketName with the name of your bucket.
    bucket = oss2.Bucket(auth, endpoint, "yourBucketName", region=region)
    
    # Specify the full path of the object. The path cannot contain the bucket name. Example: exampledir/exampleobject.txt.
    key = 'exampledir/exampleobject.txt'
    
    # List all multipart upload events for the object. For the same object, a different upload_id is returned each time init_multipart_upload is called.
    # An upload_id corresponds to a multipart upload event.
    for upload_info in oss2.ObjectUploadIterator(bucket, key):
        print('key:', upload_info.key)
        print('upload_id:', upload_info.upload_id)
  • List all multipart upload events in a bucket

    The following sample code shows how to list all multipart upload events in a bucket:

    # -*- coding: utf-8 -*-
    import os
    import oss2
    from oss2.credentials import EnvironmentVariableCredentialsProvider
    
    # An AccessKey pair of an Alibaba Cloud account has full permissions on all API operations. This is a high-risk operation. We strongly recommend that you create and use a RAM user for API access or routine O&M. To create a RAM user, log on to the RAM console.
    auth = oss2.ProviderAuthV4(EnvironmentVariableCredentialsProvider())
    
    # Specify the endpoint of the region where the bucket is located. For example, if the bucket is in the China (Hangzhou) region, set the endpoint to https://oss-cn-hangzhou.aliyuncs.com.
    endpoint = "https://oss-cn-hangzhou.aliyuncs.com"
    
    # Specify the region that corresponds to the endpoint, for example, cn-hangzhou. Note that this parameter is required for V4 signatures.
    region = "cn-hangzhou"
    
    # Replace yourBucketName with the name of your bucket.
    bucket = oss2.Bucket(auth, endpoint, "yourBucketName", region=region)
    
    # List all multipart upload events in the bucket.
    for upload_info in oss2.MultipartUploadIterator(bucket):
        print('key:', upload_info.key)
        print('upload_id:', upload_info.upload_id)
  • List the multipart upload events for objects with a specific prefix in a bucket

    The following sample code shows how to list the multipart upload events for objects with a specific prefix in a bucket:

    # -*- coding: utf-8 -*-
    import os
    import oss2
    from oss2.credentials import EnvironmentVariableCredentialsProvider
    # An AccessKey pair of an Alibaba Cloud account has full permissions on all API operations. This is a high-risk operation. We strongly recommend that you create and use a RAM user for API access or routine O&M. To create a RAM user, log on to the RAM console.
    auth = oss2.ProviderAuthV4(EnvironmentVariableCredentialsProvider())
    
    # Specify the endpoint of the region where the bucket is located. For example, if the bucket is in the China (Hangzhou) region, set the endpoint to https://oss-cn-hangzhou.aliyuncs.com.
    endpoint = "https://oss-cn-hangzhou.aliyuncs.com"
    
    # Specify the region that corresponds to the endpoint, for example, cn-hangzhou. Note that this parameter is required for V4 signatures.
    region = "cn-hangzhou"
    
    # Replace yourBucketName with the name of your bucket.
    bucket = oss2.Bucket(auth, endpoint, "yourBucketName", region=region)
    
    # List the multipart upload events for objects with the 'test' prefix in the bucket.
    for upload_info in oss2.MultipartUploadIterator(bucket, prefix='test'):
        print('key:', upload_info.key)
        print('upload_id:', upload_info.upload_id)

FAQ

How do I delete parts?

If a multipart upload task is interrupted and the AbortMultipartUpload operation is not called, the parts that are uploaded by the task are stored in the specified bucket. If you no longer require the parts, you can use one of the following methods to delete the parts to prevent unnecessary storage costs:

  1. Manually delete parts. For more information, see Delete parts.

  2. Configure lifecycle rules to delete parts. For more information, see Configure lifecycle rules to delete expired parts.

References

  • A complete multipart upload involves the following three API operations:

    • For more information about the API operation to initialize a multipart upload event, see InitiateMultipartUpload.

    • For more information about the API operation to upload a part, see UploadPart.

    • For more information about the API operation to complete a multipart upload, see CompleteMultipartUpload.

  • For more information about the API operation to cancel a multipart upload event, see AbortMultipartUpload.

  • For more information about the API operation to list uploaded parts, see ListParts.

  • For more information about the API operation to list all in-progress multipart upload events (events that are initialized but not completed or aborted), see ListMultipartUploads.