Come posso utilizzare AWS CloudFormation per distribuire automaticamente un agente DataSync in Amazon EC2 con un endpoint di AWS PrivateLink?
Desidero utilizzare AWS CloudFormation per creare un agente AWS DataSync in Amazon Elastic Compute Cloud (Amazon EC2) in una sottorete privata con un endpoint di AWS PrivateLink.
Risoluzione
Utilizza AWS CloudFormation per creare e attivare automaticamente un agente DataSync che viene eseguito in un'istanza Amazon EC2 tramite un endpoint di AWS PrivateLink.
Seleziona il modello YAML che utilizza una risorsa personalizzata basata su una funzione Lambda per recuperare la chiave di attivazione per l'agente DataSync. Copia il seguente codice YAML e salvalo come modello di AWS CloudFormation:
AWSTemplateFormatVersion: '2010-09-09' Description: >- This CloudFormation template deploys an EC2 instance with the AWS DataSync agent AMI. Metadata: AWS::CloudFormation::Interface: ParameterGroups: - Label: default: Deploy DataSync agent on Amazon EC2 via PrivateLink VPC endpoint Parameters: - InstanceType - ImageId - SubnetId - VpcId ParameterLabels: InstanceType: default: Agent EC2 Instance Size SubnetId: default: Select your Subnet VpcId: default: Select your VPC Contains Above Subnet ImageId: default: Agent Image (Keep default - Do NOT change) Parameters: InstanceType: Description: Instance type for the DataSync agent EC2 instance Type: String Default: m5.2xlarge AllowedValues: - m5.2xlarge - m5.4xlarge ConstraintDescription: must be a valid EC2 instance type. ImageId: Type: AWS::SSM::Parameter::Value<AWS::EC2::Image::Id> Default: /aws/service/datasync/ami SubnetId: Type: AWS::EC2::Subnet::Id Description: The subnet where to deploy the instance VpcId: Type: AWS::EC2::VPC::Id Description: Select the VPC containing the subnet selected above. Resources: NewKeyPair: Type: 'AWS::EC2::KeyPair' Properties: KeyName: !Sub "ssh-key-cfn-stack-${AWS::StackName}" DataSyncAgentInstance: Type: AWS::EC2::Instance Properties: ImageId: !Ref ImageId InstanceType: !Ref InstanceType SubnetId: !Ref SubnetId SecurityGroupIds: - !Ref DataSyncAgentSecurityGroup KeyName: !Ref NewKeyPair Tags: - Key: "Name" Value: !Ref 'AWS::StackName' DataSyncAgentSecurityGroup: Type: AWS::EC2::SecurityGroup Properties: GroupDescription: Enable SSH access and DataSync agent communication SecurityGroupIngress: - IpProtocol: tcp FromPort: 80 ToPort: 80 CidrIp: 0.0.0.0/0 VpcId: !Ref VpcId DsInterfaceEndpoint: Type: 'AWS::EC2::VPCEndpoint' Properties: VpcEndpointType: 'Interface' ServiceName: !Sub 'com.amazonaws.${AWS::Region}.datasync' VpcId: !Ref VpcId SubnetIds: - !Ref SubnetId SecurityGroupIds: - !Ref DsVpceSecurityGroup DsVpceSecurityGroup: Type: 'AWS::EC2::SecurityGroup' Properties: GroupDescription: 'Allow control traffic from agent' VpcId: !Ref VpcId SecurityGroupIngress: - IpProtocol: tcp FromPort: 443 ToPort: 443 CidrIp: !Sub "${DataSyncAgentInstance.PrivateIp}/32" - IpProtocol: tcp FromPort: 1024 ToPort: 1064 CidrIp: !Sub "${DataSyncAgentInstance.PrivateIp}/32" - IpProtocol: tcp FromPort: 22 ToPort: 22 CidrIp: !Sub "${DataSyncAgentInstance.PrivateIp}/32" LambdaActivator: Type: AWS::Lambda::Function DependsOn: DsInterfaceEndpoint Properties: FunctionName: !Ref 'AWS::StackName' Description: 'Lambda function to get the activation key' VpcConfig: SecurityGroupIds: - !Ref DataSyncAgentSecurityGroup SubnetIds: - !Ref SubnetId Environment: Variables: DsDnsEntryList: !Select [1, !Split [':', !Select [0, !GetAtt DsInterfaceEndpoint.DnsEntries]]] Code: ZipFile: !Sub | import boto3, json, urllib.request, socket, time, os import cfnresponse print('Loading function') def handler(event, context): print('EVENT:') print(event) responseData = {} try: if event['RequestType'] == "Create": agentIp = "${DataSyncAgentInstance.PrivateIp}" awsRegion = "${AWS::Region}" VpceDnsName = os.environ['DsDnsEntryList'] VpceIp = socket.gethostbyname(VpceDnsName) print("Agent IP: " + agentIp) print("AWS Region: " + awsRegion) print("VPC Endpoint DNS Name: " + VpceDnsName) print("VPC IP: " + VpceIp) activateUrl = "http://" + agentIp + "/?gatewayType=SYNC&activationRegion=" + awsRegion + "&privateLinkEndpoint=" + VpceIp + "&endpointType=PRIVATE_LINK&no_redirect" print(activateUrl) time.sleep(30) print("Sending URL for Getting activation key") res = urllib.request.urlopen(urllib.request.Request( url=activateUrl, method='GET'), timeout=600) print("HTTP Response :" + str(res.status) + " " + res.reason) activationKey = res.read().decode('utf-8') responseData['Data'] = activationKey elif event['RequestType'] == "Delete": print("Lambda is being deleted by the CloudFormation stack!!") else: print("Should not perform actions!!") cfnresponse.send(event, context, cfnresponse.SUCCESS, responseData, 'cfn-customresource-id') return { 'body': json.dumps('Execution completed!') } except Exception as e: print(e) cfnresponse.send(event, context, cfnresponse.FAILED, responseData, 'cfn-customresource-id') raise e Handler: index.handler Role: !GetAtt FunctionIamRole.Arn Runtime: python3.12 Timeout: 300 ActivatorInvoker: DependsOn: - LambdaActivator - DataSyncAgentInstance Type: AWS::CloudFormation::CustomResource Properties: ServiceToken: !GetAtt LambdaActivator.Arn FunctionIamRole: Type: AWS::IAM::Role Properties: AssumeRolePolicyDocument: Version: '2012-10-17' Statement: - Effect: Allow Principal: Service: - lambda.amazonaws.com Action: - 'sts:AssumeRole' ManagedPolicyArns: - "arn:aws:iam::aws:policy/service-role/AWSLambdaBasicExecutionRole" Policies: - PolicyName: !Sub "ec2-permissions-lambda-${AWS::StackName}" PolicyDocument: Version: '2012-10-17' Statement: - Effect: Allow Action: - ec2:CreateNetworkInterface - ec2:DeleteNetworkInterface - ec2:DescribeNetworkInterfaces Resource: "*" ActiveAgent: Type: AWS::DataSync::Agent Properties: ActivationKey: !GetAtt ActivatorInvoker.Data AgentName: !Sub "datasync-agent-created-from-cfn-${AWS::StackName}" VpcEndpointId: !GetAtt DsInterfaceEndpoint.Id SecurityGroupArns: - !Sub "arn:aws:ec2:${AWS::Region}:${AWS::AccountId}:security-group/${DsVpceSecurityGroup}" SubnetArns: - !Sub "arn:aws:ec2:${AWS::Region}:${AWS::AccountId}:subnet/${SubnetId}" Outputs: KeyPairId: Description: KeyPairId of the newly created SSH Key to connect the EC2 (you can download the key under Parameter Store, a capability of AWS Systems Manager) Value: !GetAtt NewKeyPair.KeyPairId PrivateIp: Description: PrivateIp of the newly created EC2 instance Value: !GetAtt DataSyncAgentInstance.PrivateIp ActivationKey: Description: Agent Activation Key Value: !GetAtt ActivatorInvoker.Data
Utilizza la console AWS CloudFormation per creare uno stack AWS in CloudFormation. Nella pagina Crea stack, per Prerequisito - Prepara modello, seleziona Scegli un modello esistente. In Specifica modello, scegli Carica un file di modello, quindi seleziona il modello che hai salvato.
**Nota:**Nella sezione Parametri, la sottorete privata specificata deve avere accesso a un servizio Amazon Simple Storage Service (Amazon S3) tramite un endpoint VPC (Amazon Virtual Private Cloud) gateway.
- Argomenti
- Management & Governance
- Lingua
- Italiano
