Điểm:0

Cú pháp câu lệnh "nếu không" của proxy ngược NGINX?

lá cờ us

Tôi có một proxy ngược nginx mà về cơ bản tôi muốn chuyển hướng bất kỳ yêu cầu url nào không phải là miền cấp cao nhất cụ thể của tôi sang 404.

Cho đến nay tôi nghĩ rằng tôi muốn một cái gì đó như thế này ở dưới cùng của tôi /etc/nginx/sites-enabled/site.conf:

người phục vụ {
        nghe 80;
        if ($host != *domain.com) {
                trả về 404 http://$host$request_uri;
        }
}

nhưng tôi không biết cú pháp chính xác ở đây. Tôi đã có các khối chuyển hướng khác phía trên khối này, tôi chỉ muốn bất kỳ yêu cầu url nào đối với tên máy chủ chỉ IP hoặc các miền khác ngay lập tức nhận được lỗi 404 và không được chuyển đến máy chủ phụ trợ.

Ngoài ra, tôi cũng có thông qua TLS mà tôi muốn làm điều tương tự, nhưng tôi hoàn toàn không biết cách triển khai câu lệnh if trên khối luồng. Khối luồng của tôi trông như thế này trong /etc/nginx/nginx.conf:

dòng {
        bản đồ $ssl_preread_server_name $name {
                máy chủ server.domain.com;
                www.miền.com www;
        }
        máy chủ ngược dòng {
                phụ trợ máy chủ: 443;
        }
        ngược dòng www {
                phụ trợ máy chủ2:443;
        }
        người phục vụ {
                nghe 443;
                proxy_pass $name;
                ssl_preread on;
        }
}

Để làm được điều đó, tôi có thể triển khai thứ gì đó như thế này ngay bên dưới khối máy chủ đầu tiên không?

        người phục vụ {
                nghe 443;
                if ($ssl_preread_server_name != *domain.com) {
                        trả về 404 https://$host$request_uri;
                }
        }

Tôi nghĩ để bảo mật, tôi cũng nên đưa default_server vào dòng nghe cho cả hai khối này với các câu lệnh if, hay điều đó có quan trọng không?

Tôi chỉ giả sử có rất nhiều cú pháp ở đây, vì vậy mọi trợ giúp sẽ được đánh giá cao.

