From fd9820ec6ab1e70c38f0c47ef1fcaf1442866a69 Mon Sep 17 00:00:00 2001 From: LT Date: Mon, 12 May 2025 14:18:03 +0800 Subject: [PATCH 1/6] =?UTF-8?q?Revert=20"=E2=9C=85=20Instruction=20complet?= =?UTF-8?q?e"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This reverts commit a89d4b358998201b5ea87e1cf7b6a9483feb6c06. --- src/api/README_Zh-TW.md | 42 +++-------------------------------------- 1 file changed, 3 insertions(+), 39 deletions(-) diff --git a/src/api/README_Zh-TW.md b/src/api/README_Zh-TW.md index 5d90bb3..a88a2a9 100644 --- a/src/api/README_Zh-TW.md +++ b/src/api/README_Zh-TW.md @@ -9,51 +9,20 @@ ### 安裝依賴項 -> [!NOTE] -> 以 Arch 為例。 - -安裝系統依賴項 - -```shell -sudo pacman -Syu xorg-server-xvfb -``` - -安裝 Python 第三方擴展元件 - -```shell -pip install -r requirement.txt -``` - -安裝 git-submodules +Arch: ```shell -git submodule update --init --recursive +sudo pacman -Syu xorg-server-xvfb && pip install -r requirement.txt ``` -> [!NOTE] 一次搞定 -> -> ```shell -> sudo pacman -Syu xorg-server-xvfb &&\ -> git submodule update --init --recursive &&\ -> git submodule update --init --recursive -> ``` - ### 規則集更新 欲更新規則集,請跟隨以下步驟: -> [!WARNING] -> 假設你輸入 `pwd` 時會跟以下顯示一樣: -> -> ```shell -> $ pwd | grep -iq '/WAFfl$' && echo "Correct directory" || echo "Wrong directory" -> Correct directory -> ``` - 1. 在專案根目錄 `/WAFfl` 底下新增檔案 `rules.conf` ```shell - touch rules.conf + touch /WAFfl/rules.conf ``` 2. 執行以下指令 @@ -69,8 +38,3 @@ git submodule update --init --recursive ``` 3. 等待約30秒即能在專案跟目錄找到 `api_records_type_sensitive.json` -4. 更新 `rules.conf` - - ```shell - python3 src/api/rules.py - ``` From 27e167f35e2b878f2deb16809e95d4d66467bbf5 Mon Sep 17 00:00:00 2001 From: LT Date: Mon, 12 May 2025 14:18:03 +0800 Subject: [PATCH 2/6] =?UTF-8?q?Revert=20"=E2=9C=A8=20Rule=20updates=20afte?= =?UTF-8?q?r=20fetching=20and=20compose=20records"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This reverts commit 87bacba67a331e45765a5a587d6e7dec52f510b7. --- src/api/main.py | 2 -- src/api/rules.py | 4 ++-- 2 files changed, 2 insertions(+), 4 deletions(-) diff --git a/src/api/main.py b/src/api/main.py index a8ecc23..f7f0ec1 100644 --- a/src/api/main.py +++ b/src/api/main.py @@ -7,7 +7,6 @@ from fetch import FetchUtil from parser import Parser from mapping import Directory -from rules import update_rule def main(config: dict[str, Any]): @@ -36,4 +35,3 @@ def main(config: dict[str, Any]): with open(Directory.CONFIG.value, "rb") as config: config: dict[str, Any] = tomllib.load(config) main(config) - update_rule() diff --git a/src/api/rules.py b/src/api/rules.py index 3520158..8a45260 100644 --- a/src/api/rules.py +++ b/src/api/rules.py @@ -119,7 +119,7 @@ def rule_dump(self, overwrite: bool = False) -> None: self.rules = [] -def update_rule(): +def main(): with open(Directory.CONFIG.value, "rb") as config: config: dict[str, Any] = tomllib.load(config) @@ -129,4 +129,4 @@ def update_rule(): if __name__ == "__main__": - update_rule() + main() From e5054a89f44a30bf6ab3c4713238fddd29440a9e Mon Sep 17 00:00:00 2001 From: LT Date: Mon, 12 May 2025 14:18:03 +0800 Subject: [PATCH 3/6] =?UTF-8?q?Revert=20"=F0=9F=8C=90=20Localization"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This reverts commit 1c9357f936a0c90b6bdb46c951a76c1ffd773fda. --- README.md | 2 -- README_Zh-TW.md | 2 -- 2 files changed, 4 deletions(-) diff --git a/README.md b/README.md index f18e155..50c3d4a 100644 --- a/README.md +++ b/README.md @@ -1,7 +1,5 @@ # WAFfl -[English|[繁體中文](./README_Zh-TW.md)] - A dynamic rule-based Web Application Firewall written in Rust. - Custom rule engine with configurable security policies. diff --git a/README_Zh-TW.md b/README_Zh-TW.md index e91926a..3817d26 100644 --- a/README_Zh-TW.md +++ b/README_Zh-TW.md @@ -1,7 +1,5 @@ # WAFfl -[[English](./README.md)|繁體中文] - 一個使用 Rust 編寫的動態規則型網頁應用防火牆(WAF)。 - 自訂規則引擎,支援可配置的安全策略。 From 22a794cc53a25643be98d318aea4d22761f39cc9 Mon Sep 17 00:00:00 2001 From: LT Date: Mon, 12 May 2025 14:18:03 +0800 Subject: [PATCH 4/6] =?UTF-8?q?Revert=20"=E2=9C=85=20Reformat=20documents"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This reverts commit 18d2919e3121dce719a9917c969ba557f357e0cf. --- README_Zh-TW.md | 49 ------------------------- src/api/parser.py | 8 ++--- src/api/rules.py | 4 +-- src/api/v_classifier.py | 2 +- src/bin/README_Zh-TW.md | 32 +++++++---------- src/bin/http_server.rs | 66 +++++++++++++++++++--------------- src/bin/main.rs | 36 +++++++++---------- tests/README_Zh-TW.md | 59 +++++++++++++----------------- tests/dynamic_rule_test.rs | 5 +-- tests/keyword_blocking_test.rs | 4 +-- tests/nginx_1_test.rs | 6 ++-- tests/nginx_2_test.rs | 6 ++-- 12 files changed, 108 insertions(+), 169 deletions(-) diff --git a/README_Zh-TW.md b/README_Zh-TW.md index 3817d26..20e40f0 100644 --- a/README_Zh-TW.md +++ b/README_Zh-TW.md @@ -1,52 +1,3 @@ # WAFfl -一個使用 Rust 編寫的動態規則型網頁應用防火牆(WAF)。 -- 自訂規則引擎,支援可配置的安全策略。 -- 以 Rust 提供輕量且高效的效能。 -- 透過 `rules.conf` 彈性定義規則。 - -## 安全規則 - -### 範例規則 - -以下範例規則會拒絕任何在請求 URL 中包含關鍵字 `admin` 的流量。 - -請在專案根目錄下建立 `rules.conf` 檔案,WAFfl 會在編譯階段加載規則。 - -```conf -SecRuleEngine On - -SecRule REQUEST_URI "@rx admin" "id:1,phase:1,deny,status:401" -``` - -## 相依套件 - -`coreruleset` - -## 系統需求 - -- `libmodsecurity` 版本 >= 3.0.13 -- `xorg-server-xvfb` 版本 >= 21.1.16 - -## 測試 - -### 規則更新 - -要測試規則更新,可以使用以下指令: - -```shell -xvfb-run -a --server-args="-screen 0 1920x1080x24" python3 src/api/main.py -``` - -## 建置 - -使用 Cargo 在 Release 模式下編譯 WAFfl: - -```shell -cargo build --release -``` - -## 授權 - -本專案採用 MIT 授權條款。 diff --git a/src/api/parser.py b/src/api/parser.py index 88e5b89..87ef916 100644 --- a/src/api/parser.py +++ b/src/api/parser.py @@ -14,7 +14,7 @@ class Parser: def __init__(self, html_raw_data: str) -> None: """ 解析 HTML,將漏洞資料轉換為 API 格式 - + Parameters --- html_raw_data: str @@ -35,7 +35,7 @@ def __find_endpoint(self, data: str) -> List[tuple[str, str]]: --- data: str HTML 原始碼 - + Return --- List[tuple[str, str]] @@ -52,7 +52,7 @@ def __find_date(self, data: str) -> List[str]: --- data: str HTML 原始碼 - + Return --- List[str] @@ -64,7 +64,7 @@ def __find_date(self, data: str) -> List[str]: def sort_by_date(self, api_data: Dict[int, Dict[str, str]]) -> Dict[int, list]: """ 依年份與月份整理漏洞資料 - + Parameters --- api_data: Dict[int, Dict[str, str]] diff --git a/src/api/rules.py b/src/api/rules.py index 8a45260..ed84974 100644 --- a/src/api/rules.py +++ b/src/api/rules.py @@ -20,12 +20,12 @@ class RuleUtil: --- RuleUtil() 初始化規則管理工具,設定來源路徑與目的路徑 - + Methods --- extract_rule() 擷取 `.conf` 規則檔案,可選擇擷取所有規則或僅擷取符合 API 記錄的規則。 - rule_dump() + rule_dump() 把規則寫入進規則檔中,如果有 `overwrite` 則不產生備份檔 """ diff --git a/src/api/v_classifier.py b/src/api/v_classifier.py index f2f1ad5..4d8a899 100644 --- a/src/api/v_classifier.py +++ b/src/api/v_classifier.py @@ -24,7 +24,7 @@ def __init__(self, api_record_raw: Dict[str, List[Dict]]) -> None: --- api_record: Dict[str, List[Dist]] 原始 API 資料 - + Returns --- None diff --git a/src/bin/README_Zh-TW.md b/src/bin/README_Zh-TW.md index 61a987a..c085a77 100644 --- a/src/bin/README_Zh-TW.md +++ b/src/bin/README_Zh-TW.md @@ -1,38 +1,30 @@ # Bin - ```plain -bin -├── http_server.rs -└── main.rs +./src/bin +|-- http_server.rs +`-- main.rs ``` - -## 使用方法 - +## 如何使用? ```bash cargo run --bin - # or - -cargo build --release --bin ./target/release/ +cargo build --release --bin +./target/release/ ``` ## Main - -主程式,配合 Nginx 的設定來達到 WAF 的功能。 - -> [!NOTE] -> [Nginx 架設與設定](../../docs/Nginx_zh-TW.md) - +主程式,配合Nginx的設定來達到WAF的功能。(參見[Nginx 架設與設定](../../docs/Nginx_zh-TW.md)) ```bash curl -X GET http://127.0.0.1/ ``` +若你使用我們提供的Nginx設定,這項指令會先將請求送至WAF,接著若請求為惡意請求,會回傳403給Nginx,再回傳403給使用者,而如果請求並非惡意請求,則會回傳200給Nginx,並轉傳請求給伺服器,且伺服器回應會再經過Nginx才回傳給使用者。 -若你使用我們提供的 Nginx 設定,這項指令會先將請求送至WAF,接著若請求為惡意請求,會回傳 403 給 Nginx,再回傳 403 給使用者,而如果請求並非惡意請求,則會回傳 200 給 Nginx,並轉傳請求給伺服器,且伺服器回應會再經過 Nginx 才回傳給使用者。 - -## HTTP Server -提供測試用的 HTTP 伺服器 +## HTTP Server +提供測試用的HTTP伺服器 ```bash curl http://localhost:3000 ``` + + diff --git a/src/bin/http_server.rs b/src/bin/http_server.rs index 678ce68..2034a1f 100644 --- a/src/bin/http_server.rs +++ b/src/bin/http_server.rs @@ -1,14 +1,18 @@ -use std::net::{ TcpListener, TcpStream }; +use std::net::{ + TcpListener,TcpStream +}; use std::thread; use std::time::Duration; use std::io::prelude::*; -use std::sync::{ mpsc, Arc, Mutex }; +use std::sync::{ + mpsc, Arc, Mutex +}; // struct Job; -type Job = Box; +type Job = Box; enum Message { NewJob(Job), - Terminate, + Terminate } struct ThreadPool { @@ -16,18 +20,20 @@ struct ThreadPool { sender: mpsc::Sender, } + impl ThreadPool { pub fn new(size: usize) -> ThreadPool { - assert!(size > 0); + assert!(size>0); let mut workers = Vec::with_capacity(size); let (sender, receiver) = mpsc::channel(); let receiver = Arc::new(Mutex::new(receiver)); for id in 0..size { workers.push(Worker::new(id, Arc::clone(&receiver))); } - ThreadPool { workers, sender } + ThreadPool {workers, sender} } - pub fn execute(&self, f: F) where F: FnOnce() + Send + 'static { + pub fn execute(&self, f: F) + where F: FnOnce()+Send+'static { let job = Box::new(f); self.sender.send(Message::NewJob(job)).unwrap(); } @@ -39,7 +45,7 @@ impl Drop for ThreadPool { for _ in &self.workers { self.sender.send(Message::Terminate).unwrap(); } - + println!("Shutting down all workers."); for worker in &mut self.workers { println!("Shutting down worker {}", worker.id); @@ -52,27 +58,29 @@ impl Drop for ThreadPool { struct Worker { id: usize, - thread: Option>, + thread: Option> } impl Worker { fn new(id: usize, receiver: Arc>>) -> Worker { - let thread = thread::spawn(move || { - loop { - let message = receiver.lock().unwrap().recv().unwrap(); - match message { - Message::NewJob(job) => { - println!("Worker {} got a job; executing.", id); - job(); - } - Message::Terminate => { - println!("Worker {} was told to terminate.", id); - break; - } + let thread = thread::spawn(move || loop { + let message = receiver + .lock() + .unwrap() + .recv() + .unwrap(); + match message { + Message::NewJob(job)=>{ + println!("Worker {} got a job; executing.", id); + job() + }, + Message::Terminate=>{ + println!("Worker {} was told to terminate.", id); + break; } } }); - Worker { id, thread: Some(thread) } + Worker {id, thread:Some(thread)} } } @@ -80,10 +88,11 @@ fn main() { let listener = TcpListener::bind("127.0.0.1:3000").unwrap(); println!("HTTP server listening on 127.0.0.1:3000"); let pool = ThreadPool::new(4); - for stream in listener.incoming() { - //.take(2) + for stream in listener.incoming() { //.take(2) let stream = stream.unwrap(); - pool.execute(|| { handle_connection(stream) }); + pool.execute(||{ + handle_connection(stream) + }); } println!("Shutdown."); } @@ -91,7 +100,7 @@ fn main() { fn handle_connection(mut stream: TcpStream) { let mut buffer = [0; 1024]; stream.read(&mut buffer).unwrap(); - + let request = String::from_utf8_lossy(&buffer); println!("請求內容:\n{}", request); @@ -106,9 +115,8 @@ fn handle_connection(mut stream: TcpStream) { // **如果 URI 以 "http://" 開頭,則去掉主機部分** if uri.starts_with("http://") { - if let Some(pos) = uri[7..].find('/') { - // 找到 `http://` 之後的 `/` - uri = &uri[pos + 7..]; // 只保留 `/xxx` + if let Some(pos) = uri[7..].find('/') { // 找到 `http://` 之後的 `/` + uri = &uri[(pos+7)..]; // 只保留 `/xxx` } else { uri = "/"; // 沒有 `/` 時,視為根目錄 } diff --git a/src/bin/main.rs b/src/bin/main.rs index b3df89f..82d3686 100644 --- a/src/bin/main.rs +++ b/src/bin/main.rs @@ -1,15 +1,10 @@ -// 搭配 Nginx 使用 +// 搭配 nginx 使用 use axum::{ - body::{ to_bytes, Body }, - extract::State, - http::{ HeaderValue, Request, StatusCode }, - response::IntoResponse, - routing, - Router, + body::{to_bytes, Body}, extract::State, http::{HeaderValue, Request, StatusCode}, response::IntoResponse, routing, Router }; -use modsecurity::{ ModSecurity, Rules }; -use std::{ net::SocketAddr, sync::Arc, usize }; -use tokio::{ net::TcpListener, sync::Mutex }; +use modsecurity::{ModSecurity, Rules}; +use std::{net::SocketAddr, sync::Arc, usize}; +use tokio::{net::TcpListener, sync::Mutex}; #[derive(Clone)] struct AppState { @@ -17,7 +12,10 @@ struct AppState { rules: Arc>, } -async fn handle_request(State(state): State, req: Request) -> impl IntoResponse { +async fn handle_request( + State(state): State, + req: Request, +) -> impl IntoResponse { println!("🔥 WAF 收到請求:{:?}", req); let ms = state.modsec.lock().await; @@ -79,21 +77,19 @@ async fn handle_request(State(state): State, req: Request) -> im response.headers_mut().insert("X-WAF-Pass", "true".parse().unwrap()); // 這行可以讓nginx導向/backend,感覺寫這邊可能會有漏洞,但這是目前最好的寫法了🥲 - response - .headers_mut() - .insert( - "X-Accel-Redirect", - HeaderValue::from_str(&format!("/backend{}", uri.as_str())).unwrap() - ); + response.headers_mut().insert("X-Accel-Redirect", HeaderValue::from_str(&format!("/backend{}", uri.as_str())).unwrap()); response } + #[tokio::main] async fn main() { // 1. 載入 ModSecurity 規則 let mut rules = Rules::new(); - rules.add_file("./rules.conf").expect("Failed to load ModSecurity rules"); + rules + .add_file("./rules.conf") + .expect("Failed to load ModSecurity rules"); let modsec = Arc::new(Mutex::new(ModSecurity::default())); let rules = Arc::new(Mutex::new(rules)); @@ -107,7 +103,7 @@ async fn main() { .fallback(handle_request) .with_state(AppState { modsec, - rules, + rules }); let addr = SocketAddr::from(([0, 0, 0, 0], 8089)); @@ -115,4 +111,4 @@ async fn main() { println!("Rust WAF running on {:?}", addr); axum::serve(listener, app).await.unwrap(); -} +} \ No newline at end of file diff --git a/tests/README_Zh-TW.md b/tests/README_Zh-TW.md index e27d94e..1b09ea7 100644 --- a/tests/README_Zh-TW.md +++ b/tests/README_Zh-TW.md @@ -1,52 +1,43 @@ -# 單元測試 +# Testing Scripts ```plain -tests -├── keyword_blocking_test.rs -├── nginx_1_test.rs -└── nginx_2_test.rs +./tests +|-- keyword_blocking_test.rs +|-- nginx_1_test.rs +`-- nginx_2_test.rs ``` -## 要求 - +## 測試要求 以下測試皆須滿足這些條件: - -- 基本 Rust 執行環境 +- 基本Rust執行環境 - libmodsecurity -- 存在 `/rules.conf` 檔案 - -## 測試 +- 存在./rules.conf檔案 -### Keyword Blocking - -執行下列指令,測試 `rust-modsecurity` 正常運作。 +## Keyword Blocking Test +### 說明 ```bash cargo test --test keyword_blocking_test ``` +執行上方指令,可以測試`rust-modsecurity`正常運作。 -### Nginx 1 - -> [!IMPORTANT] 額外要求 -> 將Nginx架設完,參見 [Nginx 架設與設定](../docs/Nginx_zh-TW.md)。 - -下列指令會做: - -1. 架設簡單的 HTTP 伺服器 -2. 架設簡單的 WAF -3. 使用 `/`和 `/admin` 兩路徑測試使用者的 Nginx 設定、Rust ModSrcurity 與環境設定沒問題 - +## Nginx 1 Test +### 額外要求 +- 將Nginx架設完畢(參見[Nginx 架設與設定](../docs/Nginx_zh-TW.md))。 +### 說明 ```bash cargo test --test nginx_1_test ``` - -### Nginx 2 - -> [!IMPORTANT] 額外要求 -> 將Nginx架設完,參見 Nginx 架設手冊。 - -這項測試與 `nginx_1_test` 唯一不同的地方是未架設 HTTP 伺服器,你可以使用自己的伺服器來進行測試: - +執行上方指令,會做以下事情: +1. 架設簡單的HTTP伺服器 +2. 架設簡單的WAF +3. 使用`/`和`/admin`兩路徑測試使用者的nginx設定、Rust ModSrcurity與環境設定沒問題 + +## Nginx 2 Test +### 額外要求 +- 將Nginx架設完畢(參見[Nginx 架設手冊]())。 +### 說明 ```bash cargo test --test nginx_2_test ``` +這項測試與`nginx_1_test`唯一不同的地方是未架設HTTP伺服器,你可以使用自己的伺服器來進行測試 \ No newline at end of file diff --git a/tests/dynamic_rule_test.rs b/tests/dynamic_rule_test.rs index 3e96bdd..333c947 100644 --- a/tests/dynamic_rule_test.rs +++ b/tests/dynamic_rule_test.rs @@ -1,5 +1,6 @@ use std::process::Command; + #[test] pub fn api_fetch() { let mut output = Command::new("xvfb-run") @@ -9,13 +10,13 @@ pub fn api_fetch() { .arg("src/api/main.py") .output() .expect("Failed to execute xvfb-run"); - + println!("api_fetch Output: {:?}", output); let output = Command::new("python3") .arg("src/api/rules.py") .output() .expect("Failed to update rules"); - + println!("rule_update Output: {:?}", output); } diff --git a/tests/keyword_blocking_test.rs b/tests/keyword_blocking_test.rs index b0df552..06857db 100644 --- a/tests/keyword_blocking_test.rs +++ b/tests/keyword_blocking_test.rs @@ -42,8 +42,8 @@ pub fn test_keyword_blocking() { sleep(Duration::from_secs(1)); // 等待初始化 let status = process_transaction(&ms, &rules); assert_eq!( - status, - 401, + status, + 401, "Please ensure that the ./rules.conf file exists in the specified path." ); } diff --git a/tests/nginx_1_test.rs b/tests/nginx_1_test.rs index f56390a..2c93080 100644 --- a/tests/nginx_1_test.rs +++ b/tests/nginx_1_test.rs @@ -42,10 +42,10 @@ fn test_waf_with_curl() { sleep(Duration::from_secs(5)); // 等待 http server 啟動 let mut _waf = start_waf_server(); sleep(Duration::from_secs(5)); // 等待 waf 啟動 - + // curl -X GET http://127.0.0.1/ let output = Command::new("curl") - .arg("-s") // 靜默模式,不顯示進度 + .arg("-s") // 靜默模式,不顯示進度 .arg("-X") .arg("GET") .arg("http://127.0.0.1/") @@ -56,7 +56,7 @@ fn test_waf_with_curl() { // curl -x http://proxy http://server/admin let output = Command::new("curl") - .arg("-s") // 靜默模式,不顯示進度 + .arg("-s") // 靜默模式,不顯示進度 .arg("-X") .arg("GET") .arg("http://127.0.0.1/admin") diff --git a/tests/nginx_2_test.rs b/tests/nginx_2_test.rs index 936b60e..52c8724 100644 --- a/tests/nginx_2_test.rs +++ b/tests/nginx_2_test.rs @@ -29,10 +29,10 @@ fn start_waf_server() -> ServerGuard { fn test_waf_with_curl() { let mut _waf = start_waf_server(); sleep(Duration::from_secs(5)); // 等待 waf 啟動 - + // curl -X GET http://127.0.0.1/ let output = Command::new("curl") - .arg("-s") // 靜默模式,不顯示進度 + .arg("-s") // 靜默模式,不顯示進度 .arg("-X") .arg("GET") .arg("http://127.0.0.1/") @@ -43,7 +43,7 @@ fn test_waf_with_curl() { // curl -x http://proxy http://server/admin let output = Command::new("curl") - .arg("-s") // 靜默模式,不顯示進度 + .arg("-s") // 靜默模式,不顯示進度 .arg("-X") .arg("GET") .arg("http://127.0.0.1/admin") From 4edab6c2a9d5c99ffd6ffd9393d3c3bd66e4f5e8 Mon Sep 17 00:00:00 2001 From: LT Date: Mon, 12 May 2025 14:18:03 +0800 Subject: [PATCH 5/6] =?UTF-8?q?Revert=20"=E2=9C=85=20Update=20document"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This reverts commit 0c9a26f39c4da2a71fdad79a3b0c3c5c601d7acf. --- docs/Nginx_zh-TW.md | 100 +++++++++++++++++++++----------------------- 1 file changed, 48 insertions(+), 52 deletions(-) diff --git a/docs/Nginx_zh-TW.md b/docs/Nginx_zh-TW.md index 5f5d297..4f077a2 100644 --- a/docs/Nginx_zh-TW.md +++ b/docs/Nginx_zh-TW.md @@ -1,56 +1,27 @@ # Nginx 架設與設定 +以Arch Linux、Ubuntu為例 -以 Arch、Ubuntu 為例。 - -## 安裝 - -Ubuntu - +## 在Ubuntu上架設與設定Nginx +### 安裝Nginx ```bash sudo apt update sudo apt install nginx -y ``` - -Arch - -```bash -sudo pacman -Syu nginx -``` - -## Nginx 服務設定 - -> [!NOTE] -> Arch 跟 Ubuntu 24.04 應該都能用 `systemctl`。 - -啟動服務: - +### 啟動並設定開機時自動開啟 ```bash +sudo systemctl enable nginx sudo systemctl start nginx ``` - -開機時自動啟動: - +### 檢查Nginx狀態 ```bash -sudo systemctl enable nginx +sudo systemctl status nginx ``` - -檢查 Nginx 狀態: - +### 撰寫設定 +若這個檔案/資料夾不存在,則自行建立一個 +#### /etc/nginx/sites-available/default ```bash -sudo systemctl status nginx +sudo vim /etc/nginx/sites-available/default ``` - -## 防火牆設定 - -### default - -> [!NOTE] -> 若 `/etc/nginx/sites-available/default` 不存在,則自行建立一個 -> -> ```bash -> sudo touch /etc/nginx/sites-available/default -> ``` - ```conf server { listen 80; @@ -90,17 +61,12 @@ server { } } ``` - -### nginx.conf - -> [!NOTE] -> 若 `/etc/nginx/nginx.conf` 不存在,則自行建立一個 -> -> ```bash -> sudo touch /etc/nginx/nginx.conf -> ``` - +#### /etc/nginx/nginx.conf +```bash +sudo vim /etc/nginx/nginx.conf +``` ```conf +... http { ... include /etc/nginx/sites-available/default; @@ -108,9 +74,39 @@ http { } ``` -## 測試與更新 - +### 測試與更新 ```bash sudo nginx -t sudo systemctl restart nginx ``` + +## 在Arch上架設與設定Nginx +### 安裝Nginx +```bash +sudo pacman -Syu nginx +``` +### 啟動並設定開機時自動開啟 +```bash +sudo systemctl enable nginx +sudo systemctl start nginx +``` +### 檢查Nginx狀態 +```bash +sudo systemctl status nginx +``` +### 撰寫設定 +若這個檔案/資料夾不存在,則自行建立一個 +/etc/nginx/sites-available/default (參見上方同名檔案範例) +```bash +sudo vim /etc/nginx/sites-available/default +``` +/etc/nginx/nginx.conf (參見上方同名檔案範例) +```bash +sudo vim /etc/nginx/nginx.conf +``` + +### 測試與更新 +```bash +sudo nginx -t +sudo systemctl restart nginx +``` \ No newline at end of file From 78a5c3eeaf98ae6ca954f501329b1ba7f075d01f Mon Sep 17 00:00:00 2001 From: LT Date: Mon, 12 May 2025 14:18:03 +0800 Subject: [PATCH 6/6] Revert ":bug: Fix redirect issue" This reverts commit 97be97be65142e1674bd88ce67af28cd06067263. --- docs/Nginx_zh-TW.md | 2 -- src/bin/main.rs | 2 +- 2 files changed, 1 insertion(+), 3 deletions(-) diff --git a/docs/Nginx_zh-TW.md b/docs/Nginx_zh-TW.md index 4f077a2..c8b1317 100644 --- a/docs/Nginx_zh-TW.md +++ b/docs/Nginx_zh-TW.md @@ -44,9 +44,7 @@ server { # 2. 接著若請求非惡意,就傳給要保護的伺服器 location /backend { internal; - rewrite /backend/(.*) /$1 break; proxy_pass http://127.0.0.1:3000; - proxy_redirect off; proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; diff --git a/src/bin/main.rs b/src/bin/main.rs index 82d3686..4738cfe 100644 --- a/src/bin/main.rs +++ b/src/bin/main.rs @@ -77,7 +77,7 @@ async fn handle_request( response.headers_mut().insert("X-WAF-Pass", "true".parse().unwrap()); // 這行可以讓nginx導向/backend,感覺寫這邊可能會有漏洞,但這是目前最好的寫法了🥲 - response.headers_mut().insert("X-Accel-Redirect", HeaderValue::from_str(&format!("/backend{}", uri.as_str())).unwrap()); + response.headers_mut().insert("X-Accel-Redirect", HeaderValue::from_static("/backend")); response }