// Code generated by smithy-go-codegen DO NOT EDIT.

package s3

import (
	"context"
	"fmt"
	awsmiddleware "github.com/aws/aws-sdk-go-v2/aws/middleware"
	"github.com/aws/aws-sdk-go-v2/aws/signer/v4"
	s3cust "github.com/aws/aws-sdk-go-v2/service/s3/internal/customizations"
	"github.com/aws/aws-sdk-go-v2/service/s3/types"
	"github.com/aws/smithy-go/middleware"
	smithyhttp "github.com/aws/smithy-go/transport/http"
	"time"
)

// This action initiates a multipart upload and returns an upload ID. This upload
// ID is used to associate all of the parts in the specific multipart upload. You
// specify this upload ID in each of your subsequent upload part requests (see [UploadPart]).
// You also include this upload ID in the final request to either complete or abort
// the multipart upload request. For more information about multipart uploads, see [Multipart Upload Overview]
// in the Amazon S3 User Guide.
//
// After you initiate a multipart upload and upload one or more parts, to stop
// being charged for storing the uploaded parts, you must either complete or abort
// the multipart upload. Amazon S3 frees up the space used to store the parts and
// stops charging you for storing them only after you either complete or abort a
// multipart upload.
//
// If you have configured a lifecycle rule to abort incomplete multipart uploads,
// the created multipart upload must be completed within the number of days
// specified in the bucket lifecycle configuration. Otherwise, the incomplete
// multipart upload becomes eligible for an abort action and Amazon S3 aborts the
// multipart upload. For more information, see [Aborting Incomplete Multipart Uploads Using a Bucket Lifecycle Configuration].
//
//   - Directory buckets - S3 Lifecycle is not supported by directory buckets.
//
//   - Directory buckets - For directory buckets, you must make requests for this
//     API operation to the Zonal endpoint. These endpoints support
//     virtual-hosted-style requests in the format
//     https://amzn-s3-demo-bucket.s3express-zone-id.region-code.amazonaws.com/key-name
//     . Path-style requests are not supported. For more information about endpoints
//     in Availability Zones, see [Regional and Zonal endpoints for directory buckets in Availability Zones]in the Amazon S3 User Guide. For more information
//     about endpoints in Local Zones, see [Concepts for directory buckets in Local Zones]in the Amazon S3 User Guide.
//
// Request signing For request signing, multipart upload is just a series of
// regular requests. You initiate a multipart upload, send one or more requests to
// upload parts, and then complete the multipart upload process. You sign each
// request individually. There is nothing special about signing multipart upload
// requests. For more information about signing, see [Authenticating Requests (Amazon Web Services Signature Version 4)]in the Amazon S3 User Guide.
//
// Permissions
//
//   - General purpose bucket permissions - To perform a multipart upload with
//     encryption using an Key Management Service (KMS) KMS key, the requester must
//     have permission to the kms:Decrypt and kms:GenerateDataKey actions on the key.
//     The requester must also have permissions for the kms:GenerateDataKey action
//     for the CreateMultipartUpload API. Then, the requester needs permissions for
//     the kms:Decrypt action on the UploadPart and UploadPartCopy APIs. These
//     permissions are required because Amazon S3 must decrypt and read data from the
//     encrypted file parts before it completes the multipart upload. For more
//     information, see [Multipart upload API and permissions]and [Protecting data using server-side encryption with Amazon Web Services KMS]in the Amazon S3 User Guide.
//
//   - Directory bucket permissions - To grant access to this API operation on a
//     directory bucket, we recommend that you use the [CreateSession]CreateSession API operation
//     for session-based authorization. Specifically, you grant the
//     s3express:CreateSession permission to the directory bucket in a bucket policy
//     or an IAM identity-based policy. Then, you make the CreateSession API call on
//     the bucket to obtain a session token. With the session token in your request
//     header, you can make API requests to this operation. After the session token
//     expires, you make another CreateSession API call to generate a new session
//     token for use. Amazon Web Services CLI or SDKs create session and refresh the
//     session token automatically to avoid service interruptions when a session
//     expires. For more information about authorization, see [CreateSession]CreateSession .
//
// Encryption
//
//   - General purpose buckets - Server-side encryption is for data encryption at
//     rest. Amazon S3 encrypts your data as it writes it to disks in its data centers
//     and decrypts it when you access it. Amazon S3 automatically encrypts all new
//     objects that are uploaded to an S3 bucket. When doing a multipart upload, if you
//     don't specify encryption information in your request, the encryption setting of
//     the uploaded parts is set to the default encryption configuration of the
//     destination bucket. By default, all buckets have a base level of encryption
//     configuration that uses server-side encryption with Amazon S3 managed keys
//     (SSE-S3). If the destination bucket has a default encryption configuration that
//     uses server-side encryption with an Key Management Service (KMS) key (SSE-KMS),
//     or a customer-provided encryption key (SSE-C), Amazon S3 uses the corresponding
//     KMS key, or a customer-provided key to encrypt the uploaded parts. When you
//     perform a CreateMultipartUpload operation, if you want to use a different type
//     of encryption setting for the uploaded parts, you can request that Amazon S3
//     encrypts the object with a different encryption key (such as an Amazon S3
//     managed key, a KMS key, or a customer-provided key). When the encryption setting
//     in your request is different from the default encryption configuration of the
//     destination bucket, the encryption setting in your request takes precedence. If
//     you choose to provide your own encryption key, the request headers you provide
//     in [UploadPart]and [UploadPartCopy]requests must match the headers you used in the CreateMultipartUpload
//     request.
//
//   - Use KMS keys (SSE-KMS) that include the Amazon Web Services managed key (
//     aws/s3 ) and KMS customer managed keys stored in Key Management Service (KMS)
//     – If you want Amazon Web Services to manage the keys used to encrypt data,
//     specify the following headers in the request.
//
//   - x-amz-server-side-encryption
//
//   - x-amz-server-side-encryption-aws-kms-key-id
//
//   - x-amz-server-side-encryption-context
//
//   - If you specify x-amz-server-side-encryption:aws:kms , but don't provide
//     x-amz-server-side-encryption-aws-kms-key-id , Amazon S3 uses the Amazon Web
//     Services managed key ( aws/s3 key) in KMS to protect the data.
//
//   - To perform a multipart upload with encryption by using an Amazon Web
//     Services KMS key, the requester must have permission to the kms:Decrypt and
//     kms:GenerateDataKey* actions on the key. These permissions are required
//     because Amazon S3 must decrypt and read data from the encrypted file parts
//     before it completes the multipart upload. For more information, see [Multipart upload API and permissions]and [Protecting data using server-side encryption with Amazon Web Services KMS]in
//     the Amazon S3 User Guide.
//
//   - If your Identity and Access Management (IAM) user or role is in the same
//     Amazon Web Services account as the KMS key, then you must have these permissions
//     on the key policy. If your IAM user or role is in a different account from the
//     key, then you must have the permissions on both the key policy and your IAM user
//     or role.
//
//   - All GET and PUT requests for an object protected by KMS fail if you don't
//     make them by using Secure Sockets Layer (SSL), Transport Layer Security (TLS),
//     or Signature Version 4. For information about configuring any of the officially
//     supported Amazon Web Services SDKs and Amazon Web Services CLI, see [Specifying the Signature Version in Request Authentication]in the
//     Amazon S3 User Guide.
//
// For more information about server-side encryption with KMS keys (SSE-KMS), see [Protecting Data Using Server-Side Encryption with KMS keys]
//
//	in the Amazon S3 User Guide.
//
//	- Use customer-provided encryption keys (SSE-C) – If you want to manage your
//	own encryption keys, provide all the following headers in the request.
//
//	- x-amz-server-side-encryption-customer-algorithm
//
//	- x-amz-server-side-encryption-customer-key
//
//	- x-amz-server-side-encryption-customer-key-MD5
//
// For more information about server-side encryption with customer-provided
//
//	encryption keys (SSE-C), see [Protecting data using server-side encryption with customer-provided encryption keys (SSE-C)]in the Amazon S3 User Guide.
//
//	- Directory buckets - For directory buckets, there are only two supported
//	options for server-side encryption: server-side encryption with Amazon S3
//	managed keys (SSE-S3) ( AES256 ) and server-side encryption with KMS keys
//	(SSE-KMS) ( aws:kms ). We recommend that the bucket's default encryption uses
//	the desired encryption configuration and you don't override the bucket default
//	encryption in your CreateSession requests or PUT object requests. Then, new
//	objects are automatically encrypted with the desired encryption settings. For
//	more information, see [Protecting data with server-side encryption]in the Amazon S3 User Guide. For more information about
//	the encryption overriding behaviors in directory buckets, see [Specifying server-side encryption with KMS for new object uploads].
//
// In the Zonal endpoint API calls (except [CopyObject]and [UploadPartCopy]) using the REST API, the
//
//	encryption request headers must match the encryption settings that are specified
//	in the CreateSession request. You can't override the values of the encryption
//	settings ( x-amz-server-side-encryption ,
//	x-amz-server-side-encryption-aws-kms-key-id ,
//	x-amz-server-side-encryption-context , and
//	x-amz-server-side-encryption-bucket-key-enabled ) that are specified in the
//	CreateSession request. You don't need to explicitly specify these encryption
//	settings values in Zonal endpoint API calls, and Amazon S3 will use the
//	encryption settings values from the CreateSession request to protect new
//	objects in the directory bucket.
//
// When you use the CLI or the Amazon Web Services SDKs, for CreateSession , the
//
//	session token refreshes automatically to avoid service interruptions when a
//	session expires. The CLI or the Amazon Web Services SDKs use the bucket's
//	default encryption configuration for the CreateSession request. It's not
//	supported to override the encryption settings values in the CreateSession
//	request. So in the Zonal endpoint API calls (except [CopyObject]and [UploadPartCopy]), the encryption
//	request headers must match the default encryption configuration of the directory
//	bucket.
//
// For directory buckets, when you perform a CreateMultipartUpload operation and an
//
//	UploadPartCopy operation, the request headers you provide in the
//	CreateMultipartUpload request must match the default encryption configuration
//	of the destination bucket.
//
// HTTP Host header syntax  Directory buckets - The HTTP Host header syntax is
// Bucket-name.s3express-zone-id.region-code.amazonaws.com .
//
// The following operations are related to CreateMultipartUpload :
//
// [UploadPart]
//
// [CompleteMultipartUpload]
//
// [AbortMultipartUpload]
//
// [ListParts]
//
// [ListMultipartUploads]
//
// [Concepts for directory buckets in Local Zones]: https://docs.aws.amazon.com/AmazonS3/latest/userguide/s3-lzs-for-directory-buckets.html
// [ListParts]: https://docs.aws.amazon.com/AmazonS3/latest/API/API_ListParts.html
// [UploadPart]: https://docs.aws.amazon.com/AmazonS3/latest/API/API_UploadPart.html
// [Protecting Data Using Server-Side Encryption with KMS keys]: https://docs.aws.amazon.com/AmazonS3/latest/userguide/UsingKMSEncryption.html
// [Specifying the Signature Version in Request Authentication]: https://docs.aws.amazon.com/AmazonS3/latest/dev/UsingAWSSDK.html#specify-signature-version
// [Aborting Incomplete Multipart Uploads Using a Bucket Lifecycle Configuration]: https://docs.aws.amazon.com/AmazonS3/latest/dev/mpuoverview.html#mpu-abort-incomplete-mpu-lifecycle-config
// [CopyObject]: https://docs.aws.amazon.com/AmazonS3/latest/API/API_CopyObject.html
// [CreateSession]: https://docs.aws.amazon.com/AmazonS3/latest/API/API_CreateSession.html
// [Multipart upload API and permissions]: https://docs.aws.amazon.com/AmazonS3/latest/userguide/mpuoverview.html#mpuAndPermissions
// [UploadPartCopy]: https://docs.aws.amazon.com/AmazonS3/latest/API/API_UploadPartCopy.html
// [CompleteMultipartUpload]: https://docs.aws.amazon.com/AmazonS3/latest/API/API_CompleteMultipartUpload.html
// [Authenticating Requests (Amazon Web Services Signature Version 4)]: https://docs.aws.amazon.com/AmazonS3/latest/API/sig-v4-authenticating-requests.html
// [AbortMultipartUpload]: https://docs.aws.amazon.com/AmazonS3/latest/API/API_AbortMultipartUpload.html
// [Multipart Upload Overview]: https://docs.aws.amazon.com/AmazonS3/latest/dev/mpuoverview.html
// [Protecting data using server-side encryption with Amazon Web Services KMS]: https://docs.aws.amazon.com/AmazonS3/latest/userguide/UsingKMSEncryption.html
// [ListMultipartUploads]: https://docs.aws.amazon.com/AmazonS3/latest/API/API_ListMultipartUploads.html
// [Regional and Zonal endpoints for directory buckets in Availability Zones]: https://docs.aws.amazon.com/AmazonS3/latest/userguide/endpoint-directory-buckets-AZ.html
//
// [Specifying server-side encryption with KMS for new object uploads]: https://docs.aws.amazon.com/AmazonS3/latest/userguide/s3-express-specifying-kms-encryption.html
// [Protecting data using server-side encryption with customer-provided encryption keys (SSE-C)]: https://docs.aws.amazon.com/AmazonS3/latest/userguide/ServerSideEncryptionCustomerKeys.html
// [Protecting data with server-side encryption]: https://docs.aws.amazon.com/AmazonS3/latest/userguide/s3-express-serv-side-encryption.html
func (c *Client) CreateMultipartUpload(ctx context.Context, params *CreateMultipartUploadInput, optFns ...func(*Options)) (*CreateMultipartUploadOutput, error) {
	if params == nil {
		params = &CreateMultipartUploadInput{}
	}

	result, metadata, err := c.invokeOperation(ctx, "CreateMultipartUpload", params, optFns, c.addOperationCreateMultipartUploadMiddlewares)
	if err != nil {
		return nil, err
	}

	out := result.(*CreateMultipartUploadOutput)
	out.ResultMetadata = metadata
	return out, nil
}

