I’ve got multiple applications I’m needing to deploy via ecs fargate using an application load balancer. The applications have separate dns records associated with them and each has their own certs of course to be attached to the ALB.
This is where things get interesting. If I deploy one of the applications on a 443 listener this works. However when I go to deploy the other set of apps on a separate https listener (since you can’t have duplicate 443 listeners) this time on 44301, I can only reach the app by passing in 44301 to the url with the route path. In other words in the first case, 443 is the default and I don’t have to pass that port in when I hit the url, but in the second case, I do have to pass in the port.
Is it possible to have the second https listener default to that other https port without having to pass in that port number?
I’m using separate https listeners to save cost and so I don’t have to create a separate alb for each dns record.
So far I haven’t tried to add a redirect rule to that port, but I’ve tried the other deployment strategies listed above and I can’t get the second https listener to work with the cert without also passing in that port to the url.
I was using an EC2 instance of AWS and deploy my app on root through HTTP.
Now I migrated to HTTPs but the app does not load correctly. But I cant see any errors on chrome developers tools. The only thing I noticed different is that there is a lot of connections (350) made to the root that is where I deployed the app. I suspect is because the change of https. To made my app HTTPs I am using a load balancer of AWS and the aws certificate manager. Sorry for my english.
Image 1
when you add SSL certificates to the Application Load Balancer, the encryption and decryption of the request is taken care of by the ALB. Read more about this here. This means that your app can operate normally and should not be concerned with the request policy.
You can create a target group and point both HTTP (port 80) and HTTPS (port 443) traffic to the same target group.
Coming to your question. It seems like you are having difficulty in connecting to the ALB on port 443 (HTTPS). If your application is working as expected on port 80 (HTTP) follow this checklist to zero down on your problem:
Make sure that the security group of the ALB allows port 443 to your users or to the world
Check if the ALB has a listener configured on port 443. Read more about this in the docs here
Check if this listener points to the application target group.
As a last step, if you are using a domain name, make sure that it is pointing to the ALB and not the origin servers (EC2 in this case)
If you would like to get better understanding of how the request flows from the users instance to your application server, I've answered a simmilar question here.
I am running a Gatsby site in development mode as a dev server on EC2 with a loadbalancer pointing from port 80 to 8000. I have setup a cname on my domain dns to point to the load balancer this works fine. However I need to display this page as an iframe in sanity.io as a web preview and it requires https.
I've read through this https://docs.aws.amazon.com/elasticloadbalancing/latest/classic/elb-create-https-ssl-load-balancer.html and most of it is pretty straight forward for the most part.
What I have done so far is created a listener for 443 https on the loadbalancer and added https 443 to the security group. i have succsufully issued a certificate to the subdomain I am using with aws and attached it to the loadbalancer listener.
Gatsby has a article about custom certs for development mode here https://www.gatsbyjs.org/docs/local-https/#custom-key-and-certificate-files What I am looking for is the cert file, the authority file and the key file in order to pass this command below
Where in the aws certificate manager do I find these files. I think that is the last piece I need to get https working, correct me if I am wrong.
thanks ahead of time.
gatsby develop --https --key-file ../relative/path/to/key.key --cert-file ../relative/path/to/cert.crt --ca-file ../relative/path/to/ca.crt
This is the process I used to request my certficate and it says it's issued
https://docs.aws.amazon.com/acm/latest/userguide/gs-acm-request-public.html
But how do I use it with the custom https command with gatsby?
There is a export option but it says only for private keys. Do I need to create a private key and then I can export these files I need?
Do I even need to run https on gatsby's side. I watched a video using apache and no change was made to the apache server to get https working with the loadbalancer.
Here is a screenshot of my loadbalancer listenr
Here is a image of my security groups
If I run the --https for gatsby develop it breaks my site I can no longer visit it via the loadbalancer or port 8000. So not sure what to do here.
I would suggest not to encrypt the connection between your ELB and the EC2 instances. If your EC2 instances are not publicly reachable, but only through the load balancer instead, it is best practice to terminate the SSL connection on the load balancer. No need to encrypt HTTP requests inside an AWS VPC (i.e. between ELB and target instances).
You can create a load balancer that listens on both the HTTP (80) and HTTPS (443) ports. If you specify that the HTTPS listener sends requests to the instances on port 80, the load balancer terminates the requests and communication from the load balancer to the instances is not encrypted. [1]
There is some discussion (e.g. on the blog of Kevin Burke) whether it is necessary to encrypt traffic inside a VPC. [2] However, most people are probably not doing it.
What it means for you: Use the same instance protocol for your targets as before: HTTP via port 8000 for both listeners. Do not set up SSL for your Gatsby service. Use a plain HTTP server config instead. No changes are necessary to ELB targets when using SSL termination on the load balancer.
References
[1] https://docs.aws.amazon.com/elasticloadbalancing/latest/classic/elb-create-https-ssl-load-balancer.html
[2] https://acloud.guru/forums/aws-certified-security-specialty/discussion/-Ld2pfsORD6ns5dDK5Y7/tlsssl-termination?answer=-LecNy4QX6fviP_ryd7x
I'm very new to AWS, so if any of the info I give you is not correct, I would appreciate a correction.
I have a single EC2 instance, running Windows, and using Internet Information Services (IIS). That instance has an elastic IP address set, so anytime I want to access my web, I do it through "http://xx.xxx.xxx.xxx/myWeb/controller/view.
I have a mobile app that opens a webview through an address like the one before, to register a credit card, and the API i'm using for that is requesting to make the connection secure. Doing research, I found about AWS Certificate Manager. It's of my uderstanding that you can only deploy a Certificate generated from the certificate manager to an ELB or CloudFront, but I don't have any of those.
All the documentation I read is fairly advanced for my understanding at this point or is focused on Linux servers, so I would like to know, how would you guys solve this? should I put ELB in front of my EC2 to be able to use Certificate Manager? or is there a better way to enable a HTTPS connection?
I also read about having to enable port 443 (HTTPS), is this an extra step I have to take, besides getting the SSL certificate?
Sorry if I'm all over the place. Any help would be greatly appreciated :)
There are 2 options, host the SSL within the Instance, or use ELB/ALB to terminate SSL (and change port) and forward the connection to the Instance. In either case you would need a domain name registered (the trust relationship is against the domain name, not the IP address).
If you choose the AWS route:
(Optional) Register the domain in Route 53, or transfer it in
Register the certificate in ACM, or upload your own
Create an ELB / ALB. Set it to use the custom domain and enable SSL.
Create a 'listener' on the ELB / ALB listening on port 443 (IIRC the SSL is actually attached to this listener). Set the listener to forward all incoming connections to the Instance on a port of your choosing (e.g. 80 now that it is HTTP).
If you are using websockets you would need to use an ALB (not ELB)
Beware there is a monetary cost for using ELB / ALB.
We are implementing a micro-services architecture in AWS. We have several EC2 instances which has the micro-services deployed on different ports. We also have an internet facing Application Load Balancer, which routes to different services based on the port.
eg:
xxxx-xx.xx.elb.amazonaws.com:8080/ go to microservice 1
xxxx-xx.xx.elb.amazonaws.com:8090/ go to microservice 2
We need to have a domain name instead of the ELB, the port should not be exposed through the domain name as well. Almost all the resources I found regarding route 53, use alias which does the following:
xx.xxxx.co.id -> xxxx-xx.xx.elb.amazonaws.com or
xx.xxxx.co.id -> 111.111.111.11 (static ip)
1) Do we need separate domains for each micro service?
2) How to use alias to point domains to a specific port of the ELB?
3) Is it possible to use this setup if the domains are from another provider other than AWS.
Important Update
Since this answer was originally written, Application Load Balancer introduced the capability for ALB to route requests to a specific target group based on the Host header of the incoming request.
The incoming host header can now be used to route requests to specific instances and ports.
Additionally, ALB introduced SNI support, allowing you to associate multiple TLS (SSL) certificates with a single balancer, and the correct certificate will be automatically selected based on the SNI presented by the client when TLS is negotiated. Multi-domain and wildcard certs from Amazon Certificate Manager also work with ALB.
Based on these factors, no separate ports or different listeners are needed -- simply assign hostnames and/or path prefixes for each service, and map those patterns to the appropriate target group of instances.
The original answer is no longer accurate, but is included below.
1.) Do we need separate domains for each micro service?
No, this won't help you. ALB does not interpret the hostname attached to the incoming request.
Separate hostnames in the same domain won't directly accomplish your objective, either.
2.) How to use alias to point domains to a specific port of the ELB?
Domains do not point to ports. Hostnames do not point to ports. DNS is only used for address resolution. This is true everywhere on the Internet.
3.) Is it possible to use this setup if the domains are from another provider other than AWS.
This is not a limitation of AWS. DNS simply does not work this way.
A service endpoint is unaware of the DNS records that point to it. The DNS entry itself is strictly used for discovering an IP address that can be used to access the endpoint. After that, the endpoint does not actually know anything about the DNS, and there is no way to tell the browser, via DNS, to use a different port.
For HTTP, the implicit port is 80. For HTTPS, it is 443. Unless a port is provided in the URL, these are the only usable ports.
However, in HTTP and HTTPS, each request is accompanied by a Host: header, sent by the web browser with each request. This is the hostname in the address bar.
To differentiate between requests for different hostnames arriving at a device (such as ELB/ALB), the device at the endpoint must interpret the incoming host header and route the request to an back-end system providing that service.
ALB does not currently support this capability.
ALB does, however, support choosing endpoints based on a path prefix. So microservices.example.com/api/foo could route to one set of services, while microservices.example.com/api/bar could route to another.
But ALB does not directly support routing by host header.
In my infrastructure, we use a combination of ELB or ALB, but the instances behind the load balancer are not the applications. Instead, they are instances that run HAProxy load balancer software, and route the requests to the backend.
A brief example of the important configuration elements looks like this:
frontend main
use_backend svc1 if { hdr(Host) -i foo.example.com }
use_backend svc2 if { hdr(Host) -i bar.example.com }
backend svc1
server foo-a 192.168.2.24:8080
server foo-b 192.168.12.18:8080
backend svc2
....
The ELB terminates the SSL and selects a proxy at random and the proxy checks the Host: header and selects a backend (a group of 1 or more instances) to which the request will be routed. It is a thin layer between the ELB and the application, which handles the request routing by examining the host header or any other characteristic of the request.
This is one solution, but is a somewhat advanced configuration, depending on your expertise.
If you are looking for an out-of-the-box, serverless, AWS-centric solution, then the answer is actually found in CloudFront. Yes, it's a CDN, but it has several other applications, including as a reverse proxy.
For each service, choose a hostname from your domain to assign to that service, foo.api.example.com or bar.api.example.com.
For each service, create a CloudFront distribution.
Configure the Alternate Domain Name of each distribution to use that service's assigned hostname.
Set the Origin Domain Name to the ELB hostname.
Set the Origin HTTP Port to the service's specific port on the ALB, e.g. 8090.
Configure the default Cache Behavior to forward any headers you need. If you don't need the caching capability of CloudFront, choose Forward All Headers. Also enable forwarding of Query Strings and Cookies if needed.
In Route 53, create foo.api.example.com as an Alias to that specific CloudFront distribution's hostname, e.g. dxxxexample.cloudfront.net.
Your problem is solved.
You see what I did there?
For each hostname you configure, a dedicated CloudFront distribution receives the request on the standard ports (80/443) and -- based on which distribution the host header matches -- CloudFront routes the requests to the same ELB/ALB hostname but a custom port number.
I think there is a possibility that he can build what he's describing. I was in the same boat for a while, here's some options for you to consider:
In R53 create a hosted zone - and point your domain at it.
Optional step: create ALIAS records. You can do this for each subdomain or
app. Leave the ALIAS field blank if using the root domain.
Create a record set using the SLA option, which is a service lookup for port
redirection. Try to point this to your LB port 80, alias the sub-domains.
Change your load balancer's listeners, to listen on port 80 - then redirect app traffic based on your apps port settings.
I havent used SLA, but this would definitely point you in that direction.