Serving Website From S3 Using Cloud Front & Route 53 - amazon-web-services

I just recently moved my domain name from a hosting provider to Amazon. I want to host my website using S3 buckets and I originally I tried to set up my buckets to be domain.com and www.domain.com but I think my previous hosting provider took these bucket names because I cannot create them.
So I am looking at a work around now ...
- created a new bucket with a unique name and put my website files in it
- I set up Cloud Front to pull the files from that bucket
- and lastly a Route 53 hosted zone with the CNAMES for domain.com and www.domain.com pointing to that Cloud Front.
Here is where my problem comes in. I cannot add www.domain.com to my CNAMEs in the Cloud Front. I get the following error:
com.amazonaws.services.cloudfront.model.CNAMEAlreadyExistsException: One or more of the CNAMEs you provided are already associated with a different resource. (Service: AmazonCloudFront; Status Code: 409; Error Code: CNAMEAlreadyExists; Request ID: 19a9a141-8b15-11e6-aa8f-87e12f4b3abf)
However, it does accept domain.com ... so when I visit domain.com I get the proper website, but when I visit www.domain.com I get the old website.
I think it is due to the fact that I can't add that CNAME in my Cloud Front. How can I fix this error?
Thank you

You cannot add an alternate domain name to a CloudFront distribution if the alternate domain name already exists in another CloudFront distribution, even if your AWS account owns the other distribution.
http://docs.aws.amazon.com/AmazonCloudFront/latest/DeveloperGuide/CNAMEs.html#alternate-domain-names-restrictions
This is the condition that would cause the error you're seeing. If you already have another CloudFront distribution configured with this, then clearly that needs to be removed and then this would work.
Otherwise, the old provider may still have your domain configured on one of their CloudFront distributions -- so you need to persuade them to remove it, or you'll need to have AWS support assist you. If the domain is already configured in CloudFront on another account, this can't be fixed by your actions alone.
AWS Support has a special process for handling exactly this situation: https://aws.amazon.com/premiumsupport/knowledge-center/resolve-cnamealreadyexists-error/

In case any of you guys have been playing with Zappa and/or AWS API Gateway before and CNAMEAlreadyExistsException occurred.
Just make sure with AWS CLI that domain you want to use isn't listed in AWS API Gateway anymore like this:
aws apigateway get-domain-names
In case you find it listed there:
aws apigateway delete-domain-name --domain-name <your-domain>
This fixed the issue for me. Piece!
BTW, I didn't find a way to list it or delete it through Web, just AWS API Gateway welcoming screens everywhere.

In my case I forgot I deployed an app using AWS Amplify in the past using the CNAMEs I wanted to use.
This is why I could not find the Cloudfront distribution on the Cloudfront console. Check to see if you have an AWS Amplify app using the desired names.

Related

I can't delete an AWS certificate because it is associated with a CloudFront distribution but the CF distribution no longer exists

I am trying to delete an AWS cert. In the ACM dashboard it states that is is still associated to a CloudFront distribution - therefore it will not let me delete it. The CloudFront distribution it states that it is associated with has been deleted for days and no longer exists.
I did a search and the only thing I have found so for is AWS telling me to delete a custom domain name for an API Gateway that might have been generated for this CF distro. I never set one up and if I look in the API gateway dashboard there are not even any API gateways there.
Any help on getting this cert deleted or disassociated with the non existent CF distribution?

Unable to configure the Route53 to point to CloudFront Distribution for the static website hosted on S3

