Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to get RDS instance hostname in CDK app?

I'm using the AWS CDK for .NET to create a stack that consists of a VPC, an RDS Database Instance and an Application Load Balanced Fargate Service in ECS. The container I'm deploying to ECS requires connection information for the RDS database to be set via environment variables, but I'm not sure how to access that information. Below is my CDK code.

using Amazon.CDK;
using EC2 = Amazon.CDK.AWS.EC2;
using ECS = Amazon.CDK.AWS.ECS;
using RDS = Amazon.CDK.AWS.RDS;

namespace PersonalSecOps
{
    public class PersonalSecOpsStack : Stack
    {
        internal PersonalSecOpsStack(Construct scope, string id, IStackProps props = null) : base(scope, id, props)
        {
            var vpc = new EC2.Vpc(this, "PersonalSecOpsVpc", new EC2.VpcProps
            {
                MaxAzs = 3 // Default is all AZs in region
            });

            var mySql = new RDS.DatabaseInstance(this, "PersonalSecOpsRds", new RDS.DatabaseInstanceProps
            {
                Engine = RDS.DatabaseInstanceEngine.MYSQL,
                PreferredBackupWindow = "05:00-06:00",
                BackupRetention = Duration.Days(7),
                RemovalPolicy = RemovalPolicy.DESTROY,
                DeletionProtection = false,
                MasterUsername = "admin",
                InstanceClass = EC2.InstanceType.Of(EC2.InstanceClass.BURSTABLE2, EC2.InstanceSize.MICRO),
                Vpc = vpc,
                InstanceIdentifier = "PersonalSecOpsRds"
            });

            var ecsCluster = new ECS.Cluster(this, "PersonalSecOpsEcs", new ECS.ClusterProps
            {
                Vpc = vpc
            });

            var nextCloudService = new ECS.Patterns.ApplicationLoadBalancedFargateService(this, "NextcloudService", new ECS.Patterns.ApplicationLoadBalancedFargateServiceProps
            {
                Cluster = ecsCluster,
                DesiredCount = 1,
                TaskImageOptions = new ECS.Patterns.ApplicationLoadBalancedTaskImageOptions
                {
                    Image = ECS.ContainerImage.FromRegistry("nextcloud"),
                    Secrets = 
                    {
                        { "MYSQL_PASSWORD", ??? }
                    },
                    Environment = {
                        { "MYSQL_DATABASE", "Nextcloud" },
                        { "MYSQL_USER", "admin" },
                        { "MYSQL_HOST", ??? }
                    } 
                },
                MemoryLimitMiB = 2048,
                PublicLoadBalancer = true
            });
        }
    }
}

Notice the two "???" where I'm attempting to set the MYSQL_PASSWORD and MYSQL_HOST environment variables on the container. I read somewhere that RDS will automatically generate a MasterUserPassword and store it in Secret Manager, but I'm not sure how to get that out. Also, I need the hostname of the RDS instance. I haven't been able to find a way to set it explicitly when creating the instance or I would just do that.

Am I going about this the right way?

like image 692
Raymond Saltrelli Avatar asked Jan 02 '20 23:01

Raymond Saltrelli


People also ask

How do I find my RDS hostname?

There is no specific IP adress shown to user in AWS Console, but you can find the hostname and FQDN of the DB under connectivity and security tab of the RDS Database.

How to create an RDS instance in AWS CDK?

Creating an RDS Instance in AWS CDK # name Description vpc The VPC in which the DB subnet group wil ... vpcSubnets The type of subnets the DB subnet group ... engine The engine for the database, in our case ... instanceType The class and size for the instance, in ... 10 more rows ...

How long do Amazon RDS instance hostnames last?

Amazon RDS instance hostnames don't change for as long as the instance is running. It persists reboots too. If you use a cluster, then you should use the cluster endpoint as the hostname in your applications. You could use the hostname as it is or create a simple CNAME record in your DNS to make it memorable.

What DNS service should I use for my RDS instance?

You should look into using Route53.. That's their DNS services. I recommend setting up Route53, adding a CNAME to your RDS instance so that you can have your code refer to it by hostname found in Route53 as opposed to the generic AWS Hostname.

How do I connect to RDS using EC2 key pair key?

Navigate to the directory where you stored the ec2-key-pair key and ssh into the instance: Now we can connect to the RDS instance. Replace YOUR_DB_ENDPOINT with the value of dbEndpoint from the cdk-outputs.json file, alternatively grab the Endpoint value from the RDS management console.


Video Answer


1 Answers

Thanks to kingofpoptart on Reddit for helping to answer this question.

using Amazon.CDK;
using EC2 = Amazon.CDK.AWS.EC2;
using ECS = Amazon.CDK.AWS.ECS;
using RDS = Amazon.CDK.AWS.RDS;

namespace PersonalSecOps
{
    public class PersonalSecOpsStack : Stack
    {
        internal PersonalSecOpsStack(Construct scope, string id, IStackProps props = null) : base(scope, id, props)
        {
            var vpc = new EC2.Vpc(this, "PersonalSecOpsVpc", new EC2.VpcProps
            {
                MaxAzs = 3 // Default is all AZs in region
            });

            var mySqlPassword = new Secret(this, "PersonalSecOpsMySqlPassword", new SecretProps
            {
                GenerateSecretString = new SecretStringGenerator
                {
                    PasswordLength = 20
                }
            });

            var mySql = new RDS.DatabaseInstance(this, "PersonalSecOpsRds", new RDS.DatabaseInstanceProps
            {
                Engine = RDS.DatabaseInstanceEngine.MYSQL,
                PreferredBackupWindow = "05:00-06:00",
                BackupRetention = Duration.Days(7),
                RemovalPolicy = RemovalPolicy.DESTROY,
                DeletionProtection = false,
                MasterUsername = "admin",
                MasterUserPassword = mySqlPassword.SecretValue,
                InstanceClass = EC2.InstanceType.Of(EC2.InstanceClass.BURSTABLE2, EC2.InstanceSize.MICRO),
                Vpc = vpc,
                InstanceIdentifier = "PersonalSecOpsRds"
            });

            var ecsCluster = new ECS.Cluster(this, "PersonalSecOpsEcs", new ECS.ClusterProps
            {
                Vpc = vpc
            });

            var nextCloudService = new ECS.Patterns.ApplicationLoadBalancedFargateService(this, "NextcloudService", new ECS.Patterns.ApplicationLoadBalancedFargateServiceProps
            {
                Cluster = ecsCluster,
                DesiredCount = 1,
                TaskImageOptions = new ECS.Patterns.ApplicationLoadBalancedTaskImageOptions
                {
                    Image = ECS.ContainerImage.FromRegistry("nextcloud"),
                    Secrets = 
                    {
                        { "MYSQL_PASSWORD", ECS.Secret.FromSecretsManager(mySqlPassword) }
                    },
                    Environment = {
                        { "MYSQL_DATABASE", "Nextcloud" },
                        { "MYSQL_USER", "admin" },
                        { "MYSQL_HOST", mySql.DbInstanceEndpointAddress }
                    } 
                },
                MemoryLimitMiB = 2048,
                PublicLoadBalancer = true
            });
        }
    }
}
like image 97
Raymond Saltrelli Avatar answered Oct 17 '22 23:10

Raymond Saltrelli