/*******************************************************************************
 *  Copyright 2012-2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
 *  Licensed under the Apache License, Version 2.0 (the "License"). You may not use
 *  this file except in compliance with the License. A copy of the License is located at
 *
 *  http://aws.amazon.com/apache2.0
 *
 *  or in the "license" file accompanying this file.
 *  This file is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
 *  CONDITIONS OF ANY KIND, either express or implied. See the License for the
 *  specific language governing permissions and limitations under the License.
 * *****************************************************************************
 *
 *  AWS Tools for Windows (TM) PowerShell (TM)
 *
 */
using System;
using System.Collections.Generic;
using System.Linq;
using System.Management.Automation;
using System.Text;
using Amazon.PowerShell.Common;
using Amazon.Runtime;
using Amazon.KeyManagementService;
using Amazon.KeyManagementService.Model;
namespace Amazon.PowerShell.Cmdlets.KMS
{
    /// 
    /// Changes the properties of a custom key store. You can use this operation to change
    /// the properties of an CloudHSM key store or an external key store.
    /// 
    ///  
    /// 
    /// Use the required CustomKeyStoreId parameter to identify the custom key
    /// store. Use the remaining optional parameters to change its properties. This operation
    /// does not return any property values. To verify the updated property values, use the
    /// DescribeCustomKeyStores operation.
    /// 
    ///  This operation is part of the custom
    /// key stores feature in KMS, which combines the convenience and extensive integration
    /// of KMS with the isolation and control of a key store that you own and manage.
    /// 
    /// When updating the properties of an external key store, verify that the updated settings
    /// connect your key store, via the external key store proxy, to the same external key
    /// manager as the previous settings, or to a backup or snapshot of the external key manager
    /// with the same cryptographic keys. If the updated connection settings fail, you can
    /// fix them and retry, although an extended delay might disrupt Amazon Web Services services.
    /// However, if KMS permanently loses its access to cryptographic keys, ciphertext encrypted
    /// under those keys is unrecoverable.
    /// 
    /// For external key stores:
    /// 
    /// Some external key managers provide a simpler method for updating an external key store.
    /// For details, see your external key manager documentation.
    /// 
    /// When updating an external key store in the KMS console, you can upload a JSON-based
    /// proxy configuration file with the desired values. You cannot upload the proxy configuration
    /// file to the UpdateCustomKeyStore operation. However, you can use the
    /// file to help you determine the correct values for the UpdateCustomKeyStore
    /// parameters.
    /// 
    /// For an CloudHSM key store, you can use this operation to change the custom key store
    /// friendly name (NewCustomKeyStoreName), to tell KMS about a change to
    /// the kmsuser crypto user password (KeyStorePassword), or
    /// to associate the custom key store with a different, but related, CloudHSM cluster
    /// (CloudHsmClusterId). To update any property of an CloudHSM key store,
    /// the ConnectionState of the CloudHSM key store must be DISCONNECTED.
    /// 
    /// 
    /// For an external key store, you can use this operation to change the custom key store
    /// friendly name (NewCustomKeyStoreName), or to tell KMS about a change
    /// to the external key store proxy authentication credentials (XksProxyAuthenticationCredential),
    /// connection method (XksProxyConnectivity), external proxy endpoint (XksProxyUriEndpoint)
    /// and path (XksProxyUriPath). For external key stores with an XksProxyConnectivity
    /// of VPC_ENDPOINT_SERVICE, you can also update the Amazon VPC endpoint
    /// service name (XksProxyVpcEndpointServiceName). To update most properties
    /// of an external key store, the ConnectionState of the external key store
    /// must be DISCONNECTED. However, you can update the CustomKeyStoreName,
    /// XksProxyAuthenticationCredential, and XksProxyUriPath of
    /// an external key store when it is in the CONNECTED or DISCONNECTED state. 
    /// 
    /// If your update requires a DISCONNECTED state, before using UpdateCustomKeyStore,
    /// use the DisconnectCustomKeyStore operation to disconnect the custom key store.
    /// After the UpdateCustomKeyStore operation completes, use the ConnectCustomKeyStore
    /// to reconnect the custom key store. To find the ConnectionState of the
    /// custom key store, use the DescribeCustomKeyStores operation. 
    /// 
    /// Before updating the custom key store, verify that the new values allow KMS to connect
    /// the custom key store to its backing key store. For example, before you change the
    /// XksProxyUriPath value, verify that the external key store proxy is reachable
    /// at the new path.
    /// 
    /// If the operation succeeds, it returns a JSON object with no properties.
    /// Cross-account use: No. You cannot perform this operation on a custom key store
    /// in a different Amazon Web Services account.
    /// Required permissions: kms:UpdateCustomKeyStore
    /// (IAM policy)
    /// Related operations:
    /// 
    [Cmdlet("Update", "KMSCustomKeyStore", SupportsShouldProcess = true, ConfirmImpact = ConfirmImpact.Medium)]
    [OutputType("None")]
    [AWSCmdlet("Calls the AWS Key Management Service UpdateCustomKeyStore API operation.", Operation = new[] {"UpdateCustomKeyStore"}, SelectReturnType = typeof(Amazon.KeyManagementService.Model.UpdateCustomKeyStoreResponse))]
    [AWSCmdletOutput("None or Amazon.KeyManagementService.Model.UpdateCustomKeyStoreResponse",
        "This cmdlet does not generate any output." +
        "The service response (type Amazon.KeyManagementService.Model.UpdateCustomKeyStoreResponse) can be referenced from properties attached to the cmdlet entry in the $AWSHistory stack."
    )]
    public partial class UpdateKMSCustomKeyStoreCmdlet : AmazonKeyManagementServiceClientCmdlet, IExecutor
    {
        