I am trying to deploy my static website to S3 configuring CloudFront in front of it. But I am not able to configure Route53 to integrate with CloudFront. Below is what I have done so far.
I create an S3 bucket enabling static hosting and allowing public access. Then I deployed/ uploaded the files. I can access my website through the S3 website static URL, http://www.waiyanhein.com.s3-website-eu-west-1.amazonaws.com/.
I have my own domain called, waiyanhein.com.
I am trying to configure the CloudFront in front of my static website. So I created a CloudFront distribution. For the Origin Domain Name, I chose the S3 Bucket's static website URL. Then I chose "Compress Objects Automatically" as YES. In the "Alternate Domain Names (CNAMEs)" text field, I entered, "waiyanhein.com". Then I created the CloudFront distribution. Now my CloudFront distribution is up and running.
Then I tried to configure Route53 pointing to the CloudFront distribution. I tried creating a record choosing "Alias to CloudFront distribution" option. But I can't find my CloudFront distribution in the resources as you can see in the screenshot below.
What's wrong with my configuration?
I have sort of found out something in the CloudFront distribution too. When I edit the CloudFront distribution, the Alternative domains field is empty for some reasons. Then I entered the domains and clicked save. Then I got the following error.
com.amazonaws.services.cloudfront.model.InvalidViewerCertificateException: To add an alternate domain name (CNAME) to a CloudFront distribution, you must attach a trusted certificate that validates your authorization to use the domain name. For more details, see: https://docs.aws.amazon.com/AmazonCloudFront/latest/DeveloperGuide/CNAMEs.html#alternate-domain-names-requirements (Service: AmazonCloudFront; Status Code: 400; Error Code: InvalidViewerCertificate; Request ID: 2d1bacd5-794c-46e5-beec-70b24fab83a6; Proxy: null)
If it does not appear automatically in the dropdown then AWS would be filtering this as it believes that the exact domain you intend to use is not usable for any CloudFront distributions in the account.
Please check the following are correct:
The exact record is covered by the alternative name(s) attached to the CloudFront distribution.
The CloudFront distribution is finished rolling out.
From the interface for the Alias value you should be able to paste the CloudFront domain name with a trailing . although in this new interface certain actions do not currently appear to work. If this is the case for you revert back to the original interface by clicking on the Switch to old console link on the left hand side of the screen and attempt from here.
Additional Comments
The screenshot indicates that an alternative domain that is being specified does not have a matching ACM certificate in us-east-1 which is attached to your CloudFront distribution.
If you do not have one generate a new one, then attach it to your CloudFront distribution when you add the alternative domain name.

AWS unable to enforce https for S3 bucket

I have tried several tutorials on how to set up https via CloudFront, but nothing is working. I am hosting from an S3 bucket and the app works fine via the http protocol, but I need it to be https.
Does anyone have a very thorough tutorial on how to make this work?
Some tutorials explain how to go about setting up a certificate, some explain how to use CloudFront to handle its distribution and I even found a CloudFront tutorial that explains how not using a link from the CloudFront setup forces the wrong region to be created for a certificate, so I even tried that.
I have not found anything that explains exactly what needs to be done for this very common setup, so I am hoping that someone here has some helpful resources.
I think the main issue I had when setting up a CloudFront distribution for an S3 static webhosting bucket was in the Orign Domain Name.
When you create a new distribution, under Origin Settings, the Origin Domain Name field works as a drop-down menu and lists your buckets. Except that picking a bucket from that list doesn't work for static webhosting. You need to specifically put the endpoint for the bucket there, for example:
mywebhostingbucket.com.s3-website-sa-east-1.amazonaws.com
And for custom domains, you must set up the CNAMEs under Distribution Settings, Alternate Domain Names (CNAMEs), and then make sure you have your custom SSL certificate in the us-east-1 region.
Then you can configure the alias record set for the CloudFront distribution.
Here is a complete answer for setting up a site with https.
I had everything in this document completed:
https://docs.aws.amazon.com/AmazonS3/latest/dev/website-hosting-custom-domain-walkthrough.html
And it worked to get the site live via http, but in order to add https, I needed to do the following:
I had requested a certificate for whatever.com, and tried several suggestions after that. But there were a couple of things missing.
To route traffic for the domain (whatever.com) to CloudFront distribution, you will need to clear the current value of the A record and fill in distribution domain name.
Several documents that I viewed said to point the whatever.com S3 bucket to the www.whatever.com S3 bucket, and use the second one to drive the site. Since CloudFront can serve multiple domain name, you may set CNAME of distribution with both, but you will need to set A record for both to distribution AND request an ACM certificate with both domain names (with and without the www). Also, I did ask this, so if you already have a certificate, you can't edit it to do this, which means you'll need to request a new one that has both whatever.com and www.whatever.com
After all of this, I still got "Access Denied" when I went to my site, so to fix this issue, I had to create a new origin in CloudFront with 'Origin Domain Name' set to the full address of the S3 bucket (without the http), and then set the Default (*) Behavior to the S3-Website-.....whatever.com bucket.
After all of this, my site was accessible via http AND https. I hope this helps anyone who experienced this challenge.

What is the best way to point domain to a S3 bucket that doesnt have the domain as bucket name

