如何配置 Nginx 作為 Jenkins 的反向代理,並啟用 SSL

介紹

默認情況下,Jenkins 自帶內置的 Web 服務器,監聽端口 8080。如果您運行的是私有 Jenkins 實例,或者您只是需要快速啟動一些東西並且不關心安全性,這很方便。但是,一旦您的主機開始處理真實的生產數據,最好使用一個更安全的 Web 服務器,如 Nginx 來處理流量。

本文將詳細介紹如何使用 Nginx Web 服務器作為 Jenkins 實例的反向代理來包裹您的站點,以添加 SSL。本教程假設您對 Linux 命令有一定的了解,擁有可運行的 Jenkins 安裝以及 Ubuntu 20.04 安裝。

如果您尚未安裝 Jenkins,您可以稍後在本教程中進行安裝。

先決條件

這個指南假設您正在使用Ubuntu 20.04。在開始之前,您應該在系統上設置一個非root用戶帳戶並具有sudo特權。您可以通過遵循Ubuntu 20.04初始服務器設置教程來了解如何操作。您還需要安裝並托管您的域的Nginx服務器。您可以通過在Ubuntu 20.04上安裝Nginx教程來了解如何操作。

此外,通過SSL將您的Jenkins實例保護起來非常重要。如果它在互聯網上可見,您可以使用Let’s Encrypt來保護它。您可以通過在Ubuntu 22.04上使用Let’s Encrypt保護Nginx教程來了解如何操作。
如前所述,本教程假設Jenkins已經安裝。如果需要,本教程將向您展示如何安裝Jenkins。您可能需要切換到root用戶閱讀該文章。

步驟1 — 配置Nginx

近年來,Nginx因其速度和靈活性而成為受歡迎的Web服務器,這使其成為我們應用的理想選擇。

編輯配置

接下來,您需要編輯預設的 Nginx 配置文件。以下示例使用nano

  1. sudo nano etc/nginx/sites-enabled/default

以下是最終配置的可能外觀;各部分被分解並簡要解釋如下。您可以更新或替換現有的配置文件,但您可能希望先備份一份副本。

server {23
    listen 80;
    return 301 https://$host$request_uri;
}

server {

    listen 443;
    server_name jenkins.domain.com;

    access_log            /var/log/nginx/jenkins.access.log;

    location / {

      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;

      proxy_pass          http://localhost:8080;
      proxy_read_timeout  90;

      proxy_redirect      http://localhost:8080 https://jenkins.domain.com;
    }
    
    ...
}

您需要使用您自己的域名更新或替換server_nameproxy_redirect行。還有一些額外的 Nginx 魔法,告訴請求被 Nginx 讀取並在響應端重新寫入,以確保反向代理正常工作。

保存並關閉文件。如果您使用的是nano,您可以按Ctrl + X,然後按Y,最後按Enter來完成。

第一部分告訴 Nginx 伺服器監聽在80端口(默認HTTP)上收到的任何請求並將其重定向到HTTPS。

...
server {
   listen 80;
   return 301 https://$host$request_uri;
}
...

之後,代理就會發生。它基本上接受任何傳入的請求並將它們代理到綁定/監聽本地網路介面上8080端口的 Jenkins 實例。

...
location / {

    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;

    proxy_pass          http://localhost:8080;
    proxy_read_timeout  90;

    proxy_redirect      http://localhost:8080 https://jenkins.domain.com;
}
...

注意:如果您想了解更多關於在 Nginx 中設置代理的信息,這個教程有一些很好的信息。

A few quick things to point out here. If you don’t have a domain name that resolves to your Jenkins server, then the proxy_redirect statement above won’t function correctly without modification, so keep that in mind. Also, if you misconfigure the proxy_pass (by adding a trailing slash for example), you will get something similar to the following in your Jenkins Configuration page.

所以,如果您看到此錯誤,請仔細檢查Nginx配置中的proxy_passproxy_redirect設置!

步驟2 — 配置Jenkins

為了使Jenkins與Nginx正常工作,我們需要更新Jenkins配置,僅在本地地址上監聽,而不是所有地址(0.0.0.0),以確保流量被正確處理。這是一個重要的安全步驟,因為如果Jenkins仍在所有地址上監聽,那麼它仍然可能通過其原始端口(8080)訪問。我們將修改/etc/default/jenkins配置文件來進行這些調整。

  1. sudo nano /etc/default/jenkins

定位JENKINS\_ARGS行並將其更新為以下內容:

JENKINS_ARGS="--webroot=/var/cache/jenkins/war --httpListenAddress=127.0.0.1 --httpPort=$HTTP_PORT -ajp13Port=$AJP_PORT"

請注意,–httpListenAddress=127.0.0.1設置必須添加或修改。

然後,請繼續重新啟動Jenkins和Nginx。

  1. sudo service jenkins restart
  2. sudo service nginx restart

現在,您應該能夠使用HTTPS訪問您的域名,並且Jenkins站點將被安全地提供。

選擇性 — 更新OAuth URL

如果您正在使用 GitHub 或其他 OAuth 插件进行身份验证,此时可能会出现故障。例如,尝试访问 URL 时,您将收到类似以下的“无法打开页面”消息,URL 如下:http://jenkins.domain.com:8080/securityRealm/finishLogin?code=random-string

要解决此问题,您需要更新 Jenkins 中的一些设置,包括您的 OAuth 插件设置。首先,在 Jenkins GUI 中更新 Jenkins URL;您可以在 Jenkins -> 管理 Jenkins -> 配置系统 -> Jenkins 位置 菜单中找到它。

将 Jenkins URL 更新为使用 HTTPS – https://jenkins.domain.com/

接下来,使用外部提供者更新您的 OAuth 设置。此示例适用于 GitHub。在 GitHub 上,可以在 设置 -> 应用程序 -> 开发人员应用程序 中找到它。

应该会有一个适用于 Jenkins 的条目。更新 主页 URL授权回调 URL 以反映 HTTPS 设置。它可能类似于以下内容:

结论

唯一剩下的事情就是验证一切是否正常工作了。如上所述,您现在应该能够通过新配置的 URL – jenkins.domain.com – 浏览,无论是使用 HTTP 还是 HTTPS。您应该被重定向到安全站点,并且应该看到一些站点信息,包括您新更新的 SSL 设置。如前所述,如果您没有通过 DNS 使用主机名,则您的重定向可能无法按预期工作。在这种情况下,您需要修改 Nginx 配置文件中的 proxy_pass 部分。

Source:
https://www.digitalocean.com/community/tutorials/how-to-configure-nginx-with-ssl-as-a-reverse-proxy-for-jenkins