        protected override bool IsSensitiveRequest { get; set; } = true;
        
        #region Parameter XksProxyAuthenticationCredential_AccessKeyId
        /// 
        /// 
        /// A unique identifier for the raw secret access key.
        /// 
        /// 
        [System.Management.Automation.Parameter(ValueFromPipelineByPropertyName = true)]
        public System.String XksProxyAuthenticationCredential_AccessKeyId { get; set; }
        #endregion
        
        #region Parameter CloudHsmClusterId
        /// 
        /// 
        /// Associates the custom key store with a related CloudHSM cluster. This parameter is
        /// valid only for custom key stores with a CustomKeyStoreType of AWS_CLOUDHSM.Enter the cluster ID of the cluster that you used to create the custom key store or
        /// a cluster that shares a backup history and has the same cluster certificate as the
        /// original cluster. You cannot use this parameter to associate a custom key store with
        /// an unrelated cluster. In addition, the replacement cluster must fulfill
        /// the requirements for a cluster associated with a custom key store. To view the
        /// cluster certificate of a cluster, use the DescribeClusters
        /// operation.To change this value, the CloudHSM key store must be disconnected.
        /// 
        /// 
        [System.Management.Automation.Parameter(ValueFromPipelineByPropertyName = true)]
        public System.String CloudHsmClusterId { get; set; }
        #endregion
        
        #region Parameter CustomKeyStoreId
        /// 
        /// 
        /// Identifies the custom key store that you want to update. Enter the ID of the custom
        /// key store. To find the ID of a custom key store, use the DescribeCustomKeyStores
        /// operation.
        /// 
        /// 
        #if !MODULAR
        [System.Management.Automation.Parameter(Position = 0, ValueFromPipelineByPropertyName = true, ValueFromPipeline = true)]
        #else
        [System.Management.Automation.Parameter(Position = 0, ValueFromPipelineByPropertyName = true, ValueFromPipeline = true, Mandatory = true)]
        [System.Management.Automation.AllowEmptyString]
        [System.Management.Automation.AllowNull]
        #endif
        [Amazon.PowerShell.Common.AWSRequiredParameter]
        public System.String CustomKeyStoreId { get; set; }
        #endregion
        
