SSF0SSF0
首页
前端
  • Node
  • Go
  • C#
  • MySql
  • Bash
  • Git
  • Docker
  • VuePress
  • CI/CD
  • 服务器
  • 网站
  • 学习资料
  • 软件
Timeline
Github
标签
分类
首页
前端
  • Node
  • Go
  • C#
  • MySql
  • Bash
  • Git
  • Docker
  • VuePress
  • CI/CD
  • 服务器
  • 网站
  • 学习资料
  • 软件
Timeline
Github
标签
分类
  • Bash

    • Bash 获取路径在不同类型电脑的区别
  • Git

    • Git 使用 ssh 与 https 的区别
    • Git 回滚、重置与变基
    • 文件名大小写发生变化的坑
    • Git 提交信息规范解读与实践指南
    • Git 历史邮箱统一 + 推送 GitHub 后的远程分支处理指南
  • Docker

    • Docker 命令大全
    • nginx 镜像部署静态文件
    • Docker 运行命令说明
    • 使用 node 镜像运行本地项目
    • 挂载和卷的区别
    • Docker 打包多平台镜像
    • Docker 使用 mysql
    • Docker 容器网络访问问题总结
  • VuePress

    • 使用 VuePress 搭建个人博客概括
  • CI/CD

    • blog 使用 Github-Actions 部署 docker 服务器
  • 服务器

    • 腾讯云使用 ssh 连接服务器(Linux 实例)
    • ssl 证书安装到 docker 服务器
    • 操作系统与架构
    • ssh 连接时长问题
  • 掌握 hosts 文件:本地开发、域名重定向与回调处理完全指南
  • Cloudflare DNS与代理:完全指南

ssl 证书安装到 docker 服务器

1. 下载证书

从服务商处下载证书,下载 Nginx(适用大部分场景)(pem 文件、crt 文件、key 文件)。

2. 使用证书,以及构建镜像

项目文件目录为:

以下所有的 strive.online 为域名,使用时请替换成自己的域名。

├── Dockerfile
├── nginx.conf
├── certs
│   ├── strive.online_bundle.pem
│   └── strives.online_bundle.crt
│   └── strive.online.key
│   └── strives.online.csr

Dockerfile 文件内容为:

FROM nginx:mainline-alpine

COPY ./nginx.conf /etc/nginx/nginx.conf
COPY ./certs/strives.online_bundle.pem /path/to/strives.online_bundle.pem
COPY ./certs/strives.online.key /path/to/strives.online.key

# 暴露需要的端口  根据nginx.conf文件 配置几个server,就暴露几个端口
EXPOSE 443

注意点:

  1. COPY 到镜像里的证书路径需要和 nginx.conf 文件中配置的路径一致。

  2. EXPOSE 443 根据 nginx.conf 文件配置的端口来暴露,如果有多个 server,就暴露多个端口。

nginx.conf 文件内容为:

events {
    worker_connections 1024; # 每个工作进程允许的最大连接数
}

