How to install Let's Encrypt SSL on reverse proxied server? - ssl

So I created an Ubuntu 16.04 droplet in DigitalOcean and used ServerPilot to set it up. ServerPilot automatically creates a webserver on top of your Ubuntu using Apache and nginx as reverse proxy.
Now I'm not sure how I can go about installing Let's Encrypt SSL on a reverse proxy server. Do I have to run Certbot for nginx since nginx serves the frontend? I'm trying to be able to use HTTPS to access my site.
Is procedure different for reverse proxy servers?

No, there's no difference. You can either use the webroot of Apache or include a rule in Nginx to answer all ACME challenge requests directly.
Example
server {
listen 80;
server_name example.org;
location / {
return 301 https://$host$request_uri;
}
location /.well-known/acme-challenge {
root /tmp;
}
}
Then use /tmp or any other path for your challenges. Personally, I use my own client written in PHP and much simpler than the official one. See https://github.com/kelunik/acme-client.

Related

Ghost blog is only accessible with www

I have a Ghost blog hosted on digitalocean, my domain can only be accessible with a secure connection (it's a .dev site).
My site is available when I access it with www, e.g. www.androidoss.dev, but not when accessed directly as androidoss.dev.
What could be the issue?
If you have deployed the Ghost on the DigitalOcean server then it's running behind the Nginx probably. So during the Ghost installation there a command is executed which is ghost setup nginx which setup Nginx for you and then run ghost setup ssl which set up Let's Encrypt SSL for the provided domain name and it doesn't create a redirection rule from non-www to www.
So you can do this by adding a redirection URI in your Nginx file.
You have to add these lines in the server block for http. It will look like this and the file-path is /etc/nginx/sites-available/ww.example.com
server {
listen 80;
...................
...................
}
you have to add the below lines at the place of dotted lines.
server_name example.com www.example.com;
return 301 https://www.example.com$request_uri;

SSL for pointed domains

I have an app that is "multi-domain", Other domain just have to point to the IP address to run on my app on the web-server.
Using letsencrypt, I have also generated SSL for those pointed domain using "HTTP" challenges.
Now, my problem is - how do I tell my webserver to read that generated SSL files for the pointed domain.
They are not hosted on my server with config settings. They are just pointed with the IP address to my App and My app renders the content based on a domain name.
I am using VestaCP to manage server, domain, and email
Pointed domains have no config file on my server. They work on the web-application level.
How do I set https for that pointed domain? On a note, I already have valid SSL files - just not sure, where to post or point them, since there is no config.
Can they be kept using "htaccess" or at a web-application level?
E.g, My app runs at "http://example.com" and shows content for example.com, and for the second domain that is pointed to my server "http://anotherExample.com" - my app shows the content for "anotherExample.com" and so on and so forth. "example.com" is hosted on my server with Nginx and apache config, so SSL is set. But anotherExample.com is not hosted on server level but only at the app level - now, where do I set SSL for it? I have already successfully generated SSL using letsencrypt with HTTP challenge.
Update: I run a platform like Blogspot.com Multi-Domain blogs - How to serve SSL for pointed domain?
Thanks
I don't think what you want is directly possible. From your question, I think you are creating multiple A records which points to your application IP address, from which your application decides what data to serve.
So what you have to do is to get SSL certificate for each and every domain you want to serve. Then configure the web server to send the corresponding certificate. This can be done easily with most web servers. Eg: On nginx
server {
listen *:443 ssl;
server_name domain1.com;
ssl_certificate /path/to/domain1.crt;
ssl_certificate_key /path/to/domain1.key;
...
}
server {
listen *:443 ssl;
server_name domain2.com;
ssl_certificate /path/to/domain2.crt;
ssl_certificate_key /path/to/domain2.key;
...
}
Incase you are serving on different subdomains like domain1.example.com and domain2.example.com, then you could get a wildcard certificate which will do the trick.

How to make nginx passthrough on 443 and redirect 80 to 443?

I have a winstone server (Jenkins) listening on 8443.
Jenkins has a valid cert, and Jenkins is doing the cert termination successfully:
JENKINS_ARGS="--httpPort=-1 --httpsKeyStore=/secure/jenkins.keystore --httpsKeyStorePassword=MY_PASSWORD --httpsPort=8443"
The only problem is that users now have to go:
https://example.com:8443
I don't want that port number in the URL.
I want:
https://example.com:8443 -> https://example.com
https://example.com -> https://example.com
http://example.com -> https://example.com
So I figure I'll run nginx on the same instance that is running Jenkins.
So my question is:
Do I have to reconfigure jenkins to NOT do cert termination so that nginx does it only?
Can nginx redirect 80 and 443 to localhost:8443 without a cert (Since Jenkins is doing cert termination)?
Do BOTH nginx AND Jenkins need to do cert termination?
Sorry for those similar questions.
I'm pretty sure an AWS ELB cannot replace what nginx is doing here, but I thought I'd throw it out there, in case an ELB can solve this for me too.
1) No, you can have Nginx Stream the connection directly to the Jenkins using the Stream Module.
Do note this was added in 1.9.0 but is not part of the default build so you might have to build it yourself.
It works a lot like an http server block but you have to set it up outside of the http block.
stream {
upstream jenkins_server {
server jenkins:443;
}
server {
listen 443;
proxy_pass jenkins_server;
}
}
2) You do not need a cert on nginx but you should have a http server block for port 80 that does a 301 to the 443 stream talked about in answer part 1.
server {
listen 80;
server_name your_server_name_here;
return 301 https://$host$request_uri;
}
3) No, you don't as you can use the nginx stream to passthru the ssl from the client to the Jenkins server.