type CreateMultipartUploadInput struct {

	// The name of the bucket where the multipart upload is initiated and where the
	// object is uploaded.
	//
	// Directory buckets - When you use this operation with a directory bucket, you
	// must use virtual-hosted-style requests in the format
	// Bucket-name.s3express-zone-id.region-code.amazonaws.com . Path-style requests
	// are not supported. Directory bucket names must be unique in the chosen Zone
	// (Availability Zone or Local Zone). Bucket names must follow the format
	// bucket-base-name--zone-id--x-s3 (for example,
	// amzn-s3-demo-bucket--usw2-az1--x-s3 ). For information about bucket naming
	// restrictions, see [Directory bucket naming rules]in the Amazon S3 User Guide.
	//
	// Access points - When you use this action with an access point for general
	// purpose buckets, you must provide the alias of the access point in place of the
	// bucket name or specify the access point ARN. When you use this action with an
	// access point for directory buckets, you must provide the access point name in
	// place of the bucket name. When using the access point ARN, you must direct
	// requests to the access point hostname. The access point hostname takes the form
	// AccessPointName-AccountId.s3-accesspoint.Region.amazonaws.com. When using this
	// action with an access point through the Amazon Web Services SDKs, you provide
	// the access point ARN in place of the bucket name. For more information about
	// access point ARNs, see [Using access points]in the Amazon S3 User Guide.
	//
	// Object Lambda access points are not supported by directory buckets.
	//
	// S3 on Outposts - When you use this action with S3 on Outposts, you must direct
	// requests to the S3 on Outposts hostname. The S3 on Outposts hostname takes the
	// form AccessPointName-AccountId.outpostID.s3-outposts.Region.amazonaws.com . When
	// you use this action with S3 on Outposts, the destination bucket must be the
	// Outposts access point ARN or the access point alias. For more information about
	// S3 on Outposts, see [What is S3 on Outposts?]in the Amazon S3 User Guide.
	//
	// [Directory bucket naming rules]: https://docs.aws.amazon.com/AmazonS3/latest/userguide/directory-bucket-naming-rules.html
	// [What is S3 on Outposts?]: https://docs.aws.amazon.com/AmazonS3/latest/userguide/S3onOutposts.html
	// [Using access points]: https://docs.aws.amazon.com/AmazonS3/latest/userguide/using-access-points.html
	//
	// This member is required.
	Bucket *string

	// Object key for which the multipart upload is to be initiated.
	//
	// This member is required.
	Key *string

	// The canned ACL to apply to the object. Amazon S3 supports a set of predefined
	// ACLs, known as canned ACLs. Each canned ACL has a predefined set of grantees and
	// permissions. For more information, see [Canned ACL]in the Amazon S3 User Guide.
	//
	// By default, all objects are private. Only the owner has full access control.
	// When uploading an object, you can grant access permissions to individual Amazon
	// Web Services accounts or to predefined groups defined by Amazon S3. These
	// permissions are then added to the access control list (ACL) on the new object.
	// For more information, see [Using ACLs]. One way to grant the permissions using the request
	// headers is to specify a canned ACL with the x-amz-acl request header.
	//
	//   - This functionality is not supported for directory buckets.
	//
	//   - This functionality is not supported for Amazon S3 on Outposts.
	//
	// [Canned ACL]: https://docs.aws.amazon.com/AmazonS3/latest/dev/acl-overview.html#CannedACL
	// [Using ACLs]: https://docs.aws.amazon.com/AmazonS3/latest/dev/S3_ACLs_UsingACLs.html
	ACL types.ObjectCannedACL

	// Specifies whether Amazon S3 should use an S3 Bucket Key for object encryption
	// with server-side encryption using Key Management Service (KMS) keys (SSE-KMS).
	//
	// General purpose buckets - Setting this header to true causes Amazon S3 to use
	// an S3 Bucket Key for object encryption with SSE-KMS. Also, specifying this
	// header with a PUT action doesn't affect bucket-level settings for S3 Bucket Key.
	//
	// Directory buckets - S3 Bucket Keys are always enabled for GET and PUT
	// operations in a directory bucket and can’t be disabled. S3 Bucket Keys aren't
	// supported, when you copy SSE-KMS encrypted objects from general purpose buckets
	// to directory buckets, from directory buckets to general purpose buckets, or
	// between directory buckets, through [CopyObject], [UploadPartCopy], [the Copy operation in Batch Operations], or [the import jobs]. In this case, Amazon S3 makes a
	// call to KMS every time a copy request is made for a KMS-encrypted object.
	//
	// [CopyObject]: https://docs.aws.amazon.com/AmazonS3/latest/API/API_CopyObject.html
	// [the import jobs]: https://docs.aws.amazon.com/AmazonS3/latest/userguide/create-import-job
	// [UploadPartCopy]: https://docs.aws.amazon.com/AmazonS3/latest/API/API_UploadPartCopy.html
	// [the Copy operation in Batch Operations]: https://docs.aws.amazon.com/AmazonS3/latest/userguide/directory-buckets-objects-Batch-Ops
	BucketKeyEnabled *bool

	// Specifies caching behavior along the request/reply chain.
	CacheControl *string

	// Indicates the algorithm that you want Amazon S3 to use to create the checksum
	// for the object. For more information, see [Checking object integrity]in the Amazon S3 User Guide.
	//
	// [Checking object integrity]: https://docs.aws.amazon.com/AmazonS3/latest/userguide/checking-object-integrity.html
	ChecksumAlgorithm types.ChecksumAlgorithm

	// Indicates the checksum type that you want Amazon S3 to use to calculate the
	// object’s checksum value. For more information, see [Checking object integrity in the Amazon S3 User Guide].
	//
	// [Checking object integrity in the Amazon S3 User Guide]: https://docs.aws.amazon.com/AmazonS3/latest/userguide/checking-object-integrity.html
	ChecksumType types.ChecksumType

	// Specifies presentational information for the object.
	ContentDisposition *string

	// Specifies what content encodings have been applied to the object and thus what
	// decoding mechanisms must be applied to obtain the media-type referenced by the
	// Content-Type header field.
	//
	// For directory buckets, only the aws-chunked value is supported in this header
	// field.
	ContentEncoding *string

	// The language that the content is in.
	ContentLanguage *string

	// A standard MIME type describing the format of the object data.
	ContentType *string

	// The account ID of the expected bucket owner. If the account ID that you provide
	// does not match the actual owner of the bucket, the request fails with the HTTP
	// status code 403 Forbidden (access denied).
	ExpectedBucketOwner *string

	// The date and time at which the object is no longer cacheable.
	Expires *time.Time

	// Specify access permissions explicitly to give the grantee READ, READ_ACP, and
	// WRITE_ACP permissions on the object.
	//
	// By default, all objects are private. Only the owner has full access control.
	// When uploading an object, you can use this header to explicitly grant access
	// permissions to specific Amazon Web Services accounts or groups. This header maps
	// to specific permissions that Amazon S3 supports in an ACL. For more information,
	// see [Access Control List (ACL) Overview]in the Amazon S3 User Guide.
	//
	// You specify each grantee as a type=value pair, where the type is one of the
	// following:
	//
	//   - id – if the value specified is the canonical user ID of an Amazon Web
	//   Services account
	//
	//   - uri – if you are granting permissions to a predefined group
	//
	//   - emailAddress – if the value specified is the email address of an Amazon Web
	//   Services account
	//
	// Using email addresses to specify a grantee is only supported in the following
	//   Amazon Web Services Regions:
	//
	//   - US East (N. Virginia)
	//
	//   - US West (N. California)
	//
	//   - US West (Oregon)
	//
	//   - Asia Pacific (Singapore)
	//
	//   - Asia Pacific (Sydney)
	//
	//   - Asia Pacific (Tokyo)
	//
	//   - Europe (Ireland)
	//
	//   - South America (São Paulo)
	//
	// For a list of all the Amazon S3 supported Regions and endpoints, see [Regions and Endpoints]in the
	//   Amazon Web Services General Reference.
	//
	// For example, the following x-amz-grant-read header grants the Amazon Web
	// Services accounts identified by account IDs permissions to read object data and
	// its metadata:
	//
	//     x-amz-grant-read: id="11112222333", id="444455556666"
	//
	//   - This functionality is not supported for directory buckets.
	//
	//   - This functionality is not supported for Amazon S3 on Outposts.
	//
	// [Regions and Endpoints]: https://docs.aws.amazon.com/general/latest/gr/rande.html#s3_region
	// [Access Control List (ACL) Overview]: https://docs.aws.amazon.com/AmazonS3/latest/dev/acl-overview.html
	GrantFullControl *string

	// Specify access permissions explicitly to allow grantee to read the object data
	// and its metadata.
	//
	// By default, all objects are private. Only the owner has full access control.
	// When uploading an object, you can use this header to explicitly grant access
	// permissions to specific Amazon Web Services accounts or groups. This header maps
	// to specific permissions that Amazon S3 supports in an ACL. For more information,
	// see [Access Control List (ACL) Overview]in the Amazon S3 User Guide.
	//
	// You specify each grantee as a type=value pair, where the type is one of the
	// following:
	//
	//   - id – if the value specified is the canonical user ID of an Amazon Web
	//   Services account
	//
	//   - uri – if you are granting permissions to a predefined group
	//
	//   - emailAddress – if the value specified is the email address of an Amazon Web
	//   Services account
	//
	// Using email addresses to specify a grantee is only supported in the following
	//   Amazon Web Services Regions:
	//
	//   - US East (N. Virginia)
	//
	//   - US West (N. California)
	//
	//   - US West (Oregon)
	//
	//   - Asia Pacific (Singapore)
	//
	//   - Asia Pacific (Sydney)
	//
	//   - Asia Pacific (Tokyo)
	//
	//   - Europe (Ireland)
	//
	//   - South America (São Paulo)
	//
	// For a list of all the Amazon S3 supported Regions and endpoints, see [Regions and Endpoints]in the
	//   Amazon Web Services General Reference.
	//
	// For example, the following x-amz-grant-read header grants the Amazon Web
	// Services accounts identified by account IDs permissions to read object data and
	// its metadata:
	//
	//     x-amz-grant-read: id="11112222333", id="444455556666"
	//
	//   - This functionality is not supported for directory buckets.
	//
	//   - This functionality is not supported for Amazon S3 on Outposts.
	//
	// [Regions and Endpoints]: https://docs.aws.amazon.com/general/latest/gr/rande.html#s3_region
	// [Access Control List (ACL) Overview]: https://docs.aws.amazon.com/AmazonS3/latest/dev/acl-overview.html
	GrantRead *string

	// Specify access permissions explicitly to allows grantee to read the object ACL.
	//
	// By default, all objects are private. Only the owner has full access control.
	// When uploading an object, you can use this header to explicitly grant access
	// permissions to specific Amazon Web Services accounts or groups. This header maps
	// to specific permissions that Amazon S3 supports in an ACL. For more information,
	// see [Access Control List (ACL) Overview]in the Amazon S3 User Guide.
	//
	// You specify each grantee as a type=value pair, where the type is one of the
	// following:
	//
	//   - id – if the value specified is the canonical user ID of an Amazon Web
	//   Services account
	//
	//   - uri – if you are granting permissions to a predefined group
	//
	//   - emailAddress – if the value specified is the email address of an Amazon Web
	//   Services account
	//
	// Using email addresses to specify a grantee is only supported in the following
	//   Amazon Web Services Regions:
	//
	//   - US East (N. Virginia)
	//
	//   - US West (N. California)
	//
	//   - US West (Oregon)
	//
	//   - Asia Pacific (Singapore)
	//
	//   - Asia Pacific (Sydney)
	//
	//   - Asia Pacific (Tokyo)
	//
	//   - Europe (Ireland)
	//
	//   - South America (São Paulo)
	//
	// For a list of all the Amazon S3 supported Regions and endpoints, see [Regions and Endpoints]in the
	//   Amazon Web Services General Reference.
	//
	// For example, the following x-amz-grant-read header grants the Amazon Web
	// Services accounts identified by account IDs permissions to read object data and
	// its metadata:
	//
	//     x-amz-grant-read: id="11112222333", id="444455556666"
	//
	//   - This functionality is not supported for directory buckets.
	//
	//   - This functionality is not supported for Amazon S3 on Outposts.
	//
	// [Regions and Endpoints]: https://docs.aws.amazon.com/general/latest/gr/rande.html#s3_region
	// [Access Control List (ACL) Overview]: https://docs.aws.amazon.com/AmazonS3/latest/dev/acl-overview.html
	GrantReadACP *string

	// Specify access permissions explicitly to allows grantee to allow grantee to
	// write the ACL for the applicable object.
	//
	// By default, all objects are private. Only the owner has full access control.
	// When uploading an object, you can use this header to explicitly grant access
	// permissions to specific Amazon Web Services accounts or groups. This header maps
	// to specific permissions that Amazon S3 supports in an ACL. For more information,
	// see [Access Control List (ACL) Overview]in the Amazon S3 User Guide.
	//
	// You specify each grantee as a type=value pair, where the type is one of the
	// following:
	//
	//   - id – if the value specified is the canonical user ID of an Amazon Web
	//   Services account
	//
	//   - uri – if you are granting permissions to a predefined group
	//
	//   - emailAddress – if the value specified is the email address of an Amazon Web
	//   Services account
	//
	// Using email addresses to specify a grantee is only supported in the following
	//   Amazon Web Services Regions:
	//
	//   - US East (N. Virginia)
	//
	//   - US West (N. California)
	//
	//   - US West (Oregon)
	//
	//   - Asia Pacific (Singapore)
	//
	//   - Asia Pacific (Sydney)
	//
	//   - Asia Pacific (Tokyo)
	//
	//   - Europe (Ireland)
	//
	//   - South America (São Paulo)
	//
	// For a list of all the Amazon S3 supported Regions and endpoints, see [Regions and Endpoints]in the
	//   Amazon Web Services General Reference.
	//
	// For example, the following x-amz-grant-read header grants the Amazon Web
	// Services accounts identified by account IDs permissions to read object data and
	// its metadata:
	//
	//     x-amz-grant-read: id="11112222333", id="444455556666"
	//
	//   - This functionality is not supported for directory buckets.
	//
	//   - This functionality is not supported for Amazon S3 on Outposts.
	//
	// [Regions and Endpoints]: https://docs.aws.amazon.com/general/latest/gr/rande.html#s3_region
	// [Access Control List (ACL) Overview]: https://docs.aws.amazon.com/AmazonS3/latest/dev/acl-overview.html
	GrantWriteACP *string

	// A map of metadata to store with the object in S3.
	Metadata map[string]string

	// Specifies whether you want to apply a legal hold to the uploaded object.
	//
	// This functionality is not supported for directory buckets.
	ObjectLockLegalHoldStatus types.ObjectLockLegalHoldStatus

	// Specifies the Object Lock mode that you want to apply to the uploaded object.
	//
	// This functionality is not supported for directory buckets.
	ObjectLockMode types.ObjectLockMode

	// Specifies the date and time when you want the Object Lock to expire.
	//
	// This functionality is not supported for directory buckets.
	ObjectLockRetainUntilDate *time.Time

	// Confirms that the requester knows that they will be charged for the request.
	// Bucket owners need not specify this parameter in their requests. If either the
	// source or destination S3 bucket has Requester Pays enabled, the requester will
	// pay for corresponding charges to copy the object. For information about
	// downloading objects from Requester Pays buckets, see [Downloading Objects in Requester Pays Buckets]in the Amazon S3 User
	// Guide.
	//
	// This functionality is not supported for directory buckets.
	//
	// [Downloading Objects in Requester Pays Buckets]: https://docs.aws.amazon.com/AmazonS3/latest/dev/ObjectsinRequesterPaysBuckets.html
	RequestPayer types.RequestPayer

	// Specifies the algorithm to use when encrypting the object (for example, AES256).
	//
	// This functionality is not supported for directory buckets.
	SSECustomerAlgorithm *string

	// Specifies the customer-provided encryption key for Amazon S3 to use in
	// encrypting data. This value is used to store the object and then it is
	// discarded; Amazon S3 does not store the encryption key. The key must be
	// appropriate for use with the algorithm specified in the
	// x-amz-server-side-encryption-customer-algorithm header.
	//
	// This functionality is not supported for directory buckets.
	SSECustomerKey *string

	// Specifies the 128-bit MD5 digest of the customer-provided encryption key
	// according to RFC 1321. Amazon S3 uses this header for a message integrity check
	// to ensure that the encryption key was transmitted without error.
	//
	// This functionality is not supported for directory buckets.
	SSECustomerKeyMD5 *string

	// Specifies the Amazon Web Services KMS Encryption Context to use for object
	// encryption. The value of this header is a Base64 encoded string of a UTF-8
	// encoded JSON, which contains the encryption context as key-value pairs.
	//
	// Directory buckets - You can optionally provide an explicit encryption context
	// value. The value must match the default encryption context - the bucket Amazon
	// Resource Name (ARN). An additional encryption context value is not supported.
	SSEKMSEncryptionContext *string

	// Specifies the KMS key ID (Key ID, Key ARN, or Key Alias) to use for object
	// encryption. If the KMS key doesn't exist in the same account that's issuing the
	// command, you must use the full Key ARN not the Key ID.
	//
	// General purpose buckets - If you specify x-amz-server-side-encryption with
	// aws:kms or aws:kms:dsse , this header specifies the ID (Key ID, Key ARN, or Key
	// Alias) of the KMS key to use. If you specify
	// x-amz-server-side-encryption:aws:kms or
	// x-amz-server-side-encryption:aws:kms:dsse , but do not provide
	// x-amz-server-side-encryption-aws-kms-key-id , Amazon S3 uses the Amazon Web
	// Services managed key ( aws/s3 ) to protect the data.
	//
	// Directory buckets - To encrypt data using SSE-KMS, it's recommended to specify
	// the x-amz-server-side-encryption header to aws:kms . Then, the
	// x-amz-server-side-encryption-aws-kms-key-id header implicitly uses the bucket's
	// default KMS customer managed key ID. If you want to explicitly set the
	// x-amz-server-side-encryption-aws-kms-key-id header, it must match the bucket's
	// default customer managed key (using key ID or ARN, not alias). Your SSE-KMS
	// configuration can only support 1 [customer managed key]per directory bucket's lifetime. The [Amazon Web Services managed key] ( aws/s3
	// ) isn't supported.
	//
	// Incorrect key specification results in an HTTP 400 Bad Request error.
	//
	// [customer managed key]: https://docs.aws.amazon.com/kms/latest/developerguide/concepts.html#customer-cmk
	// [Amazon Web Services managed key]: https://docs.aws.amazon.com/kms/latest/developerguide/concepts.html#aws-managed-cmk
	SSEKMSKeyId *string

	// The server-side encryption algorithm used when you store this object in Amazon
	// S3 (for example, AES256 , aws:kms ).
	//
	//   - Directory buckets - For directory buckets, there are only two supported
	//   options for server-side encryption: server-side encryption with Amazon S3
	//   managed keys (SSE-S3) ( AES256 ) and server-side encryption with KMS keys
	//   (SSE-KMS) ( aws:kms ). We recommend that the bucket's default encryption uses
	//   the desired encryption configuration and you don't override the bucket default
	//   encryption in your CreateSession requests or PUT object requests. Then, new
	//   objects are automatically encrypted with the desired encryption settings. For
	//   more information, see [Protecting data with server-side encryption]in the Amazon S3 User Guide. For more information about
	//   the encryption overriding behaviors in directory buckets, see [Specifying server-side encryption with KMS for new object uploads].
	//
	// In the Zonal endpoint API calls (except [CopyObject]and [UploadPartCopy]) using the REST API, the
	//   encryption request headers must match the encryption settings that are specified
	//   in the CreateSession request. You can't override the values of the encryption
	//   settings ( x-amz-server-side-encryption ,
	//   x-amz-server-side-encryption-aws-kms-key-id ,
	//   x-amz-server-side-encryption-context , and
	//   x-amz-server-side-encryption-bucket-key-enabled ) that are specified in the
	//   CreateSession request. You don't need to explicitly specify these encryption
	//   settings values in Zonal endpoint API calls, and Amazon S3 will use the
	//   encryption settings values from the CreateSession request to protect new
	//   objects in the directory bucket.
	//
	// When you use the CLI or the Amazon Web Services SDKs, for CreateSession , the
	//   session token refreshes automatically to avoid service interruptions when a
	//   session expires. The CLI or the Amazon Web Services SDKs use the bucket's
	//   default encryption configuration for the CreateSession request. It's not
	//   supported to override the encryption settings values in the CreateSession
	//   request. So in the Zonal endpoint API calls (except [CopyObject]and [UploadPartCopy]), the encryption
	//   request headers must match the default encryption configuration of the directory
	//   bucket.
	//
	// [Specifying server-side encryption with KMS for new object uploads]: https://docs.aws.amazon.com/AmazonS3/latest/userguide/s3-express-specifying-kms-encryption.html
	// [Protecting data with server-side encryption]: https://docs.aws.amazon.com/AmazonS3/latest/userguide/s3-express-serv-side-encryption.html
	// [CopyObject]: https://docs.aws.amazon.com/AmazonS3/latest/API/API_CopyObject.html
	// [UploadPartCopy]: https://docs.aws.amazon.com/AmazonS3/latest/API/API_UploadPartCopy.html
	ServerSideEncryption types.ServerSideEncryption

	// By default, Amazon S3 uses the STANDARD Storage Class to store newly created
	// objects. The STANDARD storage class provides high durability and high
	// availability. Depending on performance needs, you can specify a different
	// Storage Class. For more information, see [Storage Classes]in the Amazon S3 User Guide.
	//
	//   - Directory buckets only support EXPRESS_ONEZONE (the S3 Express One Zone
	//   storage class) in Availability Zones and ONEZONE_IA (the S3 One
	//   Zone-Infrequent Access storage class) in Dedicated Local Zones.
	//
	//   - Amazon S3 on Outposts only uses the OUTPOSTS Storage Class.
	//
	// [Storage Classes]: https://docs.aws.amazon.com/AmazonS3/latest/dev/storage-class-intro.html
	StorageClass types.StorageClass

	// The tag-set for the object. The tag-set must be encoded as URL Query parameters.
	//
	// This functionality is not supported for directory buckets.
	Tagging *string

	// If the bucket is configured as a website, redirects requests for this object to
	// another object in the same bucket or to an external URL. Amazon S3 stores the
	// value of this header in the object metadata.
	//
	// This functionality is not supported for directory buckets.
	WebsiteRedirectLocation *string

	noSmithyDocumentSerde
}

