2011-11-15 25 views

Trả lời

86

Từ các tài liệu proxy_pass:

Một trường hợp đặc biệt được sử dụng các biến trong báo cáo proxy_pass: URL được yêu cầu không được sử dụng và bạn hoàn toàn chịu trách nhiệm để xây dựng các URL mục tiêu cho mình.

Vì bạn đang sử dụng $ 1 trong mục tiêu, nginx dựa vào bạn để cho biết chính xác nội dung cần vượt qua. Bạn có thể sửa lỗi này theo hai cách. Thứ nhất, tước đầu uri với một proxy_pass là tầm thường:

location /service/ { 
    # Note the trailing slash on the proxy_pass. 
    # It tells nginx to replace /service/ with/when passing the request. 
    proxy_pass http://apache/; 
} 

Hoặc nếu bạn muốn sử dụng vị trí regex, chỉ bao gồm các args:

location ~* ^/service/(.*) { 
    proxy_pass http://apache/$1$is_args$args; 
} 
+1

Tôi không tin bạn có thể làm sau này. Tôi đã cố gắng và nginx phàn nàn với tôi. – duma

+1

Bị khiếu nại như thế nào? Tôi chỉ thử nghiệm nó trên nginx 1.3.4 và nó làm việc tốt cho tôi. – kolbyjack

+0

Humm .. Tôi không thể nhớ lại bây giờ: (Nhưng tôi cảm thấy nó có thể liên quan đến "~ *". Tuy nhiên, tôi vừa kiểm tra, và tôi có nginx 1.2.3 (thông qua homebrew). Có lẽ đó là nó? – duma

17

tôi sử dụng một phiên bản sửa đổi nhẹ của Cách tiếp cận thứ hai của kolbyjack với ~ thay vì ~*.

location ~ ^/service/ { 
    proxy_pass http://apache/$uri$is_args$args; 
} 
5

tôi sửa đổi @kolbyjack mã để làm cho nó làm việc cho

http://website1/service 
http://website1/service/ 

với các thông số

location ~ ^/service/?(.*) { 
    return 301 http://service_url/$1$is_args$args; 
} 
+1

Hãy nhớ điều này sẽ làm cho máy chủ trả về phản hồi 301 cho ứng dụng khách trước khi chuyển hướng. Lệnh 'proxy_pass' ở trên thực hiện chuyển hướng ở phía máy chủ. –

+0

Điều này sẽ phá vỡ nếu các tham số truy vấn của bạn chứa các ký tự được mã hóa URL (%). Sử dụng câu trả lời của Andrew để thay thế. –

3

bạn phải sử dụng viết lại để vượt qua params sử dụng proxy_pass đây là ví dụ tôi đã làm cho triển khai ứng dụng angularjs đến s3

S3 Static Website Hosting Route All Paths to Index.html

chấp nhận yêu cầu của bạn sẽ là một cái gì đó giống như

location /service/ { 
    rewrite ^\/service\/(.*) /$1 break; 
    proxy_pass http://apache; 
} 

nếu bạn muốn kết thúc trong http://127.0.0.1:8080/query/params/

nếu bạn muốn kết thúc trong http://127.0.0.1:8080/service/query/params/ bạn sẽ cần một cái gì đó giống như

location /service/ { 
    rewrite ^\/(.*) /$1 break; 
    proxy_pass http://apache; 
} 
+1

Có vẻ như nó xử lý thông số đường dẫn ('/ path/params') nhưng không phải là tham số truy vấn ('? Query = params')? – Will

+0

Ah không, lỗi của tôi, các thông số truy vấn sẽ được thêm tự động (chúng nằm trong thử nghiệm của tôi). – Will

-1

Để chuyển hướng Nếu không có chuỗi truy vấn, hãy thêm các dòng dưới đây vào khối Máy chủ trong khi nghe dòng cổng

if ($uri ~ .*.containingString$) { return 301 https://$host/$uri/; }

Với Query String

if ($uri ~ .*.containingString$) { return 301 https://$host/$uri/?$query_string; }

+0

Tài liệu nginx rõ ràng là tránh sử dụng 'if' khi có thể. Trong trường hợp này, giải pháp có thể đúng khi sử dụng 'vị trí' như được hiển thị trong một câu trả lời khác. –

0

github ý chính https://gist.github.com/anjia0532/da4a17f848468de5a374c860b17607e7

#set $token "?"; # deprecated 

set $token ""; # declar token is ""(empty str) for original request without args,because $is_args concat any var will be `?` 

if ($is_args) { # if the request has args update token to "&" 
    set $token "&"; 
} 

location /test { 
    set $args "${args}${token}k1=v1&k2=v2"; # update original append custom params with $token 
    # if no args $is_args is empty str,else it's "?" 
    # http is scheme 
    # service is upstream server 
    #proxy_pass http://service/$uri$is_args$args; # deprecated remove `/` 
    proxy_pass http://service$uri$is_args$args; # proxy pass 
} 

#http://localhost/test?foo=bar ==> http://service/test?foo=bar&k1=v1&k2=v2 

#http://localhost/test/ ==> http://service/test?k1=v1&k2=v2 
Các vấn đề liên quan