nginx returns SSL certificate for subdomain that should have no certificate

I have a nginx server that manages a few domains and subdomains. There are some subdomains that have an own SSL certificate and they work fine. The problem is that if I try to open blablabla.mydomain.com (this subdomain is not configured in nginx) then firefox shows me an error "Connection is not secure" and "The certificate is only valid for xyz.mydomain.com" (this domain is configured with SSL and works well)
The same happens when I open the root domain mydomain.com. Then the server also returns the certificate for xyz.mydomain.com which is rejected by firefox.
I only want nginx to return the SSL certificate for domains/subdomains I explicitly have configured HTTPS. For what I understand, my configuration should be doing exactly this.
I configured all my https-subdomains like this:
server {
listen 443 ssl;
server_name xyz.mydomain.com;
root /var/www/xyz.mydomain/;
ssl on;
ssl_certificate /etc/letsencrypt/live/xyz.mydomain.com/fullchain.pem;
ssl_certificate_key /etc/letsencrypt/live/xyz.mydomain.com/privkey.pem;
...
}
The root domain (which should have no SSL) is configured like this:
server {
listen 80;
server_name mydomain.com;
return http://some-redirection.com;
}
There is no SSL server block for this domain. Nor is for the other subdomains that do not exist. So why does nginx in these cases return the certificate for xyz.mydomain.com?
I don't use any wildcards in my server config. Is there some way to debug this? I mean, there must be a reason why nginx always returns the certificate for xyz.mydomain.com for every non-configured domain/subdomain. Why not another configured and working certificate?
I use an Ubuntu 14.04 server with nginx 1.4.6
If you need more info on my config, let me know
EDIT: I think I know why my config does not work. When using https the client encrypts also the domain name and this causes nginx to try all available server defintions. When it doesn't find one it returns the last one? And xyz.mydomain.com seems to be the last one (alphabetically)
So is there a way to avoid this? Would I have to create a ssl cert for every other subdomain?

Nginx serves different website (on the same sever) when using HTTPS

I have several websites hosted on the same sever. To simplify I have just 2 (http-only.com and https.com) and using nginx to handle requests.
One has SSL enabled. And another doesn't. I noticed links like this in Google Search Console http-only.com/https_server_path and when accessing an http-only.com server with https protocol I get requests served by an https.com server instead.
https.com:
server {
listen 443 ssl;
server_name https.com;
ssl on;
}
only-http.com:
server {
listen 80;
server_name only-http.com;
}
I think I should define something like a default ssl server to handle ssl for http.com, but don't know how to do it properly. I guess nginx should redirect https request to an http url if corresponding server doesn't handle https. Or maybe there is a better solution?