func (in *CreateMultipartUploadInput) bindEndpointParams(p *EndpointParameters) {

	p.Bucket = in.Bucket
	p.Key = in.Key

}

type CreateMultipartUploadOutput struct {

	// If the bucket has a lifecycle rule configured with an action to abort
	// incomplete multipart uploads and the prefix in the lifecycle rule matches the
	// object name in the request, the response includes this header. The header
	// indicates when the initiated multipart upload becomes eligible for an abort
	// operation. For more information, see [Aborting Incomplete Multipart Uploads Using a Bucket Lifecycle Configuration]in the Amazon S3 User Guide.
	//
	// The response also includes the x-amz-abort-rule-id header that provides the ID
	// of the lifecycle configuration rule that defines the abort action.
	//
	// This functionality is not supported for directory buckets.
	//
	// [Aborting Incomplete Multipart Uploads Using a Bucket Lifecycle Configuration]: https://docs.aws.amazon.com/AmazonS3/latest/dev/mpuoverview.html#mpu-abort-incomplete-mpu-lifecycle-config
	AbortDate *time.Time

	// This header is returned along with the x-amz-abort-date header. It identifies
	// the applicable lifecycle configuration rule that defines the action to abort
	// incomplete multipart uploads.
	//
	// This functionality is not supported for directory buckets.
	AbortRuleId *string

	// The name of the bucket to which the multipart upload was initiated. Does not
	// return the access point ARN or access point alias if used.
	//
	// Access points are not supported by directory buckets.
	Bucket *string

	// Indicates whether the multipart upload uses an S3 Bucket Key for server-side
	// encryption with Key Management Service (KMS) keys (SSE-KMS).
	BucketKeyEnabled *bool

	// The algorithm that was used to create a checksum of the object.
	ChecksumAlgorithm types.ChecksumAlgorithm

	//  Indicates the checksum type that you want Amazon S3 to use to calculate the
	// object’s checksum value. For more information, see [Checking object integrity in the Amazon S3 User Guide].
	//
	// [Checking object integrity in the Amazon S3 User Guide]: https://docs.aws.amazon.com/AmazonS3/latest/userguide/checking-object-integrity.html
	ChecksumType types.ChecksumType

	// Object key for which the multipart upload was initiated.
	Key *string

	// If present, indicates that the requester was successfully charged for the
	// request. For more information, see [Using Requester Pays buckets for storage transfers and usage]in the Amazon Simple Storage Service user
	// guide.
	//
	// This functionality is not supported for directory buckets.
	//
	// [Using Requester Pays buckets for storage transfers and usage]: https://docs.aws.amazon.com/AmazonS3/latest/userguide/RequesterPaysBuckets.html
	RequestCharged types.RequestCharged

	// If server-side encryption with a customer-provided encryption key was
	// requested, the response will include this header to confirm the encryption
	// algorithm that's used.
	//
	// This functionality is not supported for directory buckets.
	SSECustomerAlgorithm *string

	// If server-side encryption with a customer-provided encryption key was
	// requested, the response will include this header to provide the round-trip
	// message integrity verification of the customer-provided encryption key.
	//
	// This functionality is not supported for directory buckets.
	SSECustomerKeyMD5 *string

	// If present, indicates the Amazon Web Services KMS Encryption Context to use for
	// object encryption. The value of this header is a Base64 encoded string of a
	// UTF-8 encoded JSON, which contains the encryption context as key-value pairs.
	SSEKMSEncryptionContext *string

	// If present, indicates the ID of the KMS key that was used for object encryption.
	SSEKMSKeyId *string

	// The server-side encryption algorithm used when you store this object in Amazon
	// S3 (for example, AES256 , aws:kms ).
	ServerSideEncryption types.ServerSideEncryption

	// ID for the initiated multipart upload.
	UploadId *string

	// Metadata pertaining to the operation's result.
	ResultMetadata middleware.Metadata

	noSmithyDocumentSerde
}