        #region Parameter KeyStorePassword
        /// 
        /// 
        /// Enter the current password of the kmsuser crypto user (CU) in the CloudHSM
        /// cluster that is associated with the custom key store. This parameter is valid only
        /// for custom key stores with a CustomKeyStoreType of AWS_CLOUDHSM.This parameter tells KMS the current password of the kmsuser crypto user
        /// (CU). It does not set or change the password of any users in the CloudHSM cluster.To change this value, the CloudHSM key store must be disconnected.
        /// 
        /// 
        [System.Management.Automation.Parameter(ValueFromPipelineByPropertyName = true)]
        public System.String KeyStorePassword { get; set; }
        #endregion
        
        #region Parameter NewCustomKeyStoreName
        /// 
        /// 
        /// Changes the friendly name of the custom key store to the value that you specify. The
        /// custom key store name must be unique in the Amazon Web Services account.Do not include confidential or sensitive information in this field. This field may
        /// be displayed in plaintext in CloudTrail logs and other output.To change this value, an CloudHSM key store must be disconnected. An external key
        /// store can be connected or disconnected.
        /// 
        /// 
        [System.Management.Automation.Parameter(ValueFromPipelineByPropertyName = true)]
        public System.String NewCustomKeyStoreName { get; set; }
        #endregion
        
        #region Parameter XksProxyAuthenticationCredential_RawSecretAccessKey
        /// 
        /// 
        /// A secret string of 43-64 characters. Valid characters are a-z, A-Z, 0-9, /, +, and
        /// =.
        /// 
        /// 
        [System.Management.Automation.Parameter(ValueFromPipelineByPropertyName = true)]
        public System.String XksProxyAuthenticationCredential_RawSecretAccessKey { get; set; }
        #endregion
        
        #region Parameter XksProxyConnectivity
        /// 
        /// 
        /// Changes the connectivity setting for the external key store. To indicate that the
        /// external key store proxy uses a Amazon VPC endpoint service to communicate with KMS,
        /// specify VPC_ENDPOINT_SERVICE. Otherwise, specify PUBLIC_ENDPOINT.If you change the XksProxyConnectivity to VPC_ENDPOINT_SERVICE,
        /// you must also change the XksProxyUriEndpoint and add an XksProxyVpcEndpointServiceName
        /// value. If you change the XksProxyConnectivity to PUBLIC_ENDPOINT,
        /// you must also change the XksProxyUriEndpoint and specify a null or empty
        /// string for the XksProxyVpcEndpointServiceName value.To change this value, the external key store must be disconnected.
        /// 
        /// 
        [System.Management.Automation.Parameter(ValueFromPipelineByPropertyName = true)]
        [AWSConstantClassSource("Amazon.KeyManagementService.XksProxyConnectivityType")]
        public Amazon.KeyManagementService.XksProxyConnectivityType XksProxyConnectivity { get; set; }
        #endregion
        
        #region Parameter XksProxyUriEndpoint
        /// 
        /// 
        /// Changes the URI endpoint that KMS uses to connect to your external key store proxy
        /// (XKS proxy). This parameter is valid only for custom key stores with a CustomKeyStoreType
        /// of EXTERNAL_KEY_STORE.For external key stores with an XksProxyConnectivity value of PUBLIC_ENDPOINT,
        /// the protocol must be HTTPS.For external key stores with an XksProxyConnectivity value of VPC_ENDPOINT_SERVICE,
        /// specify https:// followed by the private DNS name associated with the
        /// VPC endpoint service. Each external key store must use a different private DNS name.The combined XksProxyUriEndpoint and XksProxyUriPath values
        /// must be unique in the Amazon Web Services account and Region.To change this value, the external key store must be disconnected.
        /// 
        /// 
        [System.Management.Automation.Parameter(ValueFromPipelineByPropertyName = true)]
        public System.String XksProxyUriEndpoint { get; set; }
        #endregion
        