Ivan Shatsky avatar
lá cờ gr
Bạn có thể kiểm tra khớp chính xác/không khớp trên các chuỗi hoặc thực hiện khớp phân biệt chữ hoa chữ thường/không phân biệt chữ hoa chữ thường đối với mẫu biểu thức chính quy. Có vẻ như bạn đang tìm kiếm `if ($var !~ (.*\.)?domain\.com$) { ... }`. Gần đây, tôi đã đưa ra câu trả lời chi tiết về việc chặn tất cả quyền truy cập theo địa chỉ IP thay vì tên máy chủ [tại đây](https://stackoverflow.com/questions/69824838/block-access-with-https-ipaddress-on-nginx/69825652# 69825652).
ehammer avatar
lá cờ us
Tôi đã xem bài đăng khác của bạn, điều đó giúp ích cho các khối http của tôi. Vẫn không chắc chắn về cách thực hiện với thông qua nginx TLS (trả về 444 nếu SNI không phải là một miền nhất định)
Ivan Shatsky avatar
lá cờ gr
Chà, tôi không am hiểu về mô-đun luồng như tôi về http. Bạn không thể sử dụng bất kỳ thứ gì từ mô-đun viết lại (kể cả `if`). Bạn không thể sử dụng `return 444` vì mô-đun luồng có chỉ thị [`return`](http://nginx.org/en/docs/stream/ngx_stream_return_module.html) riêng khác với chỉ thị http.
Điểm:1
lá cờ gr

Tôi không biết cách đóng kết nối với mô-đun luồng một cách duyên dáng, vì vậy tôi không chắc liệu đó có phải là giải pháp đúng hay không, nhưng nó đáng để thử (bạn có thể sử dụng bất kỳ cổng miễn phí nào cho máy chủ giả/ngược dòng):

dòng {
    bản đồ $ssl_preread_server_name $name {
        máy chủ server.domain.com;
        www.miền.com www;
        giả mặc định;
    }
    máy chủ ngược dòng {
        phụ trợ máy chủ: 443;
    }
    ngược dòng www {
        phụ trợ máy chủ2:443;
    }
    ngược dòng giả {
        phụ trợ 127.0.0.1:4343;
    }
    người phục vụ {
        nghe 443;
        proxy_pass $name;
        ssl_preread on;
    }
    người phục vụ {
        nghe 4343 ;
        trở lại "";
    }
}

Cập nhật

Sau khi thử nghiệm giải pháp trên, tôi có thể xác nhận rằng nó khả thi. Tuy nhiên, nó tạo ra một mục nhật ký lỗi như

WSARecv() không thành công (10053: Kết nối được thiết lập đã bị phần mềm trong máy chủ của bạn hủy bỏ) trong khi ủy quyền và đọc từ thượng nguồn, máy khách: 127.0.0.1, máy chủ: 127.0.0.1:443, thượng nguồn: "127.0.0.1:4343" , byte từ/đến máy khách:517/0, byte từ/đến ngược dòng:0/517

Vì vậy, sau một số suy nghĩ, tôi đã thử cái này:

http {
    người phục vụ {
        nghe 4343 ssl;
        ssl_certificate /path/to/selfsigned.crt;
        ssl_certificate_key /path/to/selfsigned.key;
        trả lại 444;
    }
}
dòng {
    bản đồ $ssl_preread_server_name $name {
        máy chủ server.domain.com;
        www.miền.com www;
        giả mặc định;
    }
    máy chủ ngược dòng {
        phụ trợ máy chủ: 443;
    }
    ngược dòng www {
        phụ trợ máy chủ2:443;
    }
    ngược dòng giả {
        phụ trợ 127.0.0.1:4343;
    }
    người phục vụ {
        nghe 443;
        proxy_pass $name;
        ssl_preread on;
    }
}

Chứng chỉ và khóa tự ký có thể được tạo bằng lệnh sau:

openssl req -nodes -new -x509 -subj "/CN=localhost" -keyout /path/to/selfsigned.key -out /path/to/selfsigned.crt

Cái này đóng kết nối chính xác.

Hơn nữa, ngay cả điều này đã làm việc:

http {
    người phục vụ {
        nghe 80 default_server;
        trả lại 444;
    }
}
dòng {
    bản đồ $ssl_preread_server_name $name {
        máy chủ server.domain.com;
        www.miền.com www;
        giả mặc định;
    }
    máy chủ ngược dòng {
        phụ trợ máy chủ: 443;
    }
    ngược dòng www {
        phụ trợ máy chủ2:443;
    }
    ngược dòng giả {
        phụ trợ 127.0.0.1:80;
    }
    người phục vụ {
        nghe 443;
        proxy_pass $name;
        ssl_preread on;
    }
}

Tất nhiên, Xoăn phàn nàn về nỗ lực bắt tay vì số phiên bản SSL không chính xác và có những mục buồn cười trong nhật ký truy cập như

127.0.0.1 - - [05/Nov/2021:01:04:34 +0200] "\x16\x03\x01\x02\x00\x01\x00\x01\xFC\x03\x03L\xF9[\xB2\x7F \x99\xB1(\xAC\xB4\x91}\xE2N\xC6H\xE3\xB3_\xD1\xEA\xA3C\x1D\xE5\xE5\xB6\x02\xDB\x04h\xB6 *\xCB\x0E\xC0\ xF5\xB7\xAF[y|\x1B\x14_\xC2g\xEA\xA2\x1E\xB4\xC4Bj3t\xE8d\xE72vm\xF2\x1B\x00>\x13\x02\x13\x03\x13\x01\xC0, \xC00\x00\x9F\xCC\xA9\xCC\xA8\xCC\xAA\xC0+\xC0/\x00\x9E\xC0$\xC0(\x00k\xC0#\xC0'\x00g\xC0" 400 163 "- " "-"

nhưng nhật ký lỗi rõ ràng.

ehammer avatar
lá cờ us
Điều đó dường như làm việc.Tôi chưa bao giờ thực sự muốn đóng một kết nối một cách duyên dáng. Tôi muốn có thêm loại chức năng http444. Âm thầm thất bại.
Ivan Shatsky avatar
lá cờ gr
@ehammer Kiểm tra bản cập nhật.
ehammer avatar
lá cờ us
Tôi thích nó. Tôi đã có một khối mặc định HTTP trỏ 127.0.0.1:80 tới HTTP444, vì vậy khối này tích hợp rất độc đáo với khối đó. Tùy chọn ```default``` trong khối bản đồ thực sự có nghĩa là default_server hay đây chỉ là một tên giữ chỗ?
Ivan Shatsky avatar
lá cờ gr
Đó là một từ khóa đặc biệt cho khối bản đồ, nghĩa là giá trị này sẽ được trả về nếu không có biến thể nào khác phù hợp. Nếu nó không được chỉ định rõ ràng, giá trị mặc định là một chuỗi rỗng.

Đăng câu trả lời

Hầu hết mọi người không hiểu rằng việc đặt nhiều câu hỏi sẽ mở ra cơ hội học hỏi và cải thiện mối quan hệ giữa các cá nhân. Ví dụ, trong các nghiên cứu của Alison, mặc dù mọi người có thể nhớ chính xác có bao nhiêu câu hỏi đã được đặt ra trong các cuộc trò chuyện của họ, nhưng họ không trực giác nhận ra mối liên hệ giữa câu hỏi và sự yêu thích. Qua bốn nghiên cứu, trong đó những người tham gia tự tham gia vào các cuộc trò chuyện hoặc đọc bản ghi lại các cuộc trò chuyện của người khác, mọi người có xu hướng không nhận ra rằng việc đặt câu hỏi sẽ ảnh hưởng—hoặc đã ảnh hưởng—mức độ thân thiện giữa những người đối thoại.