func (c *Client) addOperationCreateMultipartUploadMiddlewares(stack *middleware.Stack, options Options) (err error) {
	if err := stack.Serialize.Add(&setOperationInputMiddleware{}, middleware.After); err != nil {
		return err
	}
	err = stack.Serialize.Add(&awsRestxml_serializeOpCreateMultipartUpload{}, middleware.After)
	if err != nil {
		return err
	}
	err = stack.Deserialize.Add(&awsRestxml_deserializeOpCreateMultipartUpload{}, middleware.After)
	if err != nil {
		return err
	}
	if err := addProtocolFinalizerMiddlewares(stack, options, "CreateMultipartUpload"); err != nil {
		return fmt.Errorf("add protocol finalizers: %v", err)
	}

	if err = addlegacyEndpointContextSetter(stack, options); err != nil {
		return err
	}
	if err = addSetLoggerMiddleware(stack, options); err != nil {
		return err
	}
	if err = addClientRequestID(stack); err != nil {
		return err
	}
	if err = addComputeContentLength(stack); err != nil {
		return err
	}
	if err = addResolveEndpointMiddleware(stack, options); err != nil {
		return err
	}
	if err = addComputePayloadSHA256(stack); err != nil {
		return err
	}
	if err = addRetry(stack, options); err != nil {
		return err
	}
	if err = addRawResponseToMetadata(stack); err != nil {
		return err
	}
	if err = addRecordResponseTiming(stack); err != nil {
		return err
	}
	if err = addSpanRetryLoop(stack, options); err != nil {
		return err
	}
	if err = addClientUserAgent(stack, options); err != nil {
		return err
	}
	if err = smithyhttp.AddErrorCloseResponseBodyMiddleware(stack); err != nil {
		return err
	}
	if err = smithyhttp.AddCloseResponseBodyMiddleware(stack); err != nil {
		return err
	}
	if err = addSetLegacyContextSigningOptionsMiddleware(stack); err != nil {
		return err
	}
	if err = addPutBucketContextMiddleware(stack); err != nil {
		return err
	}
	if err = addTimeOffsetBuild(stack, c); err != nil {
		return err
	}
	if err = addUserAgentRetryMode(stack, options); err != nil {
		return err
	}
	if err = addIsExpressUserAgent(stack); err != nil {
		return err
	}
	if err = addCredentialSource(stack, options); err != nil {
		return err
	}
	if err = addOpCreateMultipartUploadValidationMiddleware(stack); err != nil {
		return err
	}
	if err = stack.Initialize.Add(newServiceMetadataMiddleware_opCreateMultipartUpload(options.Region), middleware.Before); err != nil {
		return err
	}
	if err = addMetadataRetrieverMiddleware(stack); err != nil {
		return err
	}
	if err = addRecursionDetection(stack); err != nil {
		return err
	}
	if err = addCreateMultipartUploadUpdateEndpoint(stack, options); err != nil {
		return err
	}
	if err = addResponseErrorMiddleware(stack); err != nil {
		return err
	}
	if err = v4.AddContentSHA256HeaderMiddleware(stack); err != nil {
		return err
	}
	if err = disableAcceptEncodingGzip(stack); err != nil {
		return err
	}
	if err = addRequestResponseLogging(stack, options); err != nil {
		return err
	}
	if err = addDisableHTTPSMiddleware(stack, options); err != nil {
		return err
	}
	if err = addSerializeImmutableHostnameBucketMiddleware(stack, options); err != nil {
		return err
	}
	if err = addSetCreateMPUChecksumAlgorithm(stack); err != nil {
		return err
	}
	if err = addSpanInitializeStart(stack); err != nil {
		return err
	}
	if err = addSpanInitializeEnd(stack); err != nil {
		return err
	}
	if err = addSpanBuildRequestStart(stack); err != nil {
		return err
	}
	if err = addSpanBuildRequestEnd(stack); err != nil {
		return err
	}
	return nil
}