        #region Parameter XksProxyUriPath
        /// 
        /// 
        /// Changes the base path to the proxy APIs for this external key store. To find this
        /// value, see the documentation for your external key manager and external key store
        /// proxy (XKS proxy). This parameter is valid only for custom key stores with a CustomKeyStoreType
        /// of EXTERNAL_KEY_STORE.The value must start with / and must end with /kms/xks/v1,
        /// where v1 represents the version of the KMS external key store proxy API.
        /// You can include an optional prefix between the required elements such as /example/kms/xks/v1.The combined XksProxyUriEndpoint and XksProxyUriPath values
        /// must be unique in the Amazon Web Services account and Region.You can change this value when the external key store is connected or disconnected.
        /// 
        /// 
        [System.Management.Automation.Parameter(ValueFromPipelineByPropertyName = true)]
        public System.String XksProxyUriPath { get; set; }
        #endregion
        
        #region Parameter XksProxyVpcEndpointServiceName
        /// 
        /// 
        /// Changes the name that KMS uses to identify the Amazon VPC endpoint service for your
        /// external key store proxy (XKS proxy). This parameter is valid when the CustomKeyStoreType
        /// is EXTERNAL_KEY_STORE and the XksProxyConnectivity is VPC_ENDPOINT_SERVICE.To change this value, the external key store must be disconnected.
        /// 
        /// 
        [System.Management.Automation.Parameter(ValueFromPipelineByPropertyName = true)]
        public System.String XksProxyVpcEndpointServiceName { get; set; }
        #endregion
        
        #region Parameter Select
        /// 
        /// Use the -Select parameter to control the cmdlet output. The cmdlet doesn't have a return value by default.
        /// Specifying -Select '*' will result in the cmdlet returning the whole service response (Amazon.KeyManagementService.Model.UpdateCustomKeyStoreResponse).
        /// Specifying -Select '^ParameterName' will result in the cmdlet returning the selected cmdlet parameter value.
        /// 
        [System.Management.Automation.Parameter(ValueFromPipelineByPropertyName = true)]
        public string Select { get; set; } = "*";
        #endregion
        
        #region Parameter PassThru
        /// 
        /// Changes the cmdlet behavior to return the value passed to the CustomKeyStoreId parameter.
        /// The -PassThru parameter is deprecated, use -Select '^CustomKeyStoreId' instead. This parameter will be removed in a future version.
        /// 
        [System.Obsolete("The -PassThru parameter is deprecated, use -Select '^CustomKeyStoreId' instead. This parameter will be removed in a future version.")]
        [System.Management.Automation.Parameter(ValueFromPipelineByPropertyName = true)]
        public SwitchParameter PassThru { get; set; }
        #endregion
        
        #region Parameter Force
        /// 
        /// This parameter overrides confirmation prompts to force 
        /// the cmdlet to continue its operation. This parameter should always
        /// be used with caution.
        /// 
        [System.Management.Automation.Parameter(ValueFromPipelineByPropertyName = true)]
        public SwitchParameter Force { get; set; }
        #endregion
        