I'm new to AWS and all of it's services and my first go at it I started my project with a S3 bucket that was created by default by AWS Vue CLI. I've got Cognito pool & gateway API connected to this bucket but now that I want to connect this project to a custom domain I just purchased I realize the bucket name needs to match the root domain name. From what I understand this will mean that I need to pull all non-aws files from my Vue project, duplicate it, and either reconfigure pre-existing connections or start all over.
I've got my custom domain set up with an empty S3 bucket, Cloudfront, and Router 53 so that's up and working but now I am not sure how to go about transferring this project from buckets.
So basically I started my project with Bucket1 and finished everything that included Cognito Pool & Gateway API. Now I have a custom domain I want to use have Cloudfront and Route 53 with CustomDomain bucket name and I want to have the project from Bucket1 load for the new bucket.
Using Cloud-front you can mitigate this issue.
Route 53(DNS Name) --> Cloudfront Url --> S3 origin
As you already created a bucket for website hosting, below steps can help you.
Use the Amazon S3 console t to login and search for CloudFront.
Click on Create distribution
Create a Web distribution
Select existing bucket in Origin Domain Name and complete the setup.
Update the DNS records for your domain to point your website's CNAME to your CloudFront distribution's domain name. You can find your distribution's domain name in the CloudFront console in a format that is similar to d1234abcd.cloudfront.net.
Wait for your DNS changes to propagate and for the previous DNS entries to expire.
The typical AWS way to do this is to use cloudfront - the domain points to cloudfront and cloudfront can point to any bucket name or other source location; when you introduce cloudfront into the mix, the bucketname no longer needs to match the domain name.

Domain name already associated with an "existing" CloudFront distribution

When I try to setup a domain through serverless-domain-manager with sls create_domain, it fails with:
BadRequestException: The domain name you provided is already associated with an existing CloudFront distribution.
Remove the domain name from the existing CloudFront distribution or use a different domain name.
If you own this domain name and are not using it on an existing CloudFront distribution, please contact support. api.example.com was not created.
I tracked down the line where the library fails.
Note that my account does not have anything in CloudFront. This is what I see when I open it:
It's also interesting that in Certificate Manager, it says that the certificate is in use:
Under Associated Resources I can see an entry for cloudfront: arn:aws:cloudfront:: ...
Thanx to Matt's guidance I found what caused the phantom CloudFront distros. Within the AWS console, go to:
Amazon API Gateway > Custom Domain Names
Delete all the conflicting domains there and redo the deployment steps again.
When you create an API Gateway, it will create an underlying CloudFront distribution on your behalf. You may not see it in your AWS account, but it's there.
Also, domains used for CloudFront distributions must be globally unique. Which means that if someone else already has a CloudFront distribution for api.example.com, then you cannot use it as well.
So, you already said that you do not have an existing CloudFront distribution visible in your AWS account.
If you already have an API Gateway for api.example.com, then you cannot create a second one. If this is the case, you need to use a different domain, or delete the original one.
If you don't have an API Gateway for that domain, then someone else probably already has one. If this is the case, then you'll need to use a different domain.
Here's how I've encountered and solved this problem:
Created a serverless app and ran sls create_domain
Too late did I notice that my region was the wrong one in serverless.yml
Manually deleted the CloudFormation stack from AWS, plus the Route53 records.
Changed the region, tried to create_domain again, got the error - although I've deleted everything
Ran sls delete_domain - this threw an error as well, but apparently cleaned up some "hidden" AWS stuff
Ran sls create_domain again. Voila, worked.
The "phantom" cloudfront distro isn't visible because it's in an account owned by AWS itself and used for deploying distros used by Edge-optimized instances of API gateway.
As #Daniel mentioned in his answer above, delete any custom domain names associated with the certificate in the console, but if they aren't visible (if they were already deleted, for example), try deleting them using the AWS CLI, since it appears to do a better job of fully cleaning up the links to those AWS Cloudfront distros:
aws apigateway delete-domain-name --region "<INSERT REGION>" --domain-name "<INSERT DOMAIN NAME>"
As #CGreg encountered with the sls_delete_domain command, you may encounter errors. I was trying to delete an old certificate in ACM that was associated with one of these distros via a custom domain name which I'd already deleted. I ran the above command twice per custom domain name (in any region I thought I might have originally deployed to). The first time I got a "domain name not found" error and the second time I got an "operation timed out: max retries" error, but the association to the Cloudfront distribution was removed and I was able to delete the old cert 👍🏻
Not sure if just once would do it, but since I got different error responses something different must have been happening under the hood, so no harm trying it!