在Web開發中,前後端分離架構已經成爲主流。前端負責頁面展示,後端專注於業務邏輯和數據處理,兩者通過API接口通信。但如何讓前端頁面和後端服務和諧工作,避免複雜的跨域問題,並且讓用戶訪問更便捷?這時,Nginx的反向代理功能就能派上大用場。

一、什麼是反向代理?

先從基礎概念說起。我們先回憶一下正向代理:比如你需要訪問國外網站,直接訪問不了,於是通過VPN(虛擬專用網絡)代理你的請求,這就是正向代理。此時VPN代理的是客戶端,你不知道目標服務器的真實地址。

反向代理則相反,它代理的是服務器。用戶訪問的是反向代理服務器(比如Nginx),但反向代理服務器會根據請求內容,將請求轉發到後端真實的服務器上。對用戶來說,反向代理服務器就像後端服務器本身,用戶不需要知道後端服務的具體地址。

二、爲什麼前後端分離需要反向代理?

假設你有一個前端項目(比如Vue或React)和一個後端API服務(比如Node.js或Java),它們可能運行在不同的服務器或端口上。沒有反向代理時,用戶需要分別訪問前端和後端地址(例如http://frontend.comhttp://backend.com/api),這樣會帶來幾個問題:

  1. 域名管理複雜:用戶需要記住多個域名。
  2. 跨域問題:前端直接調用不同域名的後端接口會觸發瀏覽器的跨域限制。
  3. 安全隱患:直接暴露後端服務地址,增加被攻擊風險。

而反向代理可以解決這些問題:
- 統一域名:用戶只需要訪問一個域名(例如https://example.com)。
- 隱藏後端:用戶請求被Nginx攔截後轉發到後端,後端地址對用戶透明。
- 路徑代理:不同路徑請求(如/對應前端,/api對應後端)由Nginx自動分配。

三、Nginx安裝與基本配置

1. 安裝Nginx

以Ubuntu爲例,安裝命令:

sudo apt update
sudo apt install nginx

CentOS用戶:

sudo yum install nginx

Windows用戶可從Nginx官網下載安裝包,按提示安裝。

2. 啓動與驗證

安裝完成後,啓動Nginx:

sudo systemctl start nginx

檢查狀態:

sudo systemctl status nginx

此時訪問服務器IP或域名(如http://localhost),能看到Nginx的默認歡迎頁面,說明安裝成功。

四、反向代理實戰:前端+後端分離配置

假設我們有兩個服務:
- 前端服務:靜態HTML文件(放在Nginx的/usr/share/nginx/html目錄下)。
- 後端服務:一個簡單的Node.js API服務,運行在本地3000端口(返回{"message": "Hello from backend"})。

1. 準備前端靜態文件

在Nginx的默認網站目錄(Ubuntu/CentOS通常是/usr/share/nginx/html)下創建前端頁面:

sudo nano /usr/share/nginx/html/index.html

寫入簡單內容:

<!DOCTYPE html>
<html>
<body>
  <h1>前端頁面</h1>
  <p>點擊按鈕調用後端接口:</p>
  <button onclick="callBackend()">調用API</button>
  <script>
    function callBackend() {
      fetch('/api/user')
        .then(res => res.json())
        .then(data => alert(data.message));
    }
  </script>
</body>
</html>

2. 啓動後端服務

用Node.js創建一個簡單的後端服務(需先安裝Node.js):

# 創建項目目錄
mkdir backend && cd backend
# 初始化項目
npm init -y
# 安裝Express
npm install express

創建app.js

const express = require('express');
const app = express();
const port = 3000;

app.get('/user', (req, res) => {
  res.json({ message: 'Hello from backend!' });
});

app.listen(port, () => {
  console.log(`後端服務運行在 http://localhost:${port}`);
});

啓動後端:

node app.js

3. 配置Nginx反向代理

編輯Nginx配置文件,將請求轉發到前端或後端:

sudo nano /etc/nginx/sites-available/default

server塊中添加以下配置(完整配置參考下方示例):

server {
    listen 80;
    server_name localhost;  # 替換爲你的域名或服務器IP

    # 前端靜態資源:所有路徑(除/api外)都指向前端頁面
    location / {
        root /usr/share/nginx/html;  # 前端文件目錄
        index index.html;            # 默認首頁
        try_files $uri $uri/ /index.html;  # 支持前端路由(如/#/about)
    }

    # 後端API:所有以/api開頭的請求轉發到後端服務
    location /api {
        proxy_pass http://localhost:3000;  # 後端服務地址
        proxy_set_header Host $host;       # 傳遞Host頭,讓後端知道請求來源
        proxy_set_header X-Real-IP $remote_addr;  # 傳遞真實IP
    }
}

4. 驗證配置並重啓Nginx

測試配置是否有誤:

sudo nginx -t

若提示test is successful,則重啓Nginx:

sudo systemctl restart nginx

5. 測試效果

  • 訪問http://localhost(或你的域名),能看到前端頁面。
  • 點擊頁面上的“調用API”按鈕,會觸發fetch('/api/user'),此時Nginx會將請求轉發到後端服務http://localhost:3000/user,並返回數據。

五、核心配置解析

1. location

Nginx通過location定義不同路徑的處理規則。常用匹配方式:
- location /:匹配所有路徑(需放在其他location前面)。
- location /api:匹配以/api開頭的路徑。

2. proxy_pass

proxy_pass用於指定轉發的目標地址,格式爲http://目標IP:端口。例如:

location /api {
    proxy_pass http://127.0.0.1:3000;  # 也可寫localhost:3000
}

3. proxy_set_header

傳遞HTTP頭信息給後端,常見場景:
- Host $host:後端獲取真實請求域名。
- X-Real-IP $remote_addr:後端獲取用戶真實IP(避免後端日誌顯示Nginx的IP)。

六、常見問題與解決

  1. Nginx啓動失敗
    nginx -t檢查配置語法,錯誤信息通常會指出問題行。

  2. 前端資源404
    確保root路徑和index文件存在,例如:

   location / {
       root /usr/share/nginx/html;  # 路徑必須正確
       index index.html;            # 文件必須存在
   }
  1. 後端接口無法訪問
    檢查後端服務是否啓動,端口是否被佔用,proxy_pass是否寫對地址(如http://localhost:3000而非localhost:3000)。

七、總結

反向代理是Nginx的核心功能之一,尤其在前後端分離架構中,它能幫我們:
- 隱藏後端服務地址,提升安全性。
- 統一域名和路徑,簡化用戶訪問。
- 集中管理請求轉發,便於後續擴展(如負載均衡、緩存)。

通過本文的示例,你已經可以快速上手配置反向代理,讓前端和後端服務無縫協作。接下來可以嘗試將後端服務換成Java、Python等其他技術棧,或進一步學習Nginx的緩存、SSL配置等高級功能。

小夜