        protected override void ProcessRecord()
        {
            this._AWSSignerType = "v4";
            base.ProcessRecord();
            
            var resourceIdentifiersText = FormatParameterValuesForConfirmationMsg(nameof(this.CustomKeyStoreId), MyInvocation.BoundParameters);
            if (!ConfirmShouldProceed(this.Force.IsPresent, resourceIdentifiersText, "Update-KMSCustomKeyStore (UpdateCustomKeyStore)"))
            {
                return;
            }
            
            var context = new CmdletContext();
            
            // allow for manipulation of parameters prior to loading into context
            PreExecutionContextLoad(context);
            
            #pragma warning disable CS0618, CS0612 //A class member was marked with the Obsolete attribute
            if (ParameterWasBound(nameof(this.Select)))
            {
                context.Select = CreateSelectDelegate(Select) ??
                    throw new System.ArgumentException("Invalid value for -Select parameter.", nameof(this.Select));
                if (this.PassThru.IsPresent)
                {
                    throw new System.ArgumentException("-PassThru cannot be used when -Select is specified.", nameof(this.Select));
                }
            }
            else if (this.PassThru.IsPresent)
            {
                context.Select = (response, cmdlet) => this.CustomKeyStoreId;
            }
            #pragma warning restore CS0618, CS0612 //A class member was marked with the Obsolete attribute
            context.CloudHsmClusterId = this.CloudHsmClusterId;
            context.CustomKeyStoreId = this.CustomKeyStoreId;
            #if MODULAR
            if (this.CustomKeyStoreId == null && ParameterWasBound(nameof(this.CustomKeyStoreId)))
            {
                WriteWarning("You are passing $null as a value for parameter CustomKeyStoreId which is marked as required. In case you believe this parameter was incorrectly marked as required, report this by opening an issue at https://github.com/aws/aws-tools-for-powershell/issues.");
            }
            #endif
            context.KeyStorePassword = this.KeyStorePassword;
            context.NewCustomKeyStoreName = this.NewCustomKeyStoreName;
            context.XksProxyAuthenticationCredential_AccessKeyId = this.XksProxyAuthenticationCredential_AccessKeyId;
            context.XksProxyAuthenticationCredential_RawSecretAccessKey = this.XksProxyAuthenticationCredential_RawSecretAccessKey;
            context.XksProxyConnectivity = this.XksProxyConnectivity;
            context.XksProxyUriEndpoint = this.XksProxyUriEndpoint;
            context.XksProxyUriPath = this.XksProxyUriPath;
            context.XksProxyVpcEndpointServiceName = this.XksProxyVpcEndpointServiceName;
            
            // allow further manipulation of loaded context prior to processing
            PostExecutionContextLoad(context);
            
            var output = Execute(context) as CmdletOutput;
            ProcessOutput(output);
        }
        
        #region IExecutor Members
        
        public object Execute(ExecutorContext context)
        {
            var cmdletContext = context as CmdletContext;
            // create request
            var request = new Amazon.KeyManagementService.Model.UpdateCustomKeyStoreRequest();
            
            if (cmdletContext.CloudHsmClusterId != null)
            {
                request.CloudHsmClusterId = cmdletContext.CloudHsmClusterId;
            }
            if (cmdletContext.CustomKeyStoreId != null)
            {
                request.CustomKeyStoreId = cmdletContext.CustomKeyStoreId;
            }
            if (cmdletContext.KeyStorePassword != null)
            {
                request.KeyStorePassword = cmdletContext.KeyStorePassword;
            }
            if (cmdletContext.NewCustomKeyStoreName != null)
            {
                request.NewCustomKeyStoreName = cmdletContext.NewCustomKeyStoreName;
            }
            
