share facebook facebook twitter menu hatena pocket slack

2016.10.10 MON

Nginx の rewrite を使ったリダイレクトで URL に #(アンカーリンク)が付いていたらどうなるの? nginx メモ

川原 洋平

WRITTEN BY 川原 洋平

  • 追記
  • tl;dr
  • memo
    — 試した環境
    — 結論
    — 雑な Nginx 設定
    — curl で試す
    — ブラウザで見る
    — アクセスログ見てみる
  • ということで
    — アンカーリンクは…
    — なんで?

追記

以下、同僚のぐっさんに教えて頂いたので追記。

tl;dr

http://xxx.xxx.xx.xxx/index.html#foo のようなリンクを http://xxx.xxx.xx.xxx/maintenance.html にリダイレクトさせた場合に、#foo ってどうなのかなと思って調べてみた。
出来れば、リダイレクト先では #foo を削除出来たら嬉しい。

memo

試した環境

bash-3.2$ sw_vers
ProductName:    Mac OS X
ProductVersion: 10.11.6
BuildVersion:   15G31

bash-3.2$ docker-machine -version
docker-machine version 0.6.0, build e27fb87

bash-3.2$ docker exec -t -i nginx nginx -v
nginx version: nginx/1.11.3

結論

  • リダイレクト先にも # はくっついてくる

雑な Nginx 設定

server {

    listen 80;
    server_name example.org;
    charset utf-8;

    location / {
        root   html;
        index  index.html index.htm;
        rewrite /index.html /maintenance.html permanent;
    }
}

Dockerfile は以下のように用意。

FROM nginx:alpine
RUN rm /etc/nginx/conf.d/default.conf
RUN mkdir /etc/nginx/html
ADD maintenance.html /etc/nginx/html/
ADD index.html /etc/nginx/html/
ADD demo.conf /etc/nginx/conf.d/

各コンテンツ。

bash-3.2$ cat index.html
index.html
bash-3.2$ cat maintenance.html
maintenance.html

以下のようにコンテナを起動。

docker run --name=nginx -d -p 80:80 inokappa/nginx-demo

curl で試す

bash-3.2$ curl -vL 'http://xxx.xxx.xx.xxx/index.html#foo'
*   Trying xxx.xxx.xx.xxx...
* Connected to xxx.xxx.xx.xxx (xxx.xxx.xx.xxx) port 80 (#0)
> GET /index.html HTTP/1.1
> Host: xxx.xxx.xx.xxx
> User-Agent: curl/7.43.0
> Accept: */*
>
 GET /maintenance.html HTTP/1.1
> Host: xxx.xxx.xx.xxx
> User-Agent: curl/7.43.0
> Accept: */*
>

よく見ると...


Response ヘッダの Location は http://192.168.99.100/maintenance.html で返ってきているのでなんか期待できそうだ。

ブラウザで見る

20160920230716
それ、リダイレクト。
20160920230729
うおお、#foo が付いたままや。

アクセスログ見てみる

とりあえず、アクセスログを見てみる。

# curl でアクセスした場合
xxx.xxx.xx.x - - [20/Sep/2016:13:59:40 +0000] "GET /index.html HTTP/1.1" 301 185 "-" "curl/7.43.0" "-"
xxx.xxx.xx.x - - [20/Sep/2016:13:59:40 +0000] "GET /maintenance.html HTTP/1.1" 200 17 "-" "curl/7.43.0" "-"

# ブラウザでアクセスした場合
xxx.xxx.xx.x - - [20/Sep/2016:14:03:49 +0000] "GET /index.html HTTP/1.1" 301 185 "-" "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_11_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/53.0.2785.116 Safari/537.36" "-"
xxx.xxx.xx.x - - [20/Sep/2016:14:03:49 +0000] "GET /maintenance.html HTTP/1.1" 200 17 "-" "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_11_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/53.0.2785.116 Safari/537.36" "-"

あら、ログには #foo はくっついてきてませんがな。イメージとしてクエリパラメータ(?foo=bar)と同じような内容を想定していたけど。ちなみに、クエリパラメータをくっつけた場合には以下のようなログが記録される。

# curl でアクセスした場合
xxx.xxx.xx.x - - [20/Sep/2016:14:11:34 +0000] "GET /index.html?foo=bar HTTP/1.1" 301 185 "-" "curl/7.43.0" "-"
xxx.xxx.xx.x - - [20/Sep/2016:14:11:34 +0000] "GET /maintenance.html?foo=bar HTTP/1.1" 200 17 "-" "curl/7.43.0" "-"

# ブラウザでアクセスした場合
xxx.xxx.xx.x - - [20/Sep/2016:14:12:10 +0000] "GET /index.html?foo=bar HTTP/1.1" 301 185 "-" "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_11_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/53.0.2785.116 Safari/537.36" "-"
xxx.xxx.xx.x - - [20/Sep/2016:14:12:10 +0000] "GET /maintenance.html?foo=bar HTTP/1.1" 200 17 "-" "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_11_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/53.0.2785.116 Safari/537.36" "-"

ちゃんとクエリパラメータがログに記録されている。これであればサーバーサイドでパラメータを削除したり、書き換えたりすることができそう。ちなみに、クエリパラメータを削除したい場合には以下のような設定を書くことでクエリパラメータを削除した状態でリダイレクトされる。

server {

    listen 80;
    server_name example.org;
    charset utf-8;

    location / {
        root   html;
        index  index.html index.htm;
        rewrite /index.html /maintenance.html? permanent;
    }
}

ということで

アンカーリンクは...

リダイレクト先にも引き継がれてしまう。

なんで?

アンカーリンクでサーバーサイドというよりもブラウザで解釈されるものだからかなと。
誤り等あればご指摘頂ければ幸いです。

元記事はこちら

Nginx の rewrite を使ったリダイレクトで URL に #(アンカーリンク)が付いていたらどうなるの? nginx メモ