func (v *CreateMultipartUploadInput) bucket() (string, bool) {
	if v.Bucket == nil {
		return "", false
	}
	return *v.Bucket, true
}

func newServiceMetadataMiddleware_opCreateMultipartUpload(region string) *awsmiddleware.RegisterServiceMetadata {
	return &awsmiddleware.RegisterServiceMetadata{
		Region:        region,
		ServiceID:     ServiceID,
		OperationName: "CreateMultipartUpload",
	}
}

// getCreateMultipartUploadBucketMember returns a pointer to string denoting a
// provided bucket member valueand a boolean indicating if the input has a modeled
// bucket name,
func getCreateMultipartUploadBucketMember(input interface{}) (*string, bool) {
	in := input.(*CreateMultipartUploadInput)
	if in.Bucket == nil {
		return nil, false
	}
	return in.Bucket, true
}
func addCreateMultipartUploadUpdateEndpoint(stack *middleware.Stack, options Options) error {
	return s3cust.UpdateEndpoint(stack, s3cust.UpdateEndpointOptions{
		Accessor: s3cust.UpdateEndpointParameterAccessor{
			GetBucketFromInput: getCreateMultipartUploadBucketMember,
		},
		UsePathStyle:                   options.UsePathStyle,
		UseAccelerate:                  options.UseAccelerate,
		SupportsAccelerate:             true,
		TargetS3ObjectLambda:           false,
		EndpointResolver:               options.EndpointResolver,
		EndpointResolverOptions:        options.EndpointOptions,
		UseARNRegion:                   options.UseARNRegion,
		DisableMultiRegionAccessPoints: options.DisableMultiRegionAccessPoints,
	})
}