http {
    include       /etc/nginx/mime.types; # 包含 MIME 类型配置文件
    default_type application/octet-stream; # 默认的 MIME 类型

    # -----  反向代理  -----
    # Nginx 只会把 HTTPS 的默认端口 443 代理到 HTTP 的默认端口 80,
    # 因为你在 proxy_pass 指定的是 http://strives.online,默认会使用 HTTP 的 80 端口。
    server {
        listen 443 ssl; # 监听 443 端口,表示 HTTPS
        server_name strives.online; # 指定域名

        # 指定 SSL 证书和私钥的位置
        ssl_certificate /path/to/strives.online_bundle.pem;
        ssl_certificate_key /path/to/strives.online.key;

        # 添加一些推荐的 SSL 配置
        ssl_protocols TLSv1.2 TLSv1.3;  # 只启用安全协议版本
        ssl_ciphers HIGH:!aNULL:!MD5;   # 安全密码套件
        ssl_prefer_server_ciphers on;   # 优先使用服务器端的密码配置
        ssl_session_cache shared:SSL:10m; # SSL 会话缓存 大小 10MB
        ssl_session_timeout 10m;       # SSL 会话超时时间 10 分钟

        location / {
            proxy_pass http://strives.online;  # 将请求代理到 HTTP 的默认端口80,那么docker内部服务就应该监听 80 端口,就是docker容器里ports  80/tcp的由来
            proxy_set_header Host $host; # 传递客户端请求的 Host 头
            proxy_set_header X-Real-IP $remote_addr; # 传递客户端请求的真实 IP 地址
            proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; # 传递客户端请求的原始 IP 地址 和代理服务器 IP 地址
            proxy_set_header X-Forwarded-Proto $scheme; # 传递客户端请求的协议(http 或 https)

            # 可根据需要设置超时时间或缓冲区大小
            # proxy_read_timeout 90;
            # proxy_buffer_size 16k;
            # proxy_buffers 4 32k;
            # proxy_busy_buffers_size 64k;
        }
    }

    # -----  反向代理  -----
    # 这里也是因为我们容器要开启8088端口,所以我们的api容器就不能再开启8088端口了,所以这里监听8089端口,然后重定向到8088端口使得外部访问https8088端口
    server {
        listen 8088 ssl;  # 监听宿主机的 8088 端口,使用 SSL
        server_name strives.online;  # 替换为你的域名

        ssl_certificate /path/to/strives.online_bundle.pem;
        ssl_certificate_key /path/to/strives.online.key;

        ssl_protocols TLSv1.2 TLSv1.3;  # 使用现代的 TLS 协议
        ssl_ciphers HIGH:!aNULL:!MD5;

        location / {
            # proxy_pass http://localhost:8089;  # 每个容器都是独立的,所以这里不能使用localhost 对 Nginx 容器来说只指向它自己,而不是指向你的应用服务,所以这里应该使用strives.online。
            proxy_pass http://strives.online:8089;  # 将请求转发到 Docker 容器的 8089 端口
            proxy_set_header Host $host;
            proxy_set_header X-Real-IP $remote_addr;
            proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
            proxy_set_header X-Forwarded-Proto $scheme;
        }
    }


    # -----  重定向 -----
    # # 处理 HTTP 8089 端口请求,重定向到 HTTPS 8088
    # server {     # 这里因为docker 容器运行在8088端口,api镜像就不能再启动8088端口所以这里监听api的8089端口,然后重定向到8088端口
    #     listen 8089;  # 监听 HTTP 8089 端口
    #     server_name strives.online;
    #     ssl_certificate /path/to/strives.online_bundle.pem;
    #     ssl_certificate_key /path/to/strives.online.key;
    #     location / {
    #         return 301 https://$host:8088$request_uri;  # 将 HTTP 8089 的请求重定向到 HTTPS 8088
    #     }
    # }
}

注意点:

  1. 在 nginx.conf 文件中,我们使用 proxy_pass http://strives.online; 将请求代理到 HTTP 的默认端口 80,所以容器内部的服务应该监听 80 端口。

  2. 如果容器内部的服务监听的是 8088 端口,那么在 nginx 配置文件中,应该使用 proxy_pass http://strives.online:8088; 将请求代理到 8088 端口。

  3. 使用的是反向代理,代理的地址就是域名 strives.online,而不是 localhost 或者 127.0.0.1,因为容器是独立的,所以不能使用 localhost 或者 127.0.0.1。

  4. 再次强调,我们这里配置了 N 个 server,就需要在 dockerfile 中暴露 N 个端口。

3. 打包为镜像 运行在自己的 docker 服务器上

打包本地镜像:

docker build --load -t https-ssl .

打包远程仓库镜像:

 docker buildx build --platform linux/amd64 --load -t dockerName/https-ssl:1.0.0 .

这里需要登录 docker,没有 dockerName/https-ssl 会进行创建,有的话会进行更新。 构建为 linux/amd64 架构的镜像,原因请参考 打包多平台镜像。

推送镜像到 docker 仓库:

docker push dockerName/https-ssl:1.0.0

在 docker 服务器上拉取镜像:

docker pull dockerName/https-ssl:1.0.0

docker 服务器运行容器:

docker run -d -p 443:443 --name https-ssl images:versions

运行容器有个注意点:

  1. 因为我们在 nginx 配置文件中监听了 443 端口,所以我们需要将容器的 443 端口映射到主机的 443 端口,如果我们上面配置了多个端口,那么我们需要将容器的多个端口映射到主机的多个端口。

例如:

docker run -d -p 8088:8088 -p 443:443 --name https-ssl images:versions

4. 测试

在浏览器中输入 https://strives.online,如果能够正常访问,说明 ssl 证书已经安装成功。

5. 配置后执行流程

  1. 用户请求:用户访问 https://strives.online,浏览器发送 HTTPS 请求。

  2. Docker 网络:请求首先到达 Docker 容器的 443 端口。

  3. SSL/TLS 握手:Nginx 接收到请求后,首先进行 SSL/TLS 握手,以确保连接的安全性。

  4. Nginx 反向代理:Nginx 充当反向代理,负责处理所有外部的 HTTPS 请求。

  5. 配置解析:请求进入 Nginx 配置文件中的 server 块。Nginx 根据请求的 Host 头和 URI 来决定如何处理请求。

  6. 请求匹配和转发:如果请求的 URI 是 /,Nginx 会匹配到相应的 location 块,并使用 proxy_pass http://strives.online; 将请求转发到内部的 HTTP 服务容器。

  7. 负载均衡(可选):如果配置了多个后端服务,Nginx 可以根据策略进行负载均衡。

  8. 内部服务处理:在容器内部,HTTP 服务处理请求,并生成响应。

  9. 响应返回:HTTP 服务将响应返回给 Nginx,Nginx 再将响应传递给客户端。

  10. 缓存(可选):如果配置了缓存,Nginx 可以缓存响应,以提高后续请求的速度。

6. 问题延申

  1. http 的默认端口是 80,https 的默认端口是 443,但是为什么在 docker 中查看启动的容器端口监听的是 80 (80/tcp)端口,而不是 443 端口?

    • 因为在 nginx 配置文件中,我们使用 proxy_pass http://strives.online; 将请求代理到 HTTP 的默认端口 80,所以容器内部的服务应该监听 80 端口。

    • 如果容器内部的服务监听的是 8088 端口,那么在 nginx 配置文件中,应该使用 proxy_pass http://strives.online:8088; 将请求代理到 8088 端口。

  2. 为什么 http 访问 443 就不行 https 访问 443 就可以呢

    • 因为地址访问到了 443 端口,但是因为配置钟是 listen 443 ssl,所以需要使用 https 访问。

    • listen 443 ssl:这个配置告诉 Nginx 在 443 端口上监听,并且要求使用 SSL/TLS 任何非加密的请求(即 HTTP 请求)都会被拒绝。

  3. 为什么 访问 https http 两个请求头不一样(难道不区分?), 433 端口一样 就会自动进去 433 这个 docker 容器呢? 进入容器是先根据端口吗?

    • 是的,进入容器的过程主要是基于端口映射,与请求头无关。

    • 端口映射

      • 端口映射:Docker 使用端口映射将主机上的端口(如 80 或 443)转发到容器内的对应端口。

      • 网络请求:当请求到达主机的某个端口时,Docker 会根据配置将请求转发到相应的容器。

    • 协议处理

      • 协议:HTTP 和 HTTPS 是不同的协议。虽然请求进入容器是基于端口映射,但处理请求的方式取决于容器内服务的配置。

      • Nginx 配置:如果 Nginx 配置了 listen 443 ssl;,它会期望接收到的是 HTTPS 请求,并进行 SSL/TLS 握手。

    • 结论:

      • 进入容器:是基于端口映射,与请求头无关。

      • 请求处理:在容器内,服务会根据配置处理不同类型的请求(HTTP 或 HTTPS)。

最后更新时间:
贡献者: 何风顺
上一页
腾讯云使用 ssh 连接服务器(Linux 实例)
下一页
操作系统与架构