             // populate XksProxyAuthenticationCredential
            var requestXksProxyAuthenticationCredentialIsNull = true;
            request.XksProxyAuthenticationCredential = new Amazon.KeyManagementService.Model.XksProxyAuthenticationCredentialType();
            System.String requestXksProxyAuthenticationCredential_xksProxyAuthenticationCredential_AccessKeyId = null;
            if (cmdletContext.XksProxyAuthenticationCredential_AccessKeyId != null)
            {
                requestXksProxyAuthenticationCredential_xksProxyAuthenticationCredential_AccessKeyId = cmdletContext.XksProxyAuthenticationCredential_AccessKeyId;
            }
            if (requestXksProxyAuthenticationCredential_xksProxyAuthenticationCredential_AccessKeyId != null)
            {
                request.XksProxyAuthenticationCredential.AccessKeyId = requestXksProxyAuthenticationCredential_xksProxyAuthenticationCredential_AccessKeyId;
                requestXksProxyAuthenticationCredentialIsNull = false;
            }
            System.String requestXksProxyAuthenticationCredential_xksProxyAuthenticationCredential_RawSecretAccessKey = null;
            if (cmdletContext.XksProxyAuthenticationCredential_RawSecretAccessKey != null)
            {
                requestXksProxyAuthenticationCredential_xksProxyAuthenticationCredential_RawSecretAccessKey = cmdletContext.XksProxyAuthenticationCredential_RawSecretAccessKey;
            }
            if (requestXksProxyAuthenticationCredential_xksProxyAuthenticationCredential_RawSecretAccessKey != null)
            {
                request.XksProxyAuthenticationCredential.RawSecretAccessKey = requestXksProxyAuthenticationCredential_xksProxyAuthenticationCredential_RawSecretAccessKey;
                requestXksProxyAuthenticationCredentialIsNull = false;
            }
             // determine if request.XksProxyAuthenticationCredential should be set to null
            if (requestXksProxyAuthenticationCredentialIsNull)
            {
                request.XksProxyAuthenticationCredential = null;
            }
            if (cmdletContext.XksProxyConnectivity != null)
            {
                request.XksProxyConnectivity = cmdletContext.XksProxyConnectivity;
            }
            if (cmdletContext.XksProxyUriEndpoint != null)
            {
                request.XksProxyUriEndpoint = cmdletContext.XksProxyUriEndpoint;
            }
            if (cmdletContext.XksProxyUriPath != null)
            {
                request.XksProxyUriPath = cmdletContext.XksProxyUriPath;
            }
            if (cmdletContext.XksProxyVpcEndpointServiceName != null)
            {
                request.XksProxyVpcEndpointServiceName = cmdletContext.XksProxyVpcEndpointServiceName;
            }
            
            CmdletOutput output;
            
            // issue call
            var client = Client ?? CreateClient(_CurrentCredentials, _RegionEndpoint);
            try
            {
                var response = CallAWSServiceOperation(client, request);
                object pipelineOutput = null;
                pipelineOutput = cmdletContext.Select(response, this);
                output = new CmdletOutput
                {
                    PipelineOutput = pipelineOutput,
                    ServiceResponse = response
                };
            }
            catch (Exception e)
            {
                output = new CmdletOutput { ErrorResponse = e };
            }
            
            return output;
        }
        
        public ExecutorContext CreateContext()
        {
            return new CmdletContext();
        }
        
        #endregion
        
        #region AWS Service Operation Call
        
        private Amazon.KeyManagementService.Model.UpdateCustomKeyStoreResponse CallAWSServiceOperation(IAmazonKeyManagementService client, Amazon.KeyManagementService.Model.UpdateCustomKeyStoreRequest request)
        {
            Utils.Common.WriteVerboseEndpointMessage(this, client.Config, "AWS Key Management Service", "UpdateCustomKeyStore");
            try
            {
                #if DESKTOP
                return client.UpdateCustomKeyStore(request);
                #elif CORECLR
                return client.UpdateCustomKeyStoreAsync(request).GetAwaiter().GetResult();
                #else
                        #error "Unknown build edition"
                #endif
            }
            catch (AmazonServiceException exc)
            {
                var webException = exc.InnerException as System.Net.WebException;
                if (webException != null)
                {
                    throw new Exception(Utils.Common.FormatNameResolutionFailureMessage(client.Config, webException.Message), webException);
                }
                throw;
            }
        }
        
        #endregion
        
        internal partial class CmdletContext : ExecutorContext
        {
            public System.String CloudHsmClusterId { get; set; }
            public System.String CustomKeyStoreId { get; set; }
            public System.String KeyStorePassword { get; set; }
            public System.String NewCustomKeyStoreName { get; set; }
            public System.String XksProxyAuthenticationCredential_AccessKeyId { get; set; }
            public System.String XksProxyAuthenticationCredential_RawSecretAccessKey { get; set; }
            public Amazon.KeyManagementService.XksProxyConnectivityType XksProxyConnectivity { get; set; }
            public System.String XksProxyUriEndpoint { get; set; }
            public System.String XksProxyUriPath { get; set; }
            public System.String XksProxyVpcEndpointServiceName { get; set; }
            public System.Func Select { get; set; } =
                (response, cmdlet) => null;
        }